gamesh411 created this revision.
gamesh411 added a reviewer: martong.
Herald added subscribers: cfe-commits, Szelethus, dkrupp, rnkovacs.
Herald added a project: clang.
Refactor loadExternalAST method of CrossTranslationUnitContext in order to
reduce maintenance burden and so that features are easier to add in the future.
Repository:
rG LLVM Github Monorepo
https://reviews.llvm.org/D64753
Files:
clang/include/clang/CrossTU/CrossTranslationUnit.h
clang/lib/CrossTU/CrossTranslationUnit.cpp
Index: clang/lib/CrossTU/CrossTranslationUnit.cpp
===================================================================
--- clang/lib/CrossTU/CrossTranslationUnit.cpp
+++ clang/lib/CrossTU/CrossTranslationUnit.cpp
@@ -237,8 +237,8 @@
if (LookupName.empty())
return llvm::make_error<IndexError>(
index_error_code::failed_to_generate_usr);
- llvm::Expected<ASTUnit *> ASTUnitOrError = loadExternalAST(
- LookupName, CrossTUDir, IndexName, DisplayCTUProgress);
+ llvm::Expected<ASTUnit *> ASTUnitOrError =
+ loadExternalAST(LookupName, CrossTUDir, IndexName, DisplayCTUProgress);
if (!ASTUnitOrError)
return ASTUnitOrError.takeError();
ASTUnit *Unit = *ASTUnitOrError;
@@ -340,6 +340,92 @@
}
}
+bool CrossTranslationUnitContext::checkThresholdReached() const {
+ if (NumASTLoaded >= CTULoadThreshold) {
+ ++NumASTLoadThresholdReached;
+ return true;
+ }
+ return false;
+}
+
+llvm::Error CrossTranslationUnitContext::lazyInitCTUIndex(StringRef CrossTUDir,
+ StringRef IndexName) {
+ // Dont initialize if the map is filled.
+ if (!NameFileMap.empty())
+ return llvm::Error::success();
+
+ // Get the absolute path to the index file.
+ SmallString<256> IndexFile = CrossTUDir;
+ if (llvm::sys::path::is_absolute(IndexName))
+ IndexFile = IndexName;
+ else
+ llvm::sys::path::append(IndexFile, IndexName);
+
+ if (auto IndexMapping = parseCrossTUIndex(IndexFile, CrossTUDir)) {
+ // Initialize member map.
+ NameFileMap = *IndexMapping;
+ return llvm::Error::success();
+ } else {
+ // Error while parsing CrossTU index file.
+ return IndexMapping.takeError();
+ };
+}
+
+ASTUnit *CrossTranslationUnitContext::getCachedASTUnitForName(
+ StringRef LookupName) const {
+ auto CacheEntry = NameASTUnitMap.find(LookupName);
+ if (CacheEntry != NameASTUnitMap.end())
+ return CacheEntry->second;
+ else
+ return nullptr;
+}
+
+std::unique_ptr<ASTUnit>
+CrossTranslationUnitContext::loadFromASTFile(StringRef ASTFileName) const {
+ // Load AST from ast-dump.
+ IntrusiveRefCntPtr<DiagnosticOptions> DiagOpts = new DiagnosticOptions();
+ TextDiagnosticPrinter *DiagClient =
+ new TextDiagnosticPrinter(llvm::errs(), &*DiagOpts);
+ IntrusiveRefCntPtr<DiagnosticIDs> DiagID(new DiagnosticIDs());
+ IntrusiveRefCntPtr<DiagnosticsEngine> Diags(
+ new DiagnosticsEngine(DiagID, &*DiagOpts, DiagClient));
+
+ return ASTUnit::LoadFromASTFile(
+ ASTFileName, CI.getPCHContainerOperations()->getRawReader(),
+ ASTUnit::LoadEverything, Diags, CI.getFileSystemOpts());
+}
+
+llvm::Expected<std::string>
+CrossTranslationUnitContext::getASTFileNameForLookup(
+ StringRef LookupName) const {
+ auto NameFileMapEntry = NameFileMap.find(LookupName);
+ if (NameFileMapEntry != NameFileMap.end()) {
+ return NameFileMapEntry->second;
+ } else {
+ ++NumNotInOtherTU;
+ return llvm::make_error<IndexError>(index_error_code::missing_definition);
+ }
+}
+
+ASTUnit *
+CrossTranslationUnitContext::loadFromASTFileCached(StringRef LookupName,
+ StringRef ASTFileName) {
+ ASTUnit *Unit = nullptr;
+
+ auto ASTCacheEntry = FileASTUnitMap.find(ASTFileName);
+ if (ASTCacheEntry == FileASTUnitMap.end()) {
+ // Load the ASTUnit from the pre-dumped AST file specified by ASTFileName.
+ std::unique_ptr<ASTUnit> LoadedUnit = loadFromASTFile(ASTFileName);
+ Unit = LoadedUnit.get();
+ FileASTUnitMap[ASTFileName] = std::move(LoadedUnit);
+ } else {
+ Unit = ASTCacheEntry->second.get();
+ }
+ NameASTUnitMap[LookupName] = Unit;
+
+ return Unit;
+}
+
llvm::Expected<ASTUnit *> CrossTranslationUnitContext::loadExternalAST(
StringRef LookupName, StringRef CrossTUDir, StringRef IndexName,
bool DisplayCTUProgress) {
@@ -348,65 +434,38 @@
// translation units contains decls with the same lookup name an
// error will be returned.
- if (NumASTLoaded >= CTULoadThreshold) {
- ++NumASTLoadThresholdReached;
+ // If import threshold is reached, don't import anything.
+ if (checkThresholdReached())
return llvm::make_error<IndexError>(
index_error_code::load_threshold_reached);
- }
- ASTUnit *Unit = nullptr;
- auto NameUnitCacheEntry = NameASTUnitMap.find(LookupName);
- if (NameUnitCacheEntry == NameASTUnitMap.end()) {
- if (NameFileMap.empty()) {
- SmallString<256> IndexFile = CrossTUDir;
- if (llvm::sys::path::is_absolute(IndexName))
- IndexFile = IndexName;
- else
- llvm::sys::path::append(IndexFile, IndexName);
- llvm::Expected<llvm::StringMap<std::string>> IndexOrErr =
- parseCrossTUIndex(IndexFile, CrossTUDir);
- if (IndexOrErr)
- NameFileMap = *IndexOrErr;
- else
- return IndexOrErr.takeError();
- }
+ // First try to access the cache to get the ASTUnit for the function name
+ // specified by LookupName.
+ ASTUnit *Unit = getCachedASTUnitForName(LookupName);
+ if (Unit)
+ return Unit;
- auto It = NameFileMap.find(LookupName);
- if (It == NameFileMap.end()) {
- ++NumNotInOtherTU;
- return llvm::make_error<IndexError>(index_error_code::missing_definition);
- }
- StringRef ASTFileName = It->second;
- auto ASTCacheEntry = FileASTUnitMap.find(ASTFileName);
- if (ASTCacheEntry == FileASTUnitMap.end()) {
- IntrusiveRefCntPtr<DiagnosticOptions> DiagOpts = new DiagnosticOptions();
- TextDiagnosticPrinter *DiagClient =
- new TextDiagnosticPrinter(llvm::errs(), &*DiagOpts);
- IntrusiveRefCntPtr<DiagnosticIDs> DiagID(new DiagnosticIDs());
- IntrusiveRefCntPtr<DiagnosticsEngine> Diags(
- new DiagnosticsEngine(DiagID, &*DiagOpts, DiagClient));
-
- std::unique_ptr<ASTUnit> LoadedUnit(ASTUnit::LoadFromASTFile(
- ASTFileName, CI.getPCHContainerOperations()->getRawReader(),
- ASTUnit::LoadEverything, Diags, CI.getFileSystemOpts()));
- Unit = LoadedUnit.get();
- FileASTUnitMap[ASTFileName] = std::move(LoadedUnit);
- ++NumASTLoaded;
- if (DisplayCTUProgress) {
- llvm::errs() << "CTU loaded AST file: "
- << ASTFileName << "\n";
- }
- } else {
- Unit = ASTCacheEntry->second.get();
+ // Lazily initialize the mapping from function names to AST files.
+ if (llvm::Error InitFailed = lazyInitCTUIndex(CrossTUDir, IndexName))
+ return std::move(InitFailed);
+
+ llvm::Expected<std::string> ASTFileName = getASTFileNameForLookup(LookupName);
+ if (!ASTFileName)
+ return ASTFileName.takeError();
+
+ // Try to load from ASTFile but use cache for both file and function names.
+ Unit = loadFromASTFileCached(LookupName, *ASTFileName);
+
+ if (Unit) {
+ ++NumASTLoaded;
+ if (DisplayCTUProgress) {
+ llvm::errs() << "CTU loaded AST file: " << *ASTFileName << "\n";
}
- NameASTUnitMap[LookupName] = Unit;
+ return Unit;
} else {
- Unit = NameUnitCacheEntry->second;
- }
- if (!Unit)
return llvm::make_error<IndexError>(
index_error_code::failed_to_get_external_ast);
- return Unit;
+ }
}
template <typename T>
Index: clang/include/clang/CrossTU/CrossTranslationUnit.h
===================================================================
--- clang/include/clang/CrossTU/CrossTranslationUnit.h
+++ clang/include/clang/CrossTU/CrossTranslationUnit.h
@@ -163,16 +163,22 @@
void emitCrossTUDiagnostics(const IndexError &IE);
private:
+ bool checkThresholdReached() const;
+ llvm::Error lazyInitCTUIndex(StringRef CrossTUDir, StringRef IndexName);
+ ASTUnit *getCachedASTUnitForName(StringRef LookupName) const;
+ std::unique_ptr<ASTUnit> loadFromASTFile(StringRef ASTFileName) const;
+ ASTUnit *loadFromASTFileCached(StringRef LookupName, StringRef ASTFileName);
+ llvm::Expected<std::string>
+ getASTFileNameForLookup(StringRef LookupName) const;
+
void lazyInitImporterSharedSt(TranslationUnitDecl *ToTU);
ASTImporter &getOrCreateASTImporter(ASTContext &From);
template <typename T>
- llvm::Expected<const T *> getCrossTUDefinitionImpl(const T *D,
- StringRef CrossTUDir,
- StringRef IndexName,
- bool DisplayCTUProgress);
+ llvm::Expected<const T *>
+ getCrossTUDefinitionImpl(const T *D, StringRef CrossTUDir,
+ StringRef IndexName, bool DisplayCTUProgress);
template <typename T>
- const T *findDefInDeclContext(const DeclContext *DC,
- StringRef LookupName);
+ const T *findDefInDeclContext(const DeclContext *DC, StringRef LookupName);
template <typename T>
llvm::Expected<const T *> importDefinitionImpl(const T *D);
_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits