Kale updated this revision to Diff 427822.
Kale added a comment.
Herald added subscribers: carlosgalvezp, usaxena95, kadircet, arphaman.
Herald added a project: clang-tools-extra.

Fix tests & runInvocation in clang-tools-extra.


Repository:
  rG LLVM Github Monorepo

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D124816/new/

https://reviews.llvm.org/D124816

Files:
  clang-tools-extra/clang-include-fixer/IncludeFixer.cpp
  clang-tools-extra/clang-include-fixer/IncludeFixer.h
  clang-tools-extra/clang-tidy/ClangTidy.cpp
  clang-tools-extra/clangd/indexer/IndexerMain.cpp
  clang-tools-extra/clangd/unittests/IndexActionTests.cpp
  clang-tools-extra/clangd/unittests/SymbolCollectorTests.cpp
  clang-tools-extra/unittests/clang-include-fixer/IncludeFixerTest.cpp
  
clang-tools-extra/unittests/clang-include-fixer/find-all-symbols/FindAllSymbolsTests.cpp
  clang-tools-extra/unittests/clang-tidy/ClangTidyTest.h
  clang/include/clang/Tooling/DependencyScanning/DependencyScanningWorker.h
  clang/include/clang/Tooling/Tooling.h
  clang/lib/Tooling/DependencyScanning/DependencyScanningWorker.cpp
  clang/lib/Tooling/Tooling.cpp
  
clang/test/Tooling/multiple-source-include-different-header-with-same-relative-path.cpp
  clang/tools/clang-fuzzer/handle-cxx/handle_cxx.cpp
  clang/unittests/Tooling/DependencyScannerTest.cpp
  clang/unittests/Tooling/ToolingTest.cpp

Index: clang/unittests/Tooling/ToolingTest.cpp
===================================================================
--- clang/unittests/Tooling/ToolingTest.cpp
+++ clang/unittests/Tooling/ToolingTest.cpp
@@ -179,8 +179,8 @@
   llvm::IntrusiveRefCntPtr<llvm::vfs::InMemoryFileSystem> InMemoryFileSystem(
       new llvm::vfs::InMemoryFileSystem);
   OverlayFileSystem->pushOverlay(InMemoryFileSystem);
-  llvm::IntrusiveRefCntPtr<FileManager> Files(
-      new FileManager(FileSystemOptions(), OverlayFileSystem));
+  llvm::IntrusiveRefCntPtr<ToolFileManager> Files(
+      new ToolFileManager(FileSystemOptions(), OverlayFileSystem));
   std::vector<std::string> Args;
   Args.push_back("tool-executable");
   Args.push_back("-Idef");
@@ -205,8 +205,8 @@
   llvm::IntrusiveRefCntPtr<llvm::vfs::InMemoryFileSystem> InMemoryFileSystem(
       new llvm::vfs::InMemoryFileSystem);
   OverlayFileSystem->pushOverlay(InMemoryFileSystem);
-  llvm::IntrusiveRefCntPtr<FileManager> Files(
-      new FileManager(FileSystemOptions(), OverlayFileSystem));
+  llvm::IntrusiveRefCntPtr<ToolFileManager> Files(
+      new ToolFileManager(FileSystemOptions(), OverlayFileSystem));
   std::vector<std::string> Args;
   Args.push_back("tool-executable");
   Args.push_back("-Idef");
@@ -231,8 +231,8 @@
   llvm::IntrusiveRefCntPtr<llvm::vfs::InMemoryFileSystem> InMemoryFileSystem(
       new llvm::vfs::InMemoryFileSystem);
   OverlayFileSystem->pushOverlay(InMemoryFileSystem);
-  llvm::IntrusiveRefCntPtr<FileManager> Files(
-      new FileManager(FileSystemOptions(), OverlayFileSystem));
+  llvm::IntrusiveRefCntPtr<ToolFileManager> Files(
+      new ToolFileManager(FileSystemOptions(), OverlayFileSystem));
 
   std::vector<std::string> Args;
   Args.push_back("tool-executable");
@@ -260,8 +260,8 @@
   llvm::IntrusiveRefCntPtr<llvm::vfs::InMemoryFileSystem> InMemoryFileSystem(
       new llvm::vfs::InMemoryFileSystem);
   OverlayFileSystem->pushOverlay(InMemoryFileSystem);
-  llvm::IntrusiveRefCntPtr<FileManager> Files(
-      new FileManager(FileSystemOptions(), OverlayFileSystem));
+  llvm::IntrusiveRefCntPtr<ToolFileManager> Files(
+      new ToolFileManager(FileSystemOptions(), OverlayFileSystem));
 
   std::vector<std::string> Args;
   Args.push_back("tool-executable");
@@ -306,8 +306,8 @@
   llvm::IntrusiveRefCntPtr<llvm::vfs::InMemoryFileSystem> InMemoryFileSystem(
       new llvm::vfs::InMemoryFileSystem);
   OverlayFileSystem->pushOverlay(InMemoryFileSystem);
-  llvm::IntrusiveRefCntPtr<FileManager> Files(
-      new FileManager(FileSystemOptions(), OverlayFileSystem));
+  llvm::IntrusiveRefCntPtr<ToolFileManager> Files(
+      new ToolFileManager(FileSystemOptions(), OverlayFileSystem));
   std::vector<std::string> Args;
   Args.push_back("tool-executable");
   // Note: intentional error; user probably meant -ferror-limit=0.
Index: clang/unittests/Tooling/DependencyScannerTest.cpp
===================================================================
--- clang/unittests/Tooling/DependencyScannerTest.cpp
+++ clang/unittests/Tooling/DependencyScannerTest.cpp
@@ -51,18 +51,18 @@
   TestDependencyScanningAction(std::vector<std::string> &Deps) : Deps(Deps) {}
 
   bool runInvocation(std::shared_ptr<CompilerInvocation> Invocation,
-                     FileManager *FileMgr,
+                     ToolFileManager *FileMgr,
                      std::shared_ptr<PCHContainerOperations> PCHContainerOps,
                      DiagnosticConsumer *DiagConsumer) override {
     CompilerInstance Compiler(std::move(PCHContainerOps));
     Compiler.setInvocation(std::move(Invocation));
-    Compiler.setFileManager(FileMgr);
+    Compiler.setFileManager(FileMgr->getOrCreateFileManager().get());
 
     Compiler.createDiagnostics(DiagConsumer, /*ShouldOwnClient=*/false);
     if (!Compiler.hasDiagnostics())
       return false;
 
-    Compiler.createSourceManager(*FileMgr);
+    Compiler.createSourceManager(*FileMgr->getOrCreateFileManager());
     Compiler.addDependencyCollector(std::make_shared<TestFileCollector>(
         Compiler.getInvocation().getDependencyOutputOpts(), Deps));
 
Index: clang/tools/clang-fuzzer/handle-cxx/handle_cxx.cpp
===================================================================
--- clang/tools/clang-fuzzer/handle-cxx/handle_cxx.cpp
+++ clang/tools/clang-fuzzer/handle-cxx/handle_cxx.cpp
@@ -29,8 +29,8 @@
     CC1Args.push_back(A);
   CC1Args.push_back(FileName);
 
-  llvm::IntrusiveRefCntPtr<FileManager> Files(
-      new FileManager(FileSystemOptions()));
+  llvm::IntrusiveRefCntPtr<clang::tooling::ToolFileManager> Files(
+      new clang::tooling::ToolFileManager(FileSystemOptions()));
   IgnoringDiagConsumer Diags;
   IntrusiveRefCntPtr<DiagnosticOptions> DiagOpts = new DiagnosticOptions();
   DiagnosticsEngine Diagnostics(
Index: clang/test/Tooling/multiple-source-include-different-header-with-same-relative-path.cpp
===================================================================
--- /dev/null
+++ clang/test/Tooling/multiple-source-include-different-header-with-same-relative-path.cpp
@@ -0,0 +1,42 @@
+// This test case presents a circumstance that the information related one file
+// is misused by another.
+//
+// The path tree of the test directory is as follors.
+//   .
+//   ├── a
+//   │   ├── a.c
+//   │   └── config.h
+//   ├── b
+//   │   ├── b.c
+//   │   └── config.h
+//   └── compile_commands.json
+//
+// Both source files (a/a.c and b/b.c) includes the config.h file of their own
+// directory with `#include "config.h"`. However, the two config.h files are
+// different. File a/config.h is longer than b/config.h. Both a/a.c and b/b.c
+// are compiled in their own directory, which is recorded in the compilation
+// database.
+//
+// When using ClangTool to parse these two source files one by one, since the
+// file name of both header files are the same, the FileManager will confuse
+// with them and using the file entry of a/config.h for b/config.h. And the
+// wrong file length will lead to a buffer overflow when reading the file.
+//
+// In this test case, to avoid buffer overflow, we use the leading '\0' in an
+// empty buffer to trigger the problem. We set a/config.h as an empty line
+// comment, and leave b/config.h empty. Firstly, a/config.h is read and cached,
+// then when reading b/config.h, if the size of a/config.h is used, the first
+// two chars are read and the first one must be a '\0'.
+
+// RUN: rm -rf %t
+// RUN: mkdir -p %t/a
+// RUN: mkdir -p %t/b
+// RUN: echo '#include "config.h"' > %t/a/a.c
+// RUN: echo '#include "config.h"' > %t/b/b.c
+// RUN: echo '//' > %t/a/config.h
+// RUN: echo ''   > %t/b/config.h
+// RUN: echo '[{"arguments": ["cc", "-c", "-o", "a.o", "a.c"], "directory": "%t/a", "file": "a.c"}, {"arguments": ["cc", "-c", "-o", "b.o", "b.c"], "directory": "%t/b", "file": "b.c"}]' | sed -e 's/\\/\\\\/g' > %t/compile_commands.json
+
+// The following two test RUNs should have no output.
+// RUN: cd %t && clang-check a/a.c b/b.c 2>&1 | count 0
+// RUN: cd %t && clang-check b/b.c a/a.c 2>&1 | count 0
Index: clang/lib/Tooling/Tooling.cpp
===================================================================
--- clang/lib/Tooling/Tooling.cpp
+++ clang/lib/Tooling/Tooling.cpp
@@ -207,8 +207,8 @@
   SmallString<16> FileNameStorage;
   StringRef FileNameRef = FileName.toNullTerminatedStringRef(FileNameStorage);
 
-  llvm::IntrusiveRefCntPtr<FileManager> Files(
-      new FileManager(FileSystemOptions(), VFS));
+  llvm::IntrusiveRefCntPtr<ToolFileManager> Files(
+      new ToolFileManager(FileSystemOptions(), VFS));
   ArgumentsAdjuster Adjuster = getClangStripDependencyFileAdjuster();
   ToolInvocation Invocation(
       getSyntaxOnlyToolArgs(ToolName, Adjuster(Args, FileNameRef), FileNameRef),
@@ -320,13 +320,14 @@
 
 ToolInvocation::ToolInvocation(
     std::vector<std::string> CommandLine, ToolAction *Action,
-    FileManager *Files, std::shared_ptr<PCHContainerOperations> PCHContainerOps)
+    ToolFileManager *Files,
+    std::shared_ptr<PCHContainerOperations> PCHContainerOps)
     : CommandLine(std::move(CommandLine)), Action(Action), OwnsAction(false),
       Files(Files), PCHContainerOps(std::move(PCHContainerOps)) {}
 
 ToolInvocation::ToolInvocation(
     std::vector<std::string> CommandLine,
-    std::unique_ptr<FrontendAction> FAction, FileManager *Files,
+    std::unique_ptr<FrontendAction> FAction, ToolFileManager *Files,
     std::shared_ptr<PCHContainerOperations> PCHContainerOps)
     : CommandLine(std::move(CommandLine)),
       Action(new SingleFrontendActionFactory(std::move(FAction))),
@@ -359,16 +360,17 @@
           &*DiagOpts, DiagConsumer ? DiagConsumer : &DiagnosticPrinter, false);
   // Although `Diagnostics` are used only for command-line parsing, the custom
   // `DiagConsumer` might expect a `SourceManager` to be present.
-  SourceManager SrcMgr(*Diagnostics, *Files);
+  SourceManager SrcMgr(*Diagnostics, *Files->getOrCreateFileManager());
   Diagnostics->setSourceManager(&SrcMgr);
 
   const std::unique_ptr<driver::Driver> Driver(
-      newDriver(&*Diagnostics, BinaryName, &Files->getVirtualFileSystem()));
+      newDriver(&*Diagnostics, BinaryName,
+                &Files->getOrCreateFileManager()->getVirtualFileSystem()));
   // The "input file not found" diagnostics from the driver are useful.
   // The driver is only aware of the VFS working directory, but some clients
   // change this at the FileManager level instead.
   // In this case the checks have false positives, so skip them.
-  if (!Files->getFileSystemOpts().WorkingDir.empty())
+  if (!Files->getOrCreateFileManager()->getFileSystemOpts().WorkingDir.empty())
     Driver->setCheckInputsExist(false);
   const std::unique_ptr<driver::Compilation> Compilation(
       Driver->BuildCompilation(llvm::makeArrayRef(Argv)));
@@ -400,13 +402,13 @@
 }
 
 bool FrontendActionFactory::runInvocation(
-    std::shared_ptr<CompilerInvocation> Invocation, FileManager *Files,
+    std::shared_ptr<CompilerInvocation> Invocation, ToolFileManager *Files,
     std::shared_ptr<PCHContainerOperations> PCHContainerOps,
     DiagnosticConsumer *DiagConsumer) {
   // Create a compiler instance to handle the actual work.
   CompilerInstance Compiler(std::move(PCHContainerOps));
   Compiler.setInvocation(std::move(Invocation));
-  Compiler.setFileManager(Files);
+  Compiler.setFileManager(Files->getOrCreateFileManager().get());
 
   // The FrontendAction can have lifetime requirements for Compiler or its
   // members, and we need to ensure it's deleted earlier than Compiler. So we
@@ -418,11 +420,11 @@
   if (!Compiler.hasDiagnostics())
     return false;
 
-  Compiler.createSourceManager(*Files);
+  Compiler.createSourceManager(*Files->getOrCreateFileManager());
 
   const bool Success = Compiler.ExecuteAction(*ScopedToolAction);
 
-  Files->clearStatCache();
+  Files->getOrCreateFileManager()->clearStatCache();
   return Success;
 }
 
@@ -430,13 +432,14 @@
                      ArrayRef<std::string> SourcePaths,
                      std::shared_ptr<PCHContainerOperations> PCHContainerOps,
                      IntrusiveRefCntPtr<llvm::vfs::FileSystem> BaseFS,
-                     IntrusiveRefCntPtr<FileManager> Files)
+                     IntrusiveRefCntPtr<clang::tooling::ToolFileManager> Files)
     : Compilations(Compilations), SourcePaths(SourcePaths),
       PCHContainerOps(std::move(PCHContainerOps)),
       OverlayFileSystem(new llvm::vfs::OverlayFileSystem(std::move(BaseFS))),
       InMemoryFileSystem(new llvm::vfs::InMemoryFileSystem),
       Files(Files ? Files
-                  : new FileManager(FileSystemOptions(), OverlayFileSystem)) {
+                  : new clang::tooling::ToolFileManager(FileSystemOptions(),
+                                                        OverlayFileSystem)) {
   OverlayFileSystem->pushOverlay(InMemoryFileSystem);
   appendArgumentsAdjuster(getClangStripOutputAdjuster());
   appendArgumentsAdjuster(getClangSyntaxOnlyAdjuster());
@@ -601,7 +604,7 @@
   ASTBuilderAction(std::vector<std::unique_ptr<ASTUnit>> &ASTs) : ASTs(ASTs) {}
 
   bool runInvocation(std::shared_ptr<CompilerInvocation> Invocation,
-                     FileManager *Files,
+                     ToolFileManager *Files,
                      std::shared_ptr<PCHContainerOperations> PCHContainerOps,
                      DiagnosticConsumer *DiagConsumer) override {
     std::unique_ptr<ASTUnit> AST = ASTUnit::LoadFromCompilerInvocation(
@@ -609,7 +612,7 @@
         CompilerInstance::createDiagnostics(&Invocation->getDiagnosticOpts(),
                                             DiagConsumer,
                                             /*ShouldOwnClient=*/false),
-        Files);
+        Files->getOrCreateFileManager().get());
     if (!AST)
       return false;
 
@@ -655,8 +658,8 @@
   llvm::IntrusiveRefCntPtr<llvm::vfs::InMemoryFileSystem> InMemoryFileSystem(
       new llvm::vfs::InMemoryFileSystem);
   OverlayFileSystem->pushOverlay(InMemoryFileSystem);
-  llvm::IntrusiveRefCntPtr<FileManager> Files(
-      new FileManager(FileSystemOptions(), OverlayFileSystem));
+  llvm::IntrusiveRefCntPtr<ToolFileManager> Files(
+      new ToolFileManager(FileSystemOptions(), OverlayFileSystem));
 
   ToolInvocation Invocation(
       getSyntaxOnlyToolArgs(ToolName, Adjuster(Args, FileName), FileName),
Index: clang/lib/Tooling/DependencyScanning/DependencyScanningWorker.cpp
===================================================================
--- clang/lib/Tooling/DependencyScanning/DependencyScanningWorker.cpp
+++ clang/lib/Tooling/DependencyScanning/DependencyScanningWorker.cpp
@@ -145,7 +145,7 @@
         OptimizeArgs(OptimizeArgs), ModuleName(ModuleName) {}
 
   bool runInvocation(std::shared_ptr<CompilerInvocation> Invocation,
-                     FileManager *FileMgr,
+                     ToolFileManager *ToolFileMgr,
                      std::shared_ptr<PCHContainerOperations> PCHContainerOps,
                      DiagnosticConsumer *DiagConsumer) override {
     // Make a deep copy of the original Clang invocation.
@@ -166,7 +166,7 @@
 
     ScanInstance.getFrontendOpts().GenerateGlobalModuleIndex = false;
     ScanInstance.getFrontendOpts().UseGlobalModuleIndex = false;
-
+    auto FileMgr = ToolFileMgr->getOrCreateFileManager().get();
     FileMgr->getFileSystemOpts().WorkingDir = std::string(WorkingDirectory);
     ScanInstance.setFileManager(FileMgr);
     ScanInstance.createSourceManager(*FileMgr);
@@ -199,7 +199,7 @@
 
       // Support for virtual file system overlays on top of the caching
       // filesystem.
-      FileMgr->setVirtualFileSystem(createVFSFromCompilerInvocation(
+      ToolFileMgr->setVirtualFileSystem(createVFSFromCompilerInvocation(
           ScanInstance.getInvocation(), ScanInstance.getDiagnostics(), DepFS));
 
       // Pass the skip mappings which should speed up excluded conditional block
@@ -291,7 +291,7 @@
     DepFS = new DependencyScanningWorkerFilesystem(Service.getSharedCache(),
                                                    RealFS, PPSkipMappings);
   if (Service.canReuseFileManager())
-    Files = new FileManager(FileSystemOptions(), RealFS);
+    Files = new ToolFileManager(FileSystemOptions(), RealFS);
 }
 
 static llvm::Error
@@ -320,8 +320,8 @@
   if (Files)
     Files->setVirtualFileSystem(RealFS);
 
-  llvm::IntrusiveRefCntPtr<FileManager> CurrentFiles =
-      Files ? Files : new FileManager(FileSystemOptions(), RealFS);
+  llvm::IntrusiveRefCntPtr<ToolFileManager> CurrentFiles =
+      Files ? Files : new ToolFileManager(FileSystemOptions(), RealFS);
 
   Optional<std::vector<std::string>> ModifiedCommandLine;
   if (ModuleName.hasValue()) {
Index: clang/include/clang/Tooling/Tooling.h
===================================================================
--- clang/include/clang/Tooling/Tooling.h
+++ clang/include/clang/Tooling/Tooling.h
@@ -65,6 +65,46 @@
 
 class CompilationDatabase;
 
+class ToolFileManager : public RefCountedBase<ToolFileManager> {
+  // ToolFileManager is a container who stores file managers for each CWD
+  std::map<std::string, llvm::IntrusiveRefCntPtr<FileManager>> fileManagers;
+  IntrusiveRefCntPtr<llvm::vfs::FileSystem> FS;
+  FileSystemOptions FSO;
+
+public:
+  ToolFileManager(const FileSystemOptions &FileSystemOpts,
+                  IntrusiveRefCntPtr<llvm::vfs::FileSystem> FS = nullptr)
+      : FS(FS), FSO(FileSystemOpts) {
+    if (!this->FS)
+      this->FS = llvm::vfs::getRealFileSystem();
+  };
+
+  ~ToolFileManager() = default;
+
+  llvm::IntrusiveRefCntPtr<FileManager> getOrCreateFileManager() {
+    auto Success = FS->getCurrentWorkingDirectory();
+    if (!Success)
+      llvm::report_fatal_error("Cannot get current working directory!\n");
+    std::string Cwd = Success.get();
+    if (!fileManagers.count(Cwd)) {
+      fileManagers[Cwd] = new FileManager(FSO, FS);
+    }
+    return fileManagers[Cwd];
+  }
+
+  void setVirtualFileSystem(IntrusiveRefCntPtr<llvm::vfs::FileSystem> NewFS) {
+    //  To call FileManager::setVirtualFileSystem() directly might be unsound
+    //  unless the new FS is equivalent to the old one. So here we simply
+    //  invalidate all previous file managers to ensure correctness.
+    if (this->FS != NewFS) {
+      for (auto it = fileManagers.begin(); it != fileManagers.end(); it++)
+        it->second->setVirtualFileSystem(NewFS);
+      fileManagers.clear();
+      this->FS = std::move(NewFS);
+    }
+  }
+};
+
 /// Retrieves the flags of the `-cc1` job in `Compilation` that has only source
 /// files as its inputs.
 /// Returns nullptr if there are no such jobs or multiple of them. Note that
@@ -84,7 +124,7 @@
   /// Perform an action for an invocation.
   virtual bool
   runInvocation(std::shared_ptr<CompilerInvocation> Invocation,
-                FileManager *Files,
+                ToolFileManager *Files,
                 std::shared_ptr<PCHContainerOperations> PCHContainerOps,
                 DiagnosticConsumer *DiagConsumer) = 0;
 };
@@ -101,7 +141,7 @@
 
   /// Invokes the compiler with a FrontendAction created by create().
   bool runInvocation(std::shared_ptr<CompilerInvocation> Invocation,
-                     FileManager *Files,
+                     ToolFileManager *Files,
                      std::shared_ptr<PCHContainerOperations> PCHContainerOps,
                      DiagnosticConsumer *DiagConsumer) override;
 
@@ -245,12 +285,13 @@
   /// Callers have to ensure that they are installed in a compatible location
   /// (see clang driver implementation) or mapped in via mapVirtualFile.
   /// \param FAction The action to be executed.
-  /// \param Files The FileManager used for the execution. Class does not take
-  /// ownership.
+  /// \param Files The ToolFileManager used for the execution. Class does not
+  /// take ownership.
   /// \param PCHContainerOps The PCHContainerOperations for loading and creating
   /// clang modules.
   ToolInvocation(std::vector<std::string> CommandLine,
-                 std::unique_ptr<FrontendAction> FAction, FileManager *Files,
+                 std::unique_ptr<FrontendAction> FAction,
+                 ToolFileManager *Files,
                  std::shared_ptr<PCHContainerOperations> PCHContainerOps =
                      std::make_shared<PCHContainerOperations>());
 
@@ -258,11 +299,11 @@
   ///
   /// \param CommandLine The command line arguments to clang.
   /// \param Action The action to be executed.
-  /// \param Files The FileManager used for the execution.
+  /// \param Files The ToolFileManager used for the execution.
   /// \param PCHContainerOps The PCHContainerOperations for loading and creating
   /// clang modules.
   ToolInvocation(std::vector<std::string> CommandLine, ToolAction *Action,
-                 FileManager *Files,
+                 ToolFileManager *Files,
                  std::shared_ptr<PCHContainerOperations> PCHContainerOps);
 
   ~ToolInvocation();
@@ -292,7 +333,7 @@
   std::vector<std::string> CommandLine;
   ToolAction *Action;
   bool OwnsAction;
-  FileManager *Files;
+  ToolFileManager *Files;
   std::shared_ptr<PCHContainerOperations> PCHContainerOps;
   DiagnosticConsumer *DiagConsumer = nullptr;
   DiagnosticOptions *DiagOpts = nullptr;
@@ -317,15 +358,15 @@
   /// clang modules.
   /// \param BaseFS VFS used for all underlying file accesses when running the
   /// tool.
-  /// \param Files The file manager to use for underlying file operations when
-  /// running the tool.
+  /// \param Files The container of file managers to use for underlying file
+  /// operations when running the tool.
   ClangTool(const CompilationDatabase &Compilations,
             ArrayRef<std::string> SourcePaths,
             std::shared_ptr<PCHContainerOperations> PCHContainerOps =
                 std::make_shared<PCHContainerOperations>(),
             IntrusiveRefCntPtr<llvm::vfs::FileSystem> BaseFS =
                 llvm::vfs::getRealFileSystem(),
-            IntrusiveRefCntPtr<FileManager> Files = nullptr);
+            IntrusiveRefCntPtr<ToolFileManager> Files = nullptr);
 
   ~ClangTool();
 
@@ -373,7 +414,7 @@
   /// Returns the file manager used in the tool.
   ///
   /// The file manager is shared between all translation units.
-  FileManager &getFiles() { return *Files; }
+  FileManager &getFiles() { return *Files->getOrCreateFileManager(); }
 
   llvm::ArrayRef<std::string> getSourcePaths() const { return SourcePaths; }
 
@@ -384,7 +425,7 @@
 
   llvm::IntrusiveRefCntPtr<llvm::vfs::OverlayFileSystem> OverlayFileSystem;
   llvm::IntrusiveRefCntPtr<llvm::vfs::InMemoryFileSystem> InMemoryFileSystem;
-  llvm::IntrusiveRefCntPtr<FileManager> Files;
+  llvm::IntrusiveRefCntPtr<ToolFileManager> Files;
 
   // Contains a list of pairs (<file name>, <file content>).
   std::vector<std::pair<StringRef, StringRef>> MappedFileContents;
Index: clang/include/clang/Tooling/DependencyScanning/DependencyScanningWorker.h
===================================================================
--- clang/include/clang/Tooling/DependencyScanning/DependencyScanningWorker.h
+++ clang/include/clang/Tooling/DependencyScanning/DependencyScanningWorker.h
@@ -16,6 +16,7 @@
 #include "clang/Lex/PreprocessorExcludedConditionalDirectiveSkipMapping.h"
 #include "clang/Tooling/DependencyScanning/DependencyScanningService.h"
 #include "clang/Tooling/DependencyScanning/ModuleDepCollector.h"
+#include "clang/Tooling/Tooling.h"
 #include "llvm/Support/Error.h"
 #include "llvm/Support/FileSystem.h"
 #include <string>
@@ -79,9 +80,9 @@
   /// dependencies. This filesystem persists across multiple compiler
   /// invocations.
   llvm::IntrusiveRefCntPtr<DependencyScanningWorkerFilesystem> DepFS;
-  /// The file manager that is reused across multiple invocations by this
-  /// worker. If null, the file manager will not be reused.
-  llvm::IntrusiveRefCntPtr<FileManager> Files;
+  /// The container of file managers that is reused across multiple invocations
+  /// by this worker. If null, the file manager will not be reused.
+  llvm::IntrusiveRefCntPtr<clang::tooling::ToolFileManager> Files;
   ScanningOutputFormat Format;
   /// Whether to optimize the modules' command-line arguments.
   bool OptimizeArgs;
Index: clang-tools-extra/unittests/clang-tidy/ClangTidyTest.h
===================================================================
--- clang-tools-extra/unittests/clang-tidy/ClangTidyTest.h
+++ clang-tools-extra/unittests/clang-tidy/ClangTidyTest.h
@@ -119,8 +119,9 @@
   ast_matchers::MatchFinder Finder;
   llvm::IntrusiveRefCntPtr<llvm::vfs::InMemoryFileSystem> InMemoryFileSystem(
       new llvm::vfs::InMemoryFileSystem);
-  llvm::IntrusiveRefCntPtr<FileManager> Files(
-      new FileManager(FileSystemOptions(), InMemoryFileSystem));
+  llvm::IntrusiveRefCntPtr<clang::tooling::ToolFileManager> Files(
+      new clang::tooling::ToolFileManager(FileSystemOptions(),
+                                          InMemoryFileSystem));
 
   SmallVector<std::unique_ptr<ClangTidyCheck>, sizeof...(CheckTypes)> Checks;
   tooling::ToolInvocation Invocation(
Index: clang-tools-extra/unittests/clang-include-fixer/find-all-symbols/FindAllSymbolsTests.cpp
===================================================================
--- clang-tools-extra/unittests/clang-include-fixer/find-all-symbols/FindAllSymbolsTests.cpp
+++ clang-tools-extra/unittests/clang-include-fixer/find-all-symbols/FindAllSymbolsTests.cpp
@@ -64,8 +64,9 @@
   bool runFindAllSymbols(StringRef HeaderCode, StringRef MainCode) {
     llvm::IntrusiveRefCntPtr<llvm::vfs::InMemoryFileSystem> InMemoryFileSystem(
         new llvm::vfs::InMemoryFileSystem);
-    llvm::IntrusiveRefCntPtr<FileManager> Files(
-        new FileManager(FileSystemOptions(), InMemoryFileSystem));
+    llvm::IntrusiveRefCntPtr<clang::tooling::ToolFileManager> Files(
+        new clang::tooling::ToolFileManager(FileSystemOptions(),
+                                            InMemoryFileSystem));
 
     std::string FileName = "symbol.cc";
 
Index: clang-tools-extra/unittests/clang-include-fixer/IncludeFixerTest.cpp
===================================================================
--- clang-tools-extra/unittests/clang-include-fixer/IncludeFixerTest.cpp
+++ clang-tools-extra/unittests/clang-include-fixer/IncludeFixerTest.cpp
@@ -25,8 +25,9 @@
                       const std::vector<std::string> &ExtraArgs) {
   llvm::IntrusiveRefCntPtr<llvm::vfs::InMemoryFileSystem> InMemoryFileSystem(
       new llvm::vfs::InMemoryFileSystem);
-  llvm::IntrusiveRefCntPtr<FileManager> Files(
-      new FileManager(FileSystemOptions(), InMemoryFileSystem));
+  llvm::IntrusiveRefCntPtr<clang::tooling::ToolFileManager> Files(
+      new clang::tooling::ToolFileManager(FileSystemOptions(),
+                                          InMemoryFileSystem));
   // FIXME: Investigate why -fms-compatibility breaks tests.
   std::vector<std::string> Args = {"include_fixer", "-fsyntax-only",
                                    "-fno-ms-compatibility",
Index: clang-tools-extra/clangd/unittests/SymbolCollectorTests.cpp
===================================================================
--- clang-tools-extra/clangd/unittests/SymbolCollectorTests.cpp
+++ clang-tools-extra/clangd/unittests/SymbolCollectorTests.cpp
@@ -286,8 +286,9 @@
   // HeaderCode should start with #pragma once to be treated as modular.
   bool runSymbolCollector(llvm::StringRef HeaderCode, llvm::StringRef MainCode,
                           const std::vector<std::string> &ExtraArgs = {}) {
-    llvm::IntrusiveRefCntPtr<FileManager> Files(
-        new FileManager(FileSystemOptions(), InMemoryFileSystem));
+    llvm::IntrusiveRefCntPtr<clang::tooling::ToolFileManager> Files(
+        new clang::tooling::ToolFileManager(FileSystemOptions(),
+                                            InMemoryFileSystem));
 
     auto Factory = std::make_unique<SymbolIndexActionFactory>(
         CollectorOpts, PragmaHandler.get());
Index: clang-tools-extra/clangd/unittests/IndexActionTests.cpp
===================================================================
--- clang-tools-extra/clangd/unittests/IndexActionTests.cpp
+++ clang-tools-extra/clangd/unittests/IndexActionTests.cpp
@@ -73,8 +73,9 @@
   runIndexingAction(llvm::StringRef MainFilePath,
                     const std::vector<std::string> &ExtraArgs = {}) {
     IndexFileIn IndexFile;
-    llvm::IntrusiveRefCntPtr<FileManager> Files(
-        new FileManager(FileSystemOptions(), InMemoryFileSystem));
+    llvm::IntrusiveRefCntPtr<clang::tooling::ToolFileManager> Files(
+        new clang::tooling::ToolFileManager(FileSystemOptions(),
+                                            InMemoryFileSystem));
 
     auto Action = createStaticIndexingAction(
         Opts, [&](SymbolSlab S) { IndexFile.Symbols = std::move(S); },
Index: clang-tools-extra/clangd/indexer/IndexerMain.cpp
===================================================================
--- clang-tools-extra/clangd/indexer/IndexerMain.cpp
+++ clang-tools-extra/clangd/indexer/IndexerMain.cpp
@@ -85,7 +85,7 @@
   }
 
   bool runInvocation(std::shared_ptr<CompilerInvocation> Invocation,
-                     FileManager *Files,
+                     tooling::ToolFileManager *Files,
                      std::shared_ptr<PCHContainerOperations> PCHContainerOps,
                      DiagnosticConsumer *DiagConsumer) override {
     disableUnsupportedOptions(*Invocation);
Index: clang-tools-extra/clang-tidy/ClangTidy.cpp
===================================================================
--- clang-tools-extra/clang-tidy/ClangTidy.cpp
+++ clang-tools-extra/clang-tidy/ClangTidy.cpp
@@ -554,7 +554,7 @@
     }
 
     bool runInvocation(std::shared_ptr<CompilerInvocation> Invocation,
-                       FileManager *Files,
+                       ToolFileManager *Files,
                        std::shared_ptr<PCHContainerOperations> PCHContainerOps,
                        DiagnosticConsumer *DiagConsumer) override {
       // Explicitly ask to define __clang_analyzer__ macro.
Index: clang-tools-extra/clang-include-fixer/IncludeFixer.h
===================================================================
--- clang-tools-extra/clang-include-fixer/IncludeFixer.h
+++ clang-tools-extra/clang-include-fixer/IncludeFixer.h
@@ -42,7 +42,7 @@
 
   bool
   runInvocation(std::shared_ptr<clang::CompilerInvocation> Invocation,
-                clang::FileManager *Files,
+                clang::tooling::ToolFileManager *Files,
                 std::shared_ptr<clang::PCHContainerOperations> PCHContainerOps,
                 clang::DiagnosticConsumer *Diagnostics) override;
 
Index: clang-tools-extra/clang-include-fixer/IncludeFixer.cpp
===================================================================
--- clang-tools-extra/clang-include-fixer/IncludeFixer.cpp
+++ clang-tools-extra/clang-include-fixer/IncludeFixer.cpp
@@ -82,7 +82,7 @@
 
 bool IncludeFixerActionFactory::runInvocation(
     std::shared_ptr<clang::CompilerInvocation> Invocation,
-    clang::FileManager *Files,
+    clang::tooling::ToolFileManager *Files,
     std::shared_ptr<clang::PCHContainerOperations> PCHContainerOps,
     clang::DiagnosticConsumer *Diagnostics) {
   assert(Invocation->getFrontendOpts().Inputs.size() == 1);
@@ -90,13 +90,13 @@
   // Set up Clang.
   clang::CompilerInstance Compiler(PCHContainerOps);
   Compiler.setInvocation(std::move(Invocation));
-  Compiler.setFileManager(Files);
+  Compiler.setFileManager(Files->getOrCreateFileManager().get());
 
   // Create the compiler's actual diagnostics engine. We want to drop all
   // diagnostics here.
   Compiler.createDiagnostics(new clang::IgnoringDiagConsumer,
                              /*ShouldOwnClient=*/true);
-  Compiler.createSourceManager(*Files);
+  Compiler.createSourceManager(*Files->getOrCreateFileManager());
 
   // We abort on fatal errors so don't let a large number of errors become
   // fatal. A missing #include can cause thousands of errors.
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
  • [PATCH] D124816: [... Shi Chen via Phabricator via cfe-commits

Reply via email to