diff options
Diffstat (limited to 'lib')
-rw-r--r-- | lib/Basic/FileManager.cpp | 16 | ||||
-rw-r--r-- | lib/Basic/SourceManager.cpp | 14 | ||||
-rw-r--r-- | lib/Frontend/ASTUnit.cpp | 28 | ||||
-rw-r--r-- | lib/Serialization/ASTReader.cpp | 8 |
4 files changed, 47 insertions, 19 deletions
diff --git a/lib/Basic/FileManager.cpp b/lib/Basic/FileManager.cpp index ddf8934b62..b921f3e0d9 100644 --- a/lib/Basic/FileManager.cpp +++ b/lib/Basic/FileManager.cpp @@ -488,15 +488,21 @@ void FileManager::FixupRelativePath(SmallVectorImpl<char> &path) const { } llvm::MemoryBuffer *FileManager:: -getBufferForFile(const FileEntry *Entry, std::string *ErrorStr) { +getBufferForFile(const FileEntry *Entry, std::string *ErrorStr, + bool isVolatile) { OwningPtr<llvm::MemoryBuffer> Result; llvm::error_code ec; + uint64_t FileSize = Entry->getSize(); + // If there's a high enough chance that the file have changed since we + // got its size, force a stat before opening it. + if (isVolatile) + FileSize = -1; + const char *Filename = Entry->getName(); // If the file is already open, use the open file descriptor. if (Entry->FD != -1) { - ec = llvm::MemoryBuffer::getOpenFile(Entry->FD, Filename, Result, - Entry->getSize()); + ec = llvm::MemoryBuffer::getOpenFile(Entry->FD, Filename, Result, FileSize); if (ErrorStr) *ErrorStr = ec.message(); @@ -508,7 +514,7 @@ getBufferForFile(const FileEntry *Entry, std::string *ErrorStr) { // Otherwise, open the file. if (FileSystemOpts.WorkingDir.empty()) { - ec = llvm::MemoryBuffer::getFile(Filename, Result, Entry->getSize()); + ec = llvm::MemoryBuffer::getFile(Filename, Result, FileSize); if (ec && ErrorStr) *ErrorStr = ec.message(); return Result.take(); @@ -516,7 +522,7 @@ getBufferForFile(const FileEntry *Entry, std::string *ErrorStr) { SmallString<128> FilePath(Entry->getName()); FixupRelativePath(FilePath); - ec = llvm::MemoryBuffer::getFile(FilePath.str(), Result, Entry->getSize()); + ec = llvm::MemoryBuffer::getFile(FilePath.str(), Result, FileSize); if (ec && ErrorStr) *ErrorStr = ec.message(); return Result.take(); diff --git a/lib/Basic/SourceManager.cpp b/lib/Basic/SourceManager.cpp index 5dc100a07a..9ec2474299 100644 --- a/lib/Basic/SourceManager.cpp +++ b/lib/Basic/SourceManager.cpp @@ -97,7 +97,10 @@ const llvm::MemoryBuffer *ContentCache::getBuffer(DiagnosticsEngine &Diag, } std::string ErrorStr; - Buffer.setPointer(SM.getFileManager().getBufferForFile(ContentsEntry, &ErrorStr)); + bool isVolatile = SM.userFilesAreVolatile() && !IsSystemFile; + Buffer.setPointer(SM.getFileManager().getBufferForFile(ContentsEntry, + &ErrorStr, + isVolatile)); // If we were unable to open the file, then we are in an inconsistent // situation where the content cache referenced a file which no longer @@ -367,8 +370,10 @@ LineTableInfo &SourceManager::getLineTable() { // Private 'Create' methods. //===----------------------------------------------------------------------===// -SourceManager::SourceManager(DiagnosticsEngine &Diag, FileManager &FileMgr) +SourceManager::SourceManager(DiagnosticsEngine &Diag, FileManager &FileMgr, + bool UserFilesAreVolatile) : Diag(Diag), FileMgr(FileMgr), OverridenFilesKeepOriginalName(true), + UserFilesAreVolatile(UserFilesAreVolatile), ExternalSLocEntries(0), LineTable(0), NumLinearScans(0), NumBinaryProbes(0), FakeBufferForRecovery(0), FakeContentCacheForRecovery(0) { @@ -426,7 +431,8 @@ void SourceManager::clearIDTables() { /// getOrCreateContentCache - Create or return a cached ContentCache for the /// specified file. const ContentCache * -SourceManager::getOrCreateContentCache(const FileEntry *FileEnt) { +SourceManager::getOrCreateContentCache(const FileEntry *FileEnt, + bool isSystemFile) { assert(FileEnt && "Didn't specify a file entry to use?"); // Do we already have information about this file? @@ -455,6 +461,8 @@ SourceManager::getOrCreateContentCache(const FileEntry *FileEnt) { new (Entry) ContentCache(FileEnt); } + Entry->IsSystemFile = isSystemFile; + return Entry; } diff --git a/lib/Frontend/ASTUnit.cpp b/lib/Frontend/ASTUnit.cpp index 7be25e96b4..ea2f773c56 100644 --- a/lib/Frontend/ASTUnit.cpp +++ b/lib/Frontend/ASTUnit.cpp @@ -215,7 +215,7 @@ ASTUnit::ASTUnit(bool _MainFileIsAST) PreambleRebuildCounter(0), SavedMainFileBuffer(0), PreambleBuffer(0), NumWarningsInPreamble(0), ShouldCacheCodeCompletionResults(false), - IncludeBriefCommentsInCodeCompletion(false), + IncludeBriefCommentsInCodeCompletion(false), UserFilesAreVolatile(false), CompletionCacheTopLevelHashValue(0), PreambleTopLevelHashValue(0), CurrentTopLevelHashValue(0), @@ -658,7 +658,8 @@ ASTUnit *ASTUnit::LoadFromASTFile(const std::string &Filename, RemappedFile *RemappedFiles, unsigned NumRemappedFiles, bool CaptureDiagnostics, - bool AllowPCHWithCompilerErrors) { + bool AllowPCHWithCompilerErrors, + bool UserFilesAreVolatile) { OwningPtr<ASTUnit> AST(new ASTUnit(true)); // Recover resources if we crash before exiting this method. @@ -674,8 +675,10 @@ ASTUnit *ASTUnit::LoadFromASTFile(const std::string &Filename, AST->CaptureDiagnostics = CaptureDiagnostics; AST->Diagnostics = Diags; AST->FileMgr = new FileManager(FileSystemOpts); + AST->UserFilesAreVolatile = UserFilesAreVolatile; AST->SourceMgr = new SourceManager(AST->getDiagnostics(), - AST->getFileManager()); + AST->getFileManager(), + UserFilesAreVolatile); AST->HeaderInfo.reset(new HeaderSearch(AST->getFileManager(), AST->getDiagnostics(), AST->ASTFileLangOpts, @@ -1077,7 +1080,8 @@ bool ASTUnit::Parse(llvm::MemoryBuffer *OverrideMainBuffer) { LangOpts = &Clang->getLangOpts(); FileSystemOpts = Clang->getFileSystemOpts(); FileMgr = new FileManager(FileSystemOpts); - SourceMgr = new SourceManager(getDiagnostics(), *FileMgr); + SourceMgr = new SourceManager(getDiagnostics(), *FileMgr, + UserFilesAreVolatile); TheSema.reset(); Ctx = 0; PP = 0; @@ -1665,7 +1669,8 @@ StringRef ASTUnit::getMainFileName() const { ASTUnit *ASTUnit::create(CompilerInvocation *CI, IntrusiveRefCntPtr<DiagnosticsEngine> Diags, - bool CaptureDiagnostics) { + bool CaptureDiagnostics, + bool UserFilesAreVolatile) { OwningPtr<ASTUnit> AST; AST.reset(new ASTUnit(false)); ConfigureDiags(Diags, 0, 0, *AST, CaptureDiagnostics); @@ -1673,7 +1678,9 @@ ASTUnit *ASTUnit::create(CompilerInvocation *CI, AST->Invocation = CI; AST->FileSystemOpts = CI->getFileSystemOpts(); AST->FileMgr = new FileManager(AST->FileSystemOpts); - AST->SourceMgr = new SourceManager(AST->getDiagnostics(), *AST->FileMgr); + AST->UserFilesAreVolatile = UserFilesAreVolatile; + AST->SourceMgr = new SourceManager(AST->getDiagnostics(), *AST->FileMgr, + UserFilesAreVolatile); return AST.take(); } @@ -1689,6 +1696,7 @@ ASTUnit *ASTUnit::LoadFromCompilerInvocationAction(CompilerInvocation *CI, bool PrecompilePreamble, bool CacheCodeCompletionResults, bool IncludeBriefCommentsInCodeCompletion, + bool UserFilesAreVolatile, OwningPtr<ASTUnit> *ErrAST) { assert(CI && "A CompilerInvocation is required"); @@ -1696,7 +1704,7 @@ ASTUnit *ASTUnit::LoadFromCompilerInvocationAction(CompilerInvocation *CI, ASTUnit *AST = Unit; if (!AST) { // Create the AST unit. - OwnAST.reset(create(CI, Diags, CaptureDiagnostics)); + OwnAST.reset(create(CI, Diags, CaptureDiagnostics, UserFilesAreVolatile)); AST = OwnAST.get(); } @@ -1859,7 +1867,8 @@ ASTUnit *ASTUnit::LoadFromCompilerInvocation(CompilerInvocation *CI, bool PrecompilePreamble, TranslationUnitKind TUKind, bool CacheCodeCompletionResults, - bool IncludeBriefCommentsInCodeCompletion) { + bool IncludeBriefCommentsInCodeCompletion, + bool UserFilesAreVolatile) { // Create the AST unit. OwningPtr<ASTUnit> AST; AST.reset(new ASTUnit(false)); @@ -1872,6 +1881,7 @@ ASTUnit *ASTUnit::LoadFromCompilerInvocation(CompilerInvocation *CI, AST->IncludeBriefCommentsInCodeCompletion = IncludeBriefCommentsInCodeCompletion; AST->Invocation = CI; + AST->UserFilesAreVolatile = UserFilesAreVolatile; // Recover resources if we crash before exiting this method. llvm::CrashRecoveryContextCleanupRegistrar<ASTUnit> @@ -1898,6 +1908,7 @@ ASTUnit *ASTUnit::LoadFromCommandLine(const char **ArgBegin, bool IncludeBriefCommentsInCodeCompletion, bool AllowPCHWithCompilerErrors, bool SkipFunctionBodies, + bool UserFilesAreVolatile, OwningPtr<ASTUnit> *ErrAST) { if (!Diags.getPtr()) { // No diagnostics engine was provided, so create our own diagnostics object @@ -1957,6 +1968,7 @@ ASTUnit *ASTUnit::LoadFromCommandLine(const char **ArgBegin, AST->ShouldCacheCodeCompletionResults = CacheCodeCompletionResults; AST->IncludeBriefCommentsInCodeCompletion = IncludeBriefCommentsInCodeCompletion; + AST->UserFilesAreVolatile = UserFilesAreVolatile; AST->NumStoredDiagnosticsFromDriver = StoredDiagnostics.size(); AST->StoredDiagnostics.swap(StoredDiagnostics); AST->Invocation = CI; diff --git a/lib/Serialization/ASTReader.cpp b/lib/Serialization/ASTReader.cpp index 46bd55e83e..4073e32c2c 100644 --- a/lib/Serialization/ASTReader.cpp +++ b/lib/Serialization/ASTReader.cpp @@ -1127,8 +1127,9 @@ ASTReader::ASTReadResult ASTReader::ReadSLocEntryRecord(int ID) { // This is the module's main file. IncludeLoc = getImportLocation(F); } - FileID FID = SourceMgr.createFileID(File, IncludeLoc, - (SrcMgr::CharacteristicKind)Record[2], + SrcMgr::CharacteristicKind + FileCharacter = (SrcMgr::CharacteristicKind)Record[2]; + FileID FID = SourceMgr.createFileID(File, IncludeLoc, FileCharacter, ID, BaseOffset + Record[0]); SrcMgr::FileInfo &FileInfo = const_cast<SrcMgr::FileInfo&>(SourceMgr.getSLocEntry(FID).getFile()); @@ -1145,7 +1146,8 @@ ASTReader::ASTReadResult ASTReader::ReadSLocEntryRecord(int ID) { } const SrcMgr::ContentCache *ContentCache - = SourceMgr.getOrCreateContentCache(File); + = SourceMgr.getOrCreateContentCache(File, + /*isSystemFile=*/FileCharacter != SrcMgr::C_User); if (OverriddenBuffer && !ContentCache->BufferOverridden && ContentCache->ContentsEntry == ContentCache->OrigEntry) { unsigned Code = SLocEntryCursor.ReadCode(); |