diff options
Diffstat (limited to 'contrib/llvm-project/clang/lib/Frontend/ASTUnit.cpp')
-rw-r--r-- | contrib/llvm-project/clang/lib/Frontend/ASTUnit.cpp | 103 |
1 files changed, 50 insertions, 53 deletions
diff --git a/contrib/llvm-project/clang/lib/Frontend/ASTUnit.cpp b/contrib/llvm-project/clang/lib/Frontend/ASTUnit.cpp index 57d025b7c32e..e7a87dc6b23c 100644 --- a/contrib/llvm-project/clang/lib/Frontend/ASTUnit.cpp +++ b/contrib/llvm-project/clang/lib/Frontend/ASTUnit.cpp @@ -69,6 +69,7 @@ #include "llvm/ADT/None.h" #include "llvm/ADT/Optional.h" #include "llvm/ADT/STLExtras.h" +#include "llvm/ADT/ScopeExit.h" #include "llvm/ADT/SmallString.h" #include "llvm/ADT/SmallVector.h" #include "llvm/ADT/StringMap.h" @@ -757,9 +758,8 @@ std::unique_ptr<ASTUnit> ASTUnit::LoadFromASTFile( const std::string &Filename, const PCHContainerReader &PCHContainerRdr, WhatToLoad ToLoad, IntrusiveRefCntPtr<DiagnosticsEngine> Diags, const FileSystemOptions &FileSystemOpts, bool UseDebugInfo, - bool OnlyLocalDecls, ArrayRef<RemappedFile> RemappedFiles, - CaptureDiagsKind CaptureDiagnostics, bool AllowPCHWithCompilerErrors, - bool UserFilesAreVolatile) { + bool OnlyLocalDecls, CaptureDiagsKind CaptureDiagnostics, + bool AllowASTWithCompilerErrors, bool UserFilesAreVolatile) { std::unique_ptr<ASTUnit> AST(new ASTUnit(true)); // Recover resources if we crash before exiting this method. @@ -792,9 +792,6 @@ std::unique_ptr<ASTUnit> ASTUnit::LoadFromASTFile( /*Target=*/nullptr)); AST->PPOpts = std::make_shared<PreprocessorOptions>(); - for (const auto &RemappedFile : RemappedFiles) - AST->PPOpts->addRemappedFile(RemappedFile.first, RemappedFile.second); - // Gather Info for preprocessor construction later on. HeaderSearch &HeaderInfo = *AST->HeaderInfo; @@ -812,13 +809,14 @@ std::unique_ptr<ASTUnit> ASTUnit::LoadFromASTFile( PP.getIdentifierTable(), PP.getSelectorTable(), PP.getBuiltinInfo()); - bool disableValid = false; + DisableValidationForModuleKind disableValid = + DisableValidationForModuleKind::None; if (::getenv("LIBCLANG_DISABLE_PCH_VALIDATION")) - disableValid = true; + disableValid = DisableValidationForModuleKind::All; AST->Reader = new ASTReader( PP, *AST->ModuleCache, AST->Ctx.get(), PCHContainerRdr, {}, /*isysroot=*/"", - /*DisableValidation=*/disableValid, AllowPCHWithCompilerErrors); + /*DisableValidation=*/disableValid, AllowASTWithCompilerErrors); AST->Reader->setListener(std::make_unique<ASTInfoCollector>( *AST->PP, AST->Ctx.get(), *AST->HSOpts, *AST->PPOpts, *AST->LangOpts, @@ -1118,6 +1116,19 @@ bool ASTUnit::Parse(std::shared_ptr<PCHContainerOperations> PCHContainerOps, std::unique_ptr<CompilerInstance> Clang( new CompilerInstance(std::move(PCHContainerOps))); + // Clean up on error, disengage it if the function returns successfully. + auto CleanOnError = llvm::make_scope_exit([&]() { + // Remove the overridden buffer we used for the preamble. + SavedMainFileBuffer = nullptr; + + // Keep the ownership of the data in the ASTUnit because the client may + // want to see the diagnostics. + transferASTDataFromCompilerInstance(*Clang); + FailedParseDiagnostics.swap(StoredDiagnostics); + StoredDiagnostics.clear(); + NumStoredDiagnosticsFromDriver = 0; + }); + // Ensure that Clang has a FileManager with the right VFS, which may have // changed above in AddImplicitPreamble. If VFS is nullptr, rely on // createFileManager to create one. @@ -1172,9 +1183,6 @@ bool ASTUnit::Parse(std::shared_ptr<PCHContainerOperations> PCHContainerOps, TopLevelDeclsInPreamble.clear(); } - // Create a file manager object to provide access to and cache the filesystem. - Clang->setFileManager(&getFileManager()); - // Create the source manager. Clang->setSourceManager(&getSourceManager()); @@ -1200,7 +1208,7 @@ bool ASTUnit::Parse(std::shared_ptr<PCHContainerOperations> PCHContainerOps, ActCleanup(Act.get()); if (!Act->BeginSourceFile(*Clang.get(), Clang->getFrontendOpts().Inputs[0])) - goto error; + return true; if (SavedMainFileBuffer) TranslateStoredDiagnostics(getFileManager(), getSourceManager(), @@ -1210,7 +1218,7 @@ bool ASTUnit::Parse(std::shared_ptr<PCHContainerOperations> PCHContainerOps, if (llvm::Error Err = Act->Execute()) { consumeError(std::move(Err)); // FIXME this drops errors on the floor. - goto error; + return true; } transferASTDataFromCompilerInstance(*Clang); @@ -1219,19 +1227,9 @@ bool ASTUnit::Parse(std::shared_ptr<PCHContainerOperations> PCHContainerOps, FailedParseDiagnostics.clear(); - return false; - -error: - // Remove the overridden buffer we used for the preamble. - SavedMainFileBuffer = nullptr; + CleanOnError.release(); - // Keep the ownership of the data in the ASTUnit because the client may - // want to see the diagnostics. - transferASTDataFromCompilerInstance(*Clang); - FailedParseDiagnostics.swap(StoredDiagnostics); - StoredDiagnostics.clear(); - NumStoredDiagnosticsFromDriver = 0; - return true; + return false; } static std::pair<unsigned, unsigned> @@ -1313,15 +1311,14 @@ ASTUnit::getMainBufferWithPrecompiledPreamble( if (!MainFileBuffer) return nullptr; - PreambleBounds Bounds = - ComputePreambleBounds(*PreambleInvocationIn.getLangOpts(), - MainFileBuffer.get(), MaxLines); + PreambleBounds Bounds = ComputePreambleBounds( + *PreambleInvocationIn.getLangOpts(), *MainFileBuffer, MaxLines); if (!Bounds.Size) return nullptr; if (Preamble) { - if (Preamble->CanReuse(PreambleInvocationIn, MainFileBuffer.get(), Bounds, - VFS.get())) { + if (Preamble->CanReuse(PreambleInvocationIn, *MainFileBuffer, Bounds, + *VFS)) { // Okay! We can re-use the precompiled preamble. // Set the state of the diagnostic object to mimic its state @@ -1468,7 +1465,7 @@ StringRef ASTUnit::getMainFileName() const { if (Input.isFile()) return Input.getFile(); else - return Input.getBuffer()->getBufferIdentifier(); + return Input.getBuffer().getBufferIdentifier(); } if (SourceMgr) { @@ -1517,8 +1514,7 @@ ASTUnit *ASTUnit::LoadFromCompilerInvocationAction( ASTUnit *Unit, bool Persistent, StringRef ResourceFilesPath, bool OnlyLocalDecls, CaptureDiagsKind CaptureDiagnostics, unsigned PrecompilePreambleAfterNParses, bool CacheCodeCompletionResults, - bool IncludeBriefCommentsInCodeCompletion, bool UserFilesAreVolatile, - std::unique_ptr<ASTUnit> *ErrAST) { + bool UserFilesAreVolatile, std::unique_ptr<ASTUnit> *ErrAST) { assert(CI && "A CompilerInvocation is required"); std::unique_ptr<ASTUnit> OwnAST; @@ -1541,8 +1537,7 @@ ASTUnit *ASTUnit::LoadFromCompilerInvocationAction( AST->PreambleRebuildCountdown = PrecompilePreambleAfterNParses; AST->TUKind = Action ? Action->getTranslationUnitKind() : TU_Complete; AST->ShouldCacheCodeCompletionResults = CacheCodeCompletionResults; - AST->IncludeBriefCommentsInCodeCompletion - = IncludeBriefCommentsInCodeCompletion; + AST->IncludeBriefCommentsInCodeCompletion = false; // Recover resources if we crash before exiting this method. llvm::CrashRecoveryContextCleanupRegistrar<ASTUnit> @@ -2239,28 +2234,30 @@ void ASTUnit::CodeComplete( = new AugmentedCodeCompleteConsumer(*this, Consumer, CodeCompleteOpts); Clang->setCodeCompletionConsumer(AugmentedConsumer); + auto getUniqueID = + [&FileMgr](StringRef Filename) -> Optional<llvm::sys::fs::UniqueID> { + if (auto Status = FileMgr.getVirtualFileSystem().status(Filename)) + return Status->getUniqueID(); + return None; + }; + + auto hasSameUniqueID = [getUniqueID](StringRef LHS, StringRef RHS) { + if (LHS == RHS) + return true; + if (auto LHSID = getUniqueID(LHS)) + if (auto RHSID = getUniqueID(RHS)) + return *LHSID == *RHSID; + return false; + }; + // If we have a precompiled preamble, try to use it. We only allow // the use of the precompiled preamble if we're if the completion // point is within the main file, after the end of the precompiled // preamble. std::unique_ptr<llvm::MemoryBuffer> OverrideMainBuffer; - if (Preamble) { - std::string CompleteFilePath(File); - - auto &VFS = FileMgr.getVirtualFileSystem(); - auto CompleteFileStatus = VFS.status(CompleteFilePath); - if (CompleteFileStatus) { - llvm::sys::fs::UniqueID CompleteFileID = CompleteFileStatus->getUniqueID(); - - std::string MainPath(OriginalSourceFile); - auto MainStatus = VFS.status(MainPath); - if (MainStatus) { - llvm::sys::fs::UniqueID MainID = MainStatus->getUniqueID(); - if (CompleteFileID == MainID && Line > 1) - OverrideMainBuffer = getMainBufferWithPrecompiledPreamble( - PCHContainerOps, Inv, &VFS, false, Line - 1); - } - } + if (Preamble && Line > 1 && hasSameUniqueID(File, OriginalSourceFile)) { + OverrideMainBuffer = getMainBufferWithPrecompiledPreamble( + PCHContainerOps, Inv, &FileMgr.getVirtualFileSystem(), false, Line - 1); } // If the main file has been overridden due to the use of a preamble, |