Skip to content

Commit f6326cf

Browse files
committed
[support] Use VFS in SourceMgr for loading includes
Most `SourceMgr` clients don't make use of include files, but those that do might want to specify the file system to use. This patch enables that by making it possible to pass a `vfs::FileSystem` instance into `SourceMgr`.
1 parent f642236 commit f6326cf

File tree

4 files changed

+46
-6
lines changed

4 files changed

+46
-6
lines changed

llvm/include/llvm/Support/SourceMgr.h

Lines changed: 19 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@
1515
#ifndef LLVM_SUPPORT_SOURCEMGR_H
1616
#define LLVM_SUPPORT_SOURCEMGR_H
1717

18+
#include "llvm/ADT/IntrusiveRefCntPtr.h"
1819
#include "llvm/ADT/SmallVector.h"
1920
#include "llvm/Support/Compiler.h"
2021
#include "llvm/Support/MemoryBuffer.h"
@@ -23,6 +24,10 @@
2324

2425
namespace llvm {
2526

27+
namespace vfs {
28+
class FileSystem;
29+
} // end namespace vfs
30+
2631
class raw_ostream;
2732
class SMDiagnostic;
2833
class SMFixIt;
@@ -91,15 +96,25 @@ class SourceMgr {
9196
DiagHandlerTy DiagHandler = nullptr;
9297
void *DiagContext = nullptr;
9398

99+
// Optional file system for finding include files.
100+
IntrusiveRefCntPtr<vfs::FileSystem> FS;
101+
94102
bool isValidBufferID(unsigned i) const { return i && i <= Buffers.size(); }
95103

96104
public:
97-
SourceMgr() = default;
105+
/// Create new source manager without support for include files.
106+
SourceMgr();
107+
/// Create new source manager with the capability of finding include files
108+
/// via the provided file system.
109+
explicit SourceMgr(IntrusiveRefCntPtr<vfs::FileSystem> FS);
98110
SourceMgr(const SourceMgr &) = delete;
99111
SourceMgr &operator=(const SourceMgr &) = delete;
100-
SourceMgr(SourceMgr &&) = default;
101-
SourceMgr &operator=(SourceMgr &&) = default;
102-
~SourceMgr() = default;
112+
SourceMgr(SourceMgr &&);
113+
SourceMgr &operator=(SourceMgr &&);
114+
~SourceMgr();
115+
116+
IntrusiveRefCntPtr<vfs::FileSystem> getVirtualFileSystem() const;
117+
void setVirtualFileSystem(IntrusiveRefCntPtr<vfs::FileSystem> FS);
103118

104119
/// Return the include directories of this source manager.
105120
ArrayRef<std::string> getIncludeDirs() const { return IncludeDirectories; }

llvm/lib/Support/SourceMgr.cpp

Lines changed: 22 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@
2424
#include "llvm/Support/MemoryBuffer.h"
2525
#include "llvm/Support/Path.h"
2626
#include "llvm/Support/SMLoc.h"
27+
#include "llvm/Support/VirtualFileSystem.h"
2728
#include "llvm/Support/WithColor.h"
2829
#include "llvm/Support/raw_ostream.h"
2930
#include <algorithm>
@@ -38,6 +39,22 @@ using namespace llvm;
3839

3940
static const size_t TabStop = 8;
4041

42+
// Out of line to avoid needing definition of vfs::FileSystem in header.
43+
SourceMgr::SourceMgr() = default;
44+
SourceMgr::SourceMgr(IntrusiveRefCntPtr<vfs::FileSystem> FS)
45+
: FS(std::move(FS)) {}
46+
SourceMgr::SourceMgr(SourceMgr &&) = default;
47+
SourceMgr &SourceMgr::operator=(SourceMgr &&) = default;
48+
SourceMgr::~SourceMgr() = default;
49+
50+
IntrusiveRefCntPtr<vfs::FileSystem> SourceMgr::getVirtualFileSystem() const {
51+
return FS;
52+
}
53+
54+
void SourceMgr::setVirtualFileSystem(IntrusiveRefCntPtr<vfs::FileSystem> FS) {
55+
this->FS = std::move(FS);
56+
}
57+
4158
unsigned SourceMgr::AddIncludeFile(const std::string &Filename,
4259
SMLoc IncludeLoc,
4360
std::string &IncludedFile) {
@@ -52,16 +69,19 @@ unsigned SourceMgr::AddIncludeFile(const std::string &Filename,
5269
ErrorOr<std::unique_ptr<MemoryBuffer>>
5370
SourceMgr::OpenIncludeFile(const std::string &Filename,
5471
std::string &IncludedFile) {
72+
if (!FS)
73+
reportFatalInternalError("Opening include file from SourceMgr without VFS");
74+
5575
ErrorOr<std::unique_ptr<MemoryBuffer>> NewBufOrErr =
56-
MemoryBuffer::getFile(Filename);
76+
FS->getBufferForFile(Filename);
5777

5878
SmallString<64> Buffer(Filename);
5979
// If the file didn't exist directly, see if it's in an include path.
6080
for (unsigned i = 0, e = IncludeDirectories.size(); i != e && !NewBufOrErr;
6181
++i) {
6282
Buffer = IncludeDirectories[i];
6383
sys::path::append(Buffer, Filename);
64-
NewBufOrErr = MemoryBuffer::getFile(Buffer);
84+
NewBufOrErr = FS->getBufferForFile(Buffer);
6585
}
6686

6787
if (NewBufOrErr)

llvm/lib/TableGen/Main.cpp

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@
2626
#include "llvm/Support/SMLoc.h"
2727
#include "llvm/Support/SourceMgr.h"
2828
#include "llvm/Support/ToolOutputFile.h"
29+
#include "llvm/Support/VirtualFileSystem.h"
2930
#include "llvm/Support/raw_ostream.h"
3031
#include "llvm/TableGen/Error.h"
3132
#include "llvm/TableGen/Record.h"
@@ -129,6 +130,8 @@ int llvm::TableGenMain(const char *argv0,
129130
// it later.
130131
SrcMgr.setIncludeDirs(IncludeDirs);
131132

133+
SrcMgr.setVirtualFileSystem(vfs::getRealFileSystem());
134+
132135
TGParser Parser(SrcMgr, MacroNames, Records, NoWarnOnUnusedTemplateArgs);
133136

134137
if (Parser.ParseFile())

llvm/lib/TableGen/Parser.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99
#include "llvm/TableGen/Parser.h"
1010
#include "TGParser.h"
1111
#include "llvm/Support/MemoryBuffer.h"
12+
#include "llvm/Support/VirtualFileSystem.h"
1213
#include "llvm/TableGen/Record.h"
1314

1415
using namespace llvm;
@@ -20,6 +21,7 @@ bool llvm::TableGenParseFile(SourceMgr &InputSrcMgr, RecordKeeper &Records) {
2021
// this reliance, we could drop all of this.
2122
SrcMgr = SourceMgr();
2223
SrcMgr.takeSourceBuffersFrom(InputSrcMgr);
24+
SrcMgr.setVirtualFileSystem(InputSrcMgr.getVirtualFileSystem());
2325
SrcMgr.setIncludeDirs(InputSrcMgr.getIncludeDirs());
2426
SrcMgr.setDiagHandler(InputSrcMgr.getDiagHandler(),
2527
InputSrcMgr.getDiagContext());

0 commit comments

Comments
 (0)