Skip to content

Commit 58927e9

Browse files
committed
[clangd] Remove the direct use of StdSymbolMapping.inc usage.
Replace them with the library APIs. Differential Revision: https://reviews.llvm.org/D143274
1 parent de31b5c commit 58927e9

File tree

5 files changed

+52
-66
lines changed

5 files changed

+52
-66
lines changed

clang-tools-extra/clangd/index/CanonicalIncludes.cpp

Lines changed: 21 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010
#include "Headers.h"
1111
#include "clang/Basic/FileEntry.h"
1212
#include "clang/Tooling/Inclusions/HeaderAnalysis.h"
13+
#include "clang/Tooling/Inclusions/StandardLibrary.h"
1314
#include "llvm/ADT/StringRef.h"
1415
#include "llvm/Support/FileSystem/UniqueID.h"
1516
#include "llvm/Support/Path.h"
@@ -700,8 +701,26 @@ llvm::StringRef CanonicalIncludes::mapHeader(FileEntryRef Header) const {
700701
return "";
701702
}
702703

703-
llvm::StringRef CanonicalIncludes::mapSymbol(llvm::StringRef QName) const {
704-
return StdSymbolMapping ? StdSymbolMapping->lookup(QName) : "";
704+
llvm::StringRef CanonicalIncludes::mapSymbol(llvm::StringRef Scope,
705+
llvm::StringRef Name,
706+
const LangOptions &L) const {
707+
tooling::stdlib::Lang Lang;
708+
if (L.CPlusPlus)
709+
Lang = tooling::stdlib::Lang::CXX;
710+
else if (L.C11)
711+
Lang = tooling::stdlib::Lang::C;
712+
else
713+
return "";
714+
// FIXME: remove the following special cases when the tooling stdlib supports
715+
// them.
716+
// There are two std::move()s, this is by far the most common.
717+
if (Scope == "std::" && Name == "move")
718+
return "<utility>";
719+
if (Scope == "std::" && Name == "size_t")
720+
return "<cstddef>";
721+
if (auto StdSym = tooling::stdlib::Symbol::named(Scope, Name, Lang))
722+
return StdSym->header().name();
723+
return "";
705724
}
706725

707726
std::unique_ptr<CommentHandler>
@@ -732,28 +751,6 @@ collectIWYUHeaderMaps(CanonicalIncludes *Includes) {
732751
}
733752

734753
void CanonicalIncludes::addSystemHeadersMapping(const LangOptions &Language) {
735-
if (Language.CPlusPlus) {
736-
static const auto *Symbols = new llvm::StringMap<llvm::StringRef>({
737-
#define SYMBOL(Name, NameSpace, Header) {#NameSpace #Name, #Header},
738-
#include "clang/Tooling/Inclusions/StdSymbolMap.inc"
739-
// There are two std::move()s, this is by far the most common.
740-
SYMBOL(move, std::, <utility>)
741-
// There are multiple headers for size_t, pick one.
742-
SYMBOL(size_t, std::, <cstddef>)
743-
#undef SYMBOL
744-
});
745-
StdSymbolMapping = Symbols;
746-
} else if (Language.C11) {
747-
static const auto *CSymbols = new llvm::StringMap<llvm::StringRef>({
748-
#define SYMBOL(Name, NameSpace, Header) {#Name, #Header},
749-
#include "clang/Tooling/Inclusions/CSymbolMap.inc"
750-
// There are multiple headers for size_t, pick one.
751-
SYMBOL(size_t, None, <stddef.h>)
752-
#undef SYMBOL
753-
});
754-
StdSymbolMapping = CSymbols;
755-
}
756-
757754
// FIXME: remove the std header mapping once we support ambiguous symbols, now
758755
// it serves as a fallback to disambiguate:
759756
// - symbols with multiple headers (e.g. std::move)

clang-tools-extra/clangd/index/CanonicalIncludes.h

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -39,8 +39,12 @@ class CanonicalIncludes {
3939
/// Adds a file-to-string mapping from \p ID to \p CanonicalPath.
4040
void addMapping(FileEntryRef Header, llvm::StringRef CanonicalPath);
4141

42-
/// Returns the overridden include for symbol with \p QualifiedName, or "".
43-
llvm::StringRef mapSymbol(llvm::StringRef QualifiedName) const;
42+
/// Returns the overridden include for a qualified symbol with, or "".
43+
/// \p Scope and \p Name concatenation forms the fully qualified name.
44+
/// \p Scope is the qualifier with the trailing "::" (e.g. "std::") or empty
45+
/// (for global namespace).
46+
llvm::StringRef mapSymbol(llvm::StringRef Scope, llvm::StringRef Name,
47+
const LangOptions &L) const;
4448

4549
/// Returns the overridden include for files in \p Header, or "".
4650
llvm::StringRef mapHeader(FileEntryRef Header) const;
@@ -61,9 +65,6 @@ class CanonicalIncludes {
6165
/// A map from a suffix (one or components of a path) to a canonical path.
6266
/// Used only for mapping standard headers.
6367
const llvm::StringMap<llvm::StringRef> *StdSuffixHeaderMapping = nullptr;
64-
/// A map from fully qualified symbol names to header names.
65-
/// Used only for mapping standard symbols.
66-
const llvm::StringMap<llvm::StringRef> *StdSymbolMapping = nullptr;
6768
};
6869

6970
/// Returns a CommentHandler that parses pragma comment on include files to

clang-tools-extra/clangd/index/StdLib.cpp

Lines changed: 14 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@
2222
#include "clang/Basic/LangOptions.h"
2323
#include "clang/Frontend/CompilerInvocation.h"
2424
#include "clang/Lex/PreprocessorOptions.h"
25+
#include "clang/Tooling/Inclusions/StandardLibrary.h"
2526
#include "llvm/ADT/IntrusiveRefCntPtr.h"
2627
#include "llvm/ADT/StringRef.h"
2728
#include "llvm/Support/MemoryBuffer.h"
@@ -67,7 +68,7 @@ LangStandard::Kind standardFromOpts(const LangOptions &LO) {
6768
}
6869

6970
std::string buildUmbrella(llvm::StringLiteral Mandatory,
70-
std::vector<llvm::StringLiteral> Headers) {
71+
llvm::ArrayRef<tooling::stdlib::Header> Headers) {
7172
std::string Result;
7273
llvm::raw_string_ostream OS(Result);
7374

@@ -80,13 +81,11 @@ std::string buildUmbrella(llvm::StringLiteral Mandatory,
8081
"#endif\n",
8182
Mandatory);
8283

83-
llvm::sort(Headers);
84-
auto Last = std::unique(Headers.begin(), Headers.end());
85-
for (auto Header = Headers.begin(); Header != Last; ++Header) {
84+
for (auto Header : Headers) {
8685
OS << llvm::formatv("#if __has_include({0})\n"
8786
"#include {0}\n"
8887
"#endif\n",
89-
*Header);
88+
Header);
9089
}
9190
OS.flush();
9291
return Result;
@@ -102,20 +101,14 @@ llvm::StringRef getStdlibUmbrellaHeader(const LangOptions &LO) {
102101
Lang L = langFromOpts(LO);
103102
switch (L) {
104103
case CXX:
105-
static std::string *UmbrellaCXX =
106-
new std::string(buildUmbrella(mandatoryHeader(L), {
107-
#define SYMBOL(Name, NameSpace, Header) #Header,
108-
#include "clang/Tooling/Inclusions/StdSymbolMap.inc"
109-
#undef SYMBOL
110-
}));
104+
static std::string *UmbrellaCXX = new std::string(buildUmbrella(
105+
mandatoryHeader(L),
106+
tooling::stdlib::Header::all(tooling::stdlib::Lang::CXX)));
111107
return *UmbrellaCXX;
112108
case C:
113-
static std::string *UmbrellaC =
114-
new std::string(buildUmbrella(mandatoryHeader(L), {
115-
#define SYMBOL(Name, NameSpace, Header) #Header,
116-
#include "clang/Tooling/Inclusions/CSymbolMap.inc"
117-
#undef SYMBOL
118-
}));
109+
static std::string *UmbrellaC = new std::string(
110+
buildUmbrella(mandatoryHeader(L),
111+
tooling::stdlib::Header::all(tooling::stdlib::Lang::C)));
119112
return *UmbrellaC;
120113
}
121114
llvm_unreachable("invalid Lang in langFromOpts");
@@ -141,13 +134,10 @@ SymbolSlab filter(SymbolSlab Slab, const StdLibLocation &Loc) {
141134

142135
static auto &StandardHeaders = *[] {
143136
auto *Set = new llvm::DenseSet<llvm::StringRef>();
144-
for (llvm::StringRef Header : {
145-
#define SYMBOL(Name, NameSpace, Header) #Header,
146-
#include "clang/Tooling/Inclusions/CSymbolMap.inc"
147-
#include "clang/Tooling/Inclusions/StdSymbolMap.inc"
148-
#undef SYMBOL
149-
})
150-
Set->insert(Header);
137+
for (auto Header : tooling::stdlib::Header::all(tooling::stdlib::Lang::CXX))
138+
Set->insert(Header.name());
139+
for (auto Header : tooling::stdlib::Header::all(tooling::stdlib::Lang::C))
140+
Set->insert(Header.name());
151141
return Set;
152142
}();
153143

clang-tools-extra/clangd/index/SymbolCollector.cpp

Lines changed: 4 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -829,20 +829,18 @@ void SymbolCollector::finish() {
829829
llvm::DenseMap<FileID, bool> FileToContainsImportsOrObjC;
830830
// Fill in IncludeHeaders.
831831
// We delay this until end of TU so header guards are all resolved.
832-
llvm::SmallString<128> QName;
833832
for (const auto &[SID, FID] : IncludeFiles) {
834833
if (const Symbol *S = Symbols.find(SID)) {
835834
llvm::StringRef IncludeHeader;
836835
// Look for an overridden include header for this symbol specifically.
837836
if (Opts.Includes) {
838-
QName = S->Scope;
839-
QName.append(S->Name);
840-
IncludeHeader = Opts.Includes->mapSymbol(QName);
837+
IncludeHeader =
838+
Opts.Includes->mapSymbol(S->Scope, S->Name, ASTCtx->getLangOpts());
841839
if (!IncludeHeader.empty()) {
842840
if (IncludeHeader.front() != '"' && IncludeHeader.front() != '<')
843841
IncludeHeader = HeaderFileURIs->toURI(IncludeHeader);
844-
else if (IncludeHeader == "<utility>" && QName == "std::move" &&
845-
S->Signature.contains(','))
842+
else if (IncludeHeader == "<utility>" && S->Scope == "std::" &&
843+
S->Name == "move" && S->Signature.contains(','))
846844
IncludeHeader = "<algorithm>";
847845
}
848846
}

clang-tools-extra/clangd/unittests/CanonicalIncludesTests.cpp

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -36,8 +36,8 @@ TEST(CanonicalIncludesTest, CStandardLibrary) {
3636
Language.C11 = true;
3737
CI.addSystemHeadersMapping(Language);
3838
// Usual standard library symbols are mapped correctly.
39-
EXPECT_EQ("<stdio.h>", CI.mapSymbol("printf"));
40-
EXPECT_EQ("", CI.mapSymbol("unknown_symbol"));
39+
EXPECT_EQ("<stdio.h>", CI.mapSymbol("", "printf", Language));
40+
EXPECT_EQ("", CI.mapSymbol("", "unknown_symbol", Language));
4141
}
4242

4343
TEST(CanonicalIncludesTest, CXXStandardLibrary) {
@@ -47,14 +47,14 @@ TEST(CanonicalIncludesTest, CXXStandardLibrary) {
4747
CI.addSystemHeadersMapping(Language);
4848

4949
// Usual standard library symbols are mapped correctly.
50-
EXPECT_EQ("<vector>", CI.mapSymbol("std::vector"));
51-
EXPECT_EQ("<cstdio>", CI.mapSymbol("std::printf"));
50+
EXPECT_EQ("<vector>", CI.mapSymbol("std::", "vector", Language));
51+
EXPECT_EQ("<cstdio>", CI.mapSymbol("std::", "printf", Language));
5252
// std::move is ambiguous, currently always mapped to <utility>
53-
EXPECT_EQ("<utility>", CI.mapSymbol("std::move"));
53+
EXPECT_EQ("<utility>", CI.mapSymbol("std::", "move", Language));
5454
// Unknown std symbols aren't mapped.
55-
EXPECT_EQ("", CI.mapSymbol("std::notathing"));
55+
EXPECT_EQ("", CI.mapSymbol("std::", "notathing", Language));
5656
// iosfwd declares some symbols it doesn't own.
57-
EXPECT_EQ("<ostream>", CI.mapSymbol("std::ostream"));
57+
EXPECT_EQ("<ostream>", CI.mapSymbol("std::", "ostream", Language));
5858
// And (for now) we assume it owns the others.
5959
auto InMemFS = llvm::makeIntrusiveRefCnt<llvm::vfs::InMemoryFileSystem>();
6060
FileManager Files(FileSystemOptions(), InMemFS);

0 commit comments

Comments
 (0)