Index: ClangTidy.cpp =================================================================== --- ClangTidy.cpp +++ ClangTidy.cpp @@ -608,8 +608,55 @@ raw_ostream &OS) { TranslationUnitDiagnostics TUD; TUD.MainSourceFile = MainFilePath; + + FileManager *Files = new FileManager(FileSystemOptions()); + vfs::FileSystem &FileSystem = *Files->getVirtualFileSystem(); + auto InitialWorkingDir = FileSystem.getCurrentWorkingDirectory(); + if (!InitialWorkingDir) + llvm::report_fatal_error("Cannot get current working path."); + + llvm::StringMap FileReplacements; + llvm::StringMap SingleErrors; for (const auto &Error : Errors) { - tooling::Diagnostic Diag = Error; + if (!Error.BuildDirectory.empty()) + FileSystem.setCurrentWorkingDirectory(Error.BuildDirectory); + + SmallString<128> ErrorAbsoluteFilePath = (StringRef)Error.Message.FilePath; + Files->makeAbsolutePath(ErrorAbsoluteFilePath); + if (SingleErrors.find(ErrorAbsoluteFilePath) == SingleErrors.end()) { + ClangTidyError AbsoluteError = Error; + AbsoluteError.Message.FilePath = ErrorAbsoluteFilePath.str(); + AbsoluteError.Fix.clear(); + SingleErrors.insert(std::pair( + ErrorAbsoluteFilePath, AbsoluteError)); + } + + for (const auto &FileAndReplacements : Error.Fix) { + for (const auto &Repl : FileAndReplacements.second) { + SmallString<128> FixAbsoluteFilePath = Repl.getFilePath(); + Files->makeAbsolutePath(FixAbsoluteFilePath); + + tooling::Replacement R(FixAbsoluteFilePath, Repl.getOffset(), + Repl.getLength(), Repl.getReplacementText()); + + FileReplacements[R.getFilePath()].add(R); + } + } + + FileSystem.setCurrentWorkingDirectory(InitialWorkingDir.get()); + } + + for (const auto &FileAndReplacements : FileReplacements) { + StringRef File = FileAndReplacements.first(); + Replacements Repls = FileAndReplacements.second; + + ClangTidyError AbsoluteError = SingleErrors.find(File)->second; + if (SingleErrors.find(File) == SingleErrors.end()) + llvm::report_fatal_error("Cannot find the containing ClangTidyError."); + + AbsoluteError.Fix.insert(std::pair(File, Repls)); + + tooling::Diagnostic Diag = AbsoluteError; TUD.Diagnostics.insert(TUD.Diagnostics.end(), Diag); }