Skip to content

[llvm][DebugInfo] Add new DW_AT_APPLE_enum_kind to encode enum_extensibility #124752

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions llvm/include/llvm/AsmParser/LLToken.h
Original file line number Diff line number Diff line change
Expand Up @@ -497,6 +497,7 @@ enum Kind {
DwarfMacinfo, // DW_MACINFO_foo
ChecksumKind, // CSK_foo
DbgRecordType, // dbg_foo
DwarfEnumKind, // DW_APPLE_ENUM_KIND_foo

// Type valued tokens (TyVal).
Type,
Expand Down
14 changes: 13 additions & 1 deletion llvm/include/llvm/BinaryFormat/Dwarf.def
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,8 @@
(defined HANDLE_DW_CFA && defined HANDLE_DW_CFA_PRED) || \
defined HANDLE_DW_APPLE_PROPERTY || defined HANDLE_DW_UT || \
defined HANDLE_DWARF_SECTION || defined HANDLE_DW_IDX || \
defined HANDLE_DW_END || defined HANDLE_DW_SECT)
defined HANDLE_DW_END || defined HANDLE_DW_SECT || \
defined HANDLE_DW_APPLE_ENUM_KIND)
#error "Missing macro definition of HANDLE_DW*"
#endif

Expand Down Expand Up @@ -146,6 +147,10 @@
#define HANDLE_DW_SECT(ID, NAME)
#endif

#ifndef HANDLE_DW_APPLE_ENUM_KIND
#define HANDLE_DW_APPLE_ENUM_KIND(ID, NAME)
#endif

HANDLE_DW_TAG(0x0000, null, 2, DWARF, DW_KIND_NONE)
HANDLE_DW_TAG(0x0001, array_type, 2, DWARF, DW_KIND_TYPE)
HANDLE_DW_TAG(0x0002, class_type, 2, DWARF, DW_KIND_TYPE)
Expand Down Expand Up @@ -638,6 +643,7 @@ HANDLE_DW_AT(0x3fed, APPLE_property, 0, APPLE)
HANDLE_DW_AT(0x3fee, APPLE_objc_direct, 0, APPLE)
HANDLE_DW_AT(0x3fef, APPLE_sdk, 0, APPLE)
HANDLE_DW_AT(0x3ff0, APPLE_origin, 0, APPLE)
HANDLE_DW_AT(0x3ff1, APPLE_enum_kind, 0, APPLE)

// Attribute form encodings.
HANDLE_DW_FORM(0x01, addr, 2, DWARF)
Expand Down Expand Up @@ -1269,6 +1275,11 @@ HANDLE_DW_APPLE_PROPERTY(0x1000, nullability)
HANDLE_DW_APPLE_PROPERTY(0x2000, null_resettable)
HANDLE_DW_APPLE_PROPERTY(0x4000, class)

// Enum kinds.
// Keep in sync with EnumExtensibilityAttr::Kind.
HANDLE_DW_APPLE_ENUM_KIND(0x00, Closed)
HANDLE_DW_APPLE_ENUM_KIND(0x01, Open)

// DWARF v5 Unit Types.
HANDLE_DW_UT(0x01, compile)
HANDLE_DW_UT(0x02, type)
Expand Down Expand Up @@ -1367,3 +1378,4 @@ HANDLE_DW_SECT(8, RNGLISTS)
#undef HANDLE_DW_IDX
#undef HANDLE_DW_END
#undef HANDLE_DW_SECT
#undef HANDLE_DW_APPLE_ENUM_KIND
15 changes: 12 additions & 3 deletions llvm/include/llvm/BinaryFormat/Dwarf.h
Original file line number Diff line number Diff line change
Expand Up @@ -44,9 +44,10 @@ namespace dwarf {
enum LLVMConstants : uint32_t {
/// LLVM mock tags (see also llvm/BinaryFormat/Dwarf.def).
/// \{
DW_TAG_invalid = ~0U, ///< Tag for invalid results.
DW_VIRTUALITY_invalid = ~0U, ///< Virtuality for invalid results.
DW_MACINFO_invalid = ~0U, ///< Macinfo type for invalid results.
DW_TAG_invalid = ~0U, ///< Tag for invalid results.
DW_VIRTUALITY_invalid = ~0U, ///< Virtuality for invalid results.
DW_MACINFO_invalid = ~0U, ///< Macinfo type for invalid results.
DW_APPLE_ENUM_KIND_invalid = ~0U, ///< Enum kind for invalid results.
/// \}

/// Special values for an initial length field.
Expand Down Expand Up @@ -198,6 +199,12 @@ enum VirtualityAttribute {
DW_VIRTUALITY_max = 0x02
};

enum EnumKindAttribute {
#define HANDLE_DW_APPLE_ENUM_KIND(ID, NAME) DW_APPLE_ENUM_KIND_##NAME = ID,
#include "llvm/BinaryFormat/Dwarf.def"
DW_APPLE_ENUM_KIND_max = 0x01
};

enum DefaultedMemberAttribute {
#define HANDLE_DW_DEFAULTED(ID, NAME) DW_DEFAULTED_##NAME = ID,
#include "llvm/BinaryFormat/Dwarf.def"
Expand Down Expand Up @@ -981,6 +988,7 @@ StringRef AccessibilityString(unsigned Access);
StringRef DefaultedMemberString(unsigned DefaultedEncodings);
StringRef VisibilityString(unsigned Visibility);
StringRef VirtualityString(unsigned Virtuality);
StringRef EnumKindString(unsigned EnumKind);
StringRef LanguageString(unsigned Language);
StringRef CaseString(unsigned Case);
StringRef ConventionString(unsigned Convention);
Expand Down Expand Up @@ -1020,6 +1028,7 @@ unsigned getOperationEncoding(StringRef OperationEncodingString);
unsigned getSubOperationEncoding(unsigned OpEncoding,
StringRef SubOperationEncodingString);
unsigned getVirtuality(StringRef VirtualityString);
unsigned getEnumKind(StringRef EnumKindString);
unsigned getLanguage(StringRef LanguageString);
unsigned getCallingConvention(StringRef LanguageString);
unsigned getAttributeEncoding(StringRef EncodingString);
Expand Down
18 changes: 10 additions & 8 deletions llvm/include/llvm/IR/DIBuilder.h
Original file line number Diff line number Diff line change
Expand Up @@ -632,7 +632,8 @@ namespace llvm {
DIScope *Scope, StringRef Name, DIFile *File, unsigned LineNumber,
uint64_t SizeInBits, uint32_t AlignInBits, DINodeArray Elements,
DIType *UnderlyingType, unsigned RunTimeLang = 0,
StringRef UniqueIdentifier = "", bool IsScoped = false);
StringRef UniqueIdentifier = "", bool IsScoped = false,
std::optional<uint32_t> EnumKind = std::nullopt);
/// Create debugging information entry for a set.
/// \param Scope Scope in which this set is defined.
/// \param Name Set name.
Expand Down Expand Up @@ -667,19 +668,20 @@ namespace llvm {
static DIType *createObjectPointerType(DIType *Ty, bool Implicit);

/// Create a permanent forward-declared type.
DICompositeType *createForwardDecl(unsigned Tag, StringRef Name,
DIScope *Scope, DIFile *F, unsigned Line,
unsigned RuntimeLang = 0,
uint64_t SizeInBits = 0,
uint32_t AlignInBits = 0,
StringRef UniqueIdentifier = "");
DICompositeType *
createForwardDecl(unsigned Tag, StringRef Name, DIScope *Scope, DIFile *F,
unsigned Line, unsigned RuntimeLang = 0,
uint64_t SizeInBits = 0, uint32_t AlignInBits = 0,
StringRef UniqueIdentifier = "",
std::optional<uint32_t> EnumKind = std::nullopt);

/// Create a temporary forward-declared type.
DICompositeType *createReplaceableCompositeType(
unsigned Tag, StringRef Name, DIScope *Scope, DIFile *F, unsigned Line,
unsigned RuntimeLang = 0, uint64_t SizeInBits = 0,
uint32_t AlignInBits = 0, DINode::DIFlags Flags = DINode::FlagFwdDecl,
StringRef UniqueIdentifier = "", DINodeArray Annotations = nullptr);
StringRef UniqueIdentifier = "", DINodeArray Annotations = nullptr,
std::optional<uint32_t> EnumKind = std::nullopt);

/// Retain DIScope* in a module even if it is not referenced
/// through debug info anchors.
Expand Down
77 changes: 43 additions & 34 deletions llvm/include/llvm/IR/DebugInfoMetadata.h
Original file line number Diff line number Diff line change
Expand Up @@ -1176,24 +1176,28 @@ class DICompositeType : public DIType {
friend class MDNode;

unsigned RuntimeLang;
std::optional<uint32_t> EnumKind;

DICompositeType(LLVMContext &C, StorageType Storage, unsigned Tag,
unsigned Line, unsigned RuntimeLang, uint64_t SizeInBits,
uint32_t AlignInBits, uint64_t OffsetInBits,
uint32_t NumExtraInhabitants, DIFlags Flags,
uint32_t NumExtraInhabitants,
std::optional<uint32_t> EnumKind, DIFlags Flags,
ArrayRef<Metadata *> Ops)
: DIType(C, DICompositeTypeKind, Storage, Tag, Line, SizeInBits,
AlignInBits, OffsetInBits, NumExtraInhabitants, Flags, Ops),
RuntimeLang(RuntimeLang) {}
RuntimeLang(RuntimeLang), EnumKind(EnumKind) {}
~DICompositeType() = default;

/// Change fields in place.
void mutate(unsigned Tag, unsigned Line, unsigned RuntimeLang,
uint64_t SizeInBits, uint32_t AlignInBits, uint64_t OffsetInBits,
uint32_t NumExtraInhabitants, DIFlags Flags) {
uint32_t NumExtraInhabitants, std::optional<uint32_t> EnumKind,
DIFlags Flags) {
assert(isDistinct() && "Only distinct nodes can mutate");
assert(getRawIdentifier() && "Only ODR-uniqued nodes should mutate");
this->RuntimeLang = RuntimeLang;
this->EnumKind = EnumKind;
DIType::mutate(Tag, Line, SizeInBits, AlignInBits, OffsetInBits,
NumExtraInhabitants, Flags);
}
Expand All @@ -1203,15 +1207,15 @@ class DICompositeType : public DIType {
unsigned Line, DIScope *Scope, DIType *BaseType, uint64_t SizeInBits,
uint32_t AlignInBits, uint64_t OffsetInBits, DIType *Specification,
uint32_t NumExtraInhabitants, DIFlags Flags, DINodeArray Elements,
unsigned RuntimeLang, DIType *VTableHolder,
DITemplateParameterArray TemplateParams, StringRef Identifier,
DIDerivedType *Discriminator, Metadata *DataLocation,
Metadata *Associated, Metadata *Allocated, Metadata *Rank,
DINodeArray Annotations, StorageType Storage,
unsigned RuntimeLang, std::optional<uint32_t> EnumKind,
DIType *VTableHolder, DITemplateParameterArray TemplateParams,
StringRef Identifier, DIDerivedType *Discriminator,
Metadata *DataLocation, Metadata *Associated, Metadata *Allocated,
Metadata *Rank, DINodeArray Annotations, StorageType Storage,
bool ShouldCreate = true) {
return getImpl(Context, Tag, getCanonicalMDString(Context, Name), File,
Line, Scope, BaseType, SizeInBits, AlignInBits, OffsetInBits,
Flags, Elements.get(), RuntimeLang, VTableHolder,
Flags, Elements.get(), RuntimeLang, EnumKind, VTableHolder,
TemplateParams.get(),
getCanonicalMDString(Context, Identifier), Discriminator,
DataLocation, Associated, Allocated, Rank, Annotations.get(),
Expand All @@ -1222,21 +1226,21 @@ class DICompositeType : public DIType {
unsigned Line, Metadata *Scope, Metadata *BaseType,
uint64_t SizeInBits, uint32_t AlignInBits, uint64_t OffsetInBits,
DIFlags Flags, Metadata *Elements, unsigned RuntimeLang,
Metadata *VTableHolder, Metadata *TemplateParams,
MDString *Identifier, Metadata *Discriminator, Metadata *DataLocation,
Metadata *Associated, Metadata *Allocated, Metadata *Rank,
Metadata *Annotations, Metadata *Specification,
uint32_t NumExtraInhabitants, StorageType Storage,
bool ShouldCreate = true);
std::optional<uint32_t> EnumKind, Metadata *VTableHolder,
Metadata *TemplateParams, MDString *Identifier,
Metadata *Discriminator, Metadata *DataLocation, Metadata *Associated,
Metadata *Allocated, Metadata *Rank, Metadata *Annotations,
Metadata *Specification, uint32_t NumExtraInhabitants,
StorageType Storage, bool ShouldCreate = true);

TempDICompositeType cloneImpl() const {
return getTemporary(
getContext(), getTag(), getName(), getFile(), getLine(), getScope(),
getBaseType(), getSizeInBits(), getAlignInBits(), getOffsetInBits(),
getFlags(), getElements(), getRuntimeLang(), getVTableHolder(),
getTemplateParams(), getIdentifier(), getDiscriminator(),
getRawDataLocation(), getRawAssociated(), getRawAllocated(),
getRawRank(), getAnnotations(), getSpecification(),
getFlags(), getElements(), getRuntimeLang(), getEnumKind(),
getVTableHolder(), getTemplateParams(), getIdentifier(),
getDiscriminator(), getRawDataLocation(), getRawAssociated(),
getRawAllocated(), getRawRank(), getAnnotations(), getSpecification(),
getNumExtraInhabitants());
}

Expand All @@ -1246,7 +1250,8 @@ class DICompositeType : public DIType {
(unsigned Tag, StringRef Name, DIFile *File, unsigned Line,
DIScope *Scope, DIType *BaseType, uint64_t SizeInBits,
uint32_t AlignInBits, uint64_t OffsetInBits, DIFlags Flags,
DINodeArray Elements, unsigned RuntimeLang, DIType *VTableHolder,
DINodeArray Elements, unsigned RuntimeLang,
std::optional<uint32_t> EnumKind, DIType *VTableHolder,
DITemplateParameterArray TemplateParams = nullptr,
StringRef Identifier = "", DIDerivedType *Discriminator = nullptr,
Metadata *DataLocation = nullptr, Metadata *Associated = nullptr,
Expand All @@ -1255,23 +1260,24 @@ class DICompositeType : public DIType {
uint32_t NumExtraInhabitants = 0),
(Tag, Name, File, Line, Scope, BaseType, SizeInBits, AlignInBits,
OffsetInBits, Specification, NumExtraInhabitants, Flags, Elements,
RuntimeLang, VTableHolder, TemplateParams, Identifier, Discriminator,
DataLocation, Associated, Allocated, Rank, Annotations))
RuntimeLang, EnumKind, VTableHolder, TemplateParams, Identifier,
Discriminator, DataLocation, Associated, Allocated, Rank, Annotations))
DEFINE_MDNODE_GET(
DICompositeType,
(unsigned Tag, MDString *Name, Metadata *File, unsigned Line,
Metadata *Scope, Metadata *BaseType, uint64_t SizeInBits,
uint32_t AlignInBits, uint64_t OffsetInBits, DIFlags Flags,
Metadata *Elements, unsigned RuntimeLang, Metadata *VTableHolder,
Metadata *Elements, unsigned RuntimeLang,
std::optional<uint32_t> EnumKind, Metadata *VTableHolder,
Metadata *TemplateParams = nullptr, MDString *Identifier = nullptr,
Metadata *Discriminator = nullptr, Metadata *DataLocation = nullptr,
Metadata *Associated = nullptr, Metadata *Allocated = nullptr,
Metadata *Rank = nullptr, Metadata *Annotations = nullptr,
Metadata *Specification = nullptr, uint32_t NumExtraInhabitants = 0),
(Tag, Name, File, Line, Scope, BaseType, SizeInBits, AlignInBits,
OffsetInBits, Flags, Elements, RuntimeLang, VTableHolder, TemplateParams,
Identifier, Discriminator, DataLocation, Associated, Allocated, Rank,
Annotations, Specification, NumExtraInhabitants))
OffsetInBits, Flags, Elements, RuntimeLang, EnumKind, VTableHolder,
TemplateParams, Identifier, Discriminator, DataLocation, Associated,
Allocated, Rank, Annotations, Specification, NumExtraInhabitants))

TempDICompositeType clone() const { return cloneImpl(); }

Expand All @@ -1288,10 +1294,11 @@ class DICompositeType : public DIType {
Metadata *BaseType, uint64_t SizeInBits, uint32_t AlignInBits,
uint64_t OffsetInBits, Metadata *Specification,
uint32_t NumExtraInhabitants, DIFlags Flags, Metadata *Elements,
unsigned RuntimeLang, Metadata *VTableHolder,
Metadata *TemplateParams, Metadata *Discriminator,
Metadata *DataLocation, Metadata *Associated, Metadata *Allocated,
Metadata *Rank, Metadata *Annotations);
unsigned RuntimeLang, std::optional<uint32_t> EnumKind,
Metadata *VTableHolder, Metadata *TemplateParams,
Metadata *Discriminator, Metadata *DataLocation,
Metadata *Associated, Metadata *Allocated, Metadata *Rank,
Metadata *Annotations);
static DICompositeType *getODRTypeIfExists(LLVMContext &Context,
MDString &Identifier);

Expand All @@ -1310,10 +1317,11 @@ class DICompositeType : public DIType {
Metadata *BaseType, uint64_t SizeInBits, uint32_t AlignInBits,
uint64_t OffsetInBits, Metadata *Specification,
uint32_t NumExtraInhabitants, DIFlags Flags, Metadata *Elements,
unsigned RuntimeLang, Metadata *VTableHolder,
Metadata *TemplateParams, Metadata *Discriminator,
Metadata *DataLocation, Metadata *Associated,
Metadata *Allocated, Metadata *Rank, Metadata *Annotations);
unsigned RuntimeLang, std::optional<uint32_t> EnumKind,
Metadata *VTableHolder, Metadata *TemplateParams,
Metadata *Discriminator, Metadata *DataLocation,
Metadata *Associated, Metadata *Allocated, Metadata *Rank,
Metadata *Annotations);

DIType *getBaseType() const { return cast_or_null<DIType>(getRawBaseType()); }
DINodeArray getElements() const {
Expand All @@ -1327,6 +1335,7 @@ class DICompositeType : public DIType {
}
StringRef getIdentifier() const { return getStringOperand(7); }
unsigned getRuntimeLang() const { return RuntimeLang; }
std::optional<uint32_t> getEnumKind() const { return EnumKind; }

Metadata *getRawBaseType() const { return getOperand(3); }
Metadata *getRawElements() const { return getOperand(4); }
Expand Down
1 change: 1 addition & 0 deletions llvm/lib/AsmParser/LLLexer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -975,6 +975,7 @@ lltok::Kind LLLexer::LexIdentifier() {
DWKEYWORD(CC, DwarfCC);
DWKEYWORD(OP, DwarfOp);
DWKEYWORD(MACINFO, DwarfMacinfo);
DWKEYWORD(APPLE_ENUM_KIND, DwarfEnumKind);

#undef DWKEYWORD

Expand Down
43 changes: 37 additions & 6 deletions llvm/lib/AsmParser/LLParser.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -4697,6 +4697,12 @@ struct DwarfCCField : public MDUnsignedField {
DwarfCCField() : MDUnsignedField(0, dwarf::DW_CC_hi_user) {}
};

struct DwarfEnumKindField : public MDUnsignedField {
DwarfEnumKindField()
: MDUnsignedField(dwarf::DW_APPLE_ENUM_KIND_invalid,
dwarf::DW_APPLE_ENUM_KIND_max) {}
};

struct EmissionKindField : public MDUnsignedField {
EmissionKindField() : MDUnsignedField(0, DICompileUnit::LastEmissionKind) {}
};
Expand Down Expand Up @@ -4870,6 +4876,25 @@ bool LLParser::parseMDField(LocTy Loc, StringRef Name,
return false;
}

template <>
bool LLParser::parseMDField(LocTy Loc, StringRef Name,
DwarfEnumKindField &Result) {
if (Lex.getKind() == lltok::APSInt)
return parseMDField(Loc, Name, static_cast<MDUnsignedField &>(Result));

if (Lex.getKind() != lltok::DwarfEnumKind)
return tokError("expected DWARF enum kind code");

unsigned EnumKind = dwarf::getEnumKind(Lex.getStrVal());
if (EnumKind == dwarf::DW_APPLE_ENUM_KIND_invalid)
return tokError("invalid DWARF enum kind code" + Twine(" '") +
Lex.getStrVal() + "'");
assert(EnumKind <= Result.Max && "Expected valid DWARF enum kind code");
Result.assign(EnumKind);
Lex.Lex();
return false;
}

template <>
bool LLParser::parseMDField(LocTy Loc, StringRef Name, DwarfLangField &Result) {
if (Lex.getKind() == lltok::APSInt)
Expand Down Expand Up @@ -5489,6 +5514,7 @@ bool LLParser::parseDICompositeType(MDNode *&Result, bool IsDistinct) {
OPTIONAL(flags, DIFlagField, ); \
OPTIONAL(elements, MDField, ); \
OPTIONAL(runtimeLang, DwarfLangField, ); \
OPTIONAL(enumKind, DwarfEnumKindField, ); \
OPTIONAL(vtableHolder, MDField, ); \
OPTIONAL(templateParams, MDField, ); \
OPTIONAL(identifier, MDStringField, ); \
Expand All @@ -5510,15 +5536,19 @@ bool LLParser::parseDICompositeType(MDNode *&Result, bool IsDistinct) {
else if (rank.isMDField())
Rank = rank.getMDFieldValue();

std::optional<unsigned> EnumKind;
if (enumKind.Val != dwarf::DW_APPLE_ENUM_KIND_invalid)
EnumKind = enumKind.Val;

// If this has an identifier try to build an ODR type.
if (identifier.Val)
if (auto *CT = DICompositeType::buildODRType(
Context, *identifier.Val, tag.Val, name.Val, file.Val, line.Val,
scope.Val, baseType.Val, size.Val, align.Val, offset.Val,
specification.Val, num_extra_inhabitants.Val, flags.Val,
elements.Val, runtimeLang.Val, vtableHolder.Val, templateParams.Val,
discriminator.Val, dataLocation.Val, associated.Val, allocated.Val,
Rank, annotations.Val)) {
elements.Val, runtimeLang.Val, EnumKind, vtableHolder.Val,
templateParams.Val, discriminator.Val, dataLocation.Val,
associated.Val, allocated.Val, Rank, annotations.Val)) {
Result = CT;
return false;
}
Expand All @@ -5529,9 +5559,10 @@ bool LLParser::parseDICompositeType(MDNode *&Result, bool IsDistinct) {
DICompositeType,
(Context, tag.Val, name.Val, file.Val, line.Val, scope.Val, baseType.Val,
size.Val, align.Val, offset.Val, flags.Val, elements.Val,
runtimeLang.Val, vtableHolder.Val, templateParams.Val, identifier.Val,
discriminator.Val, dataLocation.Val, associated.Val, allocated.Val, Rank,
annotations.Val, specification.Val, num_extra_inhabitants.Val));
runtimeLang.Val, EnumKind, vtableHolder.Val, templateParams.Val,
identifier.Val, discriminator.Val, dataLocation.Val, associated.Val,
allocated.Val, Rank, annotations.Val, specification.Val,
num_extra_inhabitants.Val));
return false;
}

Expand Down
Loading