10b57cec5SDimitry Andric //===- llvm/CodeGen/DwarfCompileUnit.cpp - Dwarf Compile Units ------------===// 20b57cec5SDimitry Andric // 30b57cec5SDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 40b57cec5SDimitry Andric // See https://llvm.org/LICENSE.txt for license information. 50b57cec5SDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 60b57cec5SDimitry Andric // 70b57cec5SDimitry Andric //===----------------------------------------------------------------------===// 80b57cec5SDimitry Andric // 90b57cec5SDimitry Andric // This file contains support for constructing a dwarf compile unit. 100b57cec5SDimitry Andric // 110b57cec5SDimitry Andric //===----------------------------------------------------------------------===// 120b57cec5SDimitry Andric 130b57cec5SDimitry Andric #include "DwarfCompileUnit.h" 140b57cec5SDimitry Andric #include "AddressPool.h" 150b57cec5SDimitry Andric #include "DwarfExpression.h" 160b57cec5SDimitry Andric #include "llvm/ADT/None.h" 170b57cec5SDimitry Andric #include "llvm/ADT/STLExtras.h" 180b57cec5SDimitry Andric #include "llvm/ADT/SmallString.h" 19fe6060f1SDimitry Andric #include "llvm/BinaryFormat/Dwarf.h" 200b57cec5SDimitry Andric #include "llvm/CodeGen/AsmPrinter.h" 210b57cec5SDimitry Andric #include "llvm/CodeGen/DIE.h" 220b57cec5SDimitry Andric #include "llvm/CodeGen/MachineFunction.h" 230b57cec5SDimitry Andric #include "llvm/CodeGen/MachineInstr.h" 240b57cec5SDimitry Andric #include "llvm/CodeGen/MachineOperand.h" 250b57cec5SDimitry Andric #include "llvm/CodeGen/TargetFrameLowering.h" 260b57cec5SDimitry Andric #include "llvm/CodeGen/TargetRegisterInfo.h" 270b57cec5SDimitry Andric #include "llvm/CodeGen/TargetSubtargetInfo.h" 280b57cec5SDimitry Andric #include "llvm/IR/DataLayout.h" 290b57cec5SDimitry Andric #include "llvm/IR/DebugInfo.h" 300b57cec5SDimitry Andric #include "llvm/IR/GlobalVariable.h" 310b57cec5SDimitry Andric #include "llvm/MC/MCSection.h" 320b57cec5SDimitry Andric #include "llvm/MC/MCStreamer.h" 330b57cec5SDimitry Andric #include "llvm/MC/MCSymbol.h" 345ffd83dbSDimitry Andric #include "llvm/MC/MCSymbolWasm.h" 350b57cec5SDimitry Andric #include "llvm/MC/MachineLocation.h" 360b57cec5SDimitry Andric #include "llvm/Target/TargetLoweringObjectFile.h" 370b57cec5SDimitry Andric #include "llvm/Target/TargetMachine.h" 380b57cec5SDimitry Andric #include "llvm/Target/TargetOptions.h" 390b57cec5SDimitry Andric #include <iterator> 400b57cec5SDimitry Andric #include <string> 410b57cec5SDimitry Andric #include <utility> 420b57cec5SDimitry Andric 430b57cec5SDimitry Andric using namespace llvm; 440b57cec5SDimitry Andric 45480093f4SDimitry Andric static dwarf::Tag GetCompileUnitType(UnitKind Kind, DwarfDebug *DW) { 46480093f4SDimitry Andric 47480093f4SDimitry Andric // According to DWARF Debugging Information Format Version 5, 48480093f4SDimitry Andric // 3.1.2 Skeleton Compilation Unit Entries: 49480093f4SDimitry Andric // "When generating a split DWARF object file (see Section 7.3.2 50480093f4SDimitry Andric // on page 187), the compilation unit in the .debug_info section 51480093f4SDimitry Andric // is a "skeleton" compilation unit with the tag DW_TAG_skeleton_unit" 52480093f4SDimitry Andric if (DW->getDwarfVersion() >= 5 && Kind == UnitKind::Skeleton) 53480093f4SDimitry Andric return dwarf::DW_TAG_skeleton_unit; 54480093f4SDimitry Andric 55480093f4SDimitry Andric return dwarf::DW_TAG_compile_unit; 56480093f4SDimitry Andric } 57480093f4SDimitry Andric 580b57cec5SDimitry Andric DwarfCompileUnit::DwarfCompileUnit(unsigned UID, const DICompileUnit *Node, 590b57cec5SDimitry Andric AsmPrinter *A, DwarfDebug *DW, 60480093f4SDimitry Andric DwarfFile *DWU, UnitKind Kind) 61480093f4SDimitry Andric : DwarfUnit(GetCompileUnitType(Kind, DW), Node, A, DW, DWU), UniqueID(UID) { 620b57cec5SDimitry Andric insertDIE(Node, &getUnitDie()); 630b57cec5SDimitry Andric MacroLabelBegin = Asm->createTempSymbol("cu_macro_begin"); 640b57cec5SDimitry Andric } 650b57cec5SDimitry Andric 660b57cec5SDimitry Andric /// addLabelAddress - Add a dwarf label attribute data and value using 670b57cec5SDimitry Andric /// DW_FORM_addr or DW_FORM_GNU_addr_index. 680b57cec5SDimitry Andric void DwarfCompileUnit::addLabelAddress(DIE &Die, dwarf::Attribute Attribute, 690b57cec5SDimitry Andric const MCSymbol *Label) { 700b57cec5SDimitry Andric // Don't use the address pool in non-fission or in the skeleton unit itself. 710b57cec5SDimitry Andric if ((!DD->useSplitDwarf() || !Skeleton) && DD->getDwarfVersion() < 5) 720b57cec5SDimitry Andric return addLocalLabelAddress(Die, Attribute, Label); 730b57cec5SDimitry Andric 740b57cec5SDimitry Andric if (Label) 750b57cec5SDimitry Andric DD->addArangeLabel(SymbolCU(this, Label)); 760b57cec5SDimitry Andric 77fe6060f1SDimitry Andric bool UseAddrOffsetFormOrExpressions = 78fe6060f1SDimitry Andric DD->useAddrOffsetForm() || DD->useAddrOffsetExpressions(); 79fe6060f1SDimitry Andric 80fe6060f1SDimitry Andric const MCSymbol *Base = nullptr; 81fe6060f1SDimitry Andric if (Label->isInSection() && UseAddrOffsetFormOrExpressions) 82fe6060f1SDimitry Andric Base = DD->getSectionLabel(&Label->getSection()); 83fe6060f1SDimitry Andric 84fe6060f1SDimitry Andric if (!Base || Base == Label) { 850b57cec5SDimitry Andric unsigned idx = DD->getAddressPool().getIndex(Label); 86fe6060f1SDimitry Andric addAttribute(Die, Attribute, 870b57cec5SDimitry Andric DD->getDwarfVersion() >= 5 ? dwarf::DW_FORM_addrx 880b57cec5SDimitry Andric : dwarf::DW_FORM_GNU_addr_index, 890b57cec5SDimitry Andric DIEInteger(idx)); 90fe6060f1SDimitry Andric return; 91fe6060f1SDimitry Andric } 92fe6060f1SDimitry Andric 93fe6060f1SDimitry Andric // Could be extended to work with DWARFv4 Split DWARF if that's important for 94fe6060f1SDimitry Andric // someone. In that case DW_FORM_data would be used. 95fe6060f1SDimitry Andric assert(DD->getDwarfVersion() >= 5 && 96fe6060f1SDimitry Andric "Addr+offset expressions are only valuable when using debug_addr (to " 97fe6060f1SDimitry Andric "reduce relocations) available in DWARFv5 or higher"); 98fe6060f1SDimitry Andric if (DD->useAddrOffsetExpressions()) { 99fe6060f1SDimitry Andric auto *Loc = new (DIEValueAllocator) DIEBlock(); 100fe6060f1SDimitry Andric addPoolOpAddress(*Loc, Label); 101fe6060f1SDimitry Andric addBlock(Die, Attribute, dwarf::DW_FORM_exprloc, Loc); 102fe6060f1SDimitry Andric } else 103fe6060f1SDimitry Andric addAttribute(Die, Attribute, dwarf::DW_FORM_LLVM_addrx_offset, 104fe6060f1SDimitry Andric new (DIEValueAllocator) DIEAddrOffset( 105fe6060f1SDimitry Andric DD->getAddressPool().getIndex(Base), Label, Base)); 1060b57cec5SDimitry Andric } 1070b57cec5SDimitry Andric 1080b57cec5SDimitry Andric void DwarfCompileUnit::addLocalLabelAddress(DIE &Die, 1090b57cec5SDimitry Andric dwarf::Attribute Attribute, 1100b57cec5SDimitry Andric const MCSymbol *Label) { 1110b57cec5SDimitry Andric if (Label) 1120b57cec5SDimitry Andric DD->addArangeLabel(SymbolCU(this, Label)); 1130b57cec5SDimitry Andric 1140b57cec5SDimitry Andric if (Label) 115fe6060f1SDimitry Andric addAttribute(Die, Attribute, dwarf::DW_FORM_addr, DIELabel(Label)); 1160b57cec5SDimitry Andric else 117fe6060f1SDimitry Andric addAttribute(Die, Attribute, dwarf::DW_FORM_addr, DIEInteger(0)); 1180b57cec5SDimitry Andric } 1190b57cec5SDimitry Andric 1200b57cec5SDimitry Andric unsigned DwarfCompileUnit::getOrCreateSourceID(const DIFile *File) { 1210b57cec5SDimitry Andric // If we print assembly, we can't separate .file entries according to 1220b57cec5SDimitry Andric // compile units. Thus all files will belong to the default compile unit. 1230b57cec5SDimitry Andric 1240b57cec5SDimitry Andric // FIXME: add a better feature test than hasRawTextSupport. Even better, 1250b57cec5SDimitry Andric // extend .file to support this. 1260b57cec5SDimitry Andric unsigned CUID = Asm->OutStreamer->hasRawTextSupport() ? 0 : getUniqueID(); 1270b57cec5SDimitry Andric if (!File) 1285ffd83dbSDimitry Andric return Asm->OutStreamer->emitDwarfFileDirective(0, "", "", None, None, 1295ffd83dbSDimitry Andric CUID); 1305ffd83dbSDimitry Andric return Asm->OutStreamer->emitDwarfFileDirective( 131e8d8bef9SDimitry Andric 0, File->getDirectory(), File->getFilename(), DD->getMD5AsBytes(File), 1320b57cec5SDimitry Andric File->getSource(), CUID); 1330b57cec5SDimitry Andric } 1340b57cec5SDimitry Andric 1350b57cec5SDimitry Andric DIE *DwarfCompileUnit::getOrCreateGlobalVariableDIE( 1360b57cec5SDimitry Andric const DIGlobalVariable *GV, ArrayRef<GlobalExpr> GlobalExprs) { 1370b57cec5SDimitry Andric // Check for pre-existence. 1380b57cec5SDimitry Andric if (DIE *Die = getDIE(GV)) 1390b57cec5SDimitry Andric return Die; 1400b57cec5SDimitry Andric 1410b57cec5SDimitry Andric assert(GV); 1420b57cec5SDimitry Andric 1430b57cec5SDimitry Andric auto *GVContext = GV->getScope(); 1440b57cec5SDimitry Andric const DIType *GTy = GV->getType(); 1450b57cec5SDimitry Andric 1460b57cec5SDimitry Andric auto *CB = GVContext ? dyn_cast<DICommonBlock>(GVContext) : nullptr; 1470b57cec5SDimitry Andric DIE *ContextDIE = CB ? getOrCreateCommonBlock(CB, GlobalExprs) 1480b57cec5SDimitry Andric : getOrCreateContextDIE(GVContext); 1490b57cec5SDimitry Andric 1500b57cec5SDimitry Andric // Add to map. 1510b57cec5SDimitry Andric DIE *VariableDIE = &createAndAddDIE(GV->getTag(), *ContextDIE, GV); 1520b57cec5SDimitry Andric DIScope *DeclContext; 1530b57cec5SDimitry Andric if (auto *SDMDecl = GV->getStaticDataMemberDeclaration()) { 1540b57cec5SDimitry Andric DeclContext = SDMDecl->getScope(); 1550b57cec5SDimitry Andric assert(SDMDecl->isStaticMember() && "Expected static member decl"); 1560b57cec5SDimitry Andric assert(GV->isDefinition()); 1570b57cec5SDimitry Andric // We need the declaration DIE that is in the static member's class. 1580b57cec5SDimitry Andric DIE *VariableSpecDIE = getOrCreateStaticMemberDIE(SDMDecl); 1590b57cec5SDimitry Andric addDIEEntry(*VariableDIE, dwarf::DW_AT_specification, *VariableSpecDIE); 1600b57cec5SDimitry Andric // If the global variable's type is different from the one in the class 1610b57cec5SDimitry Andric // member type, assume that it's more specific and also emit it. 1620b57cec5SDimitry Andric if (GTy != SDMDecl->getBaseType()) 1630b57cec5SDimitry Andric addType(*VariableDIE, GTy); 1640b57cec5SDimitry Andric } else { 1650b57cec5SDimitry Andric DeclContext = GV->getScope(); 1660b57cec5SDimitry Andric // Add name and type. 1670b57cec5SDimitry Andric addString(*VariableDIE, dwarf::DW_AT_name, GV->getDisplayName()); 1685ffd83dbSDimitry Andric if (GTy) 1690b57cec5SDimitry Andric addType(*VariableDIE, GTy); 1700b57cec5SDimitry Andric 1710b57cec5SDimitry Andric // Add scoping info. 1720b57cec5SDimitry Andric if (!GV->isLocalToUnit()) 1730b57cec5SDimitry Andric addFlag(*VariableDIE, dwarf::DW_AT_external); 1740b57cec5SDimitry Andric 1750b57cec5SDimitry Andric // Add line number info. 1760b57cec5SDimitry Andric addSourceLine(*VariableDIE, GV); 1770b57cec5SDimitry Andric } 1780b57cec5SDimitry Andric 1790b57cec5SDimitry Andric if (!GV->isDefinition()) 1800b57cec5SDimitry Andric addFlag(*VariableDIE, dwarf::DW_AT_declaration); 1810b57cec5SDimitry Andric else 1820b57cec5SDimitry Andric addGlobalName(GV->getName(), *VariableDIE, DeclContext); 1830b57cec5SDimitry Andric 184349cc55cSDimitry Andric addAnnotation(*VariableDIE, GV->getAnnotations()); 185349cc55cSDimitry Andric 1860b57cec5SDimitry Andric if (uint32_t AlignInBytes = GV->getAlignInBytes()) 1870b57cec5SDimitry Andric addUInt(*VariableDIE, dwarf::DW_AT_alignment, dwarf::DW_FORM_udata, 1880b57cec5SDimitry Andric AlignInBytes); 1890b57cec5SDimitry Andric 1900b57cec5SDimitry Andric if (MDTuple *TP = GV->getTemplateParams()) 1910b57cec5SDimitry Andric addTemplateParams(*VariableDIE, DINodeArray(TP)); 1920b57cec5SDimitry Andric 1930b57cec5SDimitry Andric // Add location. 1940b57cec5SDimitry Andric addLocationAttribute(VariableDIE, GV, GlobalExprs); 1950b57cec5SDimitry Andric 1960b57cec5SDimitry Andric return VariableDIE; 1970b57cec5SDimitry Andric } 1980b57cec5SDimitry Andric 1990b57cec5SDimitry Andric void DwarfCompileUnit::addLocationAttribute( 2000b57cec5SDimitry Andric DIE *VariableDIE, const DIGlobalVariable *GV, ArrayRef<GlobalExpr> GlobalExprs) { 2010b57cec5SDimitry Andric bool addToAccelTable = false; 2020b57cec5SDimitry Andric DIELoc *Loc = nullptr; 2030b57cec5SDimitry Andric Optional<unsigned> NVPTXAddressSpace; 2040b57cec5SDimitry Andric std::unique_ptr<DIEDwarfExpression> DwarfExpr; 2050b57cec5SDimitry Andric for (const auto &GE : GlobalExprs) { 2060b57cec5SDimitry Andric const GlobalVariable *Global = GE.Var; 2070b57cec5SDimitry Andric const DIExpression *Expr = GE.Expr; 2080b57cec5SDimitry Andric 2090b57cec5SDimitry Andric // For compatibility with DWARF 3 and earlier, 210fe6060f1SDimitry Andric // DW_AT_location(DW_OP_constu, X, DW_OP_stack_value) or 211fe6060f1SDimitry Andric // DW_AT_location(DW_OP_consts, X, DW_OP_stack_value) becomes 2120b57cec5SDimitry Andric // DW_AT_const_value(X). 2130b57cec5SDimitry Andric if (GlobalExprs.size() == 1 && Expr && Expr->isConstant()) { 2140b57cec5SDimitry Andric addToAccelTable = true; 215fe6060f1SDimitry Andric addConstantValue( 216fe6060f1SDimitry Andric *VariableDIE, 217fe6060f1SDimitry Andric DIExpression::SignedOrUnsignedConstant::UnsignedConstant == 218fe6060f1SDimitry Andric *Expr->isConstant(), 219fe6060f1SDimitry Andric Expr->getElement(1)); 2200b57cec5SDimitry Andric break; 2210b57cec5SDimitry Andric } 2220b57cec5SDimitry Andric 2230b57cec5SDimitry Andric // We cannot describe the location of dllimport'd variables: the 2240b57cec5SDimitry Andric // computation of their address requires loads from the IAT. 2250b57cec5SDimitry Andric if (Global && Global->hasDLLImportStorageClass()) 2260b57cec5SDimitry Andric continue; 2270b57cec5SDimitry Andric 2280b57cec5SDimitry Andric // Nothing to describe without address or constant. 2290b57cec5SDimitry Andric if (!Global && (!Expr || !Expr->isConstant())) 2300b57cec5SDimitry Andric continue; 2310b57cec5SDimitry Andric 2320b57cec5SDimitry Andric if (Global && Global->isThreadLocal() && 2330b57cec5SDimitry Andric !Asm->getObjFileLowering().supportDebugThreadLocalLocation()) 2340b57cec5SDimitry Andric continue; 2350b57cec5SDimitry Andric 2360b57cec5SDimitry Andric if (!Loc) { 2370b57cec5SDimitry Andric addToAccelTable = true; 2380b57cec5SDimitry Andric Loc = new (DIEValueAllocator) DIELoc; 2398bcb0991SDimitry Andric DwarfExpr = std::make_unique<DIEDwarfExpression>(*Asm, *this, *Loc); 2400b57cec5SDimitry Andric } 2410b57cec5SDimitry Andric 2420b57cec5SDimitry Andric if (Expr) { 2430b57cec5SDimitry Andric // According to 2440b57cec5SDimitry Andric // https://docs.nvidia.com/cuda/archive/10.0/ptx-writers-guide-to-interoperability/index.html#cuda-specific-dwarf 2450b57cec5SDimitry Andric // cuda-gdb requires DW_AT_address_class for all variables to be able to 2460b57cec5SDimitry Andric // correctly interpret address space of the variable address. 2470b57cec5SDimitry Andric // Decode DW_OP_constu <DWARF Address Space> DW_OP_swap DW_OP_xderef 2480b57cec5SDimitry Andric // sequence for the NVPTX + gdb target. 2490b57cec5SDimitry Andric unsigned LocalNVPTXAddressSpace; 2500b57cec5SDimitry Andric if (Asm->TM.getTargetTriple().isNVPTX() && DD->tuneForGDB()) { 2510b57cec5SDimitry Andric const DIExpression *NewExpr = 2520b57cec5SDimitry Andric DIExpression::extractAddressClass(Expr, LocalNVPTXAddressSpace); 2530b57cec5SDimitry Andric if (NewExpr != Expr) { 2540b57cec5SDimitry Andric Expr = NewExpr; 2550b57cec5SDimitry Andric NVPTXAddressSpace = LocalNVPTXAddressSpace; 2560b57cec5SDimitry Andric } 2570b57cec5SDimitry Andric } 2580b57cec5SDimitry Andric DwarfExpr->addFragmentOffset(Expr); 2590b57cec5SDimitry Andric } 2600b57cec5SDimitry Andric 2610b57cec5SDimitry Andric if (Global) { 2620b57cec5SDimitry Andric const MCSymbol *Sym = Asm->getSymbol(Global); 263349cc55cSDimitry Andric unsigned PointerSize = Asm->getDataLayout().getPointerSize(); 264349cc55cSDimitry Andric assert((PointerSize == 4 || PointerSize == 8) && 265349cc55cSDimitry Andric "Add support for other sizes if necessary"); 2660b57cec5SDimitry Andric if (Global->isThreadLocal()) { 2670b57cec5SDimitry Andric if (Asm->TM.useEmulatedTLS()) { 2680b57cec5SDimitry Andric // TODO: add debug info for emulated thread local mode. 2690b57cec5SDimitry Andric } else { 2700b57cec5SDimitry Andric // FIXME: Make this work with -gsplit-dwarf. 2710b57cec5SDimitry Andric // Based on GCC's support for TLS: 2720b57cec5SDimitry Andric if (!DD->useSplitDwarf()) { 2730b57cec5SDimitry Andric // 1) Start with a constNu of the appropriate pointer size 2740b57cec5SDimitry Andric addUInt(*Loc, dwarf::DW_FORM_data1, 2750b57cec5SDimitry Andric PointerSize == 4 ? dwarf::DW_OP_const4u 2760b57cec5SDimitry Andric : dwarf::DW_OP_const8u); 2770b57cec5SDimitry Andric // 2) containing the (relocated) offset of the TLS variable 2780b57cec5SDimitry Andric // within the module's TLS block. 279e8d8bef9SDimitry Andric addExpr(*Loc, 280e8d8bef9SDimitry Andric PointerSize == 4 ? dwarf::DW_FORM_data4 281e8d8bef9SDimitry Andric : dwarf::DW_FORM_data8, 2820b57cec5SDimitry Andric Asm->getObjFileLowering().getDebugThreadLocalSymbol(Sym)); 2830b57cec5SDimitry Andric } else { 2840b57cec5SDimitry Andric addUInt(*Loc, dwarf::DW_FORM_data1, dwarf::DW_OP_GNU_const_index); 2850b57cec5SDimitry Andric addUInt(*Loc, dwarf::DW_FORM_udata, 2860b57cec5SDimitry Andric DD->getAddressPool().getIndex(Sym, /* TLS */ true)); 2870b57cec5SDimitry Andric } 2880b57cec5SDimitry Andric // 3) followed by an OP to make the debugger do a TLS lookup. 2890b57cec5SDimitry Andric addUInt(*Loc, dwarf::DW_FORM_data1, 2900b57cec5SDimitry Andric DD->useGNUTLSOpcode() ? dwarf::DW_OP_GNU_push_tls_address 2910b57cec5SDimitry Andric : dwarf::DW_OP_form_tls_address); 2920b57cec5SDimitry Andric } 293349cc55cSDimitry Andric } else if (Asm->TM.getRelocationModel() == Reloc::RWPI || 294349cc55cSDimitry Andric Asm->TM.getRelocationModel() == Reloc::ROPI_RWPI) { 295349cc55cSDimitry Andric // Constant 296349cc55cSDimitry Andric addUInt(*Loc, dwarf::DW_FORM_data1, 297349cc55cSDimitry Andric PointerSize == 4 ? dwarf::DW_OP_const4u 298349cc55cSDimitry Andric : dwarf::DW_OP_const8u); 299349cc55cSDimitry Andric // Relocation offset 300349cc55cSDimitry Andric addExpr(*Loc, PointerSize == 4 ? dwarf::DW_FORM_data4 301349cc55cSDimitry Andric : dwarf::DW_FORM_data8, 302349cc55cSDimitry Andric Asm->getObjFileLowering().getIndirectSymViaRWPI(Sym)); 303349cc55cSDimitry Andric // Base register 304349cc55cSDimitry Andric Register BaseReg = Asm->getObjFileLowering().getStaticBase(); 305349cc55cSDimitry Andric BaseReg = Asm->TM.getMCRegisterInfo()->getDwarfRegNum(BaseReg, false); 306349cc55cSDimitry Andric addUInt(*Loc, dwarf::DW_FORM_data1, dwarf::DW_OP_breg0 + BaseReg); 307349cc55cSDimitry Andric // Offset from base register 308349cc55cSDimitry Andric addSInt(*Loc, dwarf::DW_FORM_sdata, 0); 309349cc55cSDimitry Andric // Operation 310349cc55cSDimitry Andric addUInt(*Loc, dwarf::DW_FORM_data1, dwarf::DW_OP_plus); 3110b57cec5SDimitry Andric } else { 3120b57cec5SDimitry Andric DD->addArangeLabel(SymbolCU(this, Sym)); 3130b57cec5SDimitry Andric addOpAddress(*Loc, Sym); 3140b57cec5SDimitry Andric } 3150b57cec5SDimitry Andric } 3160b57cec5SDimitry Andric // Global variables attached to symbols are memory locations. 3170b57cec5SDimitry Andric // It would be better if this were unconditional, but malformed input that 3180b57cec5SDimitry Andric // mixes non-fragments and fragments for the same variable is too expensive 3190b57cec5SDimitry Andric // to detect in the verifier. 3200b57cec5SDimitry Andric if (DwarfExpr->isUnknownLocation()) 3210b57cec5SDimitry Andric DwarfExpr->setMemoryLocationKind(); 3220b57cec5SDimitry Andric DwarfExpr->addExpression(Expr); 3230b57cec5SDimitry Andric } 3240b57cec5SDimitry Andric if (Asm->TM.getTargetTriple().isNVPTX() && DD->tuneForGDB()) { 3250b57cec5SDimitry Andric // According to 3260b57cec5SDimitry Andric // https://docs.nvidia.com/cuda/archive/10.0/ptx-writers-guide-to-interoperability/index.html#cuda-specific-dwarf 3270b57cec5SDimitry Andric // cuda-gdb requires DW_AT_address_class for all variables to be able to 3280b57cec5SDimitry Andric // correctly interpret address space of the variable address. 3290b57cec5SDimitry Andric const unsigned NVPTX_ADDR_global_space = 5; 3300b57cec5SDimitry Andric addUInt(*VariableDIE, dwarf::DW_AT_address_class, dwarf::DW_FORM_data1, 3310b57cec5SDimitry Andric NVPTXAddressSpace ? *NVPTXAddressSpace : NVPTX_ADDR_global_space); 3320b57cec5SDimitry Andric } 3330b57cec5SDimitry Andric if (Loc) 3340b57cec5SDimitry Andric addBlock(*VariableDIE, dwarf::DW_AT_location, DwarfExpr->finalize()); 3350b57cec5SDimitry Andric 3360b57cec5SDimitry Andric if (DD->useAllLinkageNames()) 3370b57cec5SDimitry Andric addLinkageName(*VariableDIE, GV->getLinkageName()); 3380b57cec5SDimitry Andric 3390b57cec5SDimitry Andric if (addToAccelTable) { 3400b57cec5SDimitry Andric DD->addAccelName(*CUNode, GV->getName(), *VariableDIE); 3410b57cec5SDimitry Andric 3420b57cec5SDimitry Andric // If the linkage name is different than the name, go ahead and output 3430b57cec5SDimitry Andric // that as well into the name table. 3440b57cec5SDimitry Andric if (GV->getLinkageName() != "" && GV->getName() != GV->getLinkageName() && 3450b57cec5SDimitry Andric DD->useAllLinkageNames()) 3460b57cec5SDimitry Andric DD->addAccelName(*CUNode, GV->getLinkageName(), *VariableDIE); 3470b57cec5SDimitry Andric } 3480b57cec5SDimitry Andric } 3490b57cec5SDimitry Andric 3500b57cec5SDimitry Andric DIE *DwarfCompileUnit::getOrCreateCommonBlock( 3510b57cec5SDimitry Andric const DICommonBlock *CB, ArrayRef<GlobalExpr> GlobalExprs) { 352349cc55cSDimitry Andric // Check for pre-existence. 3530b57cec5SDimitry Andric if (DIE *NDie = getDIE(CB)) 3540b57cec5SDimitry Andric return NDie; 355349cc55cSDimitry Andric DIE *ContextDIE = getOrCreateContextDIE(CB->getScope()); 3560b57cec5SDimitry Andric DIE &NDie = createAndAddDIE(dwarf::DW_TAG_common_block, *ContextDIE, CB); 3570b57cec5SDimitry Andric StringRef Name = CB->getName().empty() ? "_BLNK_" : CB->getName(); 3580b57cec5SDimitry Andric addString(NDie, dwarf::DW_AT_name, Name); 3590b57cec5SDimitry Andric addGlobalName(Name, NDie, CB->getScope()); 3600b57cec5SDimitry Andric if (CB->getFile()) 3610b57cec5SDimitry Andric addSourceLine(NDie, CB->getLineNo(), CB->getFile()); 3620b57cec5SDimitry Andric if (DIGlobalVariable *V = CB->getDecl()) 3630b57cec5SDimitry Andric getCU().addLocationAttribute(&NDie, V, GlobalExprs); 3640b57cec5SDimitry Andric return &NDie; 3650b57cec5SDimitry Andric } 3660b57cec5SDimitry Andric 3670b57cec5SDimitry Andric void DwarfCompileUnit::addRange(RangeSpan Range) { 3685ffd83dbSDimitry Andric DD->insertSectionLabel(Range.Begin); 3695ffd83dbSDimitry Andric 370349cc55cSDimitry Andric auto *PrevCU = DD->getPrevCU(); 371349cc55cSDimitry Andric bool SameAsPrevCU = this == PrevCU; 3720b57cec5SDimitry Andric DD->setPrevCU(this); 3730b57cec5SDimitry Andric // If we have no current ranges just add the range and return, otherwise, 3740b57cec5SDimitry Andric // check the current section and CU against the previous section and CU we 3750b57cec5SDimitry Andric // emitted into and the subprogram was contained within. If these are the 3760b57cec5SDimitry Andric // same then extend our current range, otherwise add this as a new range. 3770b57cec5SDimitry Andric if (CURanges.empty() || !SameAsPrevCU || 3788bcb0991SDimitry Andric (&CURanges.back().End->getSection() != 3798bcb0991SDimitry Andric &Range.End->getSection())) { 380349cc55cSDimitry Andric // Before a new range is added, always terminate the prior line table. 381349cc55cSDimitry Andric if (PrevCU) 382349cc55cSDimitry Andric DD->terminateLineTable(PrevCU); 3830b57cec5SDimitry Andric CURanges.push_back(Range); 3840b57cec5SDimitry Andric return; 3850b57cec5SDimitry Andric } 3860b57cec5SDimitry Andric 3878bcb0991SDimitry Andric CURanges.back().End = Range.End; 3880b57cec5SDimitry Andric } 3890b57cec5SDimitry Andric 3900b57cec5SDimitry Andric void DwarfCompileUnit::initStmtList() { 3910b57cec5SDimitry Andric if (CUNode->isDebugDirectivesOnly()) 3920b57cec5SDimitry Andric return; 3930b57cec5SDimitry Andric 3940b57cec5SDimitry Andric const TargetLoweringObjectFile &TLOF = Asm->getObjFileLowering(); 3950b57cec5SDimitry Andric if (DD->useSectionsAsReferences()) { 3960b57cec5SDimitry Andric LineTableStartSym = TLOF.getDwarfLineSection()->getBeginSymbol(); 3970b57cec5SDimitry Andric } else { 3980b57cec5SDimitry Andric LineTableStartSym = 3990b57cec5SDimitry Andric Asm->OutStreamer->getDwarfLineTableSymbol(getUniqueID()); 4000b57cec5SDimitry Andric } 4010b57cec5SDimitry Andric 4020b57cec5SDimitry Andric // DW_AT_stmt_list is a offset of line number information for this 4030b57cec5SDimitry Andric // compile unit in debug_line section. For split dwarf this is 4040b57cec5SDimitry Andric // left in the skeleton CU and so not included. 4050b57cec5SDimitry Andric // The line table entries are not always emitted in assembly, so it 4060b57cec5SDimitry Andric // is not okay to use line_table_start here. 4070b57cec5SDimitry Andric addSectionLabel(getUnitDie(), dwarf::DW_AT_stmt_list, LineTableStartSym, 4080b57cec5SDimitry Andric TLOF.getDwarfLineSection()->getBeginSymbol()); 4090b57cec5SDimitry Andric } 4100b57cec5SDimitry Andric 4110b57cec5SDimitry Andric void DwarfCompileUnit::applyStmtList(DIE &D) { 4125ffd83dbSDimitry Andric const TargetLoweringObjectFile &TLOF = Asm->getObjFileLowering(); 4135ffd83dbSDimitry Andric addSectionLabel(D, dwarf::DW_AT_stmt_list, LineTableStartSym, 4145ffd83dbSDimitry Andric TLOF.getDwarfLineSection()->getBeginSymbol()); 4150b57cec5SDimitry Andric } 4160b57cec5SDimitry Andric 4170b57cec5SDimitry Andric void DwarfCompileUnit::attachLowHighPC(DIE &D, const MCSymbol *Begin, 4180b57cec5SDimitry Andric const MCSymbol *End) { 4190b57cec5SDimitry Andric assert(Begin && "Begin label should not be null!"); 4200b57cec5SDimitry Andric assert(End && "End label should not be null!"); 4210b57cec5SDimitry Andric assert(Begin->isDefined() && "Invalid starting label"); 4220b57cec5SDimitry Andric assert(End->isDefined() && "Invalid end label"); 4230b57cec5SDimitry Andric 4240b57cec5SDimitry Andric addLabelAddress(D, dwarf::DW_AT_low_pc, Begin); 4250b57cec5SDimitry Andric if (DD->getDwarfVersion() < 4) 4260b57cec5SDimitry Andric addLabelAddress(D, dwarf::DW_AT_high_pc, End); 4270b57cec5SDimitry Andric else 4280b57cec5SDimitry Andric addLabelDelta(D, dwarf::DW_AT_high_pc, End, Begin); 4290b57cec5SDimitry Andric } 4300b57cec5SDimitry Andric 4310b57cec5SDimitry Andric // Find DIE for the given subprogram and attach appropriate DW_AT_low_pc 4320b57cec5SDimitry Andric // and DW_AT_high_pc attributes. If there are global variables in this 4330b57cec5SDimitry Andric // scope then create and insert DIEs for these variables. 4340b57cec5SDimitry Andric DIE &DwarfCompileUnit::updateSubprogramScopeDIE(const DISubprogram *SP) { 4350b57cec5SDimitry Andric DIE *SPDie = getOrCreateSubprogramDIE(SP, includeMinimalInlineScopes()); 4360b57cec5SDimitry Andric 4375ffd83dbSDimitry Andric SmallVector<RangeSpan, 2> BB_List; 4385ffd83dbSDimitry Andric // If basic block sections are on, ranges for each basic block section has 4395ffd83dbSDimitry Andric // to be emitted separately. 4405ffd83dbSDimitry Andric for (const auto &R : Asm->MBBSectionRanges) 4415ffd83dbSDimitry Andric BB_List.push_back({R.second.BeginLabel, R.second.EndLabel}); 4425ffd83dbSDimitry Andric 4435ffd83dbSDimitry Andric attachRangesOrLowHighPC(*SPDie, BB_List); 4445ffd83dbSDimitry Andric 4450b57cec5SDimitry Andric if (DD->useAppleExtensionAttributes() && 4460b57cec5SDimitry Andric !DD->getCurrentFunction()->getTarget().Options.DisableFramePointerElim( 4470b57cec5SDimitry Andric *DD->getCurrentFunction())) 4480b57cec5SDimitry Andric addFlag(*SPDie, dwarf::DW_AT_APPLE_omit_frame_ptr); 4490b57cec5SDimitry Andric 4500b57cec5SDimitry Andric // Only include DW_AT_frame_base in full debug info 4510b57cec5SDimitry Andric if (!includeMinimalInlineScopes()) { 4525ffd83dbSDimitry Andric const TargetFrameLowering *TFI = Asm->MF->getSubtarget().getFrameLowering(); 4535ffd83dbSDimitry Andric TargetFrameLowering::DwarfFrameBase FrameBase = 4545ffd83dbSDimitry Andric TFI->getDwarfFrameBase(*Asm->MF); 4555ffd83dbSDimitry Andric switch (FrameBase.Kind) { 4565ffd83dbSDimitry Andric case TargetFrameLowering::DwarfFrameBase::Register: { 4575ffd83dbSDimitry Andric if (Register::isPhysicalRegister(FrameBase.Location.Reg)) { 4585ffd83dbSDimitry Andric MachineLocation Location(FrameBase.Location.Reg); 4595ffd83dbSDimitry Andric addAddress(*SPDie, dwarf::DW_AT_frame_base, Location); 4605ffd83dbSDimitry Andric } 4615ffd83dbSDimitry Andric break; 4625ffd83dbSDimitry Andric } 4635ffd83dbSDimitry Andric case TargetFrameLowering::DwarfFrameBase::CFA: { 4640b57cec5SDimitry Andric DIELoc *Loc = new (DIEValueAllocator) DIELoc; 4650b57cec5SDimitry Andric addUInt(*Loc, dwarf::DW_FORM_data1, dwarf::DW_OP_call_frame_cfa); 4660b57cec5SDimitry Andric addBlock(*SPDie, dwarf::DW_AT_frame_base, Loc); 4675ffd83dbSDimitry Andric break; 4685ffd83dbSDimitry Andric } 4695ffd83dbSDimitry Andric case TargetFrameLowering::DwarfFrameBase::WasmFrameBase: { 4705ffd83dbSDimitry Andric // FIXME: duplicated from Target/WebAssembly/WebAssembly.h 4715ffd83dbSDimitry Andric // don't want to depend on target specific headers in this code? 4725ffd83dbSDimitry Andric const unsigned TI_GLOBAL_RELOC = 3; 473fe6060f1SDimitry Andric if (FrameBase.Location.WasmLoc.Kind == TI_GLOBAL_RELOC) { 4745ffd83dbSDimitry Andric // These need to be relocatable. 4755ffd83dbSDimitry Andric assert(FrameBase.Location.WasmLoc.Index == 0); // Only SP so far. 4765ffd83dbSDimitry Andric auto SPSym = cast<MCSymbolWasm>( 4775ffd83dbSDimitry Andric Asm->GetExternalSymbolSymbol("__stack_pointer")); 4785ffd83dbSDimitry Andric // FIXME: this repeats what WebAssemblyMCInstLower:: 4795ffd83dbSDimitry Andric // GetExternalSymbolSymbol does, since if there's no code that 4805ffd83dbSDimitry Andric // refers to this symbol, we have to set it here. 4815ffd83dbSDimitry Andric SPSym->setType(wasm::WASM_SYMBOL_TYPE_GLOBAL); 4825ffd83dbSDimitry Andric SPSym->setGlobalType(wasm::WasmGlobalType{ 4835ffd83dbSDimitry Andric uint8_t(Asm->getSubtargetInfo().getTargetTriple().getArch() == 4845ffd83dbSDimitry Andric Triple::wasm64 4855ffd83dbSDimitry Andric ? wasm::WASM_TYPE_I64 4865ffd83dbSDimitry Andric : wasm::WASM_TYPE_I32), 4875ffd83dbSDimitry Andric true}); 4885ffd83dbSDimitry Andric DIELoc *Loc = new (DIEValueAllocator) DIELoc; 4895ffd83dbSDimitry Andric addUInt(*Loc, dwarf::DW_FORM_data1, dwarf::DW_OP_WASM_location); 490e8d8bef9SDimitry Andric addSInt(*Loc, dwarf::DW_FORM_sdata, TI_GLOBAL_RELOC); 491fe6060f1SDimitry Andric if (!isDwoUnit()) { 492e8d8bef9SDimitry Andric addLabel(*Loc, dwarf::DW_FORM_data4, SPSym); 493fe6060f1SDimitry Andric } else { 494fe6060f1SDimitry Andric // FIXME: when writing dwo, we need to avoid relocations. Probably 495fe6060f1SDimitry Andric // the "right" solution is to treat globals the way func and data 496fe6060f1SDimitry Andric // symbols are (with entries in .debug_addr). 497fe6060f1SDimitry Andric // For now, since we only ever use index 0, this should work as-is. 498fe6060f1SDimitry Andric addUInt(*Loc, dwarf::DW_FORM_data4, FrameBase.Location.WasmLoc.Index); 499fe6060f1SDimitry Andric } 5005ffd83dbSDimitry Andric addUInt(*Loc, dwarf::DW_FORM_data1, dwarf::DW_OP_stack_value); 5015ffd83dbSDimitry Andric addBlock(*SPDie, dwarf::DW_AT_frame_base, Loc); 5020b57cec5SDimitry Andric } else { 5035ffd83dbSDimitry Andric DIELoc *Loc = new (DIEValueAllocator) DIELoc; 5045ffd83dbSDimitry Andric DIEDwarfExpression DwarfExpr(*Asm, *this, *Loc); 5055ffd83dbSDimitry Andric DIExpressionCursor Cursor({}); 5065ffd83dbSDimitry Andric DwarfExpr.addWasmLocation(FrameBase.Location.WasmLoc.Kind, 5075ffd83dbSDimitry Andric FrameBase.Location.WasmLoc.Index); 5085ffd83dbSDimitry Andric DwarfExpr.addExpression(std::move(Cursor)); 5095ffd83dbSDimitry Andric addBlock(*SPDie, dwarf::DW_AT_frame_base, DwarfExpr.finalize()); 5105ffd83dbSDimitry Andric } 5115ffd83dbSDimitry Andric break; 5125ffd83dbSDimitry Andric } 5130b57cec5SDimitry Andric } 5140b57cec5SDimitry Andric } 5150b57cec5SDimitry Andric 5160b57cec5SDimitry Andric // Add name to the name table, we do this here because we're guaranteed 5170b57cec5SDimitry Andric // to have concrete versions of our DW_TAG_subprogram nodes. 5180b57cec5SDimitry Andric DD->addSubprogramNames(*CUNode, SP, *SPDie); 5190b57cec5SDimitry Andric 5200b57cec5SDimitry Andric return *SPDie; 5210b57cec5SDimitry Andric } 5220b57cec5SDimitry Andric 5230b57cec5SDimitry Andric // Construct a DIE for this scope. 524*4824e7fdSDimitry Andric void DwarfCompileUnit::constructScopeDIE(LexicalScope *Scope, 525*4824e7fdSDimitry Andric DIE &ParentScopeDIE) { 5260b57cec5SDimitry Andric if (!Scope || !Scope->getScopeNode()) 5270b57cec5SDimitry Andric return; 5280b57cec5SDimitry Andric 5290b57cec5SDimitry Andric auto *DS = Scope->getScopeNode(); 5300b57cec5SDimitry Andric 5310b57cec5SDimitry Andric assert((Scope->getInlinedAt() || !isa<DISubprogram>(DS)) && 5320b57cec5SDimitry Andric "Only handle inlined subprograms here, use " 5330b57cec5SDimitry Andric "constructSubprogramScopeDIE for non-inlined " 5340b57cec5SDimitry Andric "subprograms"); 5350b57cec5SDimitry Andric 536*4824e7fdSDimitry Andric // Emit inlined subprograms. 5370b57cec5SDimitry Andric if (Scope->getParent() && isa<DISubprogram>(DS)) { 538*4824e7fdSDimitry Andric DIE *ScopeDIE = constructInlinedScopeDIE(Scope); 5390b57cec5SDimitry Andric if (!ScopeDIE) 5400b57cec5SDimitry Andric return; 541*4824e7fdSDimitry Andric 542*4824e7fdSDimitry Andric ParentScopeDIE.addChild(ScopeDIE); 543*4824e7fdSDimitry Andric createAndAddScopeChildren(Scope, *ScopeDIE); 544*4824e7fdSDimitry Andric return; 545*4824e7fdSDimitry Andric } 546*4824e7fdSDimitry Andric 5470b57cec5SDimitry Andric // Early exit when we know the scope DIE is going to be null. 5480b57cec5SDimitry Andric if (DD->isLexicalScopeDIENull(Scope)) 5490b57cec5SDimitry Andric return; 5500b57cec5SDimitry Andric 551*4824e7fdSDimitry Andric // Emit lexical blocks. 552*4824e7fdSDimitry Andric DIE *ScopeDIE = constructLexicalScopeDIE(Scope); 5530b57cec5SDimitry Andric assert(ScopeDIE && "Scope DIE should not be null."); 5540b57cec5SDimitry Andric 555*4824e7fdSDimitry Andric ParentScopeDIE.addChild(ScopeDIE); 556*4824e7fdSDimitry Andric createAndAddScopeChildren(Scope, *ScopeDIE); 5570b57cec5SDimitry Andric } 5580b57cec5SDimitry Andric 5590b57cec5SDimitry Andric void DwarfCompileUnit::addScopeRangeList(DIE &ScopeDIE, 5600b57cec5SDimitry Andric SmallVector<RangeSpan, 2> Range) { 5610b57cec5SDimitry Andric 5620b57cec5SDimitry Andric HasRangeLists = true; 5630b57cec5SDimitry Andric 5640b57cec5SDimitry Andric // Add the range list to the set of ranges to be emitted. 5650b57cec5SDimitry Andric auto IndexAndList = 5660b57cec5SDimitry Andric (DD->getDwarfVersion() < 5 && Skeleton ? Skeleton->DU : DU) 5670b57cec5SDimitry Andric ->addRange(*(Skeleton ? Skeleton : this), std::move(Range)); 5680b57cec5SDimitry Andric 5690b57cec5SDimitry Andric uint32_t Index = IndexAndList.first; 5700b57cec5SDimitry Andric auto &List = *IndexAndList.second; 5710b57cec5SDimitry Andric 5720b57cec5SDimitry Andric // Under fission, ranges are specified by constant offsets relative to the 5730b57cec5SDimitry Andric // CU's DW_AT_GNU_ranges_base. 5740b57cec5SDimitry Andric // FIXME: For DWARF v5, do not generate the DW_AT_ranges attribute under 5750b57cec5SDimitry Andric // fission until we support the forms using the .debug_addr section 5760b57cec5SDimitry Andric // (DW_RLE_startx_endx etc.). 5770b57cec5SDimitry Andric if (DD->getDwarfVersion() >= 5) 5780b57cec5SDimitry Andric addUInt(ScopeDIE, dwarf::DW_AT_ranges, dwarf::DW_FORM_rnglistx, Index); 5798bcb0991SDimitry Andric else { 5808bcb0991SDimitry Andric const TargetLoweringObjectFile &TLOF = Asm->getObjFileLowering(); 5818bcb0991SDimitry Andric const MCSymbol *RangeSectionSym = 5828bcb0991SDimitry Andric TLOF.getDwarfRangesSection()->getBeginSymbol(); 5838bcb0991SDimitry Andric if (isDwoUnit()) 584480093f4SDimitry Andric addSectionDelta(ScopeDIE, dwarf::DW_AT_ranges, List.Label, 5850b57cec5SDimitry Andric RangeSectionSym); 5860b57cec5SDimitry Andric else 587480093f4SDimitry Andric addSectionLabel(ScopeDIE, dwarf::DW_AT_ranges, List.Label, 5880b57cec5SDimitry Andric RangeSectionSym); 5890b57cec5SDimitry Andric } 5908bcb0991SDimitry Andric } 5910b57cec5SDimitry Andric 5920b57cec5SDimitry Andric void DwarfCompileUnit::attachRangesOrLowHighPC( 5930b57cec5SDimitry Andric DIE &Die, SmallVector<RangeSpan, 2> Ranges) { 594e8d8bef9SDimitry Andric assert(!Ranges.empty()); 595e8d8bef9SDimitry Andric if (!DD->useRangesSection() || 596e8d8bef9SDimitry Andric (Ranges.size() == 1 && 597e8d8bef9SDimitry Andric (!DD->alwaysUseRanges() || 598e8d8bef9SDimitry Andric DD->getSectionLabel(&Ranges.front().Begin->getSection()) == 599e8d8bef9SDimitry Andric Ranges.front().Begin))) { 6000b57cec5SDimitry Andric const RangeSpan &Front = Ranges.front(); 6010b57cec5SDimitry Andric const RangeSpan &Back = Ranges.back(); 6028bcb0991SDimitry Andric attachLowHighPC(Die, Front.Begin, Back.End); 6030b57cec5SDimitry Andric } else 6040b57cec5SDimitry Andric addScopeRangeList(Die, std::move(Ranges)); 6050b57cec5SDimitry Andric } 6060b57cec5SDimitry Andric 6070b57cec5SDimitry Andric void DwarfCompileUnit::attachRangesOrLowHighPC( 6080b57cec5SDimitry Andric DIE &Die, const SmallVectorImpl<InsnRange> &Ranges) { 6090b57cec5SDimitry Andric SmallVector<RangeSpan, 2> List; 6100b57cec5SDimitry Andric List.reserve(Ranges.size()); 6115ffd83dbSDimitry Andric for (const InsnRange &R : Ranges) { 6125ffd83dbSDimitry Andric auto *BeginLabel = DD->getLabelBeforeInsn(R.first); 6135ffd83dbSDimitry Andric auto *EndLabel = DD->getLabelAfterInsn(R.second); 6145ffd83dbSDimitry Andric 6155ffd83dbSDimitry Andric const auto *BeginMBB = R.first->getParent(); 6165ffd83dbSDimitry Andric const auto *EndMBB = R.second->getParent(); 6175ffd83dbSDimitry Andric 6185ffd83dbSDimitry Andric const auto *MBB = BeginMBB; 6195ffd83dbSDimitry Andric // Basic block sections allows basic block subsets to be placed in unique 6205ffd83dbSDimitry Andric // sections. For each section, the begin and end label must be added to the 6215ffd83dbSDimitry Andric // list. If there is more than one range, debug ranges must be used. 6225ffd83dbSDimitry Andric // Otherwise, low/high PC can be used. 6235ffd83dbSDimitry Andric // FIXME: Debug Info Emission depends on block order and this assumes that 6245ffd83dbSDimitry Andric // the order of blocks will be frozen beyond this point. 6255ffd83dbSDimitry Andric do { 6265ffd83dbSDimitry Andric if (MBB->sameSection(EndMBB) || MBB->isEndSection()) { 6275ffd83dbSDimitry Andric auto MBBSectionRange = Asm->MBBSectionRanges[MBB->getSectionIDNum()]; 6288bcb0991SDimitry Andric List.push_back( 6295ffd83dbSDimitry Andric {MBB->sameSection(BeginMBB) ? BeginLabel 6305ffd83dbSDimitry Andric : MBBSectionRange.BeginLabel, 6315ffd83dbSDimitry Andric MBB->sameSection(EndMBB) ? EndLabel : MBBSectionRange.EndLabel}); 6325ffd83dbSDimitry Andric } 6335ffd83dbSDimitry Andric if (MBB->sameSection(EndMBB)) 6345ffd83dbSDimitry Andric break; 6355ffd83dbSDimitry Andric MBB = MBB->getNextNode(); 6365ffd83dbSDimitry Andric } while (true); 6375ffd83dbSDimitry Andric } 6380b57cec5SDimitry Andric attachRangesOrLowHighPC(Die, std::move(List)); 6390b57cec5SDimitry Andric } 6400b57cec5SDimitry Andric 6410b57cec5SDimitry Andric // This scope represents inlined body of a function. Construct DIE to 6420b57cec5SDimitry Andric // represent this concrete inlined copy of the function. 6430b57cec5SDimitry Andric DIE *DwarfCompileUnit::constructInlinedScopeDIE(LexicalScope *Scope) { 6440b57cec5SDimitry Andric assert(Scope->getScopeNode()); 6450b57cec5SDimitry Andric auto *DS = Scope->getScopeNode(); 6460b57cec5SDimitry Andric auto *InlinedSP = getDISubprogram(DS); 6470b57cec5SDimitry Andric // Find the subprogram's DwarfCompileUnit in the SPMap in case the subprogram 6480b57cec5SDimitry Andric // was inlined from another compile unit. 6490b57cec5SDimitry Andric DIE *OriginDIE = getAbstractSPDies()[InlinedSP]; 6500b57cec5SDimitry Andric assert(OriginDIE && "Unable to find original DIE for an inlined subprogram."); 6510b57cec5SDimitry Andric 6520b57cec5SDimitry Andric auto ScopeDIE = DIE::get(DIEValueAllocator, dwarf::DW_TAG_inlined_subroutine); 6530b57cec5SDimitry Andric addDIEEntry(*ScopeDIE, dwarf::DW_AT_abstract_origin, *OriginDIE); 6540b57cec5SDimitry Andric 6550b57cec5SDimitry Andric attachRangesOrLowHighPC(*ScopeDIE, Scope->getRanges()); 6560b57cec5SDimitry Andric 6570b57cec5SDimitry Andric // Add the call site information to the DIE. 6580b57cec5SDimitry Andric const DILocation *IA = Scope->getInlinedAt(); 6590b57cec5SDimitry Andric addUInt(*ScopeDIE, dwarf::DW_AT_call_file, None, 6600b57cec5SDimitry Andric getOrCreateSourceID(IA->getFile())); 6610b57cec5SDimitry Andric addUInt(*ScopeDIE, dwarf::DW_AT_call_line, None, IA->getLine()); 6620b57cec5SDimitry Andric if (IA->getColumn()) 6630b57cec5SDimitry Andric addUInt(*ScopeDIE, dwarf::DW_AT_call_column, None, IA->getColumn()); 6640b57cec5SDimitry Andric if (IA->getDiscriminator() && DD->getDwarfVersion() >= 4) 6650b57cec5SDimitry Andric addUInt(*ScopeDIE, dwarf::DW_AT_GNU_discriminator, None, 6660b57cec5SDimitry Andric IA->getDiscriminator()); 6670b57cec5SDimitry Andric 6680b57cec5SDimitry Andric // Add name to the name table, we do this here because we're guaranteed 6690b57cec5SDimitry Andric // to have concrete versions of our DW_TAG_inlined_subprogram nodes. 6700b57cec5SDimitry Andric DD->addSubprogramNames(*CUNode, InlinedSP, *ScopeDIE); 6710b57cec5SDimitry Andric 6720b57cec5SDimitry Andric return ScopeDIE; 6730b57cec5SDimitry Andric } 6740b57cec5SDimitry Andric 6750b57cec5SDimitry Andric // Construct new DW_TAG_lexical_block for this scope and attach 6760b57cec5SDimitry Andric // DW_AT_low_pc/DW_AT_high_pc labels. 6770b57cec5SDimitry Andric DIE *DwarfCompileUnit::constructLexicalScopeDIE(LexicalScope *Scope) { 6780b57cec5SDimitry Andric if (DD->isLexicalScopeDIENull(Scope)) 6790b57cec5SDimitry Andric return nullptr; 6800b57cec5SDimitry Andric 6810b57cec5SDimitry Andric auto ScopeDIE = DIE::get(DIEValueAllocator, dwarf::DW_TAG_lexical_block); 6820b57cec5SDimitry Andric if (Scope->isAbstractScope()) 6830b57cec5SDimitry Andric return ScopeDIE; 6840b57cec5SDimitry Andric 6850b57cec5SDimitry Andric attachRangesOrLowHighPC(*ScopeDIE, Scope->getRanges()); 6860b57cec5SDimitry Andric 6870b57cec5SDimitry Andric return ScopeDIE; 6880b57cec5SDimitry Andric } 6890b57cec5SDimitry Andric 6900b57cec5SDimitry Andric /// constructVariableDIE - Construct a DIE for the given DbgVariable. 6910b57cec5SDimitry Andric DIE *DwarfCompileUnit::constructVariableDIE(DbgVariable &DV, bool Abstract) { 6920b57cec5SDimitry Andric auto D = constructVariableDIEImpl(DV, Abstract); 6930b57cec5SDimitry Andric DV.setDIE(*D); 6940b57cec5SDimitry Andric return D; 6950b57cec5SDimitry Andric } 6960b57cec5SDimitry Andric 6970b57cec5SDimitry Andric DIE *DwarfCompileUnit::constructLabelDIE(DbgLabel &DL, 6980b57cec5SDimitry Andric const LexicalScope &Scope) { 6990b57cec5SDimitry Andric auto LabelDie = DIE::get(DIEValueAllocator, DL.getTag()); 7000b57cec5SDimitry Andric insertDIE(DL.getLabel(), LabelDie); 7010b57cec5SDimitry Andric DL.setDIE(*LabelDie); 7020b57cec5SDimitry Andric 7030b57cec5SDimitry Andric if (Scope.isAbstractScope()) 7040b57cec5SDimitry Andric applyLabelAttributes(DL, *LabelDie); 7050b57cec5SDimitry Andric 7060b57cec5SDimitry Andric return LabelDie; 7070b57cec5SDimitry Andric } 7080b57cec5SDimitry Andric 7090b57cec5SDimitry Andric DIE *DwarfCompileUnit::constructVariableDIEImpl(const DbgVariable &DV, 7100b57cec5SDimitry Andric bool Abstract) { 7110b57cec5SDimitry Andric // Define variable debug information entry. 7120b57cec5SDimitry Andric auto VariableDie = DIE::get(DIEValueAllocator, DV.getTag()); 7130b57cec5SDimitry Andric insertDIE(DV.getVariable(), VariableDie); 7140b57cec5SDimitry Andric 7150b57cec5SDimitry Andric if (Abstract) { 7160b57cec5SDimitry Andric applyVariableAttributes(DV, *VariableDie); 7170b57cec5SDimitry Andric return VariableDie; 7180b57cec5SDimitry Andric } 7190b57cec5SDimitry Andric 7200b57cec5SDimitry Andric // Add variable address. 7210b57cec5SDimitry Andric 722e8d8bef9SDimitry Andric unsigned Index = DV.getDebugLocListIndex(); 723e8d8bef9SDimitry Andric if (Index != ~0U) { 724e8d8bef9SDimitry Andric addLocationList(*VariableDie, dwarf::DW_AT_location, Index); 725480093f4SDimitry Andric auto TagOffset = DV.getDebugLocListTagOffset(); 726480093f4SDimitry Andric if (TagOffset) 727480093f4SDimitry Andric addUInt(*VariableDie, dwarf::DW_AT_LLVM_tag_offset, dwarf::DW_FORM_data1, 728480093f4SDimitry Andric *TagOffset); 7290b57cec5SDimitry Andric return VariableDie; 7300b57cec5SDimitry Andric } 7310b57cec5SDimitry Andric 7320b57cec5SDimitry Andric // Check if variable has a single location description. 7330b57cec5SDimitry Andric if (auto *DVal = DV.getValueLoc()) { 734fe6060f1SDimitry Andric if (!DVal->isVariadic()) { 735fe6060f1SDimitry Andric const DbgValueLocEntry *Entry = DVal->getLocEntries().begin(); 736fe6060f1SDimitry Andric if (Entry->isLocation()) { 737fe6060f1SDimitry Andric addVariableAddress(DV, *VariableDie, Entry->getLoc()); 738fe6060f1SDimitry Andric } else if (Entry->isInt()) { 7390b57cec5SDimitry Andric auto *Expr = DV.getSingleExpression(); 7400b57cec5SDimitry Andric if (Expr && Expr->getNumElements()) { 7410b57cec5SDimitry Andric DIELoc *Loc = new (DIEValueAllocator) DIELoc; 7420b57cec5SDimitry Andric DIEDwarfExpression DwarfExpr(*Asm, *this, *Loc); 7430b57cec5SDimitry Andric // If there is an expression, emit raw unsigned bytes. 7440b57cec5SDimitry Andric DwarfExpr.addFragmentOffset(Expr); 745fe6060f1SDimitry Andric DwarfExpr.addUnsignedConstant(Entry->getInt()); 7460b57cec5SDimitry Andric DwarfExpr.addExpression(Expr); 7470b57cec5SDimitry Andric addBlock(*VariableDie, dwarf::DW_AT_location, DwarfExpr.finalize()); 748480093f4SDimitry Andric if (DwarfExpr.TagOffset) 749480093f4SDimitry Andric addUInt(*VariableDie, dwarf::DW_AT_LLVM_tag_offset, 750480093f4SDimitry Andric dwarf::DW_FORM_data1, *DwarfExpr.TagOffset); 7510b57cec5SDimitry Andric } else 752fe6060f1SDimitry Andric addConstantValue(*VariableDie, Entry->getInt(), DV.getType()); 753fe6060f1SDimitry Andric } else if (Entry->isConstantFP()) { 754fe6060f1SDimitry Andric addConstantFPValue(*VariableDie, Entry->getConstantFP()); 755fe6060f1SDimitry Andric } else if (Entry->isConstantInt()) { 756fe6060f1SDimitry Andric addConstantValue(*VariableDie, Entry->getConstantInt(), DV.getType()); 757fe6060f1SDimitry Andric } else if (Entry->isTargetIndexLocation()) { 758e8d8bef9SDimitry Andric DIELoc *Loc = new (DIEValueAllocator) DIELoc; 759e8d8bef9SDimitry Andric DIEDwarfExpression DwarfExpr(*Asm, *this, *Loc); 760e8d8bef9SDimitry Andric const DIBasicType *BT = dyn_cast<DIBasicType>( 761e8d8bef9SDimitry Andric static_cast<const Metadata *>(DV.getVariable()->getType())); 762e8d8bef9SDimitry Andric DwarfDebug::emitDebugLocValue(*Asm, BT, *DVal, DwarfExpr); 763e8d8bef9SDimitry Andric addBlock(*VariableDie, dwarf::DW_AT_location, DwarfExpr.finalize()); 7640b57cec5SDimitry Andric } 7650b57cec5SDimitry Andric return VariableDie; 7660b57cec5SDimitry Andric } 767fe6060f1SDimitry Andric // If any of the location entries are registers with the value 0, then the 768fe6060f1SDimitry Andric // location is undefined. 769fe6060f1SDimitry Andric if (any_of(DVal->getLocEntries(), [](const DbgValueLocEntry &Entry) { 770fe6060f1SDimitry Andric return Entry.isLocation() && !Entry.getLoc().getReg(); 771fe6060f1SDimitry Andric })) 772fe6060f1SDimitry Andric return VariableDie; 773fe6060f1SDimitry Andric const DIExpression *Expr = DV.getSingleExpression(); 774fe6060f1SDimitry Andric assert(Expr && "Variadic Debug Value must have an Expression."); 775fe6060f1SDimitry Andric DIELoc *Loc = new (DIEValueAllocator) DIELoc; 776fe6060f1SDimitry Andric DIEDwarfExpression DwarfExpr(*Asm, *this, *Loc); 777fe6060f1SDimitry Andric DwarfExpr.addFragmentOffset(Expr); 778fe6060f1SDimitry Andric DIExpressionCursor Cursor(Expr); 779fe6060f1SDimitry Andric const TargetRegisterInfo &TRI = *Asm->MF->getSubtarget().getRegisterInfo(); 780fe6060f1SDimitry Andric 781fe6060f1SDimitry Andric auto AddEntry = [&](const DbgValueLocEntry &Entry, 782fe6060f1SDimitry Andric DIExpressionCursor &Cursor) { 783fe6060f1SDimitry Andric if (Entry.isLocation()) { 784fe6060f1SDimitry Andric if (!DwarfExpr.addMachineRegExpression(TRI, Cursor, 785fe6060f1SDimitry Andric Entry.getLoc().getReg())) 786fe6060f1SDimitry Andric return false; 787fe6060f1SDimitry Andric } else if (Entry.isInt()) { 788fe6060f1SDimitry Andric // If there is an expression, emit raw unsigned bytes. 789fe6060f1SDimitry Andric DwarfExpr.addUnsignedConstant(Entry.getInt()); 790fe6060f1SDimitry Andric } else if (Entry.isConstantFP()) { 7919738bc28SDimitry Andric // DwarfExpression does not support arguments wider than 64 bits 7929738bc28SDimitry Andric // (see PR52584). 7939738bc28SDimitry Andric // TODO: Consider chunking expressions containing overly wide 7949738bc28SDimitry Andric // arguments into separate pointer-sized fragment expressions. 795fe6060f1SDimitry Andric APInt RawBytes = Entry.getConstantFP()->getValueAPF().bitcastToAPInt(); 7969738bc28SDimitry Andric if (RawBytes.getBitWidth() > 64) 7979738bc28SDimitry Andric return false; 7989738bc28SDimitry Andric DwarfExpr.addUnsignedConstant(RawBytes.getZExtValue()); 799fe6060f1SDimitry Andric } else if (Entry.isConstantInt()) { 800fe6060f1SDimitry Andric APInt RawBytes = Entry.getConstantInt()->getValue(); 8019738bc28SDimitry Andric if (RawBytes.getBitWidth() > 64) 8029738bc28SDimitry Andric return false; 8039738bc28SDimitry Andric DwarfExpr.addUnsignedConstant(RawBytes.getZExtValue()); 804fe6060f1SDimitry Andric } else if (Entry.isTargetIndexLocation()) { 805fe6060f1SDimitry Andric TargetIndexLocation Loc = Entry.getTargetIndexLocation(); 806fe6060f1SDimitry Andric // TODO TargetIndexLocation is a target-independent. Currently only the 807fe6060f1SDimitry Andric // WebAssembly-specific encoding is supported. 808fe6060f1SDimitry Andric assert(Asm->TM.getTargetTriple().isWasm()); 809fe6060f1SDimitry Andric DwarfExpr.addWasmLocation(Loc.Index, static_cast<uint64_t>(Loc.Offset)); 810fe6060f1SDimitry Andric } else { 811fe6060f1SDimitry Andric llvm_unreachable("Unsupported Entry type."); 812fe6060f1SDimitry Andric } 813fe6060f1SDimitry Andric return true; 814fe6060f1SDimitry Andric }; 815fe6060f1SDimitry Andric 8169738bc28SDimitry Andric if (!DwarfExpr.addExpression( 817fe6060f1SDimitry Andric std::move(Cursor), 818fe6060f1SDimitry Andric [&](unsigned Idx, DIExpressionCursor &Cursor) -> bool { 819fe6060f1SDimitry Andric return AddEntry(DVal->getLocEntries()[Idx], Cursor); 8209738bc28SDimitry Andric })) 8219738bc28SDimitry Andric return VariableDie; 822fe6060f1SDimitry Andric 823fe6060f1SDimitry Andric // Now attach the location information to the DIE. 824fe6060f1SDimitry Andric addBlock(*VariableDie, dwarf::DW_AT_location, DwarfExpr.finalize()); 825fe6060f1SDimitry Andric if (DwarfExpr.TagOffset) 826fe6060f1SDimitry Andric addUInt(*VariableDie, dwarf::DW_AT_LLVM_tag_offset, dwarf::DW_FORM_data1, 827fe6060f1SDimitry Andric *DwarfExpr.TagOffset); 828fe6060f1SDimitry Andric 829fe6060f1SDimitry Andric return VariableDie; 830fe6060f1SDimitry Andric } 8310b57cec5SDimitry Andric 8320b57cec5SDimitry Andric // .. else use frame index. 8330b57cec5SDimitry Andric if (!DV.hasFrameIndexExprs()) 8340b57cec5SDimitry Andric return VariableDie; 8350b57cec5SDimitry Andric 8360b57cec5SDimitry Andric Optional<unsigned> NVPTXAddressSpace; 8370b57cec5SDimitry Andric DIELoc *Loc = new (DIEValueAllocator) DIELoc; 8380b57cec5SDimitry Andric DIEDwarfExpression DwarfExpr(*Asm, *this, *Loc); 8390b57cec5SDimitry Andric for (auto &Fragment : DV.getFrameIndexExprs()) { 8405ffd83dbSDimitry Andric Register FrameReg; 8410b57cec5SDimitry Andric const DIExpression *Expr = Fragment.Expr; 8420b57cec5SDimitry Andric const TargetFrameLowering *TFI = Asm->MF->getSubtarget().getFrameLowering(); 843e8d8bef9SDimitry Andric StackOffset Offset = 844e8d8bef9SDimitry Andric TFI->getFrameIndexReference(*Asm->MF, Fragment.FI, FrameReg); 8450b57cec5SDimitry Andric DwarfExpr.addFragmentOffset(Expr); 846e8d8bef9SDimitry Andric 847e8d8bef9SDimitry Andric auto *TRI = Asm->MF->getSubtarget().getRegisterInfo(); 8480b57cec5SDimitry Andric SmallVector<uint64_t, 8> Ops; 849e8d8bef9SDimitry Andric TRI->getOffsetOpcodes(Offset, Ops); 850e8d8bef9SDimitry Andric 8510b57cec5SDimitry Andric // According to 8520b57cec5SDimitry Andric // https://docs.nvidia.com/cuda/archive/10.0/ptx-writers-guide-to-interoperability/index.html#cuda-specific-dwarf 8530b57cec5SDimitry Andric // cuda-gdb requires DW_AT_address_class for all variables to be able to 8540b57cec5SDimitry Andric // correctly interpret address space of the variable address. 8550b57cec5SDimitry Andric // Decode DW_OP_constu <DWARF Address Space> DW_OP_swap DW_OP_xderef 8560b57cec5SDimitry Andric // sequence for the NVPTX + gdb target. 8570b57cec5SDimitry Andric unsigned LocalNVPTXAddressSpace; 8580b57cec5SDimitry Andric if (Asm->TM.getTargetTriple().isNVPTX() && DD->tuneForGDB()) { 8590b57cec5SDimitry Andric const DIExpression *NewExpr = 8600b57cec5SDimitry Andric DIExpression::extractAddressClass(Expr, LocalNVPTXAddressSpace); 8610b57cec5SDimitry Andric if (NewExpr != Expr) { 8620b57cec5SDimitry Andric Expr = NewExpr; 8630b57cec5SDimitry Andric NVPTXAddressSpace = LocalNVPTXAddressSpace; 8640b57cec5SDimitry Andric } 8650b57cec5SDimitry Andric } 8660b57cec5SDimitry Andric if (Expr) 8670b57cec5SDimitry Andric Ops.append(Expr->elements_begin(), Expr->elements_end()); 8680b57cec5SDimitry Andric DIExpressionCursor Cursor(Ops); 8690b57cec5SDimitry Andric DwarfExpr.setMemoryLocationKind(); 8700b57cec5SDimitry Andric if (const MCSymbol *FrameSymbol = Asm->getFunctionFrameSymbol()) 8710b57cec5SDimitry Andric addOpAddress(*Loc, FrameSymbol); 8720b57cec5SDimitry Andric else 8730b57cec5SDimitry Andric DwarfExpr.addMachineRegExpression( 8740b57cec5SDimitry Andric *Asm->MF->getSubtarget().getRegisterInfo(), Cursor, FrameReg); 8750b57cec5SDimitry Andric DwarfExpr.addExpression(std::move(Cursor)); 8760b57cec5SDimitry Andric } 8770b57cec5SDimitry Andric if (Asm->TM.getTargetTriple().isNVPTX() && DD->tuneForGDB()) { 8780b57cec5SDimitry Andric // According to 8790b57cec5SDimitry Andric // https://docs.nvidia.com/cuda/archive/10.0/ptx-writers-guide-to-interoperability/index.html#cuda-specific-dwarf 8800b57cec5SDimitry Andric // cuda-gdb requires DW_AT_address_class for all variables to be able to 8810b57cec5SDimitry Andric // correctly interpret address space of the variable address. 8820b57cec5SDimitry Andric const unsigned NVPTX_ADDR_local_space = 6; 8830b57cec5SDimitry Andric addUInt(*VariableDie, dwarf::DW_AT_address_class, dwarf::DW_FORM_data1, 8840b57cec5SDimitry Andric NVPTXAddressSpace ? *NVPTXAddressSpace : NVPTX_ADDR_local_space); 8850b57cec5SDimitry Andric } 8860b57cec5SDimitry Andric addBlock(*VariableDie, dwarf::DW_AT_location, DwarfExpr.finalize()); 8870b57cec5SDimitry Andric if (DwarfExpr.TagOffset) 8880b57cec5SDimitry Andric addUInt(*VariableDie, dwarf::DW_AT_LLVM_tag_offset, dwarf::DW_FORM_data1, 8890b57cec5SDimitry Andric *DwarfExpr.TagOffset); 8900b57cec5SDimitry Andric 8910b57cec5SDimitry Andric return VariableDie; 8920b57cec5SDimitry Andric } 8930b57cec5SDimitry Andric 8940b57cec5SDimitry Andric DIE *DwarfCompileUnit::constructVariableDIE(DbgVariable &DV, 8950b57cec5SDimitry Andric const LexicalScope &Scope, 8960b57cec5SDimitry Andric DIE *&ObjectPointer) { 8970b57cec5SDimitry Andric auto Var = constructVariableDIE(DV, Scope.isAbstractScope()); 8980b57cec5SDimitry Andric if (DV.isObjectPointer()) 8990b57cec5SDimitry Andric ObjectPointer = Var; 9000b57cec5SDimitry Andric return Var; 9010b57cec5SDimitry Andric } 9020b57cec5SDimitry Andric 9030b57cec5SDimitry Andric /// Return all DIVariables that appear in count: expressions. 9040b57cec5SDimitry Andric static SmallVector<const DIVariable *, 2> dependencies(DbgVariable *Var) { 9050b57cec5SDimitry Andric SmallVector<const DIVariable *, 2> Result; 9060b57cec5SDimitry Andric auto *Array = dyn_cast<DICompositeType>(Var->getType()); 9070b57cec5SDimitry Andric if (!Array || Array->getTag() != dwarf::DW_TAG_array_type) 9080b57cec5SDimitry Andric return Result; 9095ffd83dbSDimitry Andric if (auto *DLVar = Array->getDataLocation()) 9105ffd83dbSDimitry Andric Result.push_back(DLVar); 911e8d8bef9SDimitry Andric if (auto *AsVar = Array->getAssociated()) 912e8d8bef9SDimitry Andric Result.push_back(AsVar); 913e8d8bef9SDimitry Andric if (auto *AlVar = Array->getAllocated()) 914e8d8bef9SDimitry Andric Result.push_back(AlVar); 9150b57cec5SDimitry Andric for (auto *El : Array->getElements()) { 9160b57cec5SDimitry Andric if (auto *Subrange = dyn_cast<DISubrange>(El)) { 9175ffd83dbSDimitry Andric if (auto Count = Subrange->getCount()) 9180b57cec5SDimitry Andric if (auto *Dependency = Count.dyn_cast<DIVariable *>()) 9190b57cec5SDimitry Andric Result.push_back(Dependency); 9205ffd83dbSDimitry Andric if (auto LB = Subrange->getLowerBound()) 9215ffd83dbSDimitry Andric if (auto *Dependency = LB.dyn_cast<DIVariable *>()) 9225ffd83dbSDimitry Andric Result.push_back(Dependency); 9235ffd83dbSDimitry Andric if (auto UB = Subrange->getUpperBound()) 9245ffd83dbSDimitry Andric if (auto *Dependency = UB.dyn_cast<DIVariable *>()) 9255ffd83dbSDimitry Andric Result.push_back(Dependency); 9265ffd83dbSDimitry Andric if (auto ST = Subrange->getStride()) 9275ffd83dbSDimitry Andric if (auto *Dependency = ST.dyn_cast<DIVariable *>()) 9285ffd83dbSDimitry Andric Result.push_back(Dependency); 929e8d8bef9SDimitry Andric } else if (auto *GenericSubrange = dyn_cast<DIGenericSubrange>(El)) { 930e8d8bef9SDimitry Andric if (auto Count = GenericSubrange->getCount()) 931e8d8bef9SDimitry Andric if (auto *Dependency = Count.dyn_cast<DIVariable *>()) 932e8d8bef9SDimitry Andric Result.push_back(Dependency); 933e8d8bef9SDimitry Andric if (auto LB = GenericSubrange->getLowerBound()) 934e8d8bef9SDimitry Andric if (auto *Dependency = LB.dyn_cast<DIVariable *>()) 935e8d8bef9SDimitry Andric Result.push_back(Dependency); 936e8d8bef9SDimitry Andric if (auto UB = GenericSubrange->getUpperBound()) 937e8d8bef9SDimitry Andric if (auto *Dependency = UB.dyn_cast<DIVariable *>()) 938e8d8bef9SDimitry Andric Result.push_back(Dependency); 939e8d8bef9SDimitry Andric if (auto ST = GenericSubrange->getStride()) 940e8d8bef9SDimitry Andric if (auto *Dependency = ST.dyn_cast<DIVariable *>()) 941e8d8bef9SDimitry Andric Result.push_back(Dependency); 9420b57cec5SDimitry Andric } 9430b57cec5SDimitry Andric } 9440b57cec5SDimitry Andric return Result; 9450b57cec5SDimitry Andric } 9460b57cec5SDimitry Andric 9470b57cec5SDimitry Andric /// Sort local variables so that variables appearing inside of helper 9480b57cec5SDimitry Andric /// expressions come first. 9490b57cec5SDimitry Andric static SmallVector<DbgVariable *, 8> 9500b57cec5SDimitry Andric sortLocalVars(SmallVectorImpl<DbgVariable *> &Input) { 9510b57cec5SDimitry Andric SmallVector<DbgVariable *, 8> Result; 9520b57cec5SDimitry Andric SmallVector<PointerIntPair<DbgVariable *, 1>, 8> WorkList; 9530b57cec5SDimitry Andric // Map back from a DIVariable to its containing DbgVariable. 9540b57cec5SDimitry Andric SmallDenseMap<const DILocalVariable *, DbgVariable *> DbgVar; 9550b57cec5SDimitry Andric // Set of DbgVariables in Result. 9560b57cec5SDimitry Andric SmallDenseSet<DbgVariable *, 8> Visited; 9570b57cec5SDimitry Andric // For cycle detection. 9580b57cec5SDimitry Andric SmallDenseSet<DbgVariable *, 8> Visiting; 9590b57cec5SDimitry Andric 9600b57cec5SDimitry Andric // Initialize the worklist and the DIVariable lookup table. 9610b57cec5SDimitry Andric for (auto Var : reverse(Input)) { 9620b57cec5SDimitry Andric DbgVar.insert({Var->getVariable(), Var}); 9630b57cec5SDimitry Andric WorkList.push_back({Var, 0}); 9640b57cec5SDimitry Andric } 9650b57cec5SDimitry Andric 9660b57cec5SDimitry Andric // Perform a stable topological sort by doing a DFS. 9670b57cec5SDimitry Andric while (!WorkList.empty()) { 9680b57cec5SDimitry Andric auto Item = WorkList.back(); 9690b57cec5SDimitry Andric DbgVariable *Var = Item.getPointer(); 9700b57cec5SDimitry Andric bool visitedAllDependencies = Item.getInt(); 9710b57cec5SDimitry Andric WorkList.pop_back(); 9720b57cec5SDimitry Andric 973349cc55cSDimitry Andric assert(Var); 9740b57cec5SDimitry Andric 9750b57cec5SDimitry Andric // Already handled. 9760b57cec5SDimitry Andric if (Visited.count(Var)) 9770b57cec5SDimitry Andric continue; 9780b57cec5SDimitry Andric 9790b57cec5SDimitry Andric // Add to Result if all dependencies are visited. 9800b57cec5SDimitry Andric if (visitedAllDependencies) { 9810b57cec5SDimitry Andric Visited.insert(Var); 9820b57cec5SDimitry Andric Result.push_back(Var); 9830b57cec5SDimitry Andric continue; 9840b57cec5SDimitry Andric } 9850b57cec5SDimitry Andric 9860b57cec5SDimitry Andric // Detect cycles. 9870b57cec5SDimitry Andric auto Res = Visiting.insert(Var); 9880b57cec5SDimitry Andric if (!Res.second) { 9890b57cec5SDimitry Andric assert(false && "dependency cycle in local variables"); 9900b57cec5SDimitry Andric return Result; 9910b57cec5SDimitry Andric } 9920b57cec5SDimitry Andric 9930b57cec5SDimitry Andric // Push dependencies and this node onto the worklist, so that this node is 9940b57cec5SDimitry Andric // visited again after all of its dependencies are handled. 9950b57cec5SDimitry Andric WorkList.push_back({Var, 1}); 9960b57cec5SDimitry Andric for (auto *Dependency : dependencies(Var)) { 997349cc55cSDimitry Andric // Don't add dependency if it is in a different lexical scope or a global. 998349cc55cSDimitry Andric if (const auto *Dep = dyn_cast<const DILocalVariable>(Dependency)) 999349cc55cSDimitry Andric if (DbgVariable *Var = DbgVar.lookup(Dep)) 1000349cc55cSDimitry Andric WorkList.push_back({Var, 0}); 10010b57cec5SDimitry Andric } 10020b57cec5SDimitry Andric } 10030b57cec5SDimitry Andric return Result; 10040b57cec5SDimitry Andric } 10050b57cec5SDimitry Andric 10060b57cec5SDimitry Andric DIE &DwarfCompileUnit::constructSubprogramScopeDIE(const DISubprogram *Sub, 10070b57cec5SDimitry Andric LexicalScope *Scope) { 10080b57cec5SDimitry Andric DIE &ScopeDIE = updateSubprogramScopeDIE(Sub); 10090b57cec5SDimitry Andric 10100b57cec5SDimitry Andric if (Scope) { 10110b57cec5SDimitry Andric assert(!Scope->getInlinedAt()); 10120b57cec5SDimitry Andric assert(!Scope->isAbstractScope()); 10130b57cec5SDimitry Andric // Collect lexical scope children first. 10140b57cec5SDimitry Andric // ObjectPointer might be a local (non-argument) local variable if it's a 10150b57cec5SDimitry Andric // block's synthetic this pointer. 10160b57cec5SDimitry Andric if (DIE *ObjectPointer = createAndAddScopeChildren(Scope, ScopeDIE)) 10170b57cec5SDimitry Andric addDIEEntry(ScopeDIE, dwarf::DW_AT_object_pointer, *ObjectPointer); 10180b57cec5SDimitry Andric } 10190b57cec5SDimitry Andric 10200b57cec5SDimitry Andric // If this is a variadic function, add an unspecified parameter. 10210b57cec5SDimitry Andric DITypeRefArray FnArgs = Sub->getType()->getTypeArray(); 10220b57cec5SDimitry Andric 10230b57cec5SDimitry Andric // If we have a single element of null, it is a function that returns void. 10240b57cec5SDimitry Andric // If we have more than one elements and the last one is null, it is a 10250b57cec5SDimitry Andric // variadic function. 10260b57cec5SDimitry Andric if (FnArgs.size() > 1 && !FnArgs[FnArgs.size() - 1] && 10270b57cec5SDimitry Andric !includeMinimalInlineScopes()) 10280b57cec5SDimitry Andric ScopeDIE.addChild( 10290b57cec5SDimitry Andric DIE::get(DIEValueAllocator, dwarf::DW_TAG_unspecified_parameters)); 10300b57cec5SDimitry Andric 10310b57cec5SDimitry Andric return ScopeDIE; 10320b57cec5SDimitry Andric } 10330b57cec5SDimitry Andric 10340b57cec5SDimitry Andric DIE *DwarfCompileUnit::createAndAddScopeChildren(LexicalScope *Scope, 10350b57cec5SDimitry Andric DIE &ScopeDIE) { 1036*4824e7fdSDimitry Andric DIE *ObjectPointer = nullptr; 10370b57cec5SDimitry Andric 1038*4824e7fdSDimitry Andric // Emit function arguments (order is significant). 1039*4824e7fdSDimitry Andric auto Vars = DU->getScopeVariables().lookup(Scope); 1040*4824e7fdSDimitry Andric for (auto &DV : Vars.Args) 1041*4824e7fdSDimitry Andric ScopeDIE.addChild(constructVariableDIE(*DV.second, *Scope, ObjectPointer)); 1042*4824e7fdSDimitry Andric 1043*4824e7fdSDimitry Andric // Emit local variables. 1044*4824e7fdSDimitry Andric auto Locals = sortLocalVars(Vars.Locals); 1045*4824e7fdSDimitry Andric for (DbgVariable *DV : Locals) 1046*4824e7fdSDimitry Andric ScopeDIE.addChild(constructVariableDIE(*DV, *Scope, ObjectPointer)); 1047*4824e7fdSDimitry Andric 1048*4824e7fdSDimitry Andric // Emit imported entities (skipped in gmlt-like data). 1049*4824e7fdSDimitry Andric if (!includeMinimalInlineScopes()) { 1050*4824e7fdSDimitry Andric for (const auto *IE : ImportedEntities[Scope->getScopeNode()]) 1051*4824e7fdSDimitry Andric ScopeDIE.addChild(constructImportedEntityDIE(cast<DIImportedEntity>(IE))); 1052*4824e7fdSDimitry Andric } 1053*4824e7fdSDimitry Andric 1054*4824e7fdSDimitry Andric // Emit labels. 1055*4824e7fdSDimitry Andric for (DbgLabel *DL : DU->getScopeLabels().lookup(Scope)) 1056*4824e7fdSDimitry Andric ScopeDIE.addChild(constructLabelDIE(*DL, *Scope)); 1057*4824e7fdSDimitry Andric 1058*4824e7fdSDimitry Andric // Emit inner lexical scopes. 1059*4824e7fdSDimitry Andric auto needToEmitLexicalScope = [this](LexicalScope *LS) { 1060*4824e7fdSDimitry Andric if (isa<DISubprogram>(LS->getScopeNode())) 1061*4824e7fdSDimitry Andric return true; 1062*4824e7fdSDimitry Andric auto Vars = DU->getScopeVariables().lookup(LS); 1063*4824e7fdSDimitry Andric if (!Vars.Args.empty() || !Vars.Locals.empty()) 1064*4824e7fdSDimitry Andric return true; 1065*4824e7fdSDimitry Andric if (!includeMinimalInlineScopes() && 1066*4824e7fdSDimitry Andric !ImportedEntities[LS->getScopeNode()].empty()) 1067*4824e7fdSDimitry Andric return true; 1068*4824e7fdSDimitry Andric return false; 1069*4824e7fdSDimitry Andric }; 1070*4824e7fdSDimitry Andric for (LexicalScope *LS : Scope->getChildren()) { 1071*4824e7fdSDimitry Andric // If the lexical block doesn't have non-scope children, skip 1072*4824e7fdSDimitry Andric // its emission and put its children directly to the parent scope. 1073*4824e7fdSDimitry Andric if (needToEmitLexicalScope(LS)) 1074*4824e7fdSDimitry Andric constructScopeDIE(LS, ScopeDIE); 1075*4824e7fdSDimitry Andric else 1076*4824e7fdSDimitry Andric createAndAddScopeChildren(LS, ScopeDIE); 1077*4824e7fdSDimitry Andric } 10780b57cec5SDimitry Andric 10790b57cec5SDimitry Andric return ObjectPointer; 10800b57cec5SDimitry Andric } 10810b57cec5SDimitry Andric 10820b57cec5SDimitry Andric void DwarfCompileUnit::constructAbstractSubprogramScopeDIE( 10830b57cec5SDimitry Andric LexicalScope *Scope) { 10840b57cec5SDimitry Andric DIE *&AbsDef = getAbstractSPDies()[Scope->getScopeNode()]; 10850b57cec5SDimitry Andric if (AbsDef) 10860b57cec5SDimitry Andric return; 10870b57cec5SDimitry Andric 10880b57cec5SDimitry Andric auto *SP = cast<DISubprogram>(Scope->getScopeNode()); 10890b57cec5SDimitry Andric 10900b57cec5SDimitry Andric DIE *ContextDIE; 10910b57cec5SDimitry Andric DwarfCompileUnit *ContextCU = this; 10920b57cec5SDimitry Andric 10930b57cec5SDimitry Andric if (includeMinimalInlineScopes()) 10940b57cec5SDimitry Andric ContextDIE = &getUnitDie(); 10950b57cec5SDimitry Andric // Some of this is duplicated from DwarfUnit::getOrCreateSubprogramDIE, with 10960b57cec5SDimitry Andric // the important distinction that the debug node is not associated with the 10970b57cec5SDimitry Andric // DIE (since the debug node will be associated with the concrete DIE, if 10980b57cec5SDimitry Andric // any). It could be refactored to some common utility function. 10990b57cec5SDimitry Andric else if (auto *SPDecl = SP->getDeclaration()) { 11000b57cec5SDimitry Andric ContextDIE = &getUnitDie(); 11010b57cec5SDimitry Andric getOrCreateSubprogramDIE(SPDecl); 11020b57cec5SDimitry Andric } else { 11030b57cec5SDimitry Andric ContextDIE = getOrCreateContextDIE(SP->getScope()); 11040b57cec5SDimitry Andric // The scope may be shared with a subprogram that has already been 11050b57cec5SDimitry Andric // constructed in another CU, in which case we need to construct this 11060b57cec5SDimitry Andric // subprogram in the same CU. 11070b57cec5SDimitry Andric ContextCU = DD->lookupCU(ContextDIE->getUnitDie()); 11080b57cec5SDimitry Andric } 11090b57cec5SDimitry Andric 11100b57cec5SDimitry Andric // Passing null as the associated node because the abstract definition 11110b57cec5SDimitry Andric // shouldn't be found by lookup. 11120b57cec5SDimitry Andric AbsDef = &ContextCU->createAndAddDIE(dwarf::DW_TAG_subprogram, *ContextDIE, nullptr); 11130b57cec5SDimitry Andric ContextCU->applySubprogramAttributesToDefinition(SP, *AbsDef); 1114349cc55cSDimitry Andric ContextCU->addSInt(*AbsDef, dwarf::DW_AT_inline, 1115349cc55cSDimitry Andric DD->getDwarfVersion() <= 4 ? Optional<dwarf::Form>() 1116349cc55cSDimitry Andric : dwarf::DW_FORM_implicit_const, 1117349cc55cSDimitry Andric dwarf::DW_INL_inlined); 11180b57cec5SDimitry Andric if (DIE *ObjectPointer = ContextCU->createAndAddScopeChildren(Scope, *AbsDef)) 11190b57cec5SDimitry Andric ContextCU->addDIEEntry(*AbsDef, dwarf::DW_AT_object_pointer, *ObjectPointer); 11200b57cec5SDimitry Andric } 11210b57cec5SDimitry Andric 11225ffd83dbSDimitry Andric bool DwarfCompileUnit::useGNUAnalogForDwarf5Feature() const { 1123e8d8bef9SDimitry Andric return DD->getDwarfVersion() == 4 && !DD->tuneForLLDB(); 11248bcb0991SDimitry Andric } 11258bcb0991SDimitry Andric 11268bcb0991SDimitry Andric dwarf::Tag DwarfCompileUnit::getDwarf5OrGNUTag(dwarf::Tag Tag) const { 11275ffd83dbSDimitry Andric if (!useGNUAnalogForDwarf5Feature()) 11288bcb0991SDimitry Andric return Tag; 11298bcb0991SDimitry Andric switch (Tag) { 11308bcb0991SDimitry Andric case dwarf::DW_TAG_call_site: 11318bcb0991SDimitry Andric return dwarf::DW_TAG_GNU_call_site; 11328bcb0991SDimitry Andric case dwarf::DW_TAG_call_site_parameter: 11338bcb0991SDimitry Andric return dwarf::DW_TAG_GNU_call_site_parameter; 11348bcb0991SDimitry Andric default: 11358bcb0991SDimitry Andric llvm_unreachable("DWARF5 tag with no GNU analog"); 11368bcb0991SDimitry Andric } 11378bcb0991SDimitry Andric } 11388bcb0991SDimitry Andric 11398bcb0991SDimitry Andric dwarf::Attribute 11408bcb0991SDimitry Andric DwarfCompileUnit::getDwarf5OrGNUAttr(dwarf::Attribute Attr) const { 11415ffd83dbSDimitry Andric if (!useGNUAnalogForDwarf5Feature()) 11428bcb0991SDimitry Andric return Attr; 11438bcb0991SDimitry Andric switch (Attr) { 11448bcb0991SDimitry Andric case dwarf::DW_AT_call_all_calls: 11458bcb0991SDimitry Andric return dwarf::DW_AT_GNU_all_call_sites; 11468bcb0991SDimitry Andric case dwarf::DW_AT_call_target: 11478bcb0991SDimitry Andric return dwarf::DW_AT_GNU_call_site_target; 11488bcb0991SDimitry Andric case dwarf::DW_AT_call_origin: 11498bcb0991SDimitry Andric return dwarf::DW_AT_abstract_origin; 11505ffd83dbSDimitry Andric case dwarf::DW_AT_call_return_pc: 11518bcb0991SDimitry Andric return dwarf::DW_AT_low_pc; 11528bcb0991SDimitry Andric case dwarf::DW_AT_call_value: 11538bcb0991SDimitry Andric return dwarf::DW_AT_GNU_call_site_value; 11548bcb0991SDimitry Andric case dwarf::DW_AT_call_tail_call: 11558bcb0991SDimitry Andric return dwarf::DW_AT_GNU_tail_call; 11568bcb0991SDimitry Andric default: 11578bcb0991SDimitry Andric llvm_unreachable("DWARF5 attribute with no GNU analog"); 11588bcb0991SDimitry Andric } 11598bcb0991SDimitry Andric } 11608bcb0991SDimitry Andric 11618bcb0991SDimitry Andric dwarf::LocationAtom 11628bcb0991SDimitry Andric DwarfCompileUnit::getDwarf5OrGNULocationAtom(dwarf::LocationAtom Loc) const { 11635ffd83dbSDimitry Andric if (!useGNUAnalogForDwarf5Feature()) 11648bcb0991SDimitry Andric return Loc; 11658bcb0991SDimitry Andric switch (Loc) { 11668bcb0991SDimitry Andric case dwarf::DW_OP_entry_value: 11678bcb0991SDimitry Andric return dwarf::DW_OP_GNU_entry_value; 11688bcb0991SDimitry Andric default: 11698bcb0991SDimitry Andric llvm_unreachable("DWARF5 location atom with no GNU analog"); 11708bcb0991SDimitry Andric } 11718bcb0991SDimitry Andric } 11728bcb0991SDimitry Andric 11735ffd83dbSDimitry Andric DIE &DwarfCompileUnit::constructCallSiteEntryDIE(DIE &ScopeDIE, 117469ade1e0SDimitry Andric const DISubprogram *CalleeSP, 11755ffd83dbSDimitry Andric bool IsTail, 11765ffd83dbSDimitry Andric const MCSymbol *PCAddr, 11775ffd83dbSDimitry Andric const MCSymbol *CallAddr, 11785ffd83dbSDimitry Andric unsigned CallReg) { 11790b57cec5SDimitry Andric // Insert a call site entry DIE within ScopeDIE. 11808bcb0991SDimitry Andric DIE &CallSiteDIE = createAndAddDIE(getDwarf5OrGNUTag(dwarf::DW_TAG_call_site), 11818bcb0991SDimitry Andric ScopeDIE, nullptr); 11820b57cec5SDimitry Andric 11838bcb0991SDimitry Andric if (CallReg) { 11848bcb0991SDimitry Andric // Indirect call. 11858bcb0991SDimitry Andric addAddress(CallSiteDIE, getDwarf5OrGNUAttr(dwarf::DW_AT_call_target), 11868bcb0991SDimitry Andric MachineLocation(CallReg)); 11870b57cec5SDimitry Andric } else { 118869ade1e0SDimitry Andric DIE *CalleeDIE = getOrCreateSubprogramDIE(CalleeSP); 118969ade1e0SDimitry Andric assert(CalleeDIE && "Could not create DIE for call site entry origin"); 11908bcb0991SDimitry Andric addDIEEntry(CallSiteDIE, getDwarf5OrGNUAttr(dwarf::DW_AT_call_origin), 11918bcb0991SDimitry Andric *CalleeDIE); 11928bcb0991SDimitry Andric } 11938bcb0991SDimitry Andric 11945ffd83dbSDimitry Andric if (IsTail) { 11958bcb0991SDimitry Andric // Attach DW_AT_call_tail_call to tail calls for standards compliance. 11968bcb0991SDimitry Andric addFlag(CallSiteDIE, getDwarf5OrGNUAttr(dwarf::DW_AT_call_tail_call)); 11978bcb0991SDimitry Andric 11985ffd83dbSDimitry Andric // Attach the address of the branch instruction to allow the debugger to 11995ffd83dbSDimitry Andric // show where the tail call occurred. This attribute has no GNU analog. 12005ffd83dbSDimitry Andric // 12015ffd83dbSDimitry Andric // GDB works backwards from non-standard usage of DW_AT_low_pc (in DWARF4 12025ffd83dbSDimitry Andric // mode -- equivalently, in DWARF5 mode, DW_AT_call_return_pc) at tail-call 12035ffd83dbSDimitry Andric // site entries to figure out the PC of tail-calling branch instructions. 12045ffd83dbSDimitry Andric // This means it doesn't need the compiler to emit DW_AT_call_pc, so we 12055ffd83dbSDimitry Andric // don't emit it here. 12065ffd83dbSDimitry Andric // 12075ffd83dbSDimitry Andric // There's no need to tie non-GDB debuggers to this non-standardness, as it 12085ffd83dbSDimitry Andric // adds unnecessary complexity to the debugger. For non-GDB debuggers, emit 12095ffd83dbSDimitry Andric // the standard DW_AT_call_pc info. 12105ffd83dbSDimitry Andric if (!useGNUAnalogForDwarf5Feature()) 12115ffd83dbSDimitry Andric addLabelAddress(CallSiteDIE, dwarf::DW_AT_call_pc, CallAddr); 12125ffd83dbSDimitry Andric } 12135ffd83dbSDimitry Andric 12140b57cec5SDimitry Andric // Attach the return PC to allow the debugger to disambiguate call paths 12150b57cec5SDimitry Andric // from one function to another. 12165ffd83dbSDimitry Andric // 12175ffd83dbSDimitry Andric // The return PC is only really needed when the call /isn't/ a tail call, but 12185ffd83dbSDimitry Andric // GDB expects it in DWARF4 mode, even for tail calls (see the comment above 12195ffd83dbSDimitry Andric // the DW_AT_call_pc emission logic for an explanation). 12205ffd83dbSDimitry Andric if (!IsTail || useGNUAnalogForDwarf5Feature()) { 12215ffd83dbSDimitry Andric assert(PCAddr && "Missing return PC information for a call"); 12225ffd83dbSDimitry Andric addLabelAddress(CallSiteDIE, 12235ffd83dbSDimitry Andric getDwarf5OrGNUAttr(dwarf::DW_AT_call_return_pc), PCAddr); 12240b57cec5SDimitry Andric } 12258bcb0991SDimitry Andric 12260b57cec5SDimitry Andric return CallSiteDIE; 12270b57cec5SDimitry Andric } 12280b57cec5SDimitry Andric 12298bcb0991SDimitry Andric void DwarfCompileUnit::constructCallSiteParmEntryDIEs( 12308bcb0991SDimitry Andric DIE &CallSiteDIE, SmallVector<DbgCallSiteParam, 4> &Params) { 12318bcb0991SDimitry Andric for (const auto &Param : Params) { 12328bcb0991SDimitry Andric unsigned Register = Param.getRegister(); 12338bcb0991SDimitry Andric auto CallSiteDieParam = 12348bcb0991SDimitry Andric DIE::get(DIEValueAllocator, 12358bcb0991SDimitry Andric getDwarf5OrGNUTag(dwarf::DW_TAG_call_site_parameter)); 12368bcb0991SDimitry Andric insertDIE(CallSiteDieParam); 12378bcb0991SDimitry Andric addAddress(*CallSiteDieParam, dwarf::DW_AT_location, 12388bcb0991SDimitry Andric MachineLocation(Register)); 12398bcb0991SDimitry Andric 12408bcb0991SDimitry Andric DIELoc *Loc = new (DIEValueAllocator) DIELoc; 12418bcb0991SDimitry Andric DIEDwarfExpression DwarfExpr(*Asm, *this, *Loc); 12428bcb0991SDimitry Andric DwarfExpr.setCallSiteParamValueFlag(); 12438bcb0991SDimitry Andric 12448bcb0991SDimitry Andric DwarfDebug::emitDebugLocValue(*Asm, nullptr, Param.getValue(), DwarfExpr); 12458bcb0991SDimitry Andric 12468bcb0991SDimitry Andric addBlock(*CallSiteDieParam, getDwarf5OrGNUAttr(dwarf::DW_AT_call_value), 12478bcb0991SDimitry Andric DwarfExpr.finalize()); 12488bcb0991SDimitry Andric 12498bcb0991SDimitry Andric CallSiteDIE.addChild(CallSiteDieParam); 12508bcb0991SDimitry Andric } 12518bcb0991SDimitry Andric } 12528bcb0991SDimitry Andric 12530b57cec5SDimitry Andric DIE *DwarfCompileUnit::constructImportedEntityDIE( 12540b57cec5SDimitry Andric const DIImportedEntity *Module) { 12550b57cec5SDimitry Andric DIE *IMDie = DIE::get(DIEValueAllocator, (dwarf::Tag)Module->getTag()); 12560b57cec5SDimitry Andric insertDIE(Module, IMDie); 12570b57cec5SDimitry Andric DIE *EntityDie; 12580b57cec5SDimitry Andric auto *Entity = Module->getEntity(); 12590b57cec5SDimitry Andric if (auto *NS = dyn_cast<DINamespace>(Entity)) 12600b57cec5SDimitry Andric EntityDie = getOrCreateNameSpace(NS); 12610b57cec5SDimitry Andric else if (auto *M = dyn_cast<DIModule>(Entity)) 12620b57cec5SDimitry Andric EntityDie = getOrCreateModule(M); 12630b57cec5SDimitry Andric else if (auto *SP = dyn_cast<DISubprogram>(Entity)) 12640b57cec5SDimitry Andric EntityDie = getOrCreateSubprogramDIE(SP); 12650b57cec5SDimitry Andric else if (auto *T = dyn_cast<DIType>(Entity)) 12660b57cec5SDimitry Andric EntityDie = getOrCreateTypeDIE(T); 12670b57cec5SDimitry Andric else if (auto *GV = dyn_cast<DIGlobalVariable>(Entity)) 12680b57cec5SDimitry Andric EntityDie = getOrCreateGlobalVariableDIE(GV, {}); 12690b57cec5SDimitry Andric else 12700b57cec5SDimitry Andric EntityDie = getDIE(Entity); 12710b57cec5SDimitry Andric assert(EntityDie); 12720b57cec5SDimitry Andric addSourceLine(*IMDie, Module->getLine(), Module->getFile()); 12730b57cec5SDimitry Andric addDIEEntry(*IMDie, dwarf::DW_AT_import, *EntityDie); 12740b57cec5SDimitry Andric StringRef Name = Module->getName(); 12750b57cec5SDimitry Andric if (!Name.empty()) 12760b57cec5SDimitry Andric addString(*IMDie, dwarf::DW_AT_name, Name); 12770b57cec5SDimitry Andric 1278349cc55cSDimitry Andric // This is for imported module with renamed entities (such as variables and 1279349cc55cSDimitry Andric // subprograms). 1280349cc55cSDimitry Andric DINodeArray Elements = Module->getElements(); 1281349cc55cSDimitry Andric for (const auto *Element : Elements) { 1282349cc55cSDimitry Andric if (!Element) 1283349cc55cSDimitry Andric continue; 1284349cc55cSDimitry Andric IMDie->addChild( 1285349cc55cSDimitry Andric constructImportedEntityDIE(cast<DIImportedEntity>(Element))); 1286349cc55cSDimitry Andric } 1287349cc55cSDimitry Andric 12880b57cec5SDimitry Andric return IMDie; 12890b57cec5SDimitry Andric } 12900b57cec5SDimitry Andric 12910b57cec5SDimitry Andric void DwarfCompileUnit::finishSubprogramDefinition(const DISubprogram *SP) { 12920b57cec5SDimitry Andric DIE *D = getDIE(SP); 12930b57cec5SDimitry Andric if (DIE *AbsSPDIE = getAbstractSPDies().lookup(SP)) { 12940b57cec5SDimitry Andric if (D) 12950b57cec5SDimitry Andric // If this subprogram has an abstract definition, reference that 12960b57cec5SDimitry Andric addDIEEntry(*D, dwarf::DW_AT_abstract_origin, *AbsSPDIE); 12970b57cec5SDimitry Andric } else { 12980b57cec5SDimitry Andric assert(D || includeMinimalInlineScopes()); 12990b57cec5SDimitry Andric if (D) 13000b57cec5SDimitry Andric // And attach the attributes 13010b57cec5SDimitry Andric applySubprogramAttributesToDefinition(SP, *D); 13020b57cec5SDimitry Andric } 13030b57cec5SDimitry Andric } 13040b57cec5SDimitry Andric 13050b57cec5SDimitry Andric void DwarfCompileUnit::finishEntityDefinition(const DbgEntity *Entity) { 13060b57cec5SDimitry Andric DbgEntity *AbsEntity = getExistingAbstractEntity(Entity->getEntity()); 13070b57cec5SDimitry Andric 13080b57cec5SDimitry Andric auto *Die = Entity->getDIE(); 13090b57cec5SDimitry Andric /// Label may be used to generate DW_AT_low_pc, so put it outside 13100b57cec5SDimitry Andric /// if/else block. 13110b57cec5SDimitry Andric const DbgLabel *Label = nullptr; 13120b57cec5SDimitry Andric if (AbsEntity && AbsEntity->getDIE()) { 13130b57cec5SDimitry Andric addDIEEntry(*Die, dwarf::DW_AT_abstract_origin, *AbsEntity->getDIE()); 13140b57cec5SDimitry Andric Label = dyn_cast<const DbgLabel>(Entity); 13150b57cec5SDimitry Andric } else { 13160b57cec5SDimitry Andric if (const DbgVariable *Var = dyn_cast<const DbgVariable>(Entity)) 13170b57cec5SDimitry Andric applyVariableAttributes(*Var, *Die); 13180b57cec5SDimitry Andric else if ((Label = dyn_cast<const DbgLabel>(Entity))) 13190b57cec5SDimitry Andric applyLabelAttributes(*Label, *Die); 13200b57cec5SDimitry Andric else 13210b57cec5SDimitry Andric llvm_unreachable("DbgEntity must be DbgVariable or DbgLabel."); 13220b57cec5SDimitry Andric } 13230b57cec5SDimitry Andric 13240b57cec5SDimitry Andric if (Label) 13250b57cec5SDimitry Andric if (const auto *Sym = Label->getSymbol()) 13260b57cec5SDimitry Andric addLabelAddress(*Die, dwarf::DW_AT_low_pc, Sym); 13270b57cec5SDimitry Andric } 13280b57cec5SDimitry Andric 13290b57cec5SDimitry Andric DbgEntity *DwarfCompileUnit::getExistingAbstractEntity(const DINode *Node) { 13300b57cec5SDimitry Andric auto &AbstractEntities = getAbstractEntities(); 13310b57cec5SDimitry Andric auto I = AbstractEntities.find(Node); 13320b57cec5SDimitry Andric if (I != AbstractEntities.end()) 13330b57cec5SDimitry Andric return I->second.get(); 13340b57cec5SDimitry Andric return nullptr; 13350b57cec5SDimitry Andric } 13360b57cec5SDimitry Andric 13370b57cec5SDimitry Andric void DwarfCompileUnit::createAbstractEntity(const DINode *Node, 13380b57cec5SDimitry Andric LexicalScope *Scope) { 13390b57cec5SDimitry Andric assert(Scope && Scope->isAbstractScope()); 13400b57cec5SDimitry Andric auto &Entity = getAbstractEntities()[Node]; 13410b57cec5SDimitry Andric if (isa<const DILocalVariable>(Node)) { 13428bcb0991SDimitry Andric Entity = std::make_unique<DbgVariable>( 13430b57cec5SDimitry Andric cast<const DILocalVariable>(Node), nullptr /* IA */);; 13440b57cec5SDimitry Andric DU->addScopeVariable(Scope, cast<DbgVariable>(Entity.get())); 13450b57cec5SDimitry Andric } else if (isa<const DILabel>(Node)) { 13468bcb0991SDimitry Andric Entity = std::make_unique<DbgLabel>( 13470b57cec5SDimitry Andric cast<const DILabel>(Node), nullptr /* IA */); 13480b57cec5SDimitry Andric DU->addScopeLabel(Scope, cast<DbgLabel>(Entity.get())); 13490b57cec5SDimitry Andric } 13500b57cec5SDimitry Andric } 13510b57cec5SDimitry Andric 13520b57cec5SDimitry Andric void DwarfCompileUnit::emitHeader(bool UseOffsets) { 13530b57cec5SDimitry Andric // Don't bother labeling the .dwo unit, as its offset isn't used. 13540b57cec5SDimitry Andric if (!Skeleton && !DD->useSectionsAsReferences()) { 13550b57cec5SDimitry Andric LabelBegin = Asm->createTempSymbol("cu_begin"); 13565ffd83dbSDimitry Andric Asm->OutStreamer->emitLabel(LabelBegin); 13570b57cec5SDimitry Andric } 13580b57cec5SDimitry Andric 13590b57cec5SDimitry Andric dwarf::UnitType UT = Skeleton ? dwarf::DW_UT_split_compile 13600b57cec5SDimitry Andric : DD->useSplitDwarf() ? dwarf::DW_UT_skeleton 13610b57cec5SDimitry Andric : dwarf::DW_UT_compile; 13620b57cec5SDimitry Andric DwarfUnit::emitCommonHeader(UseOffsets, UT); 13630b57cec5SDimitry Andric if (DD->getDwarfVersion() >= 5 && UT != dwarf::DW_UT_compile) 13640b57cec5SDimitry Andric Asm->emitInt64(getDWOId()); 13650b57cec5SDimitry Andric } 13660b57cec5SDimitry Andric 13670b57cec5SDimitry Andric bool DwarfCompileUnit::hasDwarfPubSections() const { 13680b57cec5SDimitry Andric switch (CUNode->getNameTableKind()) { 13690b57cec5SDimitry Andric case DICompileUnit::DebugNameTableKind::None: 13700b57cec5SDimitry Andric return false; 13710b57cec5SDimitry Andric // Opting in to GNU Pubnames/types overrides the default to ensure these are 13720b57cec5SDimitry Andric // generated for things like Gold's gdb_index generation. 13730b57cec5SDimitry Andric case DICompileUnit::DebugNameTableKind::GNU: 13740b57cec5SDimitry Andric return true; 13750b57cec5SDimitry Andric case DICompileUnit::DebugNameTableKind::Default: 13760b57cec5SDimitry Andric return DD->tuneForGDB() && !includeMinimalInlineScopes() && 13770b57cec5SDimitry Andric !CUNode->isDebugDirectivesOnly() && 13780b57cec5SDimitry Andric DD->getAccelTableKind() != AccelTableKind::Apple && 13790b57cec5SDimitry Andric DD->getDwarfVersion() < 5; 13800b57cec5SDimitry Andric } 13810b57cec5SDimitry Andric llvm_unreachable("Unhandled DICompileUnit::DebugNameTableKind enum"); 13820b57cec5SDimitry Andric } 13830b57cec5SDimitry Andric 13840b57cec5SDimitry Andric /// addGlobalName - Add a new global name to the compile unit. 13850b57cec5SDimitry Andric void DwarfCompileUnit::addGlobalName(StringRef Name, const DIE &Die, 13860b57cec5SDimitry Andric const DIScope *Context) { 13870b57cec5SDimitry Andric if (!hasDwarfPubSections()) 13880b57cec5SDimitry Andric return; 13890b57cec5SDimitry Andric std::string FullName = getParentContextString(Context) + Name.str(); 13900b57cec5SDimitry Andric GlobalNames[FullName] = &Die; 13910b57cec5SDimitry Andric } 13920b57cec5SDimitry Andric 13930b57cec5SDimitry Andric void DwarfCompileUnit::addGlobalNameForTypeUnit(StringRef Name, 13940b57cec5SDimitry Andric const DIScope *Context) { 13950b57cec5SDimitry Andric if (!hasDwarfPubSections()) 13960b57cec5SDimitry Andric return; 13970b57cec5SDimitry Andric std::string FullName = getParentContextString(Context) + Name.str(); 13980b57cec5SDimitry Andric // Insert, allowing the entry to remain as-is if it's already present 13990b57cec5SDimitry Andric // This way the CU-level type DIE is preferred over the "can't describe this 14000b57cec5SDimitry Andric // type as a unit offset because it's not really in the CU at all, it's only 14010b57cec5SDimitry Andric // in a type unit" 14020b57cec5SDimitry Andric GlobalNames.insert(std::make_pair(std::move(FullName), &getUnitDie())); 14030b57cec5SDimitry Andric } 14040b57cec5SDimitry Andric 14050b57cec5SDimitry Andric /// Add a new global type to the unit. 14060b57cec5SDimitry Andric void DwarfCompileUnit::addGlobalType(const DIType *Ty, const DIE &Die, 14070b57cec5SDimitry Andric const DIScope *Context) { 14080b57cec5SDimitry Andric if (!hasDwarfPubSections()) 14090b57cec5SDimitry Andric return; 14100b57cec5SDimitry Andric std::string FullName = getParentContextString(Context) + Ty->getName().str(); 14110b57cec5SDimitry Andric GlobalTypes[FullName] = &Die; 14120b57cec5SDimitry Andric } 14130b57cec5SDimitry Andric 14140b57cec5SDimitry Andric void DwarfCompileUnit::addGlobalTypeUnitType(const DIType *Ty, 14150b57cec5SDimitry Andric const DIScope *Context) { 14160b57cec5SDimitry Andric if (!hasDwarfPubSections()) 14170b57cec5SDimitry Andric return; 14180b57cec5SDimitry Andric std::string FullName = getParentContextString(Context) + Ty->getName().str(); 14190b57cec5SDimitry Andric // Insert, allowing the entry to remain as-is if it's already present 14200b57cec5SDimitry Andric // This way the CU-level type DIE is preferred over the "can't describe this 14210b57cec5SDimitry Andric // type as a unit offset because it's not really in the CU at all, it's only 14220b57cec5SDimitry Andric // in a type unit" 14230b57cec5SDimitry Andric GlobalTypes.insert(std::make_pair(std::move(FullName), &getUnitDie())); 14240b57cec5SDimitry Andric } 14250b57cec5SDimitry Andric 14260b57cec5SDimitry Andric void DwarfCompileUnit::addVariableAddress(const DbgVariable &DV, DIE &Die, 14270b57cec5SDimitry Andric MachineLocation Location) { 14280b57cec5SDimitry Andric if (DV.hasComplexAddress()) 14290b57cec5SDimitry Andric addComplexAddress(DV, Die, dwarf::DW_AT_location, Location); 14300b57cec5SDimitry Andric else 14310b57cec5SDimitry Andric addAddress(Die, dwarf::DW_AT_location, Location); 14320b57cec5SDimitry Andric } 14330b57cec5SDimitry Andric 14340b57cec5SDimitry Andric /// Add an address attribute to a die based on the location provided. 14350b57cec5SDimitry Andric void DwarfCompileUnit::addAddress(DIE &Die, dwarf::Attribute Attribute, 14360b57cec5SDimitry Andric const MachineLocation &Location) { 14370b57cec5SDimitry Andric DIELoc *Loc = new (DIEValueAllocator) DIELoc; 14380b57cec5SDimitry Andric DIEDwarfExpression DwarfExpr(*Asm, *this, *Loc); 14390b57cec5SDimitry Andric if (Location.isIndirect()) 14400b57cec5SDimitry Andric DwarfExpr.setMemoryLocationKind(); 14410b57cec5SDimitry Andric 14420b57cec5SDimitry Andric DIExpressionCursor Cursor({}); 14430b57cec5SDimitry Andric const TargetRegisterInfo &TRI = *Asm->MF->getSubtarget().getRegisterInfo(); 14440b57cec5SDimitry Andric if (!DwarfExpr.addMachineRegExpression(TRI, Cursor, Location.getReg())) 14450b57cec5SDimitry Andric return; 14460b57cec5SDimitry Andric DwarfExpr.addExpression(std::move(Cursor)); 14470b57cec5SDimitry Andric 14480b57cec5SDimitry Andric // Now attach the location information to the DIE. 14490b57cec5SDimitry Andric addBlock(Die, Attribute, DwarfExpr.finalize()); 1450480093f4SDimitry Andric 1451480093f4SDimitry Andric if (DwarfExpr.TagOffset) 1452480093f4SDimitry Andric addUInt(Die, dwarf::DW_AT_LLVM_tag_offset, dwarf::DW_FORM_data1, 1453480093f4SDimitry Andric *DwarfExpr.TagOffset); 14540b57cec5SDimitry Andric } 14550b57cec5SDimitry Andric 14560b57cec5SDimitry Andric /// Start with the address based on the location provided, and generate the 14570b57cec5SDimitry Andric /// DWARF information necessary to find the actual variable given the extra 14580b57cec5SDimitry Andric /// address information encoded in the DbgVariable, starting from the starting 14590b57cec5SDimitry Andric /// location. Add the DWARF information to the die. 14600b57cec5SDimitry Andric void DwarfCompileUnit::addComplexAddress(const DbgVariable &DV, DIE &Die, 14610b57cec5SDimitry Andric dwarf::Attribute Attribute, 14620b57cec5SDimitry Andric const MachineLocation &Location) { 14630b57cec5SDimitry Andric DIELoc *Loc = new (DIEValueAllocator) DIELoc; 14640b57cec5SDimitry Andric DIEDwarfExpression DwarfExpr(*Asm, *this, *Loc); 14650b57cec5SDimitry Andric const DIExpression *DIExpr = DV.getSingleExpression(); 14660b57cec5SDimitry Andric DwarfExpr.addFragmentOffset(DIExpr); 14675ffd83dbSDimitry Andric DwarfExpr.setLocation(Location, DIExpr); 14680b57cec5SDimitry Andric 14690b57cec5SDimitry Andric DIExpressionCursor Cursor(DIExpr); 14700b57cec5SDimitry Andric 14715ffd83dbSDimitry Andric if (DIExpr->isEntryValue()) 14728bcb0991SDimitry Andric DwarfExpr.beginEntryValueExpression(Cursor); 14730b57cec5SDimitry Andric 14740b57cec5SDimitry Andric const TargetRegisterInfo &TRI = *Asm->MF->getSubtarget().getRegisterInfo(); 14750b57cec5SDimitry Andric if (!DwarfExpr.addMachineRegExpression(TRI, Cursor, Location.getReg())) 14760b57cec5SDimitry Andric return; 14770b57cec5SDimitry Andric DwarfExpr.addExpression(std::move(Cursor)); 14780b57cec5SDimitry Andric 14790b57cec5SDimitry Andric // Now attach the location information to the DIE. 14800b57cec5SDimitry Andric addBlock(Die, Attribute, DwarfExpr.finalize()); 1481480093f4SDimitry Andric 1482480093f4SDimitry Andric if (DwarfExpr.TagOffset) 1483480093f4SDimitry Andric addUInt(Die, dwarf::DW_AT_LLVM_tag_offset, dwarf::DW_FORM_data1, 1484480093f4SDimitry Andric *DwarfExpr.TagOffset); 14850b57cec5SDimitry Andric } 14860b57cec5SDimitry Andric 14870b57cec5SDimitry Andric /// Add a Dwarf loclistptr attribute data and value. 14880b57cec5SDimitry Andric void DwarfCompileUnit::addLocationList(DIE &Die, dwarf::Attribute Attribute, 14890b57cec5SDimitry Andric unsigned Index) { 1490e8d8bef9SDimitry Andric dwarf::Form Form = (DD->getDwarfVersion() >= 5) 1491e8d8bef9SDimitry Andric ? dwarf::DW_FORM_loclistx 1492e8d8bef9SDimitry Andric : DD->getDwarfSectionOffsetForm(); 1493fe6060f1SDimitry Andric addAttribute(Die, Attribute, Form, DIELocList(Index)); 14940b57cec5SDimitry Andric } 14950b57cec5SDimitry Andric 14960b57cec5SDimitry Andric void DwarfCompileUnit::applyVariableAttributes(const DbgVariable &Var, 14970b57cec5SDimitry Andric DIE &VariableDie) { 14980b57cec5SDimitry Andric StringRef Name = Var.getName(); 14990b57cec5SDimitry Andric if (!Name.empty()) 15000b57cec5SDimitry Andric addString(VariableDie, dwarf::DW_AT_name, Name); 15010b57cec5SDimitry Andric const auto *DIVar = Var.getVariable(); 1502349cc55cSDimitry Andric if (DIVar) { 15030b57cec5SDimitry Andric if (uint32_t AlignInBytes = DIVar->getAlignInBytes()) 15040b57cec5SDimitry Andric addUInt(VariableDie, dwarf::DW_AT_alignment, dwarf::DW_FORM_udata, 15050b57cec5SDimitry Andric AlignInBytes); 1506349cc55cSDimitry Andric addAnnotation(VariableDie, DIVar->getAnnotations()); 1507349cc55cSDimitry Andric } 15080b57cec5SDimitry Andric 15090b57cec5SDimitry Andric addSourceLine(VariableDie, DIVar); 15100b57cec5SDimitry Andric addType(VariableDie, Var.getType()); 15110b57cec5SDimitry Andric if (Var.isArtificial()) 15120b57cec5SDimitry Andric addFlag(VariableDie, dwarf::DW_AT_artificial); 15130b57cec5SDimitry Andric } 15140b57cec5SDimitry Andric 15150b57cec5SDimitry Andric void DwarfCompileUnit::applyLabelAttributes(const DbgLabel &Label, 15160b57cec5SDimitry Andric DIE &LabelDie) { 15170b57cec5SDimitry Andric StringRef Name = Label.getName(); 15180b57cec5SDimitry Andric if (!Name.empty()) 15190b57cec5SDimitry Andric addString(LabelDie, dwarf::DW_AT_name, Name); 15200b57cec5SDimitry Andric const auto *DILabel = Label.getLabel(); 15210b57cec5SDimitry Andric addSourceLine(LabelDie, DILabel); 15220b57cec5SDimitry Andric } 15230b57cec5SDimitry Andric 15240b57cec5SDimitry Andric /// Add a Dwarf expression attribute data and value. 15250b57cec5SDimitry Andric void DwarfCompileUnit::addExpr(DIELoc &Die, dwarf::Form Form, 15260b57cec5SDimitry Andric const MCExpr *Expr) { 1527fe6060f1SDimitry Andric addAttribute(Die, (dwarf::Attribute)0, Form, DIEExpr(Expr)); 15280b57cec5SDimitry Andric } 15290b57cec5SDimitry Andric 15300b57cec5SDimitry Andric void DwarfCompileUnit::applySubprogramAttributesToDefinition( 15310b57cec5SDimitry Andric const DISubprogram *SP, DIE &SPDie) { 15320b57cec5SDimitry Andric auto *SPDecl = SP->getDeclaration(); 15330b57cec5SDimitry Andric auto *Context = SPDecl ? SPDecl->getScope() : SP->getScope(); 15340b57cec5SDimitry Andric applySubprogramAttributes(SP, SPDie, includeMinimalInlineScopes()); 15350b57cec5SDimitry Andric addGlobalName(SP->getName(), SPDie, Context); 15360b57cec5SDimitry Andric } 15370b57cec5SDimitry Andric 15380b57cec5SDimitry Andric bool DwarfCompileUnit::isDwoUnit() const { 15390b57cec5SDimitry Andric return DD->useSplitDwarf() && Skeleton; 15400b57cec5SDimitry Andric } 15410b57cec5SDimitry Andric 15420b57cec5SDimitry Andric void DwarfCompileUnit::finishNonUnitTypeDIE(DIE& D, const DICompositeType *CTy) { 15430b57cec5SDimitry Andric constructTypeDIE(D, CTy); 15440b57cec5SDimitry Andric } 15450b57cec5SDimitry Andric 15460b57cec5SDimitry Andric bool DwarfCompileUnit::includeMinimalInlineScopes() const { 15470b57cec5SDimitry Andric return getCUNode()->getEmissionKind() == DICompileUnit::LineTablesOnly || 15480b57cec5SDimitry Andric (DD->useSplitDwarf() && !Skeleton); 15490b57cec5SDimitry Andric } 15500b57cec5SDimitry Andric 15510b57cec5SDimitry Andric void DwarfCompileUnit::addAddrTableBase() { 15520b57cec5SDimitry Andric const TargetLoweringObjectFile &TLOF = Asm->getObjFileLowering(); 15530b57cec5SDimitry Andric MCSymbol *Label = DD->getAddressPool().getLabel(); 15540b57cec5SDimitry Andric addSectionLabel(getUnitDie(), 1555e8d8bef9SDimitry Andric DD->getDwarfVersion() >= 5 ? dwarf::DW_AT_addr_base 15560b57cec5SDimitry Andric : dwarf::DW_AT_GNU_addr_base, 15570b57cec5SDimitry Andric Label, TLOF.getDwarfAddrSection()->getBeginSymbol()); 15580b57cec5SDimitry Andric } 15590b57cec5SDimitry Andric 15600b57cec5SDimitry Andric void DwarfCompileUnit::addBaseTypeRef(DIEValueList &Die, int64_t Idx) { 1561fe6060f1SDimitry Andric addAttribute(Die, (dwarf::Attribute)0, dwarf::DW_FORM_udata, 15620b57cec5SDimitry Andric new (DIEValueAllocator) DIEBaseTypeRef(this, Idx)); 15630b57cec5SDimitry Andric } 15640b57cec5SDimitry Andric 15650b57cec5SDimitry Andric void DwarfCompileUnit::createBaseTypeDIEs() { 15660b57cec5SDimitry Andric // Insert the base_type DIEs directly after the CU so that their offsets will 15670b57cec5SDimitry Andric // fit in the fixed size ULEB128 used inside the location expressions. 15680b57cec5SDimitry Andric // Maintain order by iterating backwards and inserting to the front of CU 15690b57cec5SDimitry Andric // child list. 15700b57cec5SDimitry Andric for (auto &Btr : reverse(ExprRefedBaseTypes)) { 15710b57cec5SDimitry Andric DIE &Die = getUnitDie().addChildFront( 15720b57cec5SDimitry Andric DIE::get(DIEValueAllocator, dwarf::DW_TAG_base_type)); 15730b57cec5SDimitry Andric SmallString<32> Str; 15740b57cec5SDimitry Andric addString(Die, dwarf::DW_AT_name, 15750b57cec5SDimitry Andric Twine(dwarf::AttributeEncodingString(Btr.Encoding) + 15760b57cec5SDimitry Andric "_" + Twine(Btr.BitSize)).toStringRef(Str)); 15770b57cec5SDimitry Andric addUInt(Die, dwarf::DW_AT_encoding, dwarf::DW_FORM_data1, Btr.Encoding); 15780b57cec5SDimitry Andric addUInt(Die, dwarf::DW_AT_byte_size, None, Btr.BitSize / 8); 15790b57cec5SDimitry Andric 15800b57cec5SDimitry Andric Btr.Die = &Die; 15810b57cec5SDimitry Andric } 15820b57cec5SDimitry Andric } 1583