39#define DEBUG_TYPE "dwarfdebug"
45void DIEDwarfExpression::emitOp(uint8_t
Op,
const char* Comment) {
46 CU.addUInt(getActiveDIE(), dwarf::DW_FORM_data1,
Op);
49void DIEDwarfExpression::emitSigned(int64_t
Value) {
50 CU.addSInt(getActiveDIE(), dwarf::DW_FORM_sdata,
Value);
54 CU.addUInt(getActiveDIE(), dwarf::DW_FORM_udata,
Value);
57void DIEDwarfExpression::emitData1(uint8_t
Value) {
58 CU.addUInt(getActiveDIE(), dwarf::DW_FORM_data1,
Value);
61void DIEDwarfExpression::emitBaseTypeRef(
uint64_t Idx) {
62 CU.addBaseTypeRef(getActiveDIE(),
Idx);
65void DIEDwarfExpression::enableTemporaryBuffer() {
66 assert(!IsBuffering &&
"Already buffering?");
70void DIEDwarfExpression::disableTemporaryBuffer() { IsBuffering =
false; }
72unsigned DIEDwarfExpression::getTemporaryBufferSize() {
76void DIEDwarfExpression::commitTemporaryBuffer() { OutDIE.
takeValues(TmpDIE); }
80 return MachineReg ==
TRI.getFrameRegister(*AP.
MF);
85 :
DIEUnit(UnitTag), CUNode(Node), Asm(
A), DD(DW), DU(DWU) {}
91 SplitLineTable(SplitLineTable) {
101int64_t DwarfUnit::getDefaultLowerBound()
const {
107 case dwarf::DW_LANG_C:
108 case dwarf::DW_LANG_C89:
109 case dwarf::DW_LANG_C_plus_plus:
112 case dwarf::DW_LANG_Fortran77:
113 case dwarf::DW_LANG_Fortran90:
117 case dwarf::DW_LANG_C99:
118 case dwarf::DW_LANG_ObjC:
119 case dwarf::DW_LANG_ObjC_plus_plus:
124 case dwarf::DW_LANG_Fortran95:
130 case dwarf::DW_LANG_D:
131 case dwarf::DW_LANG_Java:
132 case dwarf::DW_LANG_Python:
133 case dwarf::DW_LANG_UPC:
138 case dwarf::DW_LANG_Ada83:
139 case dwarf::DW_LANG_Ada95:
140 case dwarf::DW_LANG_Cobol74:
141 case dwarf::DW_LANG_Cobol85:
142 case dwarf::DW_LANG_Modula2:
143 case dwarf::DW_LANG_Pascal83:
144 case dwarf::DW_LANG_PLI:
150 case dwarf::DW_LANG_BLISS:
151 case dwarf::DW_LANG_C11:
152 case dwarf::DW_LANG_C_plus_plus_03:
153 case dwarf::DW_LANG_C_plus_plus_11:
154 case dwarf::DW_LANG_C_plus_plus_14:
155 case dwarf::DW_LANG_Dylan:
156 case dwarf::DW_LANG_Go:
157 case dwarf::DW_LANG_Haskell:
158 case dwarf::DW_LANG_OCaml:
159 case dwarf::DW_LANG_OpenCL:
160 case dwarf::DW_LANG_RenderScript:
161 case dwarf::DW_LANG_Rust:
162 case dwarf::DW_LANG_Swift:
167 case dwarf::DW_LANG_Fortran03:
168 case dwarf::DW_LANG_Fortran08:
169 case dwarf::DW_LANG_Julia:
170 case dwarf::DW_LANG_Modula3:
190 return (isa<DIType>(
D) ||
191 (isa<DISubprogram>(
D) && !cast<DISubprogram>(
D)->isDefinition())) &&
224 assert(
Form != dwarf::DW_FORM_implicit_const &&
225 "DW_FORM_implicit_const is used only for signed integers");
235 std::optional<dwarf::Form>
Form, int64_t
Integer) {
258 isDwoUnit() ? dwarf::DW_FORM_GNU_str_index : dwarf::DW_FORM_strp;
260 auto StringPoolEntry =
267 IxForm = dwarf::DW_FORM_strx1;
269 if (
Index > 0xffffff)
270 IxForm = dwarf::DW_FORM_strx4;
271 else if (
Index > 0xffff)
272 IxForm = dwarf::DW_FORM_strx3;
273 else if (
Index > 0xff)
274 IxForm = dwarf::DW_FORM_strx2;
293unsigned DwarfTypeUnit::getOrCreateSourceID(
const DIFile *File) {
296 if (!UsedLineTable) {
297 UsedLineTable =
true;
301 return SplitLineTable->
getFile(
307 bool UseAddrOffsetFormOrExpressions =
311 if (Label->isInSection() && UseAddrOffsetFormOrExpressions)
317 addUInt(Die, dwarf::DW_FORM_data1, dwarf::DW_OP_addrx);
320 addUInt(Die, dwarf::DW_FORM_data1, dwarf::DW_OP_GNU_addr_index);
325 addUInt(Die, dwarf::DW_FORM_data1, dwarf::DW_OP_const4u);
327 addUInt(Die, dwarf::DW_FORM_data1, dwarf::DW_OP_plus);
342 addUInt(Die, dwarf::DW_FORM_data1, dwarf::DW_OP_addr);
361 addFlag(Die, dwarf::DW_AT_declaration);
363 addAttribute(Die, dwarf::DW_AT_signature, dwarf::DW_FORM_ref_sig8,
370 const DIEUnit *EntryCU = Entry.getEntry().getUnit();
379 EntryCU ==
CU ? dwarf::DW_FORM_ref4 : dwarf::DW_FORM_ref_addr,
413 addUInt(Die, dwarf::DW_AT_decl_file, std::nullopt, FileID);
414 addUInt(Die, dwarf::DW_AT_decl_line, std::nullopt, Line);
470 addUInt(Die, dwarf::DW_AT_const_value,
471 Unsigned ? dwarf::DW_FORM_udata : dwarf::DW_FORM_sdata, Val);
480 if (CIBitWidth <= 64) {
495 for (
int i = 0; i < NumBytes; i++) {
498 c = Ptr64[i / 8] >> (8 * (i & 7));
500 c = Ptr64[(NumBytes - 1 - i) / 8] >> (8 * ((NumBytes - 1 - i) & 7));
511 : dwarf::DW_AT_MIPS_linkage_name,
517 for (
const auto *Element : TParams) {
518 if (
auto *TTP = dyn_cast<DITemplateTypeParameter>(Element))
519 constructTemplateTypeParameterDIE(Buffer, TTP);
520 else if (
auto *TVP = dyn_cast<DITemplateValueParameter>(Element))
521 constructTemplateValueParameterDIE(Buffer, TVP);
527 for (
const auto *Ty : ThrownTypes) {
535 addUInt(Die, dwarf::DW_AT_accessibility, dwarf::DW_FORM_data1,
538 addUInt(Die, dwarf::DW_AT_accessibility, dwarf::DW_FORM_data1,
541 addUInt(Die, dwarf::DW_AT_accessibility, dwarf::DW_FORM_data1,
548 if (
auto *
T = dyn_cast<DIType>(
Context))
550 if (
auto *NS = dyn_cast<DINamespace>(
Context))
552 if (
auto *SP = dyn_cast<DISubprogram>(
Context))
554 if (
auto *M = dyn_cast<DIModule>(
Context))
571 updateAcceleratorTables(
Context, Ty, TyDIE);
580 updateAcceleratorTables(
Context, Ty, TyDIE);
582 if (
auto *
BT = dyn_cast<DIBasicType>(Ty))
584 else if (
auto *ST = dyn_cast<DIStringType>(Ty))
586 else if (
auto *STy = dyn_cast<DISubroutineType>(Ty))
588 else if (
auto *CTy = dyn_cast<DICompositeType>(Ty)) {
590 (Ty->
getRawName() || CTy->getRawIdentifier())) {
592 if (
MDString *TypeId = CTy->getRawIdentifier())
595 finishNonUnitTypeDIE(TyDIE, CTy);
610 auto *Ty = cast<DIType>(TyNode);
622 auto *
Context = Ty->getScope();
633void DwarfUnit::updateAcceleratorTables(
const DIScope *Context,
636 bool IsImplementation =
false;
637 if (
auto *CT = dyn_cast<DICompositeType>(Ty)) {
640 IsImplementation = CT->getRuntimeLang() == 0 || CT->isObjcClassComplete();
645 if (!Context || isa<DICompileUnit>(Context) || isa<DIFile>(Context) ||
646 isa<DINamespace>(Context) || isa<DICommonBlock>(Context))
653 assert(Ty &&
"Trying to add a type that doesn't exist?");
667 while (!isa<DICompileUnit>(
Context)) {
681 if (
Name.empty() && isa<DINamespace>(Ctx))
682 Name =
"(anonymous namespace)";
699 if (BTy->
getTag() == dwarf::DW_TAG_unspecified_type)
702 if (BTy->
getTag() != dwarf::DW_TAG_string_type)
703 addUInt(Buffer, dwarf::DW_AT_encoding, dwarf::DW_FORM_data1,
707 addUInt(Buffer, dwarf::DW_AT_byte_size, std::nullopt,
Size);
710 addUInt(Buffer, dwarf::DW_AT_endianity, std::nullopt, dwarf::DW_END_big);
712 addUInt(Buffer, dwarf::DW_AT_endianity, std::nullopt, dwarf::DW_END_little);
723 if (
auto *VarDIE =
getDIE(Var))
724 addDIEEntry(Buffer, dwarf::DW_AT_string_length, *VarDIE);
731 DwarfExpr.setMemoryLocationKind();
732 DwarfExpr.addExpression(Expr);
733 addBlock(Buffer, dwarf::DW_AT_string_length, DwarfExpr.finalize());
736 addUInt(Buffer, dwarf::DW_AT_byte_size, std::nullopt,
Size);
744 DwarfExpr.setMemoryLocationKind();
745 DwarfExpr.addExpression(Expr);
746 addBlock(Buffer, dwarf::DW_AT_data_location, DwarfExpr.finalize());
751 addUInt(Buffer, dwarf::DW_AT_encoding, dwarf::DW_FORM_data1,
763 const DIType *FromTy = DTy->getBaseType();
777 if (AlignInBytes > 0)
778 addUInt(Buffer, dwarf::DW_AT_alignment, dwarf::DW_FORM_udata,
783 if (
Size &&
Tag != dwarf::DW_TAG_pointer_type
784 &&
Tag != dwarf::DW_TAG_ptr_to_member_type
785 &&
Tag != dwarf::DW_TAG_reference_type
786 &&
Tag != dwarf::DW_TAG_rvalue_reference_type)
787 addUInt(Buffer, dwarf::DW_AT_byte_size, std::nullopt,
Size);
789 if (
Tag == dwarf::DW_TAG_ptr_to_member_type)
802 if (DTy->getDWARFAddressSpace())
803 addUInt(Buffer, dwarf::DW_AT_address_class, dwarf::DW_FORM_data4,
804 *DTy->getDWARFAddressSpace());
808 for (
unsigned i = 1,
N = Args.size(); i <
N; ++i) {
809 const DIType *Ty = Args[i];
811 assert(i ==
N-1 &&
"Unspecified parameter must be the last argument");
817 addFlag(Arg, dwarf::DW_AT_artificial);
824 auto Elements = cast<DISubroutineType>(CTy)->getTypeArray();
826 if (
auto RTy = Elements[0])
829 bool isPrototyped =
true;
830 if (Elements.size() == 2 && !Elements[1])
831 isPrototyped =
false;
838 addFlag(Buffer, dwarf::DW_AT_prototyped);
841 if (CTy->
getCC() && CTy->
getCC() != dwarf::DW_CC_normal)
842 addUInt(Buffer, dwarf::DW_AT_calling_convention, dwarf::DW_FORM_data1,
846 addFlag(Buffer, dwarf::DW_AT_reference);
849 addFlag(Buffer, dwarf::DW_AT_rvalue_reference);
857 const MDNode *MD = cast<MDNode>(Annotation);
862 addString(AnnotationDie, dwarf::DW_AT_name,
Name->getString());
863 if (
const auto *
Data = dyn_cast<MDString>(
Value))
864 addString(AnnotationDie, dwarf::DW_AT_const_value,
Data->getString());
865 else if (
const auto *
Data = dyn_cast<ConstantAsMetadata>(
Value))
869 assert(
false &&
"Unsupported annotation value type");
881 case dwarf::DW_TAG_array_type:
882 constructArrayTypeDIE(Buffer, CTy);
884 case dwarf::DW_TAG_enumeration_type:
885 constructEnumTypeDIE(Buffer, CTy);
887 case dwarf::DW_TAG_variant_part:
888 case dwarf::DW_TAG_structure_type:
889 case dwarf::DW_TAG_union_type:
890 case dwarf::DW_TAG_class_type:
891 case dwarf::DW_TAG_namelist: {
894 if (
Tag == dwarf::DW_TAG_variant_part) {
901 DIE &DiscMember = constructMemberDIE(Buffer, Discriminator);
902 addDIEEntry(Buffer, dwarf::DW_AT_discr, DiscMember);
907 if (
Tag == dwarf::DW_TAG_class_type ||
908 Tag == dwarf::DW_TAG_structure_type ||
Tag == dwarf::DW_TAG_union_type)
913 for (
const auto *Element : Elements) {
916 if (
auto *SP = dyn_cast<DISubprogram>(Element))
918 else if (
auto *DDTy = dyn_cast<DIDerivedType>(Element)) {
919 if (DDTy->getTag() == dwarf::DW_TAG_friend) {
921 addType(ElemDie, DDTy->getBaseType(), dwarf::DW_AT_friend);
922 }
else if (DDTy->isStaticMember()) {
924 }
else if (
Tag == dwarf::DW_TAG_variant_part) {
929 dyn_cast_or_null<ConstantInt>(DDTy->getDiscriminantValue())) {
931 addUInt(Variant, dwarf::DW_AT_discr_value, std::nullopt,
934 addSInt(Variant, dwarf::DW_AT_discr_value, std::nullopt,
937 constructMemberDIE(Variant, DDTy);
939 constructMemberDIE(Buffer, DDTy);
941 }
else if (
auto *Property = dyn_cast<DIObjCProperty>(Element)) {
943 StringRef PropertyName = Property->getName();
944 addString(ElemDie, dwarf::DW_AT_APPLE_property_name, PropertyName);
945 if (Property->getType())
946 addType(ElemDie, Property->getType());
948 StringRef GetterName = Property->getGetterName();
949 if (!GetterName.
empty())
950 addString(ElemDie, dwarf::DW_AT_APPLE_property_getter, GetterName);
951 StringRef SetterName = Property->getSetterName();
952 if (!SetterName.
empty())
953 addString(ElemDie, dwarf::DW_AT_APPLE_property_setter, SetterName);
954 if (
unsigned PropertyAttributes = Property->getAttributes())
955 addUInt(ElemDie, dwarf::DW_AT_APPLE_property_attribute, std::nullopt,
957 }
else if (
auto *Composite = dyn_cast<DICompositeType>(Element)) {
958 if (Composite->getTag() == dwarf::DW_TAG_variant_part) {
962 }
else if (
Tag == dwarf::DW_TAG_namelist) {
963 auto *Var = dyn_cast<DINode>(Element);
964 auto *VarDIE =
getDIE(Var);
967 addDIEEntry(ItemDie, dwarf::DW_AT_namelist_item, *VarDIE);
973 addFlag(Buffer, dwarf::DW_AT_APPLE_block);
976 addFlag(Buffer, dwarf::DW_AT_export_symbols);
987 addFlag(Buffer, dwarf::DW_AT_APPLE_objc_complete_type);
994 CC = dwarf::DW_CC_pass_by_value;
996 CC = dwarf::DW_CC_pass_by_reference;
998 addUInt(Buffer, dwarf::DW_AT_calling_convention, dwarf::DW_FORM_data1,
1013 if (
Tag == dwarf::DW_TAG_enumeration_type ||
1014 Tag == dwarf::DW_TAG_class_type ||
Tag == dwarf::DW_TAG_structure_type ||
1015 Tag == dwarf::DW_TAG_union_type) {
1021 addUInt(Buffer, dwarf::DW_AT_byte_size, std::nullopt,
Size);
1024 addUInt(Buffer, dwarf::DW_AT_byte_size, std::nullopt, 0);
1028 addFlag(Buffer, dwarf::DW_AT_declaration);
1040 addUInt(Buffer, dwarf::DW_AT_APPLE_runtime_class, dwarf::DW_FORM_data1,
1045 addUInt(Buffer, dwarf::DW_AT_alignment, dwarf::DW_FORM_udata,
1050void DwarfUnit::constructTemplateTypeParameterDIE(
1059 if (TP->
isDefault() && isCompatibleWithVersion(5))
1060 addFlag(ParamDIE, dwarf::DW_AT_default_value);
1063void DwarfUnit::constructTemplateValueParameterDIE(
1069 if (VP->
getTag() == dwarf::DW_TAG_template_value_parameter)
1073 if (VP->
isDefault() && isCompatibleWithVersion(5))
1074 addFlag(ParamDIE, dwarf::DW_AT_default_value);
1076 if (
ConstantInt *CI = mdconst::dyn_extract<ConstantInt>(Val))
1078 else if (
GlobalValue *GV = mdconst::dyn_extract<GlobalValue>(Val)) {
1081 if (!GV->hasDLLImportStorageClass()) {
1088 addUInt(*Loc, dwarf::DW_FORM_data1, dwarf::DW_OP_stack_value);
1089 addBlock(ParamDIE, dwarf::DW_AT_location, Loc);
1091 }
else if (VP->
getTag() == dwarf::DW_TAG_GNU_template_template_param) {
1092 assert(isa<MDString>(Val));
1093 addString(ParamDIE, dwarf::DW_AT_GNU_template_name,
1094 cast<MDString>(Val)->getString());
1095 }
else if (VP->
getTag() == dwarf::DW_TAG_GNU_template_parameter_pack) {
1114 Name =
"(anonymous namespace)";
1118 addFlag(NDie, dwarf::DW_AT_export_symbols);
1131 if (!M->getName().empty()) {
1132 addString(MDie, dwarf::DW_AT_name, M->getName());
1135 if (!M->getConfigurationMacros().empty())
1136 addString(MDie, dwarf::DW_AT_LLVM_config_macros,
1137 M->getConfigurationMacros());
1138 if (!M->getIncludePath().empty())
1139 addString(MDie, dwarf::DW_AT_LLVM_include_path, M->getIncludePath());
1140 if (!M->getAPINotesFile().empty())
1141 addString(MDie, dwarf::DW_AT_LLVM_apinotes, M->getAPINotesFile());
1143 addUInt(MDie, dwarf::DW_AT_decl_file, std::nullopt,
1146 addUInt(MDie, dwarf::DW_AT_decl_line, std::nullopt, M->getLineNo());
1148 addFlag(MDie, dwarf::DW_AT_declaration);
1163 if (
auto *SPDecl = SP->getDeclaration()) {
1177 if (SP->isDefinition())
1186 DIE &SPDie,
bool Minimal) {
1187 DIE *DeclDie =
nullptr;
1189 if (
auto *SPDecl = SP->getDeclaration()) {
1192 DeclArgs = SPDecl->getType()->getTypeArray();
1193 DefinitionArgs = SP->getType()->getTypeArray();
1195 if (DeclArgs.
size() && DefinitionArgs.
size())
1196 if (DefinitionArgs[0] !=
nullptr && DeclArgs[0] != DefinitionArgs[0])
1197 addType(SPDie, DefinitionArgs[0]);
1199 DeclDie =
getDIE(SPDecl);
1200 assert(DeclDie &&
"This DIE should've already been constructed when the "
1201 "definition DIE was created in "
1202 "getOrCreateSubprogramDIE");
1205 DeclLinkageName = SPDecl->getLinkageName();
1208 if (DeclID != DefID)
1209 addUInt(SPDie, dwarf::DW_AT_decl_file, std::nullopt, DefID);
1211 if (SP->getLine() != SPDecl->getLine())
1212 addUInt(SPDie, dwarf::DW_AT_decl_line, std::nullopt, SP->getLine());
1223 "decl has a linkage name and it is different");
1224 if (DeclLinkageName.
empty() &&
1234 addDIEEntry(SPDie, dwarf::DW_AT_specification, *DeclDie);
1239 bool SkipSPAttributes) {
1242 bool SkipSPSourceLocation = SkipSPAttributes &&
1244 if (!SkipSPSourceLocation)
1254 if (!SkipSPSourceLocation)
1258 if (SkipSPAttributes)
1264 addFlag(SPDie, dwarf::DW_AT_prototyped);
1266 if (SP->isObjCDirect())
1267 addFlag(SPDie, dwarf::DW_AT_APPLE_objc_direct);
1272 Args = SPTy->getTypeArray();
1277 if (
CC &&
CC != dwarf::DW_CC_normal)
1278 addUInt(SPDie, dwarf::DW_AT_calling_convention, dwarf::DW_FORM_data1,
CC);
1283 if (
auto Ty = Args[0])
1286 unsigned VK = SP->getVirtuality();
1288 addUInt(SPDie, dwarf::DW_AT_virtuality, dwarf::DW_FORM_data1, VK);
1289 if (SP->getVirtualIndex() != -1u) {
1291 addUInt(*
Block, dwarf::DW_FORM_data1, dwarf::DW_OP_constu);
1292 addUInt(*
Block, dwarf::DW_FORM_udata, SP->getVirtualIndex());
1298 if (!SP->isDefinition()) {
1299 addFlag(SPDie, dwarf::DW_AT_declaration);
1308 if (SP->isArtificial())
1309 addFlag(SPDie, dwarf::DW_AT_artificial);
1311 if (!SP->isLocalToUnit())
1312 addFlag(SPDie, dwarf::DW_AT_external);
1315 if (SP->isOptimized())
1316 addFlag(SPDie, dwarf::DW_AT_APPLE_optimized);
1319 addUInt(SPDie, dwarf::DW_AT_APPLE_isa, dwarf::DW_FORM_flag,
isa);
1322 if (SP->isLValueReference())
1323 addFlag(SPDie, dwarf::DW_AT_reference);
1325 if (SP->isRValueReference())
1326 addFlag(SPDie, dwarf::DW_AT_rvalue_reference);
1328 if (SP->isNoReturn())
1329 addFlag(SPDie, dwarf::DW_AT_noreturn);
1333 if (SP->isExplicit())
1334 addFlag(SPDie, dwarf::DW_AT_explicit);
1336 if (SP->isMainSubprogram())
1337 addFlag(SPDie, dwarf::DW_AT_main_subprogram);
1339 addFlag(SPDie, dwarf::DW_AT_pure);
1340 if (SP->isElemental())
1341 addFlag(SPDie, dwarf::DW_AT_elemental);
1342 if (SP->isRecursive())
1343 addFlag(SPDie, dwarf::DW_AT_recursive);
1345 if (!SP->getTargetFuncName().empty())
1346 addString(SPDie, dwarf::DW_AT_trampoline, SP->getTargetFuncName());
1349 addFlag(SPDie, dwarf::DW_AT_deleted);
1352void DwarfUnit::constructSubrangeDIE(
DIE &Buffer,
const DISubrange *SR,
1355 addDIEEntry(DW_Subrange, dwarf::DW_AT_type, *IndexTy);
1361 int64_t DefaultLowerBound = getDefaultLowerBound();
1364 DISubrange::BoundType Bound) ->
void {
1365 if (
auto *BV = dyn_cast_if_present<DIVariable *>(Bound)) {
1366 if (
auto *VarDIE =
getDIE(BV))
1368 }
else if (
auto *BE = dyn_cast_if_present<DIExpression *>(Bound)) {
1371 DwarfExpr.setMemoryLocationKind();
1372 DwarfExpr.addExpression(BE);
1373 addBlock(DW_Subrange, Attr, DwarfExpr.finalize());
1374 }
else if (
auto *BI = dyn_cast_if_present<ConstantInt *>(Bound)) {
1375 if (Attr == dwarf::DW_AT_count) {
1376 if (BI->getSExtValue() != -1)
1377 addUInt(DW_Subrange, Attr, std::nullopt, BI->getSExtValue());
1378 }
else if (Attr != dwarf::DW_AT_lower_bound || DefaultLowerBound == -1 ||
1379 BI->getSExtValue() != DefaultLowerBound)
1380 addSInt(DW_Subrange, Attr, dwarf::DW_FORM_sdata, BI->getSExtValue());
1384 AddBoundTypeEntry(dwarf::DW_AT_lower_bound, SR->
getLowerBound());
1386 AddBoundTypeEntry(dwarf::DW_AT_count, SR->
getCount());
1388 AddBoundTypeEntry(dwarf::DW_AT_upper_bound, SR->
getUpperBound());
1390 AddBoundTypeEntry(dwarf::DW_AT_byte_stride, SR->
getStride());
1393void DwarfUnit::constructGenericSubrangeDIE(
DIE &Buffer,
1396 DIE &DwGenericSubrange =
1398 addDIEEntry(DwGenericSubrange, dwarf::DW_AT_type, *IndexTy);
1400 int64_t DefaultLowerBound = getDefaultLowerBound();
1404 if (
auto *BV = dyn_cast_if_present<DIVariable *>(Bound)) {
1405 if (
auto *VarDIE =
getDIE(BV))
1407 }
else if (
auto *BE = dyn_cast_if_present<DIExpression *>(Bound)) {
1408 if (BE->isConstant() &&
1410 *BE->isConstant()) {
1411 if (Attr != dwarf::DW_AT_lower_bound || DefaultLowerBound == -1 ||
1412 static_cast<int64_t
>(BE->getElement(1)) != DefaultLowerBound)
1413 addSInt(DwGenericSubrange, Attr, dwarf::DW_FORM_sdata,
1418 DwarfExpr.setMemoryLocationKind();
1419 DwarfExpr.addExpression(BE);
1420 addBlock(DwGenericSubrange, Attr, DwarfExpr.finalize());
1425 AddBoundTypeEntry(dwarf::DW_AT_lower_bound, GSR->
getLowerBound());
1426 AddBoundTypeEntry(dwarf::DW_AT_count, GSR->
getCount());
1427 AddBoundTypeEntry(dwarf::DW_AT_upper_bound, GSR->
getUpperBound());
1428 AddBoundTypeEntry(dwarf::DW_AT_byte_stride, GSR->
getStride());
1431DIE *DwarfUnit::getIndexTyDie() {
1450 assert(CTy && CTy->
isVector() &&
"Composite type is not a vector");
1460 assert(Elements.size() == 1 &&
1461 Elements[0]->getTag() == dwarf::DW_TAG_subrange_type &&
1462 "Invalid vector element array, expected one element of type subrange");
1463 const auto Subrange = cast<DISubrange>(Elements[0]);
1464 const auto NumVecElements =
1465 Subrange->getCount()
1466 ? cast<ConstantInt *>(Subrange->getCount())->getSExtValue()
1471 assert(ActualSize >= (NumVecElements * ElementSize) &&
"Invalid vector size");
1472 return ActualSize != (NumVecElements * ElementSize);
1477 addFlag(Buffer, dwarf::DW_AT_GNU_vector);
1479 addUInt(Buffer, dwarf::DW_AT_byte_size, std::nullopt,
1484 if (
auto *VarDIE =
getDIE(Var))
1485 addDIEEntry(Buffer, dwarf::DW_AT_data_location, *VarDIE);
1489 DwarfExpr.setMemoryLocationKind();
1490 DwarfExpr.addExpression(Expr);
1491 addBlock(Buffer, dwarf::DW_AT_data_location, DwarfExpr.finalize());
1495 if (
auto *VarDIE =
getDIE(Var))
1496 addDIEEntry(Buffer, dwarf::DW_AT_associated, *VarDIE);
1500 DwarfExpr.setMemoryLocationKind();
1501 DwarfExpr.addExpression(Expr);
1502 addBlock(Buffer, dwarf::DW_AT_associated, DwarfExpr.finalize());
1506 if (
auto *VarDIE =
getDIE(Var))
1507 addDIEEntry(Buffer, dwarf::DW_AT_allocated, *VarDIE);
1511 DwarfExpr.setMemoryLocationKind();
1512 DwarfExpr.addExpression(Expr);
1513 addBlock(Buffer, dwarf::DW_AT_allocated, DwarfExpr.finalize());
1517 addSInt(Buffer, dwarf::DW_AT_rank, dwarf::DW_FORM_sdata,
1518 RankConst->getSExtValue());
1519 }
else if (
auto *RankExpr = CTy->
getRankExp()) {
1522 DwarfExpr.setMemoryLocationKind();
1523 DwarfExpr.addExpression(RankExpr);
1524 addBlock(Buffer, dwarf::DW_AT_rank, DwarfExpr.finalize());
1533 DIE *IdxTy = getIndexTyDie();
1539 if (
auto *Element = dyn_cast_or_null<DINode>(
E)) {
1540 if (Element->getTag() == dwarf::DW_TAG_subrange_type)
1541 constructSubrangeDIE(Buffer, cast<DISubrange>(Element), IdxTy);
1542 else if (Element->getTag() == dwarf::DW_TAG_generic_subrange)
1543 constructGenericSubrangeDIE(Buffer, cast<DIGenericSubrange>(Element),
1556 addFlag(Buffer, dwarf::DW_AT_enum_class);
1560 bool IndexEnumerators = !
Context || isa<DICompileUnit>(Context) || isa<DIFile>(Context) ||
1561 isa<DINamespace>(Context) || isa<DICommonBlock>(Context);
1565 for (
const DINode *
E : Elements) {
1566 auto *
Enum = dyn_cast_or_null<DIEnumerator>(
E);
1572 if (IndexEnumerators)
1580 DIE &SPDie = *
P.first;
1587 addDIEEntry(SPDie, dwarf::DW_AT_containing_type, *NDie);
1599 if (
DIType *Resolved = DT->getBaseType())
1611 addUInt(*VBaseLocationDie, dwarf::DW_FORM_data1, dwarf::DW_OP_dup);
1612 addUInt(*VBaseLocationDie, dwarf::DW_FORM_data1, dwarf::DW_OP_deref);
1613 addUInt(*VBaseLocationDie, dwarf::DW_FORM_data1, dwarf::DW_OP_constu);
1615 addUInt(*VBaseLocationDie, dwarf::DW_FORM_data1, dwarf::DW_OP_minus);
1616 addUInt(*VBaseLocationDie, dwarf::DW_FORM_data1, dwarf::DW_OP_deref);
1617 addUInt(*VBaseLocationDie, dwarf::DW_FORM_data1, dwarf::DW_OP_plus);
1619 addBlock(MemberDie, dwarf::DW_AT_data_member_location, VBaseLocationDie);
1630 addUInt(MemberDie, dwarf::DW_AT_byte_size, std::nullopt, FieldSize / 8);
1631 addUInt(MemberDie, dwarf::DW_AT_bit_size, std::nullopt,
Size);
1638 uint32_t AlignMask = ~(AlignInBits - 1);
1640 uint64_t StartBitOffset = Offset - (Offset & AlignMask);
1642 OffsetInBytes = (Offset - StartBitOffset) / 8;
1645 uint64_t HiMark = (Offset + FieldSize) & AlignMask;
1646 uint64_t FieldOffset = (HiMark - FieldSize);
1647 Offset -= FieldOffset;
1651 Offset = FieldSize - (Offset +
Size);
1653 addUInt(MemberDie, dwarf::DW_AT_bit_offset, std::nullopt, Offset);
1654 OffsetInBytes = FieldOffset >> 3;
1656 addUInt(MemberDie, dwarf::DW_AT_data_bit_offset, std::nullopt, Offset);
1662 addUInt(MemberDie, dwarf::DW_AT_alignment, dwarf::DW_FORM_udata,
1668 addUInt(*MemLocationDie, dwarf::DW_FORM_data1, dwarf::DW_OP_plus_uconst);
1669 addUInt(*MemLocationDie, dwarf::DW_FORM_udata, OffsetInBytes);
1670 addBlock(MemberDie, dwarf::DW_AT_data_member_location, MemLocationDie);
1677 addUInt(MemberDie, dwarf::DW_AT_data_member_location,
1678 dwarf::DW_FORM_udata, OffsetInBytes);
1680 addUInt(MemberDie, dwarf::DW_AT_data_member_location, std::nullopt,
1688 addUInt(MemberDie, dwarf::DW_AT_virtuality, dwarf::DW_FORM_data1,
1689 dwarf::DW_VIRTUALITY_virtual);
1695 dwarf::DW_FORM_ref4,
DIEEntry(*PDie));
1698 addFlag(MemberDie, dwarf::DW_AT_artificial);
1711 "Static member should belong to a type.");
1714 return StaticMemberDIE;
1718 const DIType *Ty = DT->getBaseType();
1723 addFlag(StaticMemberDIE, dwarf::DW_AT_external);
1724 addFlag(StaticMemberDIE, dwarf::DW_AT_declaration);
1736 addUInt(StaticMemberDIE, dwarf::DW_AT_alignment, dwarf::DW_FORM_udata,
1739 return &StaticMemberDIE;
1746 isDwoUnit() ?
"debug_info_dwo" :
"debug_info",
"Length of Unit");
1783 : dwarf::DW_UT_type);
1785 Asm->
OutStreamer->emitIntValue(TypeSignature,
sizeof(TypeSignature));
1805bool DwarfTypeUnit::isDwoUnit()
const {
1821const MCSymbol *DwarfUnit::getCrossSectionRelativeBaseAddress()
const {
1838 "DW_AT_rnglists_base requires DWARF version 5 or later");
1849bool DwarfUnit::isCompatibleWithVersion(
uint16_t Version)
const {
This file declares a class to represent arbitrary precision floating point values and provide a varie...
This file implements a class to represent arbitrary precision integral constant values and operations...
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
static GCRegistry::Add< ErlangGC > A("erlang", "erlang-compatible garbage collector")
static GCRegistry::Add< StatepointGC > D("statepoint-example", "an example strategy for statepoint")
static GCRegistry::Add< CoreCLRGC > E("coreclr", "CoreCLR-compatible GC")
This file contains the declarations for the subclasses of Constant, which represent the different fla...
Returns the sub type a function will return at a given Idx Should correspond to the result type of an ExtractValue instruction executed with just that one unsigned Idx
static bool hasVectorBeenPadded(const DICompositeType *CTy)
Returns true if the vector's size differs from the sum of sizes of elements the user specified.
unsigned const TargetRegisterInfo * TRI
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
static enum BaseType getBaseType(const Value *Val)
Return the baseType for Val which states whether Val is exclusively derived from constant/null,...
static unsigned getSize(unsigned Kind)
APInt bitcastToAPInt() const
Class for arbitrary precision integers.
uint64_t getZExtValue() const
Get zero extended value.
unsigned getBitWidth() const
Return the number of bits in the APInt.
const uint64_t * getRawData() const
This function returns a pointer to the internal storage of the APInt.
int64_t getSExtValue() const
Get sign extended value.
unsigned getIndex(const MCSymbol *Sym, bool TLS=false)
Returns the index into the address pool with the given label/symbol.
void resetUsedFlag(bool HasBeenUsed=false)
Annotations lets you mark points and ranges inside source code, for tests:
This class is intended to be used as a driving class for all asm writers.
const TargetLoweringObjectFile & getObjFileLowering() const
Return information about object file lowering.
MCSymbol * getSymbol(const GlobalValue *GV) const
void emitDwarfSymbolReference(const MCSymbol *Label, bool ForceOffset=false) const
Emit a reference to a symbol for use in dwarf.
void emitDwarfLengthOrOffset(uint64_t Value) const
Emit 32- or 64-bit value depending on the DWARF format.
TargetMachine & TM
Target machine description.
const MCAsmInfo * MAI
Target Asm Printer information.
MachineFunction * MF
The current machine function.
void emitInt8(int Value) const
Emit a byte directive and value.
void emitDwarfUnitLength(uint64_t Length, const Twine &Comment) const
Emit a unit length field.
MCContext & OutContext
This is the context for the output file that we are streaming.
std::unique_ptr< MCStreamer > OutStreamer
This is the MCStreamer object for the file we are generating.
virtual unsigned getISAEncoding()
Get the value for DW_AT_APPLE_isa. Zero if no isa encoding specified.
void emitInt16(int Value) const
Emit a short directive and value.
const DataLayout & getDataLayout() const
Return information about data layout.
dwarf::FormParams getDwarfFormParams() const
Returns information about the byte size of DW_FORM values.
bool doesDwarfUseRelocationsAcrossSections() const
ConstantFP - Floating Point Values [float, double].
const APFloat & getValueAPF() const
This is the shared class of boolean and integer constants.
const APInt & getValue() const
Return the constant as an APInt value reference.
Basic type, like 'int' or 'float'.
unsigned getEncoding() const
bool getDebugInfoForProfiling() const
bool isDebugDirectivesOnly() const
DIExpression * getRankExp() const
DIExpression * getAssociatedExp() const
DIVariable * getAllocated() const
DIExpression * getDataLocationExp() const
DIVariable * getAssociated() const
DIDerivedType * getDiscriminator() const
DIVariable * getDataLocation() const
unsigned getRuntimeLang() const
DINodeArray getElements() const
DITemplateParameterArray getTemplateParams() const
DIExpression * getAllocatedExp() const
DIType * getVTableHolder() const
DINodeArray getAnnotations() const
ConstantInt * getRankConst() const
DIType * getBaseType() const
DIObjCProperty * getObjCProperty() const
Constant * getConstant() const
DIEBlock - Represents a block of values.
A simple label difference DIE.
DwarfExpression implementation for singular DW_AT_location.
DIEDwarfExpression(const AsmPrinter &AP, DwarfCompileUnit &CU, DIELoc &DIE)
A pointer to another debug information entry.
A container for inline string values.
static dwarf::Form BestForm(bool IsSigned, uint64_t Int)
Choose the best form for integer.
DIELoc - Represents an expression location.
unsigned computeSize(const dwarf::FormParams &FormParams) const
Calculate the size of the location expression.
dwarf::Form BestForm(unsigned DwarfVersion) const
BestForm - Choose the best form for data.
A container for string pool string values.
Represents a compile or type unit.
MCSection * getSection() const
Return the section that this DIEUnit will be emitted into.
void takeValues(DIEValueList &Other)
Take ownership of the nodes in Other, and append them to the back of the list.
A structured debug information entry.
DIE & addChild(DIE *Child)
Add a child to the DIE.
static DIE * get(BumpPtrAllocator &Alloc, dwarf::Tag Tag)
DIEUnit * getUnit() const
Climb up the parent chain to get the compile unit or type unit that this DIE belongs to.
dwarf::Tag getTag() const
BoundType getLowerBound() const
BoundType getCount() const
BoundType getUpperBound() const
BoundType getStride() const
Represents a module in the programming language, for example, a Clang module, or a Fortran module.
DIScope * getScope() const
StringRef getName() const
bool getExportSymbols() const
Tagged DWARF-like metadata node.
dwarf::Tag getTag() const
Base class for scope-like contexts.
StringRef getName() const
DIScope * getScope() const
String type, Fortran CHARACTER(n)
unsigned getEncoding() const
DIExpression * getStringLengthExp() const
DIVariable * getStringLength() const
DIExpression * getStringLocationExp() const
BoundType getUpperBound() const
BoundType getStride() const
BoundType getLowerBound() const
BoundType getCount() const
Type array for a subprogram.
StringRef getName() const
Metadata * getValue() const
bool isLittleEndian() const
bool isLValueReference() const
bool isObjcClassComplete() const
MDString * getRawName() const
bool isAppleBlockExtension() const
uint64_t getOffsetInBits() const
StringRef getName() const
bool isForwardDecl() const
bool isTypePassByValue() const
uint64_t getSizeInBits() const
uint32_t getAlignInBytes() const
bool isRValueReference() const
bool isArtificial() const
bool getExportSymbols() const
DIScope * getScope() const
bool isTypePassByReference() const
Base class for variables.
This class represents an Operation in the Expression.
bool isLittleEndian() const
Layout endianness...
static bool isUnsignedDIType(const DIType *Ty)
Return true if type encoding is unsigned.
static uint64_t getBaseTypeSize(const DIType *Ty)
If this type is derived from a base type then return base type size.
void addGlobalNameForTypeUnit(StringRef Name, const DIScope *Context)
Add a new global name present in a type unit to this compile unit.
unsigned getOrCreateSourceID(const DIFile *File) override
Look up the source ID for the given file.
void addGlobalTypeUnitType(const DIType *Ty, const DIScope *Context)
Add a new global type present in a type unit to this compile unit.
Collects and handles dwarf debug information.
std::optional< MD5::MD5Result > getMD5AsBytes(const DIFile *File) const
If the File has an MD5 checksum, return it as an MD5Result allocated in the MCContext.
bool useAddrOffsetForm() const
uint16_t getDwarfVersion() const
Returns the Dwarf Version.
bool useAllLinkageNames() const
Returns whether we should emit all DW_AT_[MIPS_]linkage_name.
dwarf::Form getDwarfSectionOffsetForm() const
Returns a suitable DWARF form to represent a section offset, i.e.
bool useAppleExtensionAttributes() const
bool useInlineStrings() const
Returns whether to use inline strings.
bool generateTypeUnits() const
Returns whether to generate DWARF v4 type units.
AddressPool & getAddressPool()
void addAccelNamespace(const DICompileUnit &CU, StringRef Name, const DIE &Die)
void addAccelType(const DICompileUnit &CU, StringRef Name, const DIE &Die, char Flags)
bool useSectionsAsReferences() const
Returns whether to use sections as labels rather than temp symbols.
bool shareAcrossDWOCUs() const
const MCSymbol * getSectionLabel(const MCSection *S)
bool useSplitDwarf() const
Returns whether or not to change the current debug info for the split dwarf proposal support.
bool useDWARF2Bitfields() const
Returns whether to use the DWARF2 format for bitfields instyead of the DWARF4 format.
bool useAddrOffsetExpressions() const
void addDwarfTypeUnitType(DwarfCompileUnit &CU, StringRef Identifier, DIE &Die, const DICompositeType *CTy)
Add a DIE to the set of types that we're going to pull into type units.
Base class containing the logic for constructing DWARF expressions independently of whether they are ...
MCSymbol * getStringOffsetsStartSym() const
MCSymbol * getRnglistsTableBaseSym() const
DwarfStringPool & getStringPool()
Returns the string pool.
DenseMap< const DILocalScope *, DIE * > & getAbstractScopeDIEs()
void insertDIE(const MDNode *TypeMD, DIE *Die)
DIE * getDIE(const MDNode *TypeMD)
unsigned getIndex() const
EntryRef getEntry(AsmPrinter &Asm, StringRef Str)
Get a reference to an entry in the string pool.
EntryRef getIndexedEntry(AsmPrinter &Asm, StringRef Str)
Same as getEntry, except that you can use EntryRef::getIndex to obtain a unique ID of this entry (e....
void addGlobalType(const DIType *Ty, const DIE &Die, const DIScope *Context) override
Add a new global type to the compile unit.
DwarfTypeUnit(DwarfCompileUnit &CU, AsmPrinter *A, DwarfDebug *DW, DwarfFile *DWU, MCDwarfDwoLineTable *SplitLineTable=nullptr)
DwarfCompileUnit & getCU() override
void emitHeader(bool UseOffsets) override
Emit the header for this unit, not including the initial length field.
void addGlobalName(StringRef Name, const DIE &Die, const DIScope *Context) override
Add a new global name to the compile unit.
This dwarf writer support class manages information associated with a source file.
virtual DIE * getOrCreateTypeDIE(const MDNode *TyNode)
Find existing DIE or create new DIE for the given type.
DwarfUnit(dwarf::Tag, const DICompileUnit *Node, AsmPrinter *A, DwarfDebug *DW, DwarfFile *DWU)
void addThrownTypes(DIE &Die, DINodeArray ThrownTypes)
Add thrown types.
void addStringOffsetsStart()
Add the DW_AT_str_offsets_base attribute to the unit DIE.
void addAnnotation(DIE &Buffer, DINodeArray Annotations)
Add DW_TAG_LLVM_annotation.
std::vector< DIEBlock * > DIEBlocks
A list of all the DIEBlocks in use.
std::vector< DIELoc * > DIELocs
A list of all the DIELocs in use.
uint16_t getLanguage() const
void addBlock(DIE &Die, dwarf::Attribute Attribute, DIELoc *Loc)
Add block data.
void addTemplateParams(DIE &Buffer, DINodeArray TParams)
Add template parameters in buffer.
virtual DIE * getOrCreateContextDIE(const DIScope *Context)
Get context owner's DIE.
bool useSegmentedStringOffsetsTable() const
bool applySubprogramDefinitionAttributes(const DISubprogram *SP, DIE &SPDie, bool Minimal)
DIELoc * getDIELoc()
Returns a fresh newly allocated DIELoc.
void addAttribute(DIEValueList &Die, dwarf::Attribute Attribute, dwarf::Form Form, T &&Value)
void addOpAddress(DIELoc &Die, const MCSymbol *Sym)
Add a dwarf op address data and value using the form given and an op of either DW_FORM_addr or DW_FOR...
void addUInt(DIEValueList &Die, dwarf::Attribute Attribute, std::optional< dwarf::Form > Form, uint64_t Integer)
Add an unsigned integer attribute data and value.
void addString(DIE &Die, dwarf::Attribute Attribute, StringRef Str)
Add a string attribute data and value.
void addConstantValue(DIE &Die, const ConstantInt *CI, const DIType *Ty)
Add constant value entry in variable DIE.
DIE * getOrCreateNameSpace(const DINamespace *NS)
void insertDIE(const DINode *Desc, DIE *D)
Insert DIE into the map.
void addAccess(DIE &Die, DINode::DIFlags Flags)
Add the accessibility attribute.
void addSectionDelta(DIE &Die, dwarf::Attribute Attribute, const MCSymbol *Hi, const MCSymbol *Lo)
addSectionDelta - Add a label delta attribute data and value.
DIE * createTypeDIE(const DIScope *Context, DIE &ContextDIE, const DIType *Ty)
Creates type DIE with specific context.
DenseMap< DIE *, const DINode * > ContainingTypeMap
This map is used to keep track of subprogram DIEs that need DW_AT_containing_type attribute.
const DICompileUnit * CUNode
MDNode for the compile unit.
virtual unsigned getOrCreateSourceID(const DIFile *File)=0
Look up the source ID for the given file.
void addDIETypeSignature(DIE &Die, uint64_t Signature)
Add a type's DW_AT_signature and set the declaration flag.
virtual void addGlobalType(const DIType *Ty, const DIE &Die, const DIScope *Context)=0
Add a new global type to the compile unit.
virtual DwarfCompileUnit & getCU()=0
DIE * getDIE(const DINode *D) const
Returns the DIE map slot for the specified debug variable.
virtual unsigned getHeaderSize() const
Compute the size of a header for this unit, not including the initial length field.
void constructSubprogramArguments(DIE &Buffer, DITypeRefArray Args)
Construct function argument DIEs.
void addSInt(DIEValueList &Die, dwarf::Attribute Attribute, std::optional< dwarf::Form > Form, int64_t Integer)
Add an signed integer attribute data and value.
void addLabelDelta(DIEValueList &Die, dwarf::Attribute Attribute, const MCSymbol *Hi, const MCSymbol *Lo)
Add a label delta attribute data and value.
void addLinkageName(DIE &Die, StringRef LinkageName)
Add a linkage name, if it isn't empty.
std::string getParentContextString(const DIScope *Context) const
Get string containing language specific context for a global name.
void addSourceLine(DIE &Die, unsigned Line, const DIFile *File)
Add location information to specified debug information entry.
void emitCommonHeader(bool UseOffsets, dwarf::UnitType UT)
Emit the common part of the header for this unit.
BumpPtrAllocator DIEValueAllocator
DIE * IndexTyDie
An anonymous type for index type. Owned by DIEUnit.
void addRnglistsBase()
Add the DW_AT_rnglists_base attribute to the unit DIE.
DIE * getOrCreateModule(const DIModule *M)
DIE & createAndAddDIE(dwarf::Tag Tag, DIE &Parent, const DINode *N=nullptr)
Create a DIE with the given Tag, add the DIE to its parent, and call insertDIE if MD is not null.
void addSectionOffset(DIE &Die, dwarf::Attribute Attribute, uint64_t Integer)
Add an offset into a section attribute data and value.
DIE * getOrCreateStaticMemberDIE(const DIDerivedType *DT)
Create new static data member DIE.
void addLabel(DIEValueList &Die, dwarf::Attribute Attribute, dwarf::Form Form, const MCSymbol *Label)
Add a Dwarf label attribute data and value.
void addConstantFPValue(DIE &Die, const ConstantFP *CFP)
Add constant value entry in variable DIE.
void constructContainingTypeDIEs()
Construct DIEs for types that contain vtables.
DIE * getOrCreateSubprogramDIE(const DISubprogram *SP, bool Minimal=false)
void addSectionLabel(DIE &Die, dwarf::Attribute Attribute, const MCSymbol *Label, const MCSymbol *Sec)
Add a Dwarf section label attribute data and value.
bool isShareableAcrossCUs(const DINode *D) const
Check whether the DIE for this MDNode can be shared across CUs.
void addPoolOpAddress(DIEValueList &Die, const MCSymbol *Label)
DenseMap< const MDNode *, DIE * > MDNodeToDieMap
Tracks the mapping of unit level debug information variables to debug information entries.
void constructTypeDIE(DIE &Buffer, const DICompositeType *CTy)
virtual void addGlobalName(StringRef Name, const DIE &Die, const DIScope *Context)=0
Add a new global name to the compile unit.
MCSymbol * EndLabel
Emitted at the end of the CU and used to compute the CU Length field.
void addFlag(DIE &Die, dwarf::Attribute Attribute)
Add a flag that is true to the DIE.
AsmPrinter * Asm
Target of Dwarf emission.
void addType(DIE &Entity, const DIType *Ty, dwarf::Attribute Attribute=dwarf::DW_AT_type)
Add a new type attribute to the specified entity.
void applySubprogramAttributes(const DISubprogram *SP, DIE &SPDie, bool SkipSPAttributes=false)
void addDIEEntry(DIE &Die, dwarf::Attribute Attribute, DIE &Entry)
Add a DIE attribute data and value.
static StringRef dropLLVMManglingEscape(StringRef Name)
If the given string begins with the GlobalValue name mangling escape character '\1',...
unsigned getCodePointerSize() const
Get the code pointer size in bytes.
uint16_t getDwarfVersion() const
unsigned getFile(StringRef Directory, StringRef FileName, std::optional< MD5::MD5Result > Checksum, uint16_t DwarfVersion, std::optional< StringRef > Source)
MCSection * getDwarfStrOffSection() const
MCSection * getDwarfRnglistsSection() const
MCSection * getDwarfAbbrevSection() const
MCSymbol * getBeginSymbol()
MCSymbol - Instances of this class represent a symbol name in the MC file, and MCSymbols are created ...
const MDOperand & getOperand(unsigned I) const
A discriminated union of two or more pointer types, with the discriminator in the low bit of the poin...
Wrapper class representing virtual and physical registers.
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
StringRef - Represent a constant reference to a string, i.e.
constexpr bool empty() const
empty - Check if the string is empty.
unsigned DebugStrictDwarf
When set to true, don't use DWARF extensions in later DWARF versions.
TargetRegisterInfo base class - We assume that the target defines a static array of TargetRegisterDes...
LLVM Value Representation.
This provides a very simple, boring adaptor for a begin and end iterator into a range type.
UnitType
Constants for unit types in DWARF v5.
bool isCPlusPlus(SourceLanguage S)
TypeKind getArrayIndexTypeEncoding(SourceLanguage S)
@ DW_FLAG_type_implementation
bool isC(SourceLanguage S)
This is an optimization pass for GlobalISel generic memory operations.
auto reverse(ContainerTy &&C)
bool isa(const From &Val)
isa<X> - Return true if the parameter to the template is an instance of one of the template type argu...
Description of the encoding of one expression Op.