return lowerTypeModifier(cast<DIDerivedType>(Ty));
case dwarf::DW_TAG_subroutine_type:
return lowerTypeFunction(cast<DISubroutineType>(Ty));
+ case dwarf::DW_TAG_enumeration_type:
+ return lowerTypeEnum(cast<DICompositeType>(Ty));
case dwarf::DW_TAG_class_type:
case dwarf::DW_TAG_structure_type:
return lowerTypeClass(cast<DICompositeType>(Ty));
: ClassOptions::None;
}
+TypeIndex CodeViewDebug::lowerTypeEnum(const DICompositeType *Ty) {
+ ClassOptions CO = ClassOptions::None | getRecordUniqueNameOption(Ty);
+ TypeIndex FTI;
+ unsigned FieldCount = 0;
+
+ if (Ty->isForwardDecl())
+ CO |= ClassOptions::ForwardReference;
+ else
+ std::tie(FTI, FieldCount) = lowerRecordFieldList(Ty);
+
+ return TypeTable.writeEnum(EnumRecord(FieldCount, CO, FTI, Ty->getName(),
+ Ty->getIdentifier(),
+ getTypeIndex(Ty->getBaseType())));
+}
+
TypeIndex CodeViewDebug::lowerTypeClass(const DICompositeType *Ty) {
// First, construct the forward decl. Don't look into Ty to compute the
// forward decl options, since it might not be available in all TUs.
}
// FIXME: Get clang to emit nested types here and do something with
// them.
+ } else if (auto *Enumerator = dyn_cast<DIEnumerator>(Element)) {
+ Fields.writeEnumerator(EnumeratorRecord(
+ MemberAccess::Public, APSInt::getUnsigned(Enumerator->getValue()),
+ Enumerator->getName()));
}
// Skip other unrecognized kinds of elements.
}
--- /dev/null
+; RUN: llc < %s -filetype=obj | llvm-readobj - -codeview | FileCheck %s
+
+; Generated from the following C++ source:
+; enum E : int { BLAH };
+; E e;
+
+; CHECK: CodeViewTypes [
+; CHECK: UnknownLeaf (0x1000) {
+; CHECK-NEXT: TypeLeafKind: LF_FIELDLIST (0x1203)
+; CHECK-NEXT: Enumerator {
+; CHECK-NEXT: AccessSpecifier: Public (0x3)
+; CHECK-NEXT: EnumValue: 0
+; CHECK-NEXT: Name: BLAH
+; CHECK-NEXT: }
+; CHECK-NEXT: }
+; CHECK-NEXT: Enum (0x1001) {
+; CHECK-NEXT: TypeLeafKind: LF_ENUM (0x1507)
+; CHECK-NEXT: NumEnumerators: 0
+; CHECK-NEXT: Properties [ (0x0)
+; CHECK-NEXT: ]
+; CHECK-NEXT: UnderlyingType: int (0x74)
+; CHECK-NEXT: FieldListType: BLAH (0x1000)
+; CHECK-NEXT: Name: E
+; CHECK-NEXT: }
+
+target datalayout = "e-m:x-p:32:32-i64:64-f80:32-n8:16:32-a:0:32-S32"
+target triple = "i686-pc-windows-msvc18.0.0"
+
+@"\01?e@@3W4E@@A" = global i32 0, align 4
+
+!llvm.dbg.cu = !{!0}
+!llvm.module.flags = !{!10, !11}
+!llvm.ident = !{!12}
+
+!0 = distinct !DICompileUnit(language: DW_LANG_C_plus_plus, file: !1, producer: "clang version 3.9.0 (trunk 272790) (llvm/trunk 272813)", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug, enums: !2, globals: !8)
+!1 = !DIFile(filename: "-", directory: "/")
+!2 = !{!3}
+!3 = !DICompositeType(tag: DW_TAG_enumeration_type, name: "E", file: !4, line: 1, baseType: !5, size: 32, align: 32, elements: !6)
+!4 = !DIFile(filename: "<stdin>", directory: "/")
+!5 = !DIBasicType(name: "int", size: 32, align: 32, encoding: DW_ATE_signed)
+!6 = !{!7}
+!7 = !DIEnumerator(name: "BLAH", value: 0)
+!8 = !{!9}
+!9 = distinct !DIGlobalVariable(name: "e", linkageName: "\01?e@@3W4E@@A", scope: !0, file: !4, line: 2, type: !3, isLocal: false, isDefinition: true, variable: i32* @"\01?e@@3W4E@@A")
+!10 = !{i32 2, !"CodeView", i32 1}
+!11 = !{i32 2, !"Debug Info Version", i32 3}
+!12 = !{!"clang version 3.9.0 (trunk 272790) (llvm/trunk 272813)"}