Index: clangd/AST.h =================================================================== --- clangd/AST.h +++ clangd/AST.h @@ -16,6 +16,7 @@ #include "clang/AST/Decl.h" #include "clang/Basic/SourceLocation.h" +#include "index/Index.h" namespace clang { class SourceManager; @@ -33,6 +34,9 @@ /// like inline namespaces. std::string printQualifiedName(const NamedDecl &ND); +/// Gets the symbol ID for a declaration, if possible. +llvm::Optional getSymbolID(const Decl *D); + } // namespace clangd } // namespace clang Index: clangd/AST.cpp =================================================================== --- clangd/AST.cpp +++ clangd/AST.cpp @@ -12,6 +12,7 @@ #include "clang/AST/ASTContext.h" #include "clang/AST/Decl.h" #include "clang/Basic/SourceManager.h" +#include "clang/Index/USRGeneration.h" namespace clang { namespace clangd { @@ -53,5 +54,12 @@ return QName; } +llvm::Optional getSymbolID(const Decl *D) { + llvm::SmallString<128> USR; + if (index::generateUSRForDecl(D, USR)) + return None; + return SymbolID(USR); +} + } // namespace clangd } // namespace clang Index: clangd/CodeComplete.cpp =================================================================== --- clangd/CodeComplete.cpp +++ clangd/CodeComplete.cpp @@ -396,10 +396,7 @@ switch (R.Kind) { case CodeCompletionResult::RK_Declaration: case CodeCompletionResult::RK_Pattern: { - llvm::SmallString<128> USR; - if (/*Ignore=*/clang::index::generateUSRForDecl(R.Declaration, USR)) - return None; - return SymbolID(USR); + return clang::clangd::getSymbolID(R.Declaration); } case CodeCompletionResult::RK_Macro: // FIXME: Macros do have USRs, but the CCR doesn't contain enough info. Index: clangd/XRefs.cpp =================================================================== --- clangd/XRefs.cpp +++ clangd/XRefs.cpp @@ -202,15 +202,6 @@ return L; } -// Get the symbol ID for a declaration, if possible. -llvm::Optional getSymbolID(const Decl *D) { - llvm::SmallString<128> USR; - if (index::generateUSRForDecl(D, USR)) { - return None; - } - return SymbolID(USR); -} - } // namespace std::vector findDefinitions(ParsedAST &AST, Position Pos, Index: clangd/index/SymbolCollector.cpp =================================================================== --- clangd/index/SymbolCollector.cpp +++ clangd/index/SymbolCollector.cpp @@ -320,21 +320,20 @@ if (!shouldCollectSymbol(*ND, *ASTCtx, Opts)) return true; - llvm::SmallString<128> USR; - if (index::generateUSRForDecl(ND, USR)) + auto ID = getSymbolID(ND); + if (!ID) return true; - SymbolID ID(USR); const NamedDecl &OriginalDecl = *cast(ASTNode.OrigD); - const Symbol *BasicSymbol = Symbols.find(ID); + const Symbol *BasicSymbol = Symbols.find(*ID); if (!BasicSymbol) // Regardless of role, ND is the canonical declaration. - BasicSymbol = addDeclaration(*ND, std::move(ID)); + BasicSymbol = addDeclaration(*ND, std::move(*ID)); else if (isPreferredDeclaration(OriginalDecl, Roles)) // If OriginalDecl is preferred, replace the existing canonical // declaration (e.g. a class forward declaration). There should be at most // one duplicate as we expect to see only one preferred declaration per // TU, because in practice they are definitions. - BasicSymbol = addDeclaration(OriginalDecl, std::move(ID)); + BasicSymbol = addDeclaration(OriginalDecl, std::move(*ID)); if (Roles & static_cast(index::SymbolRole::Definition)) addDefinition(OriginalDecl, *BasicSymbol); @@ -423,9 +422,9 @@ } }; for (const NamedDecl *ND : ReferencedDecls) { - llvm::SmallString<128> USR; - if (!index::generateUSRForDecl(ND, USR)) - IncRef(SymbolID(USR)); + if (auto ID = getSymbolID(ND)) { + IncRef(*ID); + } } if (Opts.CollectMacro) { assert(PP);