zixuw created this revision.
Herald added a reviewer: dang.
Herald added a project: All.
zixuw requested review of this revision.
Herald added a project: clang.
Herald added a subscriber: cfe-commits.
Add support for enum records
- Add `EnumConstantRecord` and `EnumRecord` to store API information for enums
- Implement `VisitEnumDecl` in `ExtractAPIVisitor`
- Implement serializatin for enum records and `MemberOf` relationship
- Add test case for enum records
- Few other improvements
Repository:
rG LLVM Github Monorepo
https://reviews.llvm.org/D121873
Files:
clang/include/clang/SymbolGraph/API.h
clang/include/clang/SymbolGraph/DeclarationFragments.h
clang/include/clang/SymbolGraph/Serialization.h
clang/lib/SymbolGraph/API.cpp
clang/lib/SymbolGraph/DeclarationFragments.cpp
clang/lib/SymbolGraph/ExtractAPIConsumer.cpp
clang/lib/SymbolGraph/Serialization.cpp
clang/test/SymbolGraph/enum.c
Index: clang/test/SymbolGraph/enum.c
===================================================================
--- /dev/null
+++ clang/test/SymbolGraph/enum.c
@@ -0,0 +1,505 @@
+// RUN: rm -rf %t
+// RUN: split-file %s %t
+// RUN: sed -e "s@INPUT_DIR@%/t@g" %t/reference.output.json.in >> \
+// RUN: %t/reference.output.json
+// RUN: %clang -extract-api -target arm64-apple-macosx \
+// RUN: %t/input.c -o %t/output.json | FileCheck -allow-empty %s
+
+// Generator version is not consistent across test runs, normalize it.
+// RUN: sed -e "s@\"generator\": \".*\"@\"generator\": \"?\"@g" \
+// RUN: %t/output.json >> %t/output-normalized.json
+// RUN: diff %t/reference.output.json %t/output-normalized.json
+
+// CHECK-NOT: error:
+// CHECK-NOT: warning:
+
+//--- input.c
+/// Kinds of vehicles
+enum Vehicle {
+ Bicycle,
+ Car,
+ Train, ///< Move this to the top! -Sheldon
+ Ship,
+ Airplane,
+};
+
+enum Direction : unsigned char {
+ North = 0,
+ East,
+ South,
+ West
+};
+
+//--- reference.output.json.in
+{
+ "metadata": {
+ "formatVersion": {
+ "major": 0,
+ "minor": 5,
+ "patch": 3
+ },
+ "generator": "?"
+ },
+ "module": {
+ "name": "",
+ "platform": {
+ "architecture": "arm64",
+ "operatingSystem": {
+ "minimumVersion": {
+ "major": 11,
+ "minor": 0,
+ "patch": 0
+ },
+ "name": "macosx"
+ },
+ "vendor": "apple"
+ }
+ },
+ "relationhips": [
+ {
+ "kind": "memberOf",
+ "source": "c:@E@Vehicle@Bicycle",
+ "target": "c:@E@Vehicle"
+ },
+ {
+ "kind": "memberOf",
+ "source": "c:@E@Vehicle@Car",
+ "target": "c:@E@Vehicle"
+ },
+ {
+ "kind": "memberOf",
+ "source": "c:@E@Vehicle@Train",
+ "target": "c:@E@Vehicle"
+ },
+ {
+ "kind": "memberOf",
+ "source": "c:@E@Vehicle@Ship",
+ "target": "c:@E@Vehicle"
+ },
+ {
+ "kind": "memberOf",
+ "source": "c:@E@Vehicle@Airplane",
+ "target": "c:@E@Vehicle"
+ },
+ {
+ "kind": "memberOf",
+ "source": "c:@E@Direction@North",
+ "target": "c:@E@Direction"
+ },
+ {
+ "kind": "memberOf",
+ "source": "c:@E@Direction@East",
+ "target": "c:@E@Direction"
+ },
+ {
+ "kind": "memberOf",
+ "source": "c:@E@Direction@South",
+ "target": "c:@E@Direction"
+ },
+ {
+ "kind": "memberOf",
+ "source": "c:@E@Direction@West",
+ "target": "c:@E@Direction"
+ }
+ ],
+ "symbols": [
+ {
+ "declarationFragments": [
+ {
+ "kind": "keyword",
+ "spelling": "enum"
+ },
+ {
+ "kind": "text",
+ "spelling": " "
+ },
+ {
+ "kind": "identifier",
+ "spelling": "Vehicle"
+ },
+ {
+ "kind": "text",
+ "spelling": ": "
+ },
+ {
+ "kind": "typeIdentifier",
+ "preciseIdentifier": "c:i",
+ "spelling": "unsigned int"
+ }
+ ],
+ "docComment": {
+ "lines": [
+ {
+ "range": {
+ "end": {
+ "character": 22,
+ "line": 1
+ },
+ "start": {
+ "character": 5,
+ "line": 1
+ }
+ },
+ "text": "Kinds of vehicles"
+ }
+ ]
+ },
+ "identifier": {
+ "interfaceLanguage": "c",
+ "precise": "c:@E@Vehicle"
+ },
+ "kind": {
+ "displayName": "Enum",
+ "identifier": "c.enum"
+ },
+ "location": {
+ "character": 6,
+ "line": 2,
+ "uri": "file://INPUT_DIR/input.c"
+ },
+ "names": {
+ "subHeading": [
+ {
+ "kind": "identifier",
+ "spelling": "Vehicle"
+ }
+ ],
+ "title": "Vehicle"
+ }
+ },
+ {
+ "declarationFragments": [
+ {
+ "kind": "identifier",
+ "spelling": "Bicycle"
+ }
+ ],
+ "identifier": {
+ "interfaceLanguage": "c",
+ "precise": "c:@E@Vehicle@Bicycle"
+ },
+ "kind": {
+ "displayName": "Enum Case",
+ "identifier": "c.enum.case"
+ },
+ "location": {
+ "character": 3,
+ "line": 3,
+ "uri": "file://INPUT_DIR/input.c"
+ },
+ "names": {
+ "subHeading": [
+ {
+ "kind": "identifier",
+ "spelling": "Bicycle"
+ }
+ ],
+ "title": "Bicycle"
+ }
+ },
+ {
+ "declarationFragments": [
+ {
+ "kind": "identifier",
+ "spelling": "Car"
+ }
+ ],
+ "identifier": {
+ "interfaceLanguage": "c",
+ "precise": "c:@E@Vehicle@Car"
+ },
+ "kind": {
+ "displayName": "Enum Case",
+ "identifier": "c.enum.case"
+ },
+ "location": {
+ "character": 3,
+ "line": 4,
+ "uri": "file://INPUT_DIR/input.c"
+ },
+ "names": {
+ "subHeading": [
+ {
+ "kind": "identifier",
+ "spelling": "Car"
+ }
+ ],
+ "title": "Car"
+ }
+ },
+ {
+ "declarationFragments": [
+ {
+ "kind": "identifier",
+ "spelling": "Train"
+ }
+ ],
+ "docComment": {
+ "lines": [
+ {
+ "range": {
+ "end": {
+ "character": 45,
+ "line": 5
+ },
+ "start": {
+ "character": 15,
+ "line": 5
+ }
+ },
+ "text": "Move this to the top! -Sheldon"
+ }
+ ]
+ },
+ "identifier": {
+ "interfaceLanguage": "c",
+ "precise": "c:@E@Vehicle@Train"
+ },
+ "kind": {
+ "displayName": "Enum Case",
+ "identifier": "c.enum.case"
+ },
+ "location": {
+ "character": 3,
+ "line": 5,
+ "uri": "file://INPUT_DIR/input.c"
+ },
+ "names": {
+ "subHeading": [
+ {
+ "kind": "identifier",
+ "spelling": "Train"
+ }
+ ],
+ "title": "Train"
+ }
+ },
+ {
+ "declarationFragments": [
+ {
+ "kind": "identifier",
+ "spelling": "Ship"
+ }
+ ],
+ "identifier": {
+ "interfaceLanguage": "c",
+ "precise": "c:@E@Vehicle@Ship"
+ },
+ "kind": {
+ "displayName": "Enum Case",
+ "identifier": "c.enum.case"
+ },
+ "location": {
+ "character": 3,
+ "line": 6,
+ "uri": "file://INPUT_DIR/input.c"
+ },
+ "names": {
+ "subHeading": [
+ {
+ "kind": "identifier",
+ "spelling": "Ship"
+ }
+ ],
+ "title": "Ship"
+ }
+ },
+ {
+ "declarationFragments": [
+ {
+ "kind": "identifier",
+ "spelling": "Airplane"
+ }
+ ],
+ "identifier": {
+ "interfaceLanguage": "c",
+ "precise": "c:@E@Vehicle@Airplane"
+ },
+ "kind": {
+ "displayName": "Enum Case",
+ "identifier": "c.enum.case"
+ },
+ "location": {
+ "character": 3,
+ "line": 7,
+ "uri": "file://INPUT_DIR/input.c"
+ },
+ "names": {
+ "subHeading": [
+ {
+ "kind": "identifier",
+ "spelling": "Airplane"
+ }
+ ],
+ "title": "Airplane"
+ }
+ },
+ {
+ "declarationFragments": [
+ {
+ "kind": "keyword",
+ "spelling": "enum"
+ },
+ {
+ "kind": "text",
+ "spelling": " "
+ },
+ {
+ "kind": "identifier",
+ "spelling": "Direction"
+ },
+ {
+ "kind": "text",
+ "spelling": ": "
+ },
+ {
+ "kind": "typeIdentifier",
+ "preciseIdentifier": "c:c",
+ "spelling": "unsigned char"
+ }
+ ],
+ "identifier": {
+ "interfaceLanguage": "c",
+ "precise": "c:@E@Direction"
+ },
+ "kind": {
+ "displayName": "Enum",
+ "identifier": "c.enum"
+ },
+ "location": {
+ "character": 6,
+ "line": 10,
+ "uri": "file://INPUT_DIR/input.c"
+ },
+ "names": {
+ "subHeading": [
+ {
+ "kind": "identifier",
+ "spelling": "Direction"
+ }
+ ],
+ "title": "Direction"
+ }
+ },
+ {
+ "declarationFragments": [
+ {
+ "kind": "identifier",
+ "spelling": "North"
+ }
+ ],
+ "identifier": {
+ "interfaceLanguage": "c",
+ "precise": "c:@E@Direction@North"
+ },
+ "kind": {
+ "displayName": "Enum Case",
+ "identifier": "c.enum.case"
+ },
+ "location": {
+ "character": 3,
+ "line": 11,
+ "uri": "file://INPUT_DIR/input.c"
+ },
+ "names": {
+ "subHeading": [
+ {
+ "kind": "identifier",
+ "spelling": "North"
+ }
+ ],
+ "title": "North"
+ }
+ },
+ {
+ "declarationFragments": [
+ {
+ "kind": "identifier",
+ "spelling": "East"
+ }
+ ],
+ "identifier": {
+ "interfaceLanguage": "c",
+ "precise": "c:@E@Direction@East"
+ },
+ "kind": {
+ "displayName": "Enum Case",
+ "identifier": "c.enum.case"
+ },
+ "location": {
+ "character": 3,
+ "line": 12,
+ "uri": "file://INPUT_DIR/input.c"
+ },
+ "names": {
+ "subHeading": [
+ {
+ "kind": "identifier",
+ "spelling": "East"
+ }
+ ],
+ "title": "East"
+ }
+ },
+ {
+ "declarationFragments": [
+ {
+ "kind": "identifier",
+ "spelling": "South"
+ }
+ ],
+ "identifier": {
+ "interfaceLanguage": "c",
+ "precise": "c:@E@Direction@South"
+ },
+ "kind": {
+ "displayName": "Enum Case",
+ "identifier": "c.enum.case"
+ },
+ "location": {
+ "character": 3,
+ "line": 13,
+ "uri": "file://INPUT_DIR/input.c"
+ },
+ "names": {
+ "subHeading": [
+ {
+ "kind": "identifier",
+ "spelling": "South"
+ }
+ ],
+ "title": "South"
+ }
+ },
+ {
+ "declarationFragments": [
+ {
+ "kind": "identifier",
+ "spelling": "West"
+ }
+ ],
+ "identifier": {
+ "interfaceLanguage": "c",
+ "precise": "c:@E@Direction@West"
+ },
+ "kind": {
+ "displayName": "Enum Case",
+ "identifier": "c.enum.case"
+ },
+ "location": {
+ "character": 3,
+ "line": 14,
+ "uri": "file://INPUT_DIR/input.c"
+ },
+ "names": {
+ "subHeading": [
+ {
+ "kind": "identifier",
+ "spelling": "West"
+ }
+ ],
+ "title": "West"
+ }
+ }
+ ]
+}
Index: clang/lib/SymbolGraph/Serialization.cpp
===================================================================
--- clang/lib/SymbolGraph/Serialization.cpp
+++ clang/lib/SymbolGraph/Serialization.cpp
@@ -225,17 +225,21 @@
// SymbolGraph: Symbol::kind
static Object serializeSymbolKind(const APIRecord &Record,
const LangOptions &LangOpts) {
+ auto AddLangPrefix = [&LangOpts](StringRef S) -> std::string {
+ return (getLanguageName(LangOpts) + "." + S).str();
+ };
+
Object Kind;
switch (Record.getKind()) {
- case APIRecord::RK_Global:
+ case APIRecord::RK_Global: {
auto *GR = dyn_cast<GlobalRecord>(&Record);
switch (GR->GlobalKind) {
case GVKind::Function:
- Kind["identifier"] = (getLanguageName(LangOpts) + ".func").str();
+ Kind["identifier"] = AddLangPrefix("func");
Kind["displayName"] = "Function";
break;
case GVKind::Variable:
- Kind["identifier"] = (getLanguageName(LangOpts) + ".var").str();
+ Kind["identifier"] = AddLangPrefix("var");
Kind["displayName"] = "Global Variable";
break;
case GVKind::Unknown:
@@ -244,6 +248,15 @@
}
break;
}
+ case APIRecord::RK_EnumConstant:
+ Kind["identifier"] = AddLangPrefix("enum.case");
+ Kind["displayName"] = "Enum Case";
+ break;
+ case APIRecord::RK_Enum:
+ Kind["identifier"] = AddLangPrefix("enum");
+ Kind["displayName"] = "Enum";
+ break;
+ }
return Kind;
}
@@ -297,6 +310,21 @@
return Obj;
}
+void Serializer::serializeRelationship(RelationshipKind Kind,
+ const APIRecord &Source,
+ const APIRecord &Target) {
+ Object Relationship;
+ Relationship["source"] = Source.USR;
+ Relationship["target"] = Target.USR;
+ switch (Kind) {
+ case RelationshipKind::MemberOf:
+ Relationship["kind"] = "memberOf";
+ break;
+ }
+
+ Relationships.emplace_back(std::move(Relationship));
+}
+
void Serializer::serializeGlobalRecord(const GlobalRecord &Record) {
auto Obj = serializeAPIRecord(Record);
if (!Obj)
@@ -309,6 +337,23 @@
Symbols.emplace_back(std::move(*Obj));
}
+void Serializer::serializeEnumRecord(const EnumRecord &Record) {
+ auto Enum = serializeAPIRecord(Record);
+ if (!Enum)
+ return;
+
+ Symbols.emplace_back(std::move(*Enum));
+
+ for (const auto &Constant : Record.Constants) {
+ auto EnumConstant = serializeAPIRecord(*Constant);
+ if (!EnumConstant)
+ continue;
+
+ Symbols.emplace_back(std::move(*EnumConstant));
+ serializeRelationship(RelationshipKind::MemberOf, *Constant, Record);
+ }
+}
+
Object Serializer::serialize() {
Object Root;
serializeObject(Root, "metadata", serializeMetadata());
@@ -317,6 +362,9 @@
for (const auto &Global : API.getGlobals())
serializeGlobalRecord(*Global.second);
+ for (const auto &Enum : API.getEnums())
+ serializeEnumRecord(*Enum.second);
+
Root["symbols"] = std::move(Symbols);
Root["relationhips"] = std::move(Relationships);
Index: clang/lib/SymbolGraph/ExtractAPIConsumer.cpp
===================================================================
--- clang/lib/SymbolGraph/ExtractAPIConsumer.cpp
+++ clang/lib/SymbolGraph/ExtractAPIConsumer.cpp
@@ -134,6 +134,36 @@
return true;
}
+ bool VisitEnumDecl(const EnumDecl *Decl) {
+ if (!Decl->isComplete())
+ return true;
+
+ // Skip forward declaration.
+ if (!Decl->isThisDeclarationADefinition())
+ return true;
+
+ StringRef Name = Decl->getName();
+ StringRef USR = API.recordUSR(Decl);
+ PresumedLoc Loc =
+ Context.getSourceManager().getPresumedLoc(Decl->getLocation());
+ AvailabilityInfo Availability = getAvailability(Decl);
+ DocComment Comment;
+ if (auto *RawComment = Context.getRawCommentForDeclNoCache(Decl))
+ Comment = RawComment->getFormattedLines(Context.getSourceManager(),
+ Context.getDiagnostics());
+ DeclarationFragments Declaration =
+ DeclarationFragmentsBuilder::getFragmentsForEnum(Decl);
+ DeclarationFragments SubHeading =
+ DeclarationFragmentsBuilder::getSubHeading(Decl);
+
+ EnumRecord *EnumRecord = API.addEnum(Name, USR, Loc, Availability, Comment,
+ Declaration, SubHeading);
+
+ recordEnumConstants(EnumRecord, Decl->enumerators());
+
+ return true;
+ }
+
private:
AvailabilityInfo getAvailability(const Decl *D) const {
StringRef PlatformName = Context.getTargetInfo().getPlatformName();
@@ -164,6 +194,28 @@
return Availability;
}
+ void recordEnumConstants(EnumRecord *EnumRecord,
+ const EnumDecl::enumerator_range Constants) {
+ for (const auto *Constant : Constants) {
+ StringRef Name = Constant->getName();
+ StringRef USR = API.recordUSR(Constant);
+ PresumedLoc Loc =
+ Context.getSourceManager().getPresumedLoc(Constant->getLocation());
+ AvailabilityInfo Availability = getAvailability(Constant);
+ DocComment Comment;
+ if (auto *RawComment = Context.getRawCommentForDeclNoCache(Constant))
+ Comment = RawComment->getFormattedLines(Context.getSourceManager(),
+ Context.getDiagnostics());
+ DeclarationFragments Declaration =
+ DeclarationFragmentsBuilder::getFragmentsForEnumConstant(Constant);
+ DeclarationFragments SubHeading =
+ DeclarationFragmentsBuilder::getSubHeading(Constant);
+
+ API.addEnumConstant(EnumRecord, Name, USR, Loc, Availability, Comment,
+ Declaration, SubHeading);
+ }
+ }
+
ASTContext &Context;
APISet API;
};
Index: clang/lib/SymbolGraph/DeclarationFragments.cpp
===================================================================
--- clang/lib/SymbolGraph/DeclarationFragments.cpp
+++ clang/lib/SymbolGraph/DeclarationFragments.cpp
@@ -399,6 +399,35 @@
return Fragments;
}
+DeclarationFragments DeclarationFragmentsBuilder::getFragmentsForEnumConstant(
+ const EnumConstantDecl *EnumConstDecl) {
+ DeclarationFragments Fragments;
+ return Fragments.append(EnumConstDecl->getName(),
+ DeclarationFragments::FragmentKind::Identifier);
+}
+
+DeclarationFragments
+DeclarationFragmentsBuilder::getFragmentsForEnum(const EnumDecl *EnumDecl) {
+ // TODO: After we support typedef records, if there's a typedef for this enum
+ // just use the declaration fragments of the typedef decl.
+
+ DeclarationFragments Fragments, After;
+ Fragments.append("enum", DeclarationFragments::FragmentKind::Keyword);
+
+ if (!EnumDecl->getName().empty())
+ Fragments.appendSpace().append(
+ EnumDecl->getName(), DeclarationFragments::FragmentKind::Identifier);
+
+ QualType IntegerType = EnumDecl->getIntegerType();
+ if (!IntegerType.isNull())
+ Fragments.append(": ", DeclarationFragments::FragmentKind::Text)
+ .append(
+ getFragmentsForType(IntegerType, EnumDecl->getASTContext(), After))
+ .append(std::move(After));
+
+ return Fragments;
+}
+
FunctionSignature
DeclarationFragmentsBuilder::getFunctionSignature(const FunctionDecl *Func) {
FunctionSignature Signature;
Index: clang/lib/SymbolGraph/API.cpp
===================================================================
--- clang/lib/SymbolGraph/API.cpp
+++ clang/lib/SymbolGraph/API.cpp
@@ -59,6 +59,30 @@
Comment, Fragments, SubHeading, Signature);
}
+EnumConstantRecord *APISet::addEnumConstant(
+ EnumRecord *Enum, StringRef Name, StringRef USR, PresumedLoc Loc,
+ const AvailabilityInfo &Availability, const DocComment &Comment,
+ DeclarationFragments Declaration, DeclarationFragments SubHeading) {
+ EnumConstantRecord *Record = new (Allocator) EnumConstantRecord{
+ Name, USR, Loc, Availability, Comment, Declaration, SubHeading};
+ Enum->Constants.push_back(Record);
+ return Record;
+}
+
+EnumRecord *APISet::addEnum(StringRef Name, StringRef USR, PresumedLoc Loc,
+ const AvailabilityInfo &Availability,
+ const DocComment &Comment,
+ DeclarationFragments Declaration,
+ DeclarationFragments SubHeading) {
+ auto Result = Enums.insert({Name, nullptr});
+ if (Result.second) {
+ EnumRecord *Record = new (Allocator) EnumRecord{
+ Name, USR, Loc, Availability, Comment, Declaration, SubHeading};
+ Result.first->second = Record;
+ }
+ return Result.first->second;
+}
+
StringRef APISet::recordUSR(const Decl *D) {
SmallString<128> USR;
index::generateUSRForDecl(D, USR);
Index: clang/include/clang/SymbolGraph/Serialization.h
===================================================================
--- clang/include/clang/SymbolGraph/Serialization.h
+++ clang/include/clang/SymbolGraph/Serialization.h
@@ -36,11 +36,19 @@
Object serialize();
void serialize(raw_ostream &os);
+ enum RelationshipKind {
+ MemberOf,
+ };
+
private:
+ void serializeGlobalRecord(const GlobalRecord &Record);
+ void serializeEnumRecord(const EnumRecord &Record);
+
Object serializeMetadata() const;
Object serializeModule() const;
Optional<Object> serializeAPIRecord(const APIRecord &Record) const;
- void serializeGlobalRecord(const GlobalRecord &Record);
+ void serializeRelationship(RelationshipKind Kind, const APIRecord &Source,
+ const APIRecord &Target);
bool shouldSkip(const APIRecord &Record) const;
Index: clang/include/clang/SymbolGraph/DeclarationFragments.h
===================================================================
--- clang/include/clang/SymbolGraph/DeclarationFragments.h
+++ clang/include/clang/SymbolGraph/DeclarationFragments.h
@@ -117,6 +117,10 @@
public:
static DeclarationFragments getFragmentsForVar(const VarDecl *);
static DeclarationFragments getFragmentsForFunction(const FunctionDecl *);
+ static DeclarationFragments
+ getFragmentsForEnumConstant(const EnumConstantDecl *);
+ static DeclarationFragments getFragmentsForEnum(const EnumDecl *);
+
static DeclarationFragments getSubHeading(const NamedDecl *);
static FunctionSignature getFunctionSignature(const FunctionDecl *);
Index: clang/include/clang/SymbolGraph/API.h
===================================================================
--- clang/include/clang/SymbolGraph/API.h
+++ clang/include/clang/SymbolGraph/API.h
@@ -43,6 +43,8 @@
/// Discriminator for LLVM-style RTTI (dyn_cast<> et al.)
enum RecordKind {
RK_Global,
+ RK_EnumConstant,
+ RK_Enum,
};
private:
@@ -88,6 +90,34 @@
}
};
+struct EnumConstantRecord : APIRecord {
+ EnumConstantRecord(StringRef Name, StringRef USR, PresumedLoc Loc,
+ const AvailabilityInfo &Availability,
+ const DocComment &Comment,
+ DeclarationFragments Declaration,
+ DeclarationFragments SubHeading)
+ : APIRecord(RK_EnumConstant, Name, USR, Loc, Availability,
+ LinkageInfo::none(), Comment, Declaration, SubHeading) {}
+
+ static bool classof(const APIRecord *Record) {
+ return Record->getKind() == RK_EnumConstant;
+ }
+};
+
+struct EnumRecord : APIRecord {
+ SmallVector<EnumConstantRecord *> Constants;
+
+ EnumRecord(StringRef Name, StringRef USR, PresumedLoc Loc,
+ const AvailabilityInfo &Availability, const DocComment &Comment,
+ DeclarationFragments Declaration, DeclarationFragments SubHeading)
+ : APIRecord(RK_Enum, Name, USR, Loc, Availability, LinkageInfo::none(),
+ Comment, Declaration, SubHeading) {}
+
+ static bool classof(const APIRecord *Record) {
+ return Record->getKind() == RK_Enum;
+ }
+};
+
class APISet {
public:
APISet(const llvm::Triple &Target, const LangOptions &LangOpts)
@@ -116,13 +146,28 @@
DeclarationFragments SubHeading,
FunctionSignature Signature);
+ EnumConstantRecord *addEnumConstant(EnumRecord *Enum, StringRef Name,
+ StringRef USR, PresumedLoc Loc,
+ const AvailabilityInfo &Availability,
+ const DocComment &Comment,
+ DeclarationFragments Declaration,
+ DeclarationFragments SubHeading);
+
+ EnumRecord *addEnum(StringRef Name, StringRef USR, PresumedLoc Loc,
+ const AvailabilityInfo &Availability,
+ const DocComment &Comment,
+ DeclarationFragments Declaration,
+ DeclarationFragments SubHeading);
+
StringRef recordUSR(const Decl *D);
StringRef copyString(StringRef String, llvm::BumpPtrAllocator &Allocator);
StringRef copyString(StringRef String);
using GlobalRecordMap = llvm::MapVector<StringRef, GlobalRecord *>;
+ using EnumRecordMap = llvm::MapVector<StringRef, EnumRecord *>;
const GlobalRecordMap &getGlobals() const { return Globals; }
+ const EnumRecordMap &getEnums() const { return Enums; }
private:
llvm::BumpPtrAllocator Allocator;
@@ -130,6 +175,7 @@
const LangOptions LangOpts;
GlobalRecordMap Globals;
+ EnumRecordMap Enums;
};
} // namespace symbolgraph
_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits