[clang-tools-extra] 0628705 - [clangd][NFC] Rename FSProvider and getFileSystem

Kadir Cetinkaya via cfe-commits cfe-commits at lists.llvm.org
Fri Jun 19 03:14:27 PDT 2020


Author: Kadir Cetinkaya
Date: 2020-06-19T12:12:03+02:00
New Revision: 0628705efaf7345c82887aeb61bb9bf1e06e5dd9

URL: https://github.com/llvm/llvm-project/commit/0628705efaf7345c82887aeb61bb9bf1e06e5dd9
DIFF: https://github.com/llvm/llvm-project/commit/0628705efaf7345c82887aeb61bb9bf1e06e5dd9.diff

LOG: [clangd][NFC] Rename FSProvider and getFileSystem

Summary:
Clangd uses FSProvider to get threadsafe views into file systems. This
patch changes naming to make that more explicit.

Depends on D81920

Reviewers: sammccall

Subscribers: ilya-biryukov, MaskRay, jkorous, arphaman, usaxena95, cfe-commits

Tags: #clang

Differential Revision: https://reviews.llvm.org/D81998

Added: 
    clang-tools-extra/clangd/support/ThreadsafeFS.cpp
    clang-tools-extra/clangd/support/ThreadsafeFS.h

Modified: 
    clang-tools-extra/clangd/ClangdLSPServer.cpp
    clang-tools-extra/clangd/ClangdLSPServer.h
    clang-tools-extra/clangd/ClangdServer.cpp
    clang-tools-extra/clangd/ClangdServer.h
    clang-tools-extra/clangd/CodeComplete.cpp
    clang-tools-extra/clangd/Compiler.cpp
    clang-tools-extra/clangd/Compiler.h
    clang-tools-extra/clangd/ParsedAST.cpp
    clang-tools-extra/clangd/Preamble.cpp
    clang-tools-extra/clangd/SourceCode.cpp
    clang-tools-extra/clangd/SourceCode.h
    clang-tools-extra/clangd/fuzzer/clangd-fuzzer.cpp
    clang-tools-extra/clangd/index/Background.cpp
    clang-tools-extra/clangd/index/Background.h
    clang-tools-extra/clangd/support/CMakeLists.txt
    clang-tools-extra/clangd/tool/ClangdMain.cpp
    clang-tools-extra/clangd/unittests/BackgroundIndexTests.cpp
    clang-tools-extra/clangd/unittests/ClangdLSPServerTests.cpp
    clang-tools-extra/clangd/unittests/ClangdTests.cpp
    clang-tools-extra/clangd/unittests/CodeCompleteTests.cpp
    clang-tools-extra/clangd/unittests/CompilerTests.cpp
    clang-tools-extra/clangd/unittests/FileIndexTests.cpp
    clang-tools-extra/clangd/unittests/FindSymbolsTests.cpp
    clang-tools-extra/clangd/unittests/HeaderSourceSwitchTests.cpp
    clang-tools-extra/clangd/unittests/HeadersTests.cpp
    clang-tools-extra/clangd/unittests/ParsedASTTests.cpp
    clang-tools-extra/clangd/unittests/PreambleTests.cpp
    clang-tools-extra/clangd/unittests/RenameTests.cpp
    clang-tools-extra/clangd/unittests/SemanticHighlightingTests.cpp
    clang-tools-extra/clangd/unittests/SemanticSelectionTests.cpp
    clang-tools-extra/clangd/unittests/TUSchedulerTests.cpp
    clang-tools-extra/clangd/unittests/TestFS.h
    clang-tools-extra/clangd/unittests/TestTU.cpp
    clang-tools-extra/clangd/unittests/TestTU.h
    clang-tools-extra/clangd/unittests/XRefsTests.cpp

Removed: 
    clang-tools-extra/clangd/support/FSProvider.cpp
    clang-tools-extra/clangd/support/FSProvider.h


################################################################################
diff  --git a/clang-tools-extra/clangd/ClangdLSPServer.cpp b/clang-tools-extra/clangd/ClangdLSPServer.cpp
index db9932a43e5a..a42616116858 100644
--- a/clang-tools-extra/clangd/ClangdLSPServer.cpp
+++ b/clang-tools-extra/clangd/ClangdLSPServer.cpp
@@ -1340,7 +1340,7 @@ void ClangdLSPServer::onSemanticTokensEdits(
 }
 
 ClangdLSPServer::ClangdLSPServer(
-    class Transport &Transp, const FileSystemProvider &FSProvider,
+    class Transport &Transp, const ThreadsafeFS &FSProvider,
     const clangd::CodeCompleteOptions &CCOpts,
     const clangd::RenameOptions &RenameOpts,
     llvm::Optional<Path> CompileCommandsDir, bool UseDirBasedCDB,

diff  --git a/clang-tools-extra/clangd/ClangdLSPServer.h b/clang-tools-extra/clangd/ClangdLSPServer.h
index c3da2f9a9457..a62f2cebcae2 100644
--- a/clang-tools-extra/clangd/ClangdLSPServer.h
+++ b/clang-tools-extra/clangd/ClangdLSPServer.h
@@ -41,7 +41,7 @@ class ClangdLSPServer : private ClangdServer::Callbacks {
   /// for compile_commands.json in all parent directories of each file.
   /// If UseDirBasedCDB is false, compile commands are not read from disk.
   // FIXME: Clean up signature around CDBs.
-  ClangdLSPServer(Transport &Transp, const FileSystemProvider &FSProvider,
+  ClangdLSPServer(Transport &Transp, const ThreadsafeFS &FSProvider,
                   const clangd::CodeCompleteOptions &CCOpts,
                   const clangd::RenameOptions &RenameOpts,
                   llvm::Optional<Path> CompileCommandsDir, bool UseDirBasedCDB,
@@ -207,7 +207,7 @@ class ClangdLSPServer : private ClangdServer::Callbacks {
     notify("$/progress", Params);
   }
 
-  const FileSystemProvider &FSProvider;
+  const ThreadsafeFS &FSProvider;
   /// Options used for code completion
   clangd::CodeCompleteOptions CCOpts;
   /// Options used for rename.

diff  --git a/clang-tools-extra/clangd/ClangdServer.cpp b/clang-tools-extra/clangd/ClangdServer.cpp
index 2007f922c9e3..f8c0ee9df3a3 100644
--- a/clang-tools-extra/clangd/ClangdServer.cpp
+++ b/clang-tools-extra/clangd/ClangdServer.cpp
@@ -27,6 +27,7 @@
 #include "refactor/Tweak.h"
 #include "support/Logger.h"
 #include "support/Markup.h"
+#include "support/ThreadsafeFS.h"
 #include "support/Trace.h"
 #include "clang/Format/Format.h"
 #include "clang/Frontend/CompilerInstance.h"
@@ -129,8 +130,8 @@ ClangdServer::Options::operator TUScheduler::Options() const {
 }
 
 ClangdServer::ClangdServer(const GlobalCompilationDatabase &CDB,
-                           const FileSystemProvider &FSProvider,
-                           const Options &Opts, Callbacks *Callbacks)
+                           const ThreadsafeFS &FSProvider, const Options &Opts,
+                           Callbacks *Callbacks)
     : FSProvider(FSProvider),
       DynamicIdx(Opts.BuildDynamicSymbolIndex
                      ? new FileIndex(Opts.HeavyweightDynamicSymbolIndex)
@@ -183,8 +184,8 @@ void ClangdServer::addDocument(PathRef File, llvm::StringRef Contents,
   Opts.ClangTidyOpts = tidy::ClangTidyOptions::getDefaults();
   // FIXME: call tidy options builder on the worker thread, it can do IO.
   if (GetClangTidyOptions)
-    Opts.ClangTidyOpts = GetClangTidyOptions(
-        *FSProvider.getFileSystem(/*CWD=*/llvm::None), File);
+    Opts.ClangTidyOpts =
+        GetClangTidyOptions(*FSProvider.view(/*CWD=*/llvm::None), File);
   Opts.SuggestMissingIncludes = SuggestMissingIncludes;
 
   // Compile command is set asynchronously during update, as it can be slow.
@@ -318,9 +319,9 @@ ClangdServer::formatOnType(llvm::StringRef Code, PathRef File, Position Pos,
   llvm::Expected<size_t> CursorPos = positionToOffset(Code, Pos);
   if (!CursorPos)
     return CursorPos.takeError();
-  auto Style = format::getStyle(
-      format::DefaultFormatStyle, File, format::DefaultFallbackStyle, Code,
-      FSProvider.getFileSystem(/*CWD=*/llvm::None).get());
+  auto Style = format::getStyle(format::DefaultFormatStyle, File,
+                                format::DefaultFallbackStyle, Code,
+                                FSProvider.view(/*CWD=*/llvm::None).get());
   if (!Style)
     return Style.takeError();
 
@@ -549,7 +550,7 @@ void ClangdServer::switchSourceHeader(
   //  2) if 1) fails, we use the AST&Index approach, it is slower but supports
   //     
diff erent code layout.
   if (auto CorrespondingFile = getCorrespondingHeaderOrSource(
-          std::string(Path), FSProvider.getFileSystem(llvm::None)))
+          std::string(Path), FSProvider.view(llvm::None)))
     return CB(std::move(CorrespondingFile));
   auto Action = [Path = Path.str(), CB = std::move(CB),
                  this](llvm::Expected<InputsAndAST> InpAST) mutable {

diff  --git a/clang-tools-extra/clangd/ClangdServer.h b/clang-tools-extra/clangd/ClangdServer.h
index b758a5f32aa7..64ac5f9428d6 100644
--- a/clang-tools-extra/clangd/ClangdServer.h
+++ b/clang-tools-extra/clangd/ClangdServer.h
@@ -23,8 +23,8 @@
 #include "refactor/Rename.h"
 #include "refactor/Tweak.h"
 #include "support/Cancellation.h"
-#include "support/FSProvider.h"
 #include "support/Function.h"
+#include "support/ThreadsafeFS.h"
 #include "clang/Tooling/CompilationDatabase.h"
 #include "clang/Tooling/Core/Replacement.h"
 #include "llvm/ADT/FunctionExtras.h"
@@ -172,7 +172,7 @@ class ClangdServer {
   /// those arguments for subsequent reparses. However, ClangdServer will check
   /// if compilation arguments changed on calls to forceReparse().
   ClangdServer(const GlobalCompilationDatabase &CDB,
-               const FileSystemProvider &FSProvider, const Options &Opts,
+               const ThreadsafeFS &FSProvider, const Options &Opts,
                Callbacks *Callbacks = nullptr);
 
   /// Add a \p File to the list of tracked C++ files or update the contents if
@@ -330,7 +330,7 @@ class ClangdServer {
   formatCode(llvm::StringRef Code, PathRef File,
              ArrayRef<tooling::Range> Ranges);
 
-  const FileSystemProvider &FSProvider;
+  const ThreadsafeFS &FSProvider;
 
   Path ResourceDir;
   // The index used to look up symbols. This could be:

diff  --git a/clang-tools-extra/clangd/CodeComplete.cpp b/clang-tools-extra/clangd/CodeComplete.cpp
index 511bf028d2d9..4c483bfda373 100644
--- a/clang-tools-extra/clangd/CodeComplete.cpp
+++ b/clang-tools-extra/clangd/CodeComplete.cpp
@@ -36,9 +36,9 @@
 #include "index/Index.h"
 #include "index/Symbol.h"
 #include "index/SymbolOrigin.h"
-#include "support/FSProvider.h"
 #include "support/Logger.h"
 #include "support/Threading.h"
+#include "support/ThreadsafeFS.h"
 #include "support/Trace.h"
 #include "clang/AST/Decl.h"
 #include "clang/AST/DeclBase.h"
@@ -1113,7 +1113,7 @@ bool semaCodeComplete(std::unique_ptr<CodeCompleteConsumer> Consumer,
   // NOTE: we must call BeginSourceFile after prepareCompilerInstance. Otherwise
   // the remapped buffers do not get freed.
   llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem> VFS =
-      Input.ParseInput.FSProvider->getFileSystem(
+      Input.ParseInput.FSProvider->view(
           Input.ParseInput.CompileCommand.Directory);
   if (Input.Preamble.StatCache)
     VFS = Input.Preamble.StatCache->getConsumingFS(std::move(VFS));
@@ -1364,7 +1364,7 @@ class CodeCompleteFlow {
   }
 
   CodeCompleteResult runWithoutSema(llvm::StringRef Content, size_t Offset,
-                                    const FileSystemProvider &FSProvider) && {
+                                    const ThreadsafeFS &FSProvider) && {
     trace::Span Tracer("CodeCompleteWithoutSema");
     // Fill in fields normally set by runWithSema()
     HeuristicPrefix = guessCompletionPrefix(Content, Offset);

diff  --git a/clang-tools-extra/clangd/Compiler.cpp b/clang-tools-extra/clangd/Compiler.cpp
index 170e8035cf50..e1882b188317 100644
--- a/clang-tools-extra/clangd/Compiler.cpp
+++ b/clang-tools-extra/clangd/Compiler.cpp
@@ -48,7 +48,7 @@ buildCompilerInvocation(const ParseInputs &Inputs, clang::DiagnosticConsumer &D,
   for (const auto &S : Inputs.CompileCommand.CommandLine)
     ArgStrs.push_back(S.c_str());
 
-  auto VFS = Inputs.FSProvider->getFileSystem(Inputs.CompileCommand.Directory);
+  auto VFS = Inputs.FSProvider->view(Inputs.CompileCommand.Directory);
   llvm::IntrusiveRefCntPtr<DiagnosticsEngine> CommandLineDiagsEngine =
       CompilerInstance::createDiagnostics(new DiagnosticOptions, &D, false);
   std::unique_ptr<CompilerInvocation> CI = createInvocationFromCommandLine(

diff  --git a/clang-tools-extra/clangd/Compiler.h b/clang-tools-extra/clangd/Compiler.h
index a4edf957549e..bbec9982fc6b 100644
--- a/clang-tools-extra/clangd/Compiler.h
+++ b/clang-tools-extra/clangd/Compiler.h
@@ -18,7 +18,7 @@
 #include "../clang-tidy/ClangTidyOptions.h"
 #include "GlobalCompilationDatabase.h"
 #include "index/Index.h"
-#include "support/FSProvider.h"
+#include "support/ThreadsafeFS.h"
 #include "clang/Frontend/CompilerInstance.h"
 #include "clang/Frontend/PrecompiledPreamble.h"
 #include "clang/Tooling/CompilationDatabase.h"
@@ -46,7 +46,7 @@ struct ParseOptions {
 /// Information required to run clang, e.g. to parse AST or do code completion.
 struct ParseInputs {
   tooling::CompileCommand CompileCommand;
-  const FileSystemProvider *FSProvider;
+  const ThreadsafeFS *FSProvider;
   std::string Contents;
   // Version identifier for Contents, provided by the client and opaque to us.
   std::string Version = "null";

diff  --git a/clang-tools-extra/clangd/ParsedAST.cpp b/clang-tools-extra/clangd/ParsedAST.cpp
index d9a26cb999e1..2664c32922ee 100644
--- a/clang-tools-extra/clangd/ParsedAST.cpp
+++ b/clang-tools-extra/clangd/ParsedAST.cpp
@@ -249,7 +249,7 @@ ParsedAST::build(llvm::StringRef Filename, const ParseInputs &Inputs,
   trace::Span Tracer("BuildAST");
   SPAN_ATTACH(Tracer, "File", Filename);
 
-  auto VFS = Inputs.FSProvider->getFileSystem(Inputs.CompileCommand.Directory);
+  auto VFS = Inputs.FSProvider->view(Inputs.CompileCommand.Directory);
   if (Preamble && Preamble->StatCache)
     VFS = Preamble->StatCache->getConsumingFS(std::move(VFS));
 

diff  --git a/clang-tools-extra/clangd/Preamble.cpp b/clang-tools-extra/clangd/Preamble.cpp
index 2788c9c57e75..7a610503bf36 100644
--- a/clang-tools-extra/clangd/Preamble.cpp
+++ b/clang-tools-extra/clangd/Preamble.cpp
@@ -10,8 +10,8 @@
 #include "Compiler.h"
 #include "Headers.h"
 #include "SourceCode.h"
-#include "support/FSProvider.h"
 #include "support/Logger.h"
+#include "support/ThreadsafeFS.h"
 #include "support/Trace.h"
 #include "clang/AST/DeclTemplate.h"
 #include "clang/Basic/Diagnostic.h"
@@ -234,12 +234,12 @@ scanPreamble(llvm::StringRef Contents,
   // than vfs::FileSystem, that way we can just use ParseInputs without this
   // hack.
   auto GetFSProvider = [](llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem> FS) {
-    class VFSProvider : public FileSystemProvider {
+    class VFSProvider : public ThreadsafeFS {
     public:
       VFSProvider(llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem> FS)
           : VFS(std::move(FS)) {}
       llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem>
-      getFileSystem(llvm::NoneType) const override {
+      view(llvm::NoneType) const override {
         return VFS;
       }
 
@@ -358,7 +358,7 @@ buildPreamble(PathRef FileName, CompilerInvocation CI,
   CI.getPreprocessorOpts().WriteCommentListToPCH = false;
 
   CppFilePreambleCallbacks SerializedDeclsCollector(FileName, PreambleCallback);
-  auto VFS = Inputs.FSProvider->getFileSystem(Inputs.CompileCommand.Directory);
+  auto VFS = Inputs.FSProvider->view(Inputs.CompileCommand.Directory);
   llvm::SmallString<32> AbsFileName(FileName);
   VFS->makeAbsolute(AbsFileName);
   auto StatCache = std::make_unique<PreambleFileStatusCache>(AbsFileName);
@@ -395,7 +395,7 @@ bool isPreambleCompatible(const PreambleData &Preamble,
       llvm::MemoryBuffer::getMemBuffer(Inputs.Contents, FileName);
   auto Bounds =
       ComputePreambleBounds(*CI.getLangOpts(), ContentsBuffer.get(), 0);
-  auto VFS = Inputs.FSProvider->getFileSystem(Inputs.CompileCommand.Directory);
+  auto VFS = Inputs.FSProvider->view(Inputs.CompileCommand.Directory);
   return compileCommandsAreEqual(Inputs.CompileCommand,
                                  Preamble.CompileCommand) &&
          Preamble.Preamble.CanReuse(CI, ContentsBuffer.get(), Bounds,
@@ -423,7 +423,7 @@ PreamblePatch PreamblePatch::create(llvm::StringRef FileName,
   SPAN_ATTACH(Tracer, "File", FileName);
   assert(llvm::sys::path::is_absolute(FileName) && "relative FileName!");
   auto VFS = Baseline.StatCache->getConsumingFS(
-      Modified.FSProvider->getFileSystem(/*CWD=*/llvm::None));
+      Modified.FSProvider->view(/*CWD=*/llvm::None));
   // First scan preprocessor directives in Baseline and Modified. These will be
   // used to figure out newly added directives in Modified. Scanning can fail,
   // the code just bails out and creates an empty patch in such cases, as:

diff  --git a/clang-tools-extra/clangd/SourceCode.cpp b/clang-tools-extra/clangd/SourceCode.cpp
index 10547919c664..d816f299c5a0 100644
--- a/clang-tools-extra/clangd/SourceCode.cpp
+++ b/clang-tools-extra/clangd/SourceCode.cpp
@@ -12,8 +12,8 @@
 #include "Protocol.h"
 #include "refactor/Tweak.h"
 #include "support/Context.h"
-#include "support/FSProvider.h"
 #include "support/Logger.h"
+#include "support/Threading.h"
 #include "clang/AST/ASTContext.h"
 #include "clang/Basic/LangOptions.h"
 #include "clang/Basic/SourceLocation.h"
@@ -575,12 +575,12 @@ llvm::Optional<FileDigest> digestFile(const SourceManager &SM, FileID FID) {
   return digest(Content);
 }
 
-format::FormatStyle
-getFormatStyleForFile(llvm::StringRef File, llvm::StringRef Content,
-                      const FileSystemProvider &FSProvider) {
-  auto Style = format::getStyle(
-      format::DefaultFormatStyle, File, format::DefaultFallbackStyle, Content,
-      FSProvider.getFileSystem(/*CWD=*/llvm::None).get());
+format::FormatStyle getFormatStyleForFile(llvm::StringRef File,
+                                          llvm::StringRef Content,
+                                          const ThreadsafeFS &FSProvider) {
+  auto Style = format::getStyle(format::DefaultFormatStyle, File,
+                                format::DefaultFallbackStyle, Content,
+                                FSProvider.view(/*CWD=*/llvm::None).get());
   if (!Style) {
     log("getStyle() failed for file {0}: {1}. Fallback is LLVM style.", File,
         Style.takeError());

diff  --git a/clang-tools-extra/clangd/SourceCode.h b/clang-tools-extra/clangd/SourceCode.h
index 6f36069163a0..d1355504df99 100644
--- a/clang-tools-extra/clangd/SourceCode.h
+++ b/clang-tools-extra/clangd/SourceCode.h
@@ -15,7 +15,7 @@
 
 #include "Protocol.h"
 #include "support/Context.h"
-#include "support/FSProvider.h"
+#include "support/ThreadsafeFS.h"
 #include "clang/Basic/Diagnostic.h"
 #include "clang/Basic/LangOptions.h"
 #include "clang/Basic/SourceLocation.h"
@@ -168,7 +168,7 @@ llvm::Optional<std::string> getCanonicalPath(const FileEntry *F,
 /// though the latter may have been overridden in main()!
 format::FormatStyle getFormatStyleForFile(llvm::StringRef File,
                                           llvm::StringRef Content,
-                                          const FileSystemProvider &FSProvider);
+                                          const ThreadsafeFS &FSProvider);
 
 /// Cleanup and format the given replacements.
 llvm::Expected<tooling::Replacements>

diff  --git a/clang-tools-extra/clangd/fuzzer/clangd-fuzzer.cpp b/clang-tools-extra/clangd/fuzzer/clangd-fuzzer.cpp
index 982d5fa292d3..e620342499bf 100644
--- a/clang-tools-extra/clangd/fuzzer/clangd-fuzzer.cpp
+++ b/clang-tools-extra/clangd/fuzzer/clangd-fuzzer.cpp
@@ -16,7 +16,7 @@
 #include "ClangdServer.h"
 #include "CodeComplete.h"
 #include "refactor/Rename.h"
-#include "support/FSProvider.h"
+#include "support/ThreadsafeFS.h"
 #include <cstdio>
 #include <sstream>
 
@@ -31,7 +31,7 @@ extern "C" int LLVMFuzzerTestOneInput(uint8_t *data, size_t size) {
   auto Transport = newJSONTransport(In, llvm::nulls(),
                                     /*InMirror=*/nullptr, /*Pretty=*/false,
                                     /*Style=*/JSONStreamStyle::Delimited);
-  RealFileSystemProvider FS;
+  RealThreadsafeFS FS;
   CodeCompleteOptions CCOpts;
   CCOpts.EnableSnippets = false;
   ClangdServer::Options Opts;

diff  --git a/clang-tools-extra/clangd/index/Background.cpp b/clang-tools-extra/clangd/index/Background.cpp
index 6490cfcd1c00..bc0070a2a338 100644
--- a/clang-tools-extra/clangd/index/Background.cpp
+++ b/clang-tools-extra/clangd/index/Background.cpp
@@ -22,10 +22,10 @@
 #include "index/Serialization.h"
 #include "index/SymbolCollector.h"
 #include "support/Context.h"
-#include "support/FSProvider.h"
 #include "support/Logger.h"
 #include "support/Path.h"
 #include "support/Threading.h"
+#include "support/ThreadsafeFS.h"
 #include "support/Trace.h"
 #include "clang/Basic/SourceLocation.h"
 #include "clang/Basic/SourceManager.h"
@@ -90,7 +90,7 @@ bool shardIsStale(const LoadedShard &LS, llvm::vfs::FileSystem *FS) {
 } // namespace
 
 BackgroundIndex::BackgroundIndex(
-    Context BackgroundContext, const FileSystemProvider &FSProvider,
+    Context BackgroundContext, const ThreadsafeFS &FSProvider,
     const GlobalCompilationDatabase &CDB,
     BackgroundIndexStorage::Factory IndexStorageFactory, size_t ThreadPoolSize,
     std::function<void(BackgroundQueue::Stats)> OnProgress)
@@ -244,7 +244,7 @@ llvm::Error BackgroundIndex::index(tooling::CompileCommand Cmd) {
   SPAN_ATTACH(Tracer, "file", Cmd.Filename);
   auto AbsolutePath = getAbsolutePath(Cmd);
 
-  auto FS = FSProvider.getFileSystem(Cmd.Directory);
+  auto FS = FSProvider.view(Cmd.Directory);
   auto Buf = FS->getBufferForFile(AbsolutePath);
   if (!Buf)
     return llvm::errorCodeToError(Buf.getError());
@@ -381,7 +381,7 @@ BackgroundIndex::loadProject(std::vector<std::string> MainFiles) {
   Rebuilder.loadedShard(LoadedShards);
   Rebuilder.doneLoading();
 
-  auto FS = FSProvider.getFileSystem(/*CWD=*/llvm::None);
+  auto FS = FSProvider.view(/*CWD=*/llvm::None);
   llvm::DenseSet<PathRef> TUsToIndex;
   // We'll accept data from stale shards, but ensure the files get reindexed
   // soon.

diff  --git a/clang-tools-extra/clangd/index/Background.h b/clang-tools-extra/clangd/index/Background.h
index ffaea75c5d41..7b0368e012c3 100644
--- a/clang-tools-extra/clangd/index/Background.h
+++ b/clang-tools-extra/clangd/index/Background.h
@@ -16,9 +16,9 @@
 #include "index/Index.h"
 #include "index/Serialization.h"
 #include "support/Context.h"
-#include "support/FSProvider.h"
 #include "support/Path.h"
 #include "support/Threading.h"
+#include "support/ThreadsafeFS.h"
 #include "clang/Tooling/CompilationDatabase.h"
 #include "llvm/ADT/StringMap.h"
 #include "llvm/Support/Threading.h"
@@ -132,7 +132,7 @@ class BackgroundIndex : public SwapIndex {
   /// rebuilt periodically (one per \p BuildIndexPeriodMs); otherwise, index is
   /// rebuilt for each indexed file.
   BackgroundIndex(
-      Context BackgroundContext, const FileSystemProvider &,
+      Context BackgroundContext, const ThreadsafeFS &,
       const GlobalCompilationDatabase &CDB,
       BackgroundIndexStorage::Factory IndexStorageFactory,
       size_t ThreadPoolSize = 0, // 0 = use all hardware threads
@@ -178,7 +178,7 @@ class BackgroundIndex : public SwapIndex {
               bool HadErrors);
 
   // configuration
-  const FileSystemProvider &FSProvider;
+  const ThreadsafeFS &FSProvider;
   const GlobalCompilationDatabase &CDB;
   Context BackgroundContext;
 

diff  --git a/clang-tools-extra/clangd/support/CMakeLists.txt b/clang-tools-extra/clangd/support/CMakeLists.txt
index 04a897e67037..ce08f7d58cd0 100644
--- a/clang-tools-extra/clangd/support/CMakeLists.txt
+++ b/clang-tools-extra/clangd/support/CMakeLists.txt
@@ -19,11 +19,11 @@ include_directories(..)
 add_clang_library(clangdSupport
   Cancellation.cpp
   Context.cpp
-  FSProvider.cpp
   Logger.cpp
   Markup.cpp
   Shutdown.cpp
   Threading.cpp
+  ThreadsafeFS.cpp
   Trace.cpp
 
   LINK_LIBS

diff  --git a/clang-tools-extra/clangd/support/FSProvider.h b/clang-tools-extra/clangd/support/FSProvider.h
deleted file mode 100644
index 8c6b8c880c82..000000000000
--- a/clang-tools-extra/clangd/support/FSProvider.h
+++ /dev/null
@@ -1,51 +0,0 @@
-//===--- FSProvider.h - VFS provider for ClangdServer ------------*- C++-*-===//
-//
-// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
-// See https://llvm.org/LICENSE.txt for license information.
-// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
-//
-//===----------------------------------------------------------------------===//
-
-#ifndef LLVM_CLANG_TOOLS_EXTRA_CLANGD_SUPPORT_FSPROVIDER_H
-#define LLVM_CLANG_TOOLS_EXTRA_CLANGD_SUPPORT_FSPROVIDER_H
-
-#include "Path.h"
-#include "llvm/ADT/IntrusiveRefCntPtr.h"
-#include "llvm/ADT/None.h"
-#include "llvm/ADT/Optional.h"
-#include "llvm/Support/VirtualFileSystem.h"
-#include <memory>
-
-namespace clang {
-namespace clangd {
-
-// Wrapper for vfs::FileSystem for use in multithreaded programs like clangd.
-// As FileSystem is not threadsafe, concurrent threads must each obtain one.
-class FileSystemProvider {
-public:
-  virtual ~FileSystemProvider() = default;
-  /// Called by ClangdServer to obtain a vfs::FileSystem to be used for parsing.
-  /// Context::current() will be the context passed to the clang entrypoint,
-  /// such as addDocument(), and will also be propagated to result callbacks.
-  /// Embedders may use this to isolate filesystem accesses.
-  /// Initial working directory is arbitrary.
-  virtual llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem>
-  getFileSystem(llvm::NoneType CWD) const = 0;
-
-  /// As above, except it will try to set current working directory to \p CWD.
-  /// This is an overload instead of an optional to make implicit string ->
-  /// StringRef conversion possible.
-  virtual llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem>
-  getFileSystem(PathRef CWD) const;
-};
-
-class RealFileSystemProvider : public FileSystemProvider {
-public:
-  llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem>
-      getFileSystem(llvm::NoneType) const override;
-};
-
-} // namespace clangd
-} // namespace clang
-
-#endif

diff  --git a/clang-tools-extra/clangd/support/FSProvider.cpp b/clang-tools-extra/clangd/support/ThreadsafeFS.cpp
similarity index 92%
rename from clang-tools-extra/clangd/support/FSProvider.cpp
rename to clang-tools-extra/clangd/support/ThreadsafeFS.cpp
index 080bd06a811b..a25ac773bfa2 100644
--- a/clang-tools-extra/clangd/support/FSProvider.cpp
+++ b/clang-tools-extra/clangd/support/ThreadsafeFS.cpp
@@ -1,4 +1,4 @@
-//===--- FSProvider.cpp - VFS provider for ClangdServer -------------------===//
+//===--- ThreadsafeFS.cpp -------------------------------------------------===//
 //
 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
 // See https://llvm.org/LICENSE.txt for license information.
@@ -6,7 +6,7 @@
 //
 //===----------------------------------------------------------------------===//
 
-#include "support/FSProvider.h"
+#include "support/ThreadsafeFS.h"
 #include "Logger.h"
 #include "llvm/ADT/None.h"
 #include "llvm/ADT/Optional.h"
@@ -75,15 +75,15 @@ class VolatileFileSystem : public llvm::vfs::ProxyFileSystem {
 } // namespace
 
 llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem>
-FileSystemProvider::getFileSystem(PathRef CWD) const {
-  auto FS = getFileSystem(/*CWD=*/llvm::None);
+ThreadsafeFS::view(PathRef CWD) const {
+  auto FS = view(llvm::None);
   if (auto EC = FS->setCurrentWorkingDirectory(CWD))
     elog("VFS: failed to set CWD to {0}: {1}", CWD, EC.message());
   return FS;
 }
 
 llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem>
-clang::clangd::RealFileSystemProvider::getFileSystem(llvm::NoneType) const {
+RealThreadsafeFS::view(llvm::NoneType) const {
   // Avoid using memory-mapped files.
   // FIXME: Try to use a similar approach in Sema instead of relying on
   //        propagation of the 'isVolatile' flag through all layers.

diff  --git a/clang-tools-extra/clangd/support/ThreadsafeFS.h b/clang-tools-extra/clangd/support/ThreadsafeFS.h
new file mode 100644
index 000000000000..aa6825fb3999
--- /dev/null
+++ b/clang-tools-extra/clangd/support/ThreadsafeFS.h
@@ -0,0 +1,52 @@
+//===--- ThreadsafeFS.h ------------------------------------------*- C++-*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_CLANG_TOOLS_EXTRA_CLANGD_SUPPORT_THREADSAFEFS_H
+#define LLVM_CLANG_TOOLS_EXTRA_CLANGD_SUPPORT_THREADSAFEFS_H
+
+#include "Path.h"
+#include "llvm/ADT/IntrusiveRefCntPtr.h"
+#include "llvm/ADT/None.h"
+#include "llvm/ADT/Optional.h"
+#include "llvm/Support/VirtualFileSystem.h"
+#include <memory>
+
+namespace clang {
+namespace clangd {
+
+/// Wrapper for vfs::FileSystem for use in multithreaded programs like clangd.
+/// As FileSystem is not threadsafe, concurrent threads must each obtain one.
+/// Implementations may choose to depend on Context::current() e.g. to implement
+/// snapshot semantics. clangd will not create vfs::FileSystems for use in
+/// 
diff erent contexts, so either ThreadsafeFS::view or the returned FS may
+/// contain this logic.
+class ThreadsafeFS {
+public:
+  virtual ~ThreadsafeFS() = default;
+
+  /// Obtain a vfs::FileSystem with an arbitrary initial working directory.
+  virtual llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem>
+  view(llvm::NoneType CWD) const = 0;
+
+  /// Obtain a vfs::FileSystem with a specified working directory.
+  /// If the working directory can't be set (e.g. doesn't exist), logs and
+  /// returns the FS anyway.
+  virtual llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem>
+  view(PathRef CWD) const;
+};
+
+class RealThreadsafeFS : public ThreadsafeFS {
+public:
+  llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem>
+      view(llvm::NoneType) const override;
+};
+
+} // namespace clangd
+} // namespace clang
+
+#endif

diff  --git a/clang-tools-extra/clangd/tool/ClangdMain.cpp b/clang-tools-extra/clangd/tool/ClangdMain.cpp
index 503983746ab6..9322811b6449 100644
--- a/clang-tools-extra/clangd/tool/ClangdMain.cpp
+++ b/clang-tools-extra/clangd/tool/ClangdMain.cpp
@@ -17,6 +17,7 @@
 #include "refactor/Rename.h"
 #include "support/Path.h"
 #include "support/Shutdown.h"
+#include "support/ThreadsafeFS.h"
 #include "support/Trace.h"
 #include "clang/Basic/Version.h"
 #include "clang/Format/Format.h"
@@ -675,7 +676,7 @@ clangd accepts flags on the commandline, and in the CLANGD_FLAGS environment var
   CCOpts.AllScopes = AllScopesCompletion;
   CCOpts.RunParser = CodeCompletionParse;
 
-  RealFileSystemProvider FSProvider;
+  RealThreadsafeFS FSProvider;
   // Initialize and run ClangdLSPServer.
   // Change stdin to binary to not lose \r\n on windows.
   llvm::sys::ChangeStdinToBinary();
@@ -719,7 +720,7 @@ clangd accepts flags on the commandline, and in the CLANGD_FLAGS environment var
         tidy::ClangTidyGlobalOptions(),
         /* Default */ EmptyDefaults,
         /* Override */ OverrideClangTidyOptions,
-        FSProvider.getFileSystem(/*CWD=*/llvm::None));
+        FSProvider.view(/*CWD=*/llvm::None));
     Opts.GetClangTidyOptions = [&](llvm::vfs::FileSystem &,
                                    llvm::StringRef File) {
       // This function must be thread-safe and tidy option providers are not.

diff  --git a/clang-tools-extra/clangd/unittests/BackgroundIndexTests.cpp b/clang-tools-extra/clangd/unittests/BackgroundIndexTests.cpp
index b870a8ed5a83..24322e1575ab 100644
--- a/clang-tools-extra/clangd/unittests/BackgroundIndexTests.cpp
+++ b/clang-tools-extra/clangd/unittests/BackgroundIndexTests.cpp
@@ -86,7 +86,7 @@ class BackgroundIndexTest : public ::testing::Test {
 };
 
 TEST_F(BackgroundIndexTest, NoCrashOnErrorFile) {
-  MockFSProvider FS;
+  MockFS FS;
   FS.Files[testPath("root/A.cc")] = "error file";
   llvm::StringMap<std::string> Storage;
   size_t CacheHits = 0;
@@ -105,7 +105,7 @@ TEST_F(BackgroundIndexTest, NoCrashOnErrorFile) {
 }
 
 TEST_F(BackgroundIndexTest, IndexTwoFiles) {
-  MockFSProvider FS;
+  MockFS FS;
   // a.h yields 
diff erent symbols when included by A.cc vs B.cc.
   FS.Files[testPath("root/A.h")] = R"cpp(
       void common();
@@ -175,7 +175,7 @@ TEST_F(BackgroundIndexTest, IndexTwoFiles) {
 }
 
 TEST_F(BackgroundIndexTest, ShardStorageTest) {
-  MockFSProvider FS;
+  MockFS FS;
   FS.Files[testPath("root/A.h")] = R"cpp(
       void common();
       void f_b();
@@ -246,7 +246,7 @@ TEST_F(BackgroundIndexTest, ShardStorageTest) {
 }
 
 TEST_F(BackgroundIndexTest, DirectIncludesTest) {
-  MockFSProvider FS;
+  MockFS FS;
   FS.Files[testPath("root/B.h")] = "";
   FS.Files[testPath("root/A.h")] = R"cpp(
       #include "B.h"
@@ -297,7 +297,7 @@ TEST_F(BackgroundIndexTest, DirectIncludesTest) {
 }
 
 TEST_F(BackgroundIndexTest, ShardStorageLoad) {
-  MockFSProvider FS;
+  MockFS FS;
   FS.Files[testPath("root/A.h")] = R"cpp(
       void common();
       void f_b();
@@ -368,7 +368,7 @@ TEST_F(BackgroundIndexTest, ShardStorageLoad) {
 }
 
 TEST_F(BackgroundIndexTest, ShardStorageEmptyFile) {
-  MockFSProvider FS;
+  MockFS FS;
   FS.Files[testPath("root/A.h")] = R"cpp(
       void common();
       void f_b();
@@ -436,7 +436,7 @@ TEST_F(BackgroundIndexTest, ShardStorageEmptyFile) {
 }
 
 TEST_F(BackgroundIndexTest, NoDotsInAbsPath) {
-  MockFSProvider FS;
+  MockFS FS;
   llvm::StringMap<std::string> Storage;
   size_t CacheHits = 0;
   MemoryShardStorage MSS(Storage, CacheHits);
@@ -467,7 +467,7 @@ TEST_F(BackgroundIndexTest, NoDotsInAbsPath) {
 }
 
 TEST_F(BackgroundIndexTest, UncompilableFiles) {
-  MockFSProvider FS;
+  MockFS FS;
   llvm::StringMap<std::string> Storage;
   size_t CacheHits = 0;
   MemoryShardStorage MSS(Storage, CacheHits);
@@ -530,7 +530,7 @@ TEST_F(BackgroundIndexTest, UncompilableFiles) {
 }
 
 TEST_F(BackgroundIndexTest, CmdLineHash) {
-  MockFSProvider FS;
+  MockFS FS;
   llvm::StringMap<std::string> Storage;
   size_t CacheHits = 0;
   MemoryShardStorage MSS(Storage, CacheHits);

diff  --git a/clang-tools-extra/clangd/unittests/ClangdLSPServerTests.cpp b/clang-tools-extra/clangd/unittests/ClangdLSPServerTests.cpp
index 431c36c72b91..eaa6035df5ea 100644
--- a/clang-tools-extra/clangd/unittests/ClangdLSPServerTests.cpp
+++ b/clang-tools-extra/clangd/unittests/ClangdLSPServerTests.cpp
@@ -63,7 +63,7 @@ class LSPTest : public ::testing::Test, private clangd::Logger {
       stop();
   }
 
-  MockFSProvider FS;
+  MockFS FS;
   CodeCompleteOptions CCOpts;
   RenameOptions RenameOpts;
   ClangdServer::Options Opts = ClangdServer::optsForTest();

diff  --git a/clang-tools-extra/clangd/unittests/ClangdTests.cpp b/clang-tools-extra/clangd/unittests/ClangdTests.cpp
index 6cfdeaff335c..ffe752f50f4f 100644
--- a/clang-tools-extra/clangd/unittests/ClangdTests.cpp
+++ b/clang-tools-extra/clangd/unittests/ClangdTests.cpp
@@ -145,7 +145,7 @@ class ClangdVFSTest : public ::testing::Test {
       PathRef SourceFileRelPath, llvm::StringRef SourceContents,
       std::vector<std::pair<PathRef, llvm::StringRef>> ExtraFiles = {},
       bool ExpectErrors = false) {
-    MockFSProvider FS;
+    MockFS FS;
     ErrorCheckingCallbacks DiagConsumer;
     MockCompilationDatabase CDB;
     ClangdServer Server(CDB, FS, ClangdServer::optsForTest(), &DiagConsumer);
@@ -198,7 +198,7 @@ int b = a;
 }
 
 TEST_F(ClangdVFSTest, Reparse) {
-  MockFSProvider FS;
+  MockFS FS;
   ErrorCheckingCallbacks DiagConsumer;
   MockCompilationDatabase CDB;
   ClangdServer Server(CDB, FS, ClangdServer::optsForTest(), &DiagConsumer);
@@ -233,7 +233,7 @@ int b = a;
 }
 
 TEST_F(ClangdVFSTest, ReparseOnHeaderChange) {
-  MockFSProvider FS;
+  MockFS FS;
   ErrorCheckingCallbacks DiagConsumer;
   MockCompilationDatabase CDB;
   ClangdServer Server(CDB, FS, ClangdServer::optsForTest(), &DiagConsumer);
@@ -272,9 +272,9 @@ int b = a;
 
 TEST_F(ClangdVFSTest, PropagatesContexts) {
   static Key<int> Secret;
-  struct FSProvider : public FileSystemProvider {
+  struct FSProvider : public ThreadsafeFS {
     IntrusiveRefCntPtr<llvm::vfs::FileSystem>
-    getFileSystem(llvm::NoneType) const override {
+    view(llvm::NoneType) const override {
       Got = Context::current().getExisting(Secret);
       return buildTestFS({});
     }
@@ -302,7 +302,7 @@ TEST_F(ClangdVFSTest, PropagatesContexts) {
 
 TEST_F(ClangdVFSTest, PropagatesVersion) {
   MockCompilationDatabase CDB;
-  MockFSProvider FS;
+  MockFS FS;
   struct Callbacks : public ClangdServer::Callbacks {
     void onDiagnosticsReady(PathRef File, llvm::StringRef Version,
                             std::vector<Diag> Diagnostics) override {
@@ -321,7 +321,7 @@ TEST_F(ClangdVFSTest, PropagatesVersion) {
 #ifdef LLVM_ON_UNIX
 TEST_F(ClangdVFSTest, SearchLibDir) {
   // Checks that searches for GCC installation is done through vfs.
-  MockFSProvider FS;
+  MockFS FS;
   ErrorCheckingCallbacks DiagConsumer;
   MockCompilationDatabase CDB;
   CDB.ExtraClangFlags.insert(CDB.ExtraClangFlags.end(),
@@ -370,7 +370,7 @@ std::string x;
 #endif // LLVM_ON_UNIX
 
 TEST_F(ClangdVFSTest, ForceReparseCompileCommand) {
-  MockFSProvider FS;
+  MockFS FS;
   ErrorCheckingCallbacks DiagConsumer;
   MockCompilationDatabase CDB;
   ClangdServer Server(CDB, FS, ClangdServer::optsForTest(), &DiagConsumer);
@@ -406,7 +406,7 @@ struct bar { T x; };
 }
 
 TEST_F(ClangdVFSTest, ForceReparseCompileCommandDefines) {
-  MockFSProvider FS;
+  MockFS FS;
   ErrorCheckingCallbacks DiagConsumer;
   MockCompilationDatabase CDB;
   ClangdServer Server(CDB, FS, ClangdServer::optsForTest(), &DiagConsumer);
@@ -458,7 +458,7 @@ this is an error
 int hello;
 )cpp");
 
-  MockFSProvider FS;
+  MockFS FS;
   MockCompilationDatabase CDB;
   MultipleErrorCheckingCallbacks DiagConsumer;
   ClangdServer Server(CDB, FS, ClangdServer::optsForTest(), &DiagConsumer);
@@ -508,7 +508,7 @@ MATCHER_P4(Stats, Name, UsesMemory, PreambleBuilds, ASTBuilds, "") {
 }
 
 TEST_F(ClangdVFSTest, FileStats) {
-  MockFSProvider FS;
+  MockFS FS;
   ErrorCheckingCallbacks DiagConsumer;
   MockCompilationDatabase CDB;
   ClangdServer Server(CDB, FS, ClangdServer::optsForTest(), &DiagConsumer);
@@ -544,7 +544,7 @@ struct Something {
 }
 
 TEST_F(ClangdVFSTest, InvalidCompileCommand) {
-  MockFSProvider FS;
+  MockFS FS;
   ErrorCheckingCallbacks DiagConsumer;
   MockCompilationDatabase CDB;
 
@@ -605,7 +605,7 @@ int d;
   unsigned MaxColumnForFileRequests = 10;
 
   std::vector<std::string> FilePaths;
-  MockFSProvider FS;
+  MockFS FS;
   for (unsigned I = 0; I < FilesCount; ++I) {
     std::string Name = std::string("Foo") + std::to_string(I) + ".cpp";
     FS.Files[Name] = "";
@@ -839,7 +839,7 @@ int d;
 )cpp";
 
   auto FooCpp = testPath("foo.cpp");
-  MockFSProvider FS;
+  MockFS FS;
   FS.Files[FooCpp] = "";
 
   std::promise<void> StartSecondPromise;
@@ -856,7 +856,7 @@ int d;
 }
 
 TEST_F(ClangdVFSTest, FormatCode) {
-  MockFSProvider FS;
+  MockFS FS;
   ErrorCheckingCallbacks DiagConsumer;
   MockCompilationDatabase CDB;
   ClangdServer Server(CDB, FS, ClangdServer::optsForTest(), &DiagConsumer);
@@ -885,7 +885,7 @@ void f() {}
 }
 
 TEST_F(ClangdVFSTest, ChangedHeaderFromISystem) {
-  MockFSProvider FS;
+  MockFS FS;
   ErrorCheckingCallbacks DiagConsumer;
   MockCompilationDatabase CDB;
   ClangdServer Server(CDB, FS, ClangdServer::optsForTest(), &DiagConsumer);
@@ -924,13 +924,13 @@ TEST_F(ClangdVFSTest, ChangedHeaderFromISystem) {
 // Check that running code completion doesn't stat() a bunch of files from the
 // preamble again. (They should be using the preamble's stat-cache)
 TEST(ClangdTests, PreambleVFSStatCache) {
-  class ListenStatsFSProvider : public FileSystemProvider {
+  class ListenStatsFSProvider : public ThreadsafeFS {
   public:
     ListenStatsFSProvider(llvm::StringMap<unsigned> &CountStats)
         : CountStats(CountStats) {}
 
     IntrusiveRefCntPtr<llvm::vfs::FileSystem>
-    getFileSystem(llvm::NoneType) const override {
+    view(llvm::NoneType) const override {
       class ListenStatVFS : public llvm::vfs::ProxyFileSystem {
       public:
         ListenStatVFS(IntrusiveRefCntPtr<llvm::vfs::FileSystem> FS,
@@ -990,7 +990,7 @@ TEST(ClangdTests, PreambleVFSStatCache) {
 #endif
 
 TEST_F(ClangdVFSTest, FallbackWhenPreambleIsNotReady) {
-  MockFSProvider FS;
+  MockFS FS;
   ErrorCheckingCallbacks DiagConsumer;
   MockCompilationDatabase CDB;
   ClangdServer Server(CDB, FS, ClangdServer::optsForTest(), &DiagConsumer);
@@ -1036,7 +1036,7 @@ TEST_F(ClangdVFSTest, FallbackWhenPreambleIsNotReady) {
 }
 
 TEST_F(ClangdVFSTest, FallbackWhenWaitingForCompileCommand) {
-  MockFSProvider FS;
+  MockFS FS;
   ErrorCheckingCallbacks DiagConsumer;
   // Returns compile command only when notified.
   class DelayedCompilationDatabase : public GlobalCompilationDatabase {
@@ -1098,7 +1098,7 @@ TEST_F(ClangdVFSTest, FallbackWhenWaitingForCompileCommand) {
 // test as a workaround.
 #if !defined(__has_feature) || !__has_feature(address_sanitizer)
 TEST_F(ClangdVFSTest, TestStackOverflow) {
-  MockFSProvider FS;
+  MockFS FS;
   ErrorCheckingCallbacks DiagConsumer;
   MockCompilationDatabase CDB;
   ClangdServer Server(CDB, FS, ClangdServer::optsForTest(), &DiagConsumer);

diff  --git a/clang-tools-extra/clangd/unittests/CodeCompleteTests.cpp b/clang-tools-extra/clangd/unittests/CodeCompleteTests.cpp
index 909ffce9df59..31a1c2d46c09 100644
--- a/clang-tools-extra/clangd/unittests/CodeCompleteTests.cpp
+++ b/clang-tools-extra/clangd/unittests/CodeCompleteTests.cpp
@@ -108,7 +108,7 @@ CodeCompleteResult completions(const TestTU &TU, Position Point,
     Opts.Index = OverrideIndex.get();
   }
 
-  MockFSProvider FS;
+  MockFS FS;
   auto Inputs = TU.inputs(FS);
   Inputs.Opts.BuildRecoveryAST = true;
   Inputs.Opts.PreserveRecoveryASTType = true;
@@ -149,7 +149,7 @@ CodeCompleteResult completionsNoCompile(llvm::StringRef Text,
     Opts.Index = OverrideIndex.get();
   }
 
-  MockFSProvider FS;
+  MockFS FS;
   Annotations Test(Text);
   ParseInputs ParseInput{tooling::CompileCommand(), &FS, Test.code().str()};
   return codeComplete(FilePath, Test.point(), /*Preamble=*/nullptr, ParseInput,
@@ -770,7 +770,7 @@ TEST(CompletionTest, CompletionRecoveryASTType) {
 }
 
 TEST(CompletionTest, DynamicIndexIncludeInsertion) {
-  MockFSProvider FS;
+  MockFS FS;
   MockCompilationDatabase CDB;
   ClangdServer::Options Opts = ClangdServer::optsForTest();
   Opts.BuildDynamicSymbolIndex = true;
@@ -805,7 +805,7 @@ TEST(CompletionTest, DynamicIndexIncludeInsertion) {
 }
 
 TEST(CompletionTest, DynamicIndexMultiFile) {
-  MockFSProvider FS;
+  MockFS FS;
   MockCompilationDatabase CDB;
   auto Opts = ClangdServer::optsForTest();
   Opts.BuildDynamicSymbolIndex = true;
@@ -865,7 +865,7 @@ TEST(CompletionTest, Documentation) {
 }
 
 TEST(CompletionTest, CommentsFromSystemHeaders) {
-  MockFSProvider FS;
+  MockFS FS;
   MockCompilationDatabase CDB;
 
   auto Opts = ClangdServer::optsForTest();
@@ -1057,7 +1057,7 @@ SignatureHelp signatures(llvm::StringRef Text, Position Point,
     Index = memIndex(IndexSymbols);
 
   auto TU = TestTU::withCode(Text);
-  MockFSProvider FS;
+  MockFS FS;
   auto Inputs = TU.inputs(FS);
   Inputs.Index = Index.get();
   Inputs.Opts.BuildRecoveryAST = true;
@@ -1214,7 +1214,7 @@ TEST(SignatureHelpTest, StalePreamble) {
   TestTU TU;
   TU.Code = "";
   IgnoreDiagnostics Diags;
-  MockFSProvider FS;
+  MockFS FS;
   auto Inputs = TU.inputs(FS);
   auto CI = buildCompilerInvocation(Inputs, Diags);
   ASSERT_TRUE(CI);
@@ -1537,7 +1537,7 @@ TEST(CompletionTest, OverloadBundling) {
 }
 
 TEST(CompletionTest, DocumentationFromChangedFileCrash) {
-  MockFSProvider FS;
+  MockFS FS;
   auto FooH = testPath("foo.h");
   auto FooCpp = testPath("foo.cpp");
   FS.Files[FooH] = R"cpp(
@@ -1632,7 +1632,7 @@ TEST(CompletionTest, CompleteOnInvalidLine) {
   auto FooCpp = testPath("foo.cpp");
 
   MockCompilationDatabase CDB;
-  MockFSProvider FS;
+  MockFS FS;
   FS.Files[FooCpp] = "// empty file";
 
   ClangdServer Server(CDB, FS, ClangdServer::optsForTest());
@@ -1761,7 +1761,7 @@ TEST(CompletionTest, CodeCompletionContext) {
 }
 
 TEST(CompletionTest, FixItForArrowToDot) {
-  MockFSProvider FS;
+  MockFS FS;
   MockCompilationDatabase CDB;
 
   CodeCompleteOptions Opts;
@@ -1872,7 +1872,7 @@ TEST(CompletionTest, RenderWithFixItNonMerged) {
 }
 
 TEST(CompletionTest, CompletionTokenRange) {
-  MockFSProvider FS;
+  MockFS FS;
   MockCompilationDatabase CDB;
   TestTU TU;
   TU.AdditionalFiles["foo/abc/foo.h"] = "";
@@ -2037,7 +2037,7 @@ TEST(SignatureHelpTest, IndexDocumentation) {
 }
 
 TEST(SignatureHelpTest, DynamicIndexDocumentation) {
-  MockFSProvider FS;
+  MockFS FS;
   MockCompilationDatabase CDB;
   ClangdServer::Options Opts = ClangdServer::optsForTest();
   Opts.BuildDynamicSymbolIndex = true;
@@ -2209,7 +2209,7 @@ TEST(GuessCompletionPrefix, Filters) {
 }
 
 TEST(CompletionTest, EnableSpeculativeIndexRequest) {
-  MockFSProvider FS;
+  MockFS FS;
   MockCompilationDatabase CDB;
   ClangdServer Server(CDB, FS, ClangdServer::optsForTest());
 

diff  --git a/clang-tools-extra/clangd/unittests/CompilerTests.cpp b/clang-tools-extra/clangd/unittests/CompilerTests.cpp
index 58210a95df3c..59feb9312d23 100644
--- a/clang-tools-extra/clangd/unittests/CompilerTests.cpp
+++ b/clang-tools-extra/clangd/unittests/CompilerTests.cpp
@@ -19,7 +19,7 @@ namespace {
 using testing::IsEmpty;
 
 TEST(BuildCompilerInvocation, DropsPCH) {
-  MockFSProvider FS;
+  MockFS FS;
   IgnoreDiagnostics Diags;
   TestTU TU;
   TU.AdditionalFiles["test.h.pch"] = "";

diff  --git a/clang-tools-extra/clangd/unittests/FileIndexTests.cpp b/clang-tools-extra/clangd/unittests/FileIndexTests.cpp
index bd8a089df238..b4412131f837 100644
--- a/clang-tools-extra/clangd/unittests/FileIndexTests.cpp
+++ b/clang-tools-extra/clangd/unittests/FileIndexTests.cpp
@@ -272,7 +272,7 @@ TEST(FileIndexTest, RebuildWithPreamble) {
   PI.CompileCommand.Filename = FooCpp;
   PI.CompileCommand.CommandLine = {"clang", "-xc++", FooCpp};
 
-  MockFSProvider FSProvider;
+  MockFS FSProvider;
   FSProvider.Files[FooCpp] = "";
   FSProvider.Files[FooH] = R"cpp(
     namespace ns_in_header {

diff  --git a/clang-tools-extra/clangd/unittests/FindSymbolsTests.cpp b/clang-tools-extra/clangd/unittests/FindSymbolsTests.cpp
index 3b3d0f61436e..39ee2866b84f 100644
--- a/clang-tools-extra/clangd/unittests/FindSymbolsTests.cpp
+++ b/clang-tools-extra/clangd/unittests/FindSymbolsTests.cpp
@@ -58,7 +58,7 @@ class WorkspaceSymbolsTest : public ::testing::Test {
   }
 
 protected:
-  MockFSProvider FSProvider;
+  MockFS FSProvider;
   MockCompilationDatabase CDB;
   ClangdServer Server;
   int Limit = 0;
@@ -310,7 +310,7 @@ class DocumentSymbolsTest : public ::testing::Test {
   DocumentSymbolsTest() : Server(CDB, FSProvider, optsForTests()) {}
 
 protected:
-  MockFSProvider FSProvider;
+  MockFS FSProvider;
   MockCompilationDatabase CDB;
   ClangdServer Server;
 

diff  --git a/clang-tools-extra/clangd/unittests/HeaderSourceSwitchTests.cpp b/clang-tools-extra/clangd/unittests/HeaderSourceSwitchTests.cpp
index 63f18e4f9214..fbfb080062c1 100644
--- a/clang-tools-extra/clangd/unittests/HeaderSourceSwitchTests.cpp
+++ b/clang-tools-extra/clangd/unittests/HeaderSourceSwitchTests.cpp
@@ -12,6 +12,7 @@
 #include "TestFS.h"
 #include "TestTU.h"
 #include "index/MemIndex.h"
+#include "llvm/ADT/None.h"
 #include "gmock/gmock.h"
 #include "gtest/gtest.h"
 
@@ -20,7 +21,7 @@ namespace clangd {
 namespace {
 
 TEST(HeaderSourceSwitchTest, FileHeuristic) {
-  MockFSProvider FS;
+  MockFS FS;
   auto FooCpp = testPath("foo.cpp");
   auto FooH = testPath("foo.h");
   auto Invalid = testPath("main.cpp");
@@ -29,11 +30,11 @@ TEST(HeaderSourceSwitchTest, FileHeuristic) {
   FS.Files[FooH];
   FS.Files[Invalid];
   Optional<Path> PathResult =
-      getCorrespondingHeaderOrSource(FooCpp, FS.getFileSystem());
+      getCorrespondingHeaderOrSource(FooCpp, FS.view(llvm::None));
   EXPECT_TRUE(PathResult.hasValue());
   ASSERT_EQ(PathResult.getValue(), FooH);
 
-  PathResult = getCorrespondingHeaderOrSource(FooH, FS.getFileSystem());
+  PathResult = getCorrespondingHeaderOrSource(FooH, FS.view(llvm::None));
   EXPECT_TRUE(PathResult.hasValue());
   ASSERT_EQ(PathResult.getValue(), FooCpp);
 
@@ -44,7 +45,7 @@ TEST(HeaderSourceSwitchTest, FileHeuristic) {
 
   FS.Files[FooC];
   FS.Files[FooHH];
-  PathResult = getCorrespondingHeaderOrSource(FooC, FS.getFileSystem());
+  PathResult = getCorrespondingHeaderOrSource(FooC, FS.view(llvm::None));
   EXPECT_TRUE(PathResult.hasValue());
   ASSERT_EQ(PathResult.getValue(), FooHH);
 
@@ -53,7 +54,7 @@ TEST(HeaderSourceSwitchTest, FileHeuristic) {
   auto Foo2HH = testPath("foo2.HH");
   FS.Files[Foo2C];
   FS.Files[Foo2HH];
-  PathResult = getCorrespondingHeaderOrSource(Foo2C, FS.getFileSystem());
+  PathResult = getCorrespondingHeaderOrSource(Foo2C, FS.view(llvm::None));
   EXPECT_TRUE(PathResult.hasValue());
   ASSERT_EQ(PathResult.getValue(), Foo2HH);
 
@@ -63,13 +64,13 @@ TEST(HeaderSourceSwitchTest, FileHeuristic) {
 
   FS.Files[Foo3C];
   FS.Files[Foo3HXX];
-  PathResult = getCorrespondingHeaderOrSource(Foo3C, FS.getFileSystem());
+  PathResult = getCorrespondingHeaderOrSource(Foo3C, FS.view(llvm::None));
   EXPECT_TRUE(PathResult.hasValue());
   ASSERT_EQ(PathResult.getValue(), Foo3HXX);
 
   // Test if asking for a corresponding file that doesn't exist returns an empty
   // string.
-  PathResult = getCorrespondingHeaderOrSource(Invalid, FS.getFileSystem());
+  PathResult = getCorrespondingHeaderOrSource(Invalid, FS.view(llvm::None));
   EXPECT_FALSE(PathResult.hasValue());
 }
 
@@ -252,7 +253,7 @@ TEST(HeaderSourceSwitchTest, ClangdServerIntegration) {
   MockCompilationDatabase CDB;
   CDB.ExtraClangFlags = {"-I" +
                          testPath("src/include")}; // add search directory.
-  MockFSProvider FS;
+  MockFS FS;
   // File heuristic fails here, we rely on the index to find the .h file.
   std::string CppPath = testPath("src/lib/test.cpp");
   std::string HeaderPath = testPath("src/include/test.h");

diff  --git a/clang-tools-extra/clangd/unittests/HeadersTests.cpp b/clang-tools-extra/clangd/unittests/HeadersTests.cpp
index f243bfca6cd5..7fbf71e23707 100644
--- a/clang-tools-extra/clangd/unittests/HeadersTests.cpp
+++ b/clang-tools-extra/clangd/unittests/HeadersTests.cpp
@@ -53,7 +53,7 @@ class HeadersTest : public ::testing::Test {
     EXPECT_TRUE(static_cast<bool>(CI));
     // The diagnostic options must be set before creating a CompilerInstance.
     CI->getDiagnosticOpts().IgnoreWarnings = true;
-    auto VFS = PI.FSProvider->getFileSystem(Cmd->Directory);
+    auto VFS = PI.FSProvider->view(Cmd->Directory);
     auto Clang = prepareCompilerInstance(
         std::move(CI), /*Preamble=*/nullptr,
         llvm::MemoryBuffer::getMemBuffer(FS.Files[MainFile], MainFile),
@@ -120,7 +120,7 @@ class HeadersTest : public ::testing::Test {
     return Edit;
   }
 
-  MockFSProvider FS;
+  MockFS FS;
   MockCompilationDatabase CDB;
   std::string MainFile = testPath("main.cpp");
   std::string Subdir = testPath("sub");

diff  --git a/clang-tools-extra/clangd/unittests/ParsedASTTests.cpp b/clang-tools-extra/clangd/unittests/ParsedASTTests.cpp
index 05396739addd..72dc9a7720a1 100644
--- a/clang-tools-extra/clangd/unittests/ParsedASTTests.cpp
+++ b/clang-tools-extra/clangd/unittests/ParsedASTTests.cpp
@@ -249,7 +249,7 @@ TEST(ParsedASTTest, NoCrashOnTokensWithTidyCheck) {
 }
 
 TEST(ParsedASTTest, CanBuildInvocationWithUnknownArgs) {
-  MockFSProvider FSProvider;
+  MockFS FSProvider;
   FSProvider.Files = {{testPath("foo.cpp"), "void test() {}"}};
   // Unknown flags should not prevent a build of compiler invocation.
   ParseInputs Inputs;
@@ -451,7 +451,7 @@ TEST(ParsedASTTest, ReplayPreambleForTidyCheckers) {
   llvm::StringLiteral Baseline = R"cpp(
     #include "a.h"
     #include "c.h")cpp";
-  MockFSProvider FS;
+  MockFS FS;
   TU.Code = Baseline.str();
   auto Inputs = TU.inputs(FS);
   auto BaselinePreamble = TU.preamble();
@@ -539,7 +539,7 @@ TEST(ParsedASTTest, PatchesAdditionalIncludes) {
   // Build preamble with no includes.
   TU.Code = "";
   StoreDiags Diags;
-  MockFSProvider FS;
+  MockFS FS;
   auto Inputs = TU.inputs(FS);
   auto CI = buildCompilerInvocation(Inputs, Diags);
   auto EmptyPreamble =
@@ -582,7 +582,7 @@ TEST(ParsedASTTest, PatchesDeletedIncludes) {
   // Build preamble with no includes.
   TU.Code = R"cpp(#include <foo.h>)cpp";
   StoreDiags Diags;
-  MockFSProvider FS;
+  MockFS FS;
   auto Inputs = TU.inputs(FS);
   auto CI = buildCompilerInvocation(Inputs, Diags);
   auto BaselinePreamble =

diff  --git a/clang-tools-extra/clangd/unittests/PreambleTests.cpp b/clang-tools-extra/clangd/unittests/PreambleTests.cpp
index ee63953da173..e93ec31f9c6b 100644
--- a/clang-tools-extra/clangd/unittests/PreambleTests.cpp
+++ b/clang-tools-extra/clangd/unittests/PreambleTests.cpp
@@ -50,7 +50,7 @@ IncludeStructure
 collectPatchedIncludes(llvm::StringRef ModifiedContents,
                        llvm::StringRef BaselineContents,
                        llvm::StringRef MainFileName = "main.cpp") {
-  MockFSProvider FS;
+  MockFS FS;
   auto TU = TestTU::withCode(BaselineContents);
   TU.Filename = MainFileName.str();
   // ms-compatibility changes meaning of #import, make sure it is turned off.
@@ -74,7 +74,7 @@ collectPatchedIncludes(llvm::StringRef ModifiedContents,
       std::move(CI), &BaselinePreamble->Preamble,
       llvm::MemoryBuffer::getMemBufferCopy(
           ModifiedContents.slice(0, Bounds.Size).str()),
-      PI.FSProvider->getFileSystem(PI.CompileCommand.Directory), Diags);
+      PI.FSProvider->view(PI.CompileCommand.Directory), Diags);
   PreprocessOnlyAction Action;
   if (!Action.BeginSourceFile(*Clang, Clang->getFrontendOpts().Inputs[0])) {
     ADD_FAILURE() << "failed begin source file";
@@ -165,7 +165,7 @@ TEST(PreamblePatchTest, MainFileIsEscaped) {
 }
 
 TEST(PreamblePatchTest, PatchesPreambleIncludes) {
-  MockFSProvider FS;
+  MockFS FS;
   IgnoreDiagnostics Diags;
   auto TU = TestTU::withCode(R"cpp(
     #include "a.h"
@@ -201,7 +201,7 @@ llvm::Optional<ParsedAST> createPatchedAST(llvm::StringRef Baseline,
   }
 
   IgnoreDiagnostics Diags;
-  MockFSProvider FS;
+  MockFS FS;
   auto TU = TestTU::withCode(Modified);
   auto CI = buildCompilerInvocation(TU.inputs(FS), Diags);
   if (!CI) {
@@ -219,7 +219,7 @@ std::string getPreamblePatch(llvm::StringRef Baseline,
     ADD_FAILURE() << "Failed to build baseline preamble";
     return "";
   }
-  MockFSProvider FS;
+  MockFS FS;
   auto TU = TestTU::withCode(Modified);
   return PreamblePatch::create(testPath("main.cpp"), TU.inputs(FS),
                                *BaselinePreamble)
@@ -518,7 +518,7 @@ TEST(PreamblePatch, ModifiedBounds) {
 
     Annotations Modified(Case.Modified);
     TU.Code = Modified.code().str();
-    MockFSProvider FSProvider;
+    MockFS FSProvider;
     auto PP = PreamblePatch::create(testPath(TU.Filename),
                                     TU.inputs(FSProvider), *BaselinePreamble);
 

diff  --git a/clang-tools-extra/clangd/unittests/RenameTests.cpp b/clang-tools-extra/clangd/unittests/RenameTests.cpp
index 2d2835a12ff7..56d562d3b15c 100644
--- a/clang-tools-extra/clangd/unittests/RenameTests.cpp
+++ b/clang-tools-extra/clangd/unittests/RenameTests.cpp
@@ -1027,7 +1027,7 @@ TEST(CrossFileRenameTests, WithUpToDateIndex) {
     std::string FooHPath = testPath("foo.h");
     std::string FooCCPath = testPath("foo.cc");
 
-    MockFSProvider FS;
+    MockFS FS;
     FS.Files[FooHPath] = std::string(FooH.code());
     FS.Files[FooCCPath] = std::string(FooCC.code());
 

diff  --git a/clang-tools-extra/clangd/unittests/SemanticHighlightingTests.cpp b/clang-tools-extra/clangd/unittests/SemanticHighlightingTests.cpp
index 98080e98ca17..453986552ac5 100644
--- a/clang-tools-extra/clangd/unittests/SemanticHighlightingTests.cpp
+++ b/clang-tools-extra/clangd/unittests/SemanticHighlightingTests.cpp
@@ -728,7 +728,7 @@ TEST(SemanticHighlighting, GeneratesHighlightsWhenFileChange) {
   };
 
   auto FooCpp = testPath("foo.cpp");
-  MockFSProvider FS;
+  MockFS FS;
   FS.Files[FooCpp] = "";
 
   MockCompilationDatabase MCD;

diff  --git a/clang-tools-extra/clangd/unittests/SemanticSelectionTests.cpp b/clang-tools-extra/clangd/unittests/SemanticSelectionTests.cpp
index 0b0b7550cc52..cd1d79834167 100644
--- a/clang-tools-extra/clangd/unittests/SemanticSelectionTests.cpp
+++ b/clang-tools-extra/clangd/unittests/SemanticSelectionTests.cpp
@@ -149,7 +149,7 @@ TEST(SemanticSelection, All) {
 }
 
 TEST(SemanticSelection, RunViaClangdServer) {
-  MockFSProvider FS;
+  MockFS FS;
   MockCompilationDatabase CDB;
   ClangdServer Server(CDB, FS, ClangdServer::optsForTest());
 

diff  --git a/clang-tools-extra/clangd/unittests/TUSchedulerTests.cpp b/clang-tools-extra/clangd/unittests/TUSchedulerTests.cpp
index c04e186ca6b4..7e397af51de0 100644
--- a/clang-tools-extra/clangd/unittests/TUSchedulerTests.cpp
+++ b/clang-tools-extra/clangd/unittests/TUSchedulerTests.cpp
@@ -16,10 +16,10 @@
 #include "TestFS.h"
 #include "support/Cancellation.h"
 #include "support/Context.h"
-#include "support/FSProvider.h"
 #include "support/Path.h"
 #include "support/TestTracer.h"
 #include "support/Threading.h"
+#include "support/ThreadsafeFS.h"
 #include "clang/Basic/DiagnosticDriver.h"
 #include "llvm/ADT/ArrayRef.h"
 #include "llvm/ADT/FunctionExtras.h"
@@ -150,7 +150,7 @@ class TUSchedulerTests : public ::testing::Test {
                            std::move(CB));
   }
 
-  MockFSProvider FSProvider;
+  MockFS FSProvider;
   MockCompilationDatabase CDB;
 };
 
@@ -775,12 +775,11 @@ TEST_F(TUSchedulerTests, MissingHeader) {
   FSProvider.Timestamps[HeaderB] = time_t(1);
 
   // The addition of the missing header file triggers a rebuild, no errors.
-  updateWithDiags(
-      S, Source, Inputs, WantDiagnostics::Yes,
-      [&DiagCount](std::vector<Diag> Diags) {
-        ++DiagCount;
-        EXPECT_THAT(Diags, IsEmpty());
-      });
+  updateWithDiags(S, Source, Inputs, WantDiagnostics::Yes,
+                  [&DiagCount](std::vector<Diag> Diags) {
+                    ++DiagCount;
+                    EXPECT_THAT(Diags, IsEmpty());
+                  });
 
   // Ensure previous assertions are done before we touch the FS again.
   ASSERT_TRUE(S.blockUntilIdle(timeoutSeconds(10)));
@@ -798,12 +797,12 @@ TEST_F(TUSchedulerTests, MissingHeader) {
 
   // Forcing the reload should should cause a rebuild.
   Inputs.ForceRebuild = true;
-  updateWithDiags(S, Source, Inputs, WantDiagnostics::Yes,
-                  [&DiagCount](std::vector<Diag> Diags) {
-                    ++DiagCount;
-                    ElementsAre(Field(&Diag::Message,
-                                      "use of undeclared identifier 'b'"));
-                  });
+  updateWithDiags(
+      S, Source, Inputs, WantDiagnostics::Yes,
+      [&DiagCount](std::vector<Diag> Diags) {
+        ++DiagCount;
+        ElementsAre(Field(&Diag::Message, "use of undeclared identifier 'b'"));
+      });
 
   ASSERT_TRUE(S.blockUntilIdle(timeoutSeconds(10)));
   EXPECT_EQ(DiagCount, 3U);
@@ -901,7 +900,7 @@ TEST_F(TUSchedulerTests, TUStatus) {
     std::vector<ASTAction::Kind> ASTActions;
     std::vector<PreambleAction> PreambleActions;
   } CaptureTUStatus;
-  MockFSProvider FS;
+  MockFS FS;
   MockCompilationDatabase CDB;
   ClangdServer Server(CDB, FS, ClangdServer::optsForTest(), &CaptureTUStatus);
   Annotations Code("int m^ain () {}");

diff  --git a/clang-tools-extra/clangd/unittests/TestFS.h b/clang-tools-extra/clangd/unittests/TestFS.h
index 5b541d2f22fb..a487a361bfe1 100644
--- a/clang-tools-extra/clangd/unittests/TestFS.h
+++ b/clang-tools-extra/clangd/unittests/TestFS.h
@@ -13,8 +13,8 @@
 #define LLVM_CLANG_TOOLS_EXTRA_UNITTESTS_CLANGD_TESTFS_H
 #include "ClangdServer.h"
 #include "GlobalCompilationDatabase.h"
-#include "support/FSProvider.h"
 #include "support/Path.h"
+#include "support/ThreadsafeFS.h"
 #include "llvm/ADT/IntrusiveRefCntPtr.h"
 #include "llvm/ADT/None.h"
 #include "llvm/ADT/Optional.h"
@@ -31,18 +31,11 @@ buildTestFS(llvm::StringMap<std::string> const &Files,
             llvm::StringMap<time_t> const &Timestamps = {});
 
 // A VFS provider that returns TestFSes containing a provided set of files.
-class MockFSProvider : public FileSystemProvider {
+class MockFS : public ThreadsafeFS {
 public:
-  // Prevent name hiding caused by the overload below.
-  using FileSystemProvider::getFileSystem;
-
-  IntrusiveRefCntPtr<llvm::vfs::FileSystem> getFileSystem() const {
-    return buildTestFS(Files, Timestamps);
-  }
-
   IntrusiveRefCntPtr<llvm::vfs::FileSystem>
-  getFileSystem(llvm::NoneType) const override {
-    return getFileSystem();
+  view(llvm::NoneType) const override {
+    return buildTestFS(Files, Timestamps);
   }
 
   // If relative paths are used, they are resolved with testPath().

diff  --git a/clang-tools-extra/clangd/unittests/TestTU.cpp b/clang-tools-extra/clangd/unittests/TestTU.cpp
index 9c812298742e..6bebb355e50c 100644
--- a/clang-tools-extra/clangd/unittests/TestTU.cpp
+++ b/clang-tools-extra/clangd/unittests/TestTU.cpp
@@ -20,7 +20,7 @@
 namespace clang {
 namespace clangd {
 
-ParseInputs TestTU::inputs(MockFSProvider &FSProvider) const {
+ParseInputs TestTU::inputs(MockFS &FSProvider) const {
   std::string FullFilename = testPath(Filename),
               FullHeaderName = testPath(HeaderFilename),
               ImportThunk = testPath("import_thunk.h");
@@ -67,7 +67,7 @@ ParseInputs TestTU::inputs(MockFSProvider &FSProvider) const {
 }
 
 std::shared_ptr<const PreambleData> TestTU::preamble() const {
-  MockFSProvider FSProvider;
+  MockFS FSProvider;
   auto Inputs = inputs(FSProvider);
   IgnoreDiagnostics Diags;
   auto CI = buildCompilerInvocation(Inputs, Diags);
@@ -78,7 +78,7 @@ std::shared_ptr<const PreambleData> TestTU::preamble() const {
 }
 
 ParsedAST TestTU::build() const {
-  MockFSProvider FSProvider;
+  MockFS FSProvider;
   auto Inputs = inputs(FSProvider);
   StoreDiags Diags;
   auto CI = buildCompilerInvocation(Inputs, Diags);

diff  --git a/clang-tools-extra/clangd/unittests/TestTU.h b/clang-tools-extra/clangd/unittests/TestTU.h
index 05629a891bef..ebc05b38426e 100644
--- a/clang-tools-extra/clangd/unittests/TestTU.h
+++ b/clang-tools-extra/clangd/unittests/TestTU.h
@@ -70,7 +70,7 @@ struct TestTU {
   // Suppress this behavior by adding an 'error-ok' comment to the code.
   ParsedAST build() const;
   std::shared_ptr<const PreambleData> preamble() const;
-  ParseInputs inputs(MockFSProvider &FSProvider) const;
+  ParseInputs inputs(MockFS &FSProvider) const;
   SymbolSlab headerSymbols() const;
   RefSlab headerRefs() const;
   std::unique_ptr<SymbolIndex> index() const;

diff  --git a/clang-tools-extra/clangd/unittests/XRefsTests.cpp b/clang-tools-extra/clangd/unittests/XRefsTests.cpp
index e260285a179c..0428303f5b0a 100644
--- a/clang-tools-extra/clangd/unittests/XRefsTests.cpp
+++ b/clang-tools-extra/clangd/unittests/XRefsTests.cpp
@@ -974,7 +974,7 @@ int [[bar_not_preamble]];
   std::string BuildDir = testPath("build");
   MockCompilationDatabase CDB(BuildDir, RelPathPrefix);
 
-  MockFSProvider FS;
+  MockFS FS;
   ClangdServer Server(CDB, FS, ClangdServer::optsForTest());
 
   // Fill the filesystem.
@@ -1010,7 +1010,7 @@ int [[bar_not_preamble]];
 }
 
 TEST(GoToInclude, All) {
-  MockFSProvider FS;
+  MockFS FS;
   MockCompilationDatabase CDB;
   ClangdServer Server(CDB, FS, ClangdServer::optsForTest());
 
@@ -1084,7 +1084,7 @@ TEST(GoToInclude, All) {
 TEST(LocateSymbol, WithPreamble) {
   // Test stragety: AST should always use the latest preamble instead of last
   // good preamble.
-  MockFSProvider FS;
+  MockFS FS;
   MockCompilationDatabase CDB;
   ClangdServer Server(CDB, FS, ClangdServer::optsForTest());
 


        


More information about the cfe-commits mailing list