12cab237bSDimitry Andric //===- llvm/CodeGen/DwarfCompileUnit.cpp - Dwarf Compile Units ------------===//
27a7e6055SDimitry Andric //
37a7e6055SDimitry Andric //                     The LLVM Compiler Infrastructure
47a7e6055SDimitry Andric //
57a7e6055SDimitry Andric // This file is distributed under the University of Illinois Open Source
67a7e6055SDimitry Andric // License. See LICENSE.TXT for details.
77a7e6055SDimitry Andric //
87a7e6055SDimitry Andric //===----------------------------------------------------------------------===//
97a7e6055SDimitry Andric //
107a7e6055SDimitry Andric // This file contains support for constructing a dwarf compile unit.
117a7e6055SDimitry Andric //
127a7e6055SDimitry Andric //===----------------------------------------------------------------------===//
137a7e6055SDimitry Andric 
1439d628a0SDimitry Andric #include "DwarfCompileUnit.h"
152cab237bSDimitry Andric #include "AddressPool.h"
162cab237bSDimitry Andric #include "DwarfDebug.h"
1739d628a0SDimitry Andric #include "DwarfExpression.h"
182cab237bSDimitry Andric #include "DwarfUnit.h"
192cab237bSDimitry Andric #include "llvm/ADT/None.h"
202cab237bSDimitry Andric #include "llvm/ADT/STLExtras.h"
212cab237bSDimitry Andric #include "llvm/ADT/SmallVector.h"
222cab237bSDimitry Andric #include "llvm/ADT/StringRef.h"
232cab237bSDimitry Andric #include "llvm/BinaryFormat/Dwarf.h"
242cab237bSDimitry Andric #include "llvm/CodeGen/AsmPrinter.h"
252cab237bSDimitry Andric #include "llvm/CodeGen/DIE.h"
262cab237bSDimitry Andric #include "llvm/CodeGen/LexicalScopes.h"
2739d628a0SDimitry Andric #include "llvm/CodeGen/MachineFunction.h"
282cab237bSDimitry Andric #include "llvm/CodeGen/MachineInstr.h"
292cab237bSDimitry Andric #include "llvm/CodeGen/MachineOperand.h"
302cab237bSDimitry Andric #include "llvm/CodeGen/TargetFrameLowering.h"
312cab237bSDimitry Andric #include "llvm/CodeGen/TargetRegisterInfo.h"
322cab237bSDimitry Andric #include "llvm/CodeGen/TargetSubtargetInfo.h"
3339d628a0SDimitry Andric #include "llvm/IR/DataLayout.h"
342cab237bSDimitry Andric #include "llvm/IR/DebugInfo.h"
352cab237bSDimitry Andric #include "llvm/IR/DebugInfoMetadata.h"
3639d628a0SDimitry Andric #include "llvm/IR/GlobalVariable.h"
372cab237bSDimitry Andric #include "llvm/MC/MCSection.h"
3839d628a0SDimitry Andric #include "llvm/MC/MCStreamer.h"
392cab237bSDimitry Andric #include "llvm/MC/MCSymbol.h"
402cab237bSDimitry Andric #include "llvm/MC/MachineLocation.h"
412cab237bSDimitry Andric #include "llvm/Support/Casting.h"
424ba319b5SDimitry Andric #include "llvm/Target/TargetLoweringObjectFile.h"
4339d628a0SDimitry Andric #include "llvm/Target/TargetMachine.h"
442cab237bSDimitry Andric #include "llvm/Target/TargetOptions.h"
452cab237bSDimitry Andric #include <algorithm>
462cab237bSDimitry Andric #include <cassert>
472cab237bSDimitry Andric #include <cstdint>
482cab237bSDimitry Andric #include <iterator>
492cab237bSDimitry Andric #include <memory>
502cab237bSDimitry Andric #include <string>
512cab237bSDimitry Andric #include <utility>
5239d628a0SDimitry Andric 
532cab237bSDimitry Andric using namespace llvm;
5439d628a0SDimitry Andric 
DwarfCompileUnit(unsigned UID,const DICompileUnit * Node,AsmPrinter * A,DwarfDebug * DW,DwarfFile * DWU)55ff0cc061SDimitry Andric DwarfCompileUnit::DwarfCompileUnit(unsigned UID, const DICompileUnit *Node,
5639d628a0SDimitry Andric                                    AsmPrinter *A, DwarfDebug *DW,
5739d628a0SDimitry Andric                                    DwarfFile *DWU)
582cab237bSDimitry Andric     : DwarfUnit(dwarf::DW_TAG_compile_unit, Node, A, DW, DWU), UniqueID(UID) {
5939d628a0SDimitry Andric   insertDIE(Node, &getUnitDie());
603ca95b02SDimitry Andric   MacroLabelBegin = Asm->createTempSymbol("cu_macro_begin");
6139d628a0SDimitry Andric }
6239d628a0SDimitry Andric 
6339d628a0SDimitry Andric /// addLabelAddress - Add a dwarf label attribute data and value using
6439d628a0SDimitry Andric /// DW_FORM_addr or DW_FORM_GNU_addr_index.
addLabelAddress(DIE & Die,dwarf::Attribute Attribute,const MCSymbol * Label)6539d628a0SDimitry Andric void DwarfCompileUnit::addLabelAddress(DIE &Die, dwarf::Attribute Attribute,
6639d628a0SDimitry Andric                                        const MCSymbol *Label) {
6739d628a0SDimitry Andric   // Don't use the address pool in non-fission or in the skeleton unit itself.
6839d628a0SDimitry Andric   // FIXME: Once GDB supports this, it's probably worthwhile using the address
6939d628a0SDimitry Andric   // pool from the skeleton - maybe even in non-fission (possibly fewer
7039d628a0SDimitry Andric   // relocations by sharing them in the pool, but we have other ideas about how
7139d628a0SDimitry Andric   // to reduce the number of relocations as well/instead).
72*b5893f02SDimitry Andric   if ((!DD->useSplitDwarf() || !Skeleton) && DD->getDwarfVersion() < 5)
7339d628a0SDimitry Andric     return addLocalLabelAddress(Die, Attribute, Label);
7439d628a0SDimitry Andric 
7539d628a0SDimitry Andric   if (Label)
7639d628a0SDimitry Andric     DD->addArangeLabel(SymbolCU(this, Label));
7739d628a0SDimitry Andric 
7839d628a0SDimitry Andric   unsigned idx = DD->getAddressPool().getIndex(Label);
79*b5893f02SDimitry Andric   Die.addValue(DIEValueAllocator, Attribute,
80*b5893f02SDimitry Andric                DD->getDwarfVersion() >= 5 ? dwarf::DW_FORM_addrx
81*b5893f02SDimitry Andric                                           : dwarf::DW_FORM_GNU_addr_index,
823dac3a9bSDimitry Andric                DIEInteger(idx));
8339d628a0SDimitry Andric }
8439d628a0SDimitry Andric 
addLocalLabelAddress(DIE & Die,dwarf::Attribute Attribute,const MCSymbol * Label)8539d628a0SDimitry Andric void DwarfCompileUnit::addLocalLabelAddress(DIE &Die,
8639d628a0SDimitry Andric                                             dwarf::Attribute Attribute,
8739d628a0SDimitry Andric                                             const MCSymbol *Label) {
8839d628a0SDimitry Andric   if (Label)
8939d628a0SDimitry Andric     DD->addArangeLabel(SymbolCU(this, Label));
9039d628a0SDimitry Andric 
9197bc6c73SDimitry Andric   if (Label)
923dac3a9bSDimitry Andric     Die.addValue(DIEValueAllocator, Attribute, dwarf::DW_FORM_addr,
933dac3a9bSDimitry Andric                  DIELabel(Label));
9497bc6c73SDimitry Andric   else
953dac3a9bSDimitry Andric     Die.addValue(DIEValueAllocator, Attribute, dwarf::DW_FORM_addr,
963dac3a9bSDimitry Andric                  DIEInteger(0));
9739d628a0SDimitry Andric }
9839d628a0SDimitry Andric 
getOrCreateSourceID(const DIFile * File)994ba319b5SDimitry Andric unsigned DwarfCompileUnit::getOrCreateSourceID(const DIFile *File) {
10039d628a0SDimitry Andric   // If we print assembly, we can't separate .file entries according to
10139d628a0SDimitry Andric   // compile units. Thus all files will belong to the default compile unit.
10239d628a0SDimitry Andric 
10339d628a0SDimitry Andric   // FIXME: add a better feature test than hasRawTextSupport. Even better,
10439d628a0SDimitry Andric   // extend .file to support this.
1054ba319b5SDimitry Andric   unsigned CUID = Asm->OutStreamer->hasRawTextSupport() ? 0 : getUniqueID();
1064ba319b5SDimitry Andric   if (!File)
1074ba319b5SDimitry Andric     return Asm->OutStreamer->EmitDwarfFileDirective(0, "", "", nullptr, None, CUID);
108ff0cc061SDimitry Andric   return Asm->OutStreamer->EmitDwarfFileDirective(
1094ba319b5SDimitry Andric       0, File->getDirectory(), File->getFilename(), getMD5AsBytes(File),
1104ba319b5SDimitry Andric       File->getSource(), CUID);
11139d628a0SDimitry Andric }
11239d628a0SDimitry Andric 
getOrCreateGlobalVariableDIE(const DIGlobalVariable * GV,ArrayRef<GlobalExpr> GlobalExprs)113ff0cc061SDimitry Andric DIE *DwarfCompileUnit::getOrCreateGlobalVariableDIE(
114d88c1a5aSDimitry Andric     const DIGlobalVariable *GV, ArrayRef<GlobalExpr> GlobalExprs) {
11539d628a0SDimitry Andric   // Check for pre-existence.
11639d628a0SDimitry Andric   if (DIE *Die = getDIE(GV))
11739d628a0SDimitry Andric     return Die;
11839d628a0SDimitry Andric 
119ff0cc061SDimitry Andric   assert(GV);
12039d628a0SDimitry Andric 
121ff0cc061SDimitry Andric   auto *GVContext = GV->getScope();
122ff0cc061SDimitry Andric   auto *GTy = DD->resolve(GV->getType());
12339d628a0SDimitry Andric 
12439d628a0SDimitry Andric   // Construct the context before querying for the existence of the DIE in
12539d628a0SDimitry Andric   // case such construction creates the DIE.
12639d628a0SDimitry Andric   DIE *ContextDIE = getOrCreateContextDIE(GVContext);
12739d628a0SDimitry Andric 
12839d628a0SDimitry Andric   // Add to map.
129ff0cc061SDimitry Andric   DIE *VariableDIE = &createAndAddDIE(GV->getTag(), *ContextDIE, GV);
130ff0cc061SDimitry Andric   DIScope *DeclContext;
131ff0cc061SDimitry Andric   if (auto *SDMDecl = GV->getStaticDataMemberDeclaration()) {
132ff0cc061SDimitry Andric     DeclContext = resolve(SDMDecl->getScope());
133ff0cc061SDimitry Andric     assert(SDMDecl->isStaticMember() && "Expected static member decl");
134ff0cc061SDimitry Andric     assert(GV->isDefinition());
13539d628a0SDimitry Andric     // We need the declaration DIE that is in the static member's class.
13639d628a0SDimitry Andric     DIE *VariableSpecDIE = getOrCreateStaticMemberDIE(SDMDecl);
13739d628a0SDimitry Andric     addDIEEntry(*VariableDIE, dwarf::DW_AT_specification, *VariableSpecDIE);
138d88c1a5aSDimitry Andric     // If the global variable's type is different from the one in the class
139d88c1a5aSDimitry Andric     // member type, assume that it's more specific and also emit it.
140d88c1a5aSDimitry Andric     if (GTy != DD->resolve(SDMDecl->getBaseType()))
141d88c1a5aSDimitry Andric       addType(*VariableDIE, GTy);
14239d628a0SDimitry Andric   } else {
143ff0cc061SDimitry Andric     DeclContext = GV->getScope();
14439d628a0SDimitry Andric     // Add name and type.
145ff0cc061SDimitry Andric     addString(*VariableDIE, dwarf::DW_AT_name, GV->getDisplayName());
14639d628a0SDimitry Andric     addType(*VariableDIE, GTy);
14739d628a0SDimitry Andric 
14839d628a0SDimitry Andric     // Add scoping info.
149ff0cc061SDimitry Andric     if (!GV->isLocalToUnit())
15039d628a0SDimitry Andric       addFlag(*VariableDIE, dwarf::DW_AT_external);
15139d628a0SDimitry Andric 
15239d628a0SDimitry Andric     // Add line number info.
15339d628a0SDimitry Andric     addSourceLine(*VariableDIE, GV);
15439d628a0SDimitry Andric   }
15539d628a0SDimitry Andric 
156ff0cc061SDimitry Andric   if (!GV->isDefinition())
15739d628a0SDimitry Andric     addFlag(*VariableDIE, dwarf::DW_AT_declaration);
158ff0cc061SDimitry Andric   else
159ff0cc061SDimitry Andric     addGlobalName(GV->getName(), *VariableDIE, DeclContext);
16039d628a0SDimitry Andric 
161d88c1a5aSDimitry Andric   if (uint32_t AlignInBytes = GV->getAlignInBytes())
162d88c1a5aSDimitry Andric     addUInt(*VariableDIE, dwarf::DW_AT_alignment, dwarf::DW_FORM_udata,
163d88c1a5aSDimitry Andric             AlignInBytes);
164d88c1a5aSDimitry Andric 
165*b5893f02SDimitry Andric   if (MDTuple *TP = GV->getTemplateParams())
166*b5893f02SDimitry Andric     addTemplateParams(*VariableDIE, DINodeArray(TP));
167*b5893f02SDimitry Andric 
16839d628a0SDimitry Andric   // Add location.
16939d628a0SDimitry Andric   bool addToAccelTable = false;
170d88c1a5aSDimitry Andric   DIELoc *Loc = nullptr;
171d88c1a5aSDimitry Andric   std::unique_ptr<DIEDwarfExpression> DwarfExpr;
172d88c1a5aSDimitry Andric   for (const auto &GE : GlobalExprs) {
173d88c1a5aSDimitry Andric     const GlobalVariable *Global = GE.Var;
174d88c1a5aSDimitry Andric     const DIExpression *Expr = GE.Expr;
1757a7e6055SDimitry Andric 
176d88c1a5aSDimitry Andric     // For compatibility with DWARF 3 and earlier,
177d88c1a5aSDimitry Andric     // DW_AT_location(DW_OP_constu, X, DW_OP_stack_value) becomes
178d88c1a5aSDimitry Andric     // DW_AT_const_value(X).
179d88c1a5aSDimitry Andric     if (GlobalExprs.size() == 1 && Expr && Expr->isConstant()) {
1807a7e6055SDimitry Andric       addToAccelTable = true;
181d88c1a5aSDimitry Andric       addConstantValue(*VariableDIE, /*Unsigned=*/true, Expr->getElement(1));
1827a7e6055SDimitry Andric       break;
1837a7e6055SDimitry Andric     }
1847a7e6055SDimitry Andric 
185d88c1a5aSDimitry Andric     // We cannot describe the location of dllimport'd variables: the
186d88c1a5aSDimitry Andric     // computation of their address requires loads from the IAT.
1877a7e6055SDimitry Andric     if (Global && Global->hasDLLImportStorageClass())
1887a7e6055SDimitry Andric       continue;
1897a7e6055SDimitry Andric 
1907a7e6055SDimitry Andric     // Nothing to describe without address or constant.
1917a7e6055SDimitry Andric     if (!Global && (!Expr || !Expr->isConstant()))
1927a7e6055SDimitry Andric       continue;
1937a7e6055SDimitry Andric 
194*b5893f02SDimitry Andric     if (Global && Global->isThreadLocal() &&
195*b5893f02SDimitry Andric         !Asm->getObjFileLowering().supportDebugThreadLocalLocation())
196*b5893f02SDimitry Andric       continue;
197*b5893f02SDimitry Andric 
198d88c1a5aSDimitry Andric     if (!Loc) {
1997a7e6055SDimitry Andric       addToAccelTable = true;
200d88c1a5aSDimitry Andric       Loc = new (DIEValueAllocator) DIELoc;
201d88c1a5aSDimitry Andric       DwarfExpr = llvm::make_unique<DIEDwarfExpression>(*Asm, *this, *Loc);
202d88c1a5aSDimitry Andric     }
2037a7e6055SDimitry Andric 
2044ba319b5SDimitry Andric     if (Expr)
2054ba319b5SDimitry Andric       DwarfExpr->addFragmentOffset(Expr);
2064ba319b5SDimitry Andric 
207d88c1a5aSDimitry Andric     if (Global) {
208ff0cc061SDimitry Andric       const MCSymbol *Sym = Asm->getSymbol(Global);
209ff0cc061SDimitry Andric       if (Global->isThreadLocal()) {
2104ba319b5SDimitry Andric         if (Asm->TM.useEmulatedTLS()) {
2117d523365SDimitry Andric           // TODO: add debug info for emulated thread local mode.
2127d523365SDimitry Andric         } else {
21339d628a0SDimitry Andric           // FIXME: Make this work with -gsplit-dwarf.
21439d628a0SDimitry Andric           unsigned PointerSize = Asm->getDataLayout().getPointerSize();
21539d628a0SDimitry Andric           assert((PointerSize == 4 || PointerSize == 8) &&
21639d628a0SDimitry Andric                  "Add support for other sizes if necessary");
21739d628a0SDimitry Andric           // Based on GCC's support for TLS:
21839d628a0SDimitry Andric           if (!DD->useSplitDwarf()) {
21939d628a0SDimitry Andric             // 1) Start with a constNu of the appropriate pointer size
220d88c1a5aSDimitry Andric             addUInt(*Loc, dwarf::DW_FORM_data1,
221d88c1a5aSDimitry Andric                     PointerSize == 4 ? dwarf::DW_OP_const4u
2227d523365SDimitry Andric                                      : dwarf::DW_OP_const8u);
22339d628a0SDimitry Andric             // 2) containing the (relocated) offset of the TLS variable
22439d628a0SDimitry Andric             //    within the module's TLS block.
22539d628a0SDimitry Andric             addExpr(*Loc, dwarf::DW_FORM_udata,
22639d628a0SDimitry Andric                     Asm->getObjFileLowering().getDebugThreadLocalSymbol(Sym));
22739d628a0SDimitry Andric           } else {
22839d628a0SDimitry Andric             addUInt(*Loc, dwarf::DW_FORM_data1, dwarf::DW_OP_GNU_const_index);
22939d628a0SDimitry Andric             addUInt(*Loc, dwarf::DW_FORM_udata,
23039d628a0SDimitry Andric                     DD->getAddressPool().getIndex(Sym, /* TLS */ true));
23139d628a0SDimitry Andric           }
232ff0cc061SDimitry Andric           // 3) followed by an OP to make the debugger do a TLS lookup.
233ff0cc061SDimitry Andric           addUInt(*Loc, dwarf::DW_FORM_data1,
234ff0cc061SDimitry Andric                   DD->useGNUTLSOpcode() ? dwarf::DW_OP_GNU_push_tls_address
235ff0cc061SDimitry Andric                                         : dwarf::DW_OP_form_tls_address);
2367d523365SDimitry Andric         }
23739d628a0SDimitry Andric       } else {
23839d628a0SDimitry Andric         DD->addArangeLabel(SymbolCU(this, Sym));
23939d628a0SDimitry Andric         addOpAddress(*Loc, Sym);
24039d628a0SDimitry Andric       }
241d88c1a5aSDimitry Andric     }
2424ba319b5SDimitry Andric     // Global variables attached to symbols are memory locations.
2434ba319b5SDimitry Andric     // It would be better if this were unconditional, but malformed input that
2444ba319b5SDimitry Andric     // mixes non-fragments and fragments for the same variable is too expensive
2454ba319b5SDimitry Andric     // to detect in the verifier.
2464ba319b5SDimitry Andric     if (DwarfExpr->isUnknownLocation())
2474ba319b5SDimitry Andric       DwarfExpr->setMemoryLocationKind();
2487a7e6055SDimitry Andric     DwarfExpr->addExpression(Expr);
249d88c1a5aSDimitry Andric   }
250d88c1a5aSDimitry Andric   if (Loc)
251d88c1a5aSDimitry Andric     addBlock(*VariableDIE, dwarf::DW_AT_location, DwarfExpr->finalize());
25239d628a0SDimitry Andric 
2533ca95b02SDimitry Andric   if (DD->useAllLinkageNames())
254ff0cc061SDimitry Andric     addLinkageName(*VariableDIE, GV->getLinkageName());
25539d628a0SDimitry Andric 
25639d628a0SDimitry Andric   if (addToAccelTable) {
257*b5893f02SDimitry Andric     DD->addAccelName(*CUNode, GV->getName(), *VariableDIE);
25839d628a0SDimitry Andric 
25939d628a0SDimitry Andric     // If the linkage name is different than the name, go ahead and output
26039d628a0SDimitry Andric     // that as well into the name table.
2614ba319b5SDimitry Andric     if (GV->getLinkageName() != "" && GV->getName() != GV->getLinkageName() &&
2624ba319b5SDimitry Andric         DD->useAllLinkageNames())
263*b5893f02SDimitry Andric       DD->addAccelName(*CUNode, GV->getLinkageName(), *VariableDIE);
26439d628a0SDimitry Andric   }
26539d628a0SDimitry Andric 
26639d628a0SDimitry Andric   return VariableDIE;
26739d628a0SDimitry Andric }
26839d628a0SDimitry Andric 
addRange(RangeSpan Range)26939d628a0SDimitry Andric void DwarfCompileUnit::addRange(RangeSpan Range) {
27039d628a0SDimitry Andric   bool SameAsPrevCU = this == DD->getPrevCU();
27139d628a0SDimitry Andric   DD->setPrevCU(this);
27239d628a0SDimitry Andric   // If we have no current ranges just add the range and return, otherwise,
27339d628a0SDimitry Andric   // check the current section and CU against the previous section and CU we
27439d628a0SDimitry Andric   // emitted into and the subprogram was contained within. If these are the
27539d628a0SDimitry Andric   // same then extend our current range, otherwise add this as a new range.
27639d628a0SDimitry Andric   if (CURanges.empty() || !SameAsPrevCU ||
27739d628a0SDimitry Andric       (&CURanges.back().getEnd()->getSection() !=
27839d628a0SDimitry Andric        &Range.getEnd()->getSection())) {
27939d628a0SDimitry Andric     CURanges.push_back(Range);
280*b5893f02SDimitry Andric     DD->addSectionLabel(Range.getStart());
28139d628a0SDimitry Andric     return;
28239d628a0SDimitry Andric   }
28339d628a0SDimitry Andric 
28439d628a0SDimitry Andric   CURanges.back().setEnd(Range.getEnd());
28539d628a0SDimitry Andric }
28639d628a0SDimitry Andric 
initStmtList()287ff0cc061SDimitry Andric void DwarfCompileUnit::initStmtList() {
288*b5893f02SDimitry Andric   if (CUNode->isDebugDirectivesOnly())
289*b5893f02SDimitry Andric     return;
290*b5893f02SDimitry Andric 
29139d628a0SDimitry Andric   // Define start line table label for each Compile Unit.
2924ba319b5SDimitry Andric   MCSymbol *LineTableStartSym;
2934ba319b5SDimitry Andric   const TargetLoweringObjectFile &TLOF = Asm->getObjFileLowering();
2944ba319b5SDimitry Andric   if (DD->useSectionsAsReferences()) {
2954ba319b5SDimitry Andric     LineTableStartSym = TLOF.getDwarfLineSection()->getBeginSymbol();
2964ba319b5SDimitry Andric   } else {
2974ba319b5SDimitry Andric     LineTableStartSym =
298ff0cc061SDimitry Andric         Asm->OutStreamer->getDwarfLineTableSymbol(getUniqueID());
2994ba319b5SDimitry Andric   }
30039d628a0SDimitry Andric 
30139d628a0SDimitry Andric   // DW_AT_stmt_list is a offset of line number information for this
30239d628a0SDimitry Andric   // compile unit in debug_line section. For split dwarf this is
30339d628a0SDimitry Andric   // left in the skeleton CU and so not included.
30439d628a0SDimitry Andric   // The line table entries are not always emitted in assembly, so it
30539d628a0SDimitry Andric   // is not okay to use line_table_start here.
3063dac3a9bSDimitry Andric   StmtListValue =
307d88c1a5aSDimitry Andric       addSectionLabel(getUnitDie(), dwarf::DW_AT_stmt_list, LineTableStartSym,
308ff0cc061SDimitry Andric                       TLOF.getDwarfLineSection()->getBeginSymbol());
30939d628a0SDimitry Andric }
31039d628a0SDimitry Andric 
applyStmtList(DIE & D)31139d628a0SDimitry Andric void DwarfCompileUnit::applyStmtList(DIE &D) {
3123dac3a9bSDimitry Andric   D.addValue(DIEValueAllocator, *StmtListValue);
31339d628a0SDimitry Andric }
31439d628a0SDimitry Andric 
attachLowHighPC(DIE & D,const MCSymbol * Begin,const MCSymbol * End)31539d628a0SDimitry Andric void DwarfCompileUnit::attachLowHighPC(DIE &D, const MCSymbol *Begin,
31639d628a0SDimitry Andric                                        const MCSymbol *End) {
31739d628a0SDimitry Andric   assert(Begin && "Begin label should not be null!");
31839d628a0SDimitry Andric   assert(End && "End label should not be null!");
31939d628a0SDimitry Andric   assert(Begin->isDefined() && "Invalid starting label");
32039d628a0SDimitry Andric   assert(End->isDefined() && "Invalid end label");
32139d628a0SDimitry Andric 
32239d628a0SDimitry Andric   addLabelAddress(D, dwarf::DW_AT_low_pc, Begin);
32339d628a0SDimitry Andric   if (DD->getDwarfVersion() < 4)
32439d628a0SDimitry Andric     addLabelAddress(D, dwarf::DW_AT_high_pc, End);
32539d628a0SDimitry Andric   else
32639d628a0SDimitry Andric     addLabelDelta(D, dwarf::DW_AT_high_pc, End, Begin);
32739d628a0SDimitry Andric }
32839d628a0SDimitry Andric 
32939d628a0SDimitry Andric // Find DIE for the given subprogram and attach appropriate DW_AT_low_pc
33039d628a0SDimitry Andric // and DW_AT_high_pc attributes. If there are global variables in this
33139d628a0SDimitry Andric // scope then create and insert DIEs for these variables.
updateSubprogramScopeDIE(const DISubprogram * SP)332ff0cc061SDimitry Andric DIE &DwarfCompileUnit::updateSubprogramScopeDIE(const DISubprogram *SP) {
33339d628a0SDimitry Andric   DIE *SPDie = getOrCreateSubprogramDIE(SP, includeMinimalInlineScopes());
33439d628a0SDimitry Andric 
335ff0cc061SDimitry Andric   attachLowHighPC(*SPDie, Asm->getFunctionBegin(), Asm->getFunctionEnd());
3363ca95b02SDimitry Andric   if (DD->useAppleExtensionAttributes() &&
3373ca95b02SDimitry Andric       !DD->getCurrentFunction()->getTarget().Options.DisableFramePointerElim(
33839d628a0SDimitry Andric           *DD->getCurrentFunction()))
33939d628a0SDimitry Andric     addFlag(*SPDie, dwarf::DW_AT_APPLE_omit_frame_ptr);
34039d628a0SDimitry Andric 
34139d628a0SDimitry Andric   // Only include DW_AT_frame_base in full debug info
34239d628a0SDimitry Andric   if (!includeMinimalInlineScopes()) {
3434ba319b5SDimitry Andric     if (Asm->MF->getTarget().getTargetTriple().isNVPTX()) {
3444ba319b5SDimitry Andric       DIELoc *Loc = new (DIEValueAllocator) DIELoc;
3454ba319b5SDimitry Andric       addUInt(*Loc, dwarf::DW_FORM_data1, dwarf::DW_OP_call_frame_cfa);
3464ba319b5SDimitry Andric       addBlock(*SPDie, dwarf::DW_AT_frame_base, Loc);
3474ba319b5SDimitry Andric     } else {
348ff0cc061SDimitry Andric       const TargetRegisterInfo *RI = Asm->MF->getSubtarget().getRegisterInfo();
34939d628a0SDimitry Andric       MachineLocation Location(RI->getFrameRegister(*Asm->MF));
35039d628a0SDimitry Andric       if (RI->isPhysicalRegister(Location.getReg()))
35139d628a0SDimitry Andric         addAddress(*SPDie, dwarf::DW_AT_frame_base, Location);
35239d628a0SDimitry Andric     }
3534ba319b5SDimitry Andric   }
35439d628a0SDimitry Andric 
35539d628a0SDimitry Andric   // Add name to the name table, we do this here because we're guaranteed
35639d628a0SDimitry Andric   // to have concrete versions of our DW_TAG_subprogram nodes.
357*b5893f02SDimitry Andric   DD->addSubprogramNames(*CUNode, SP, *SPDie);
35839d628a0SDimitry Andric 
35939d628a0SDimitry Andric   return *SPDie;
36039d628a0SDimitry Andric }
36139d628a0SDimitry Andric 
36239d628a0SDimitry Andric // Construct a DIE for this scope.
constructScopeDIE(LexicalScope * Scope,SmallVectorImpl<DIE * > & FinalChildren)36339d628a0SDimitry Andric void DwarfCompileUnit::constructScopeDIE(
3643dac3a9bSDimitry Andric     LexicalScope *Scope, SmallVectorImpl<DIE *> &FinalChildren) {
36539d628a0SDimitry Andric   if (!Scope || !Scope->getScopeNode())
36639d628a0SDimitry Andric     return;
36739d628a0SDimitry Andric 
368ff0cc061SDimitry Andric   auto *DS = Scope->getScopeNode();
36939d628a0SDimitry Andric 
370ff0cc061SDimitry Andric   assert((Scope->getInlinedAt() || !isa<DISubprogram>(DS)) &&
37139d628a0SDimitry Andric          "Only handle inlined subprograms here, use "
37239d628a0SDimitry Andric          "constructSubprogramScopeDIE for non-inlined "
37339d628a0SDimitry Andric          "subprograms");
37439d628a0SDimitry Andric 
3753dac3a9bSDimitry Andric   SmallVector<DIE *, 8> Children;
37639d628a0SDimitry Andric 
37739d628a0SDimitry Andric   // We try to create the scope DIE first, then the children DIEs. This will
37839d628a0SDimitry Andric   // avoid creating un-used children then removing them later when we find out
37939d628a0SDimitry Andric   // the scope DIE is null.
3803dac3a9bSDimitry Andric   DIE *ScopeDIE;
381ff0cc061SDimitry Andric   if (Scope->getParent() && isa<DISubprogram>(DS)) {
38239d628a0SDimitry Andric     ScopeDIE = constructInlinedScopeDIE(Scope);
38339d628a0SDimitry Andric     if (!ScopeDIE)
38439d628a0SDimitry Andric       return;
38539d628a0SDimitry Andric     // We create children when the scope DIE is not null.
38639d628a0SDimitry Andric     createScopeChildrenDIE(Scope, Children);
38739d628a0SDimitry Andric   } else {
38839d628a0SDimitry Andric     // Early exit when we know the scope DIE is going to be null.
38939d628a0SDimitry Andric     if (DD->isLexicalScopeDIENull(Scope))
39039d628a0SDimitry Andric       return;
39139d628a0SDimitry Andric 
3922cab237bSDimitry Andric     bool HasNonScopeChildren = false;
39339d628a0SDimitry Andric 
39439d628a0SDimitry Andric     // We create children here when we know the scope DIE is not going to be
39539d628a0SDimitry Andric     // null and the children will be added to the scope DIE.
3962cab237bSDimitry Andric     createScopeChildrenDIE(Scope, Children, &HasNonScopeChildren);
39739d628a0SDimitry Andric 
39839d628a0SDimitry Andric     // If there are only other scopes as children, put them directly in the
39939d628a0SDimitry Andric     // parent instead, as this scope would serve no purpose.
4002cab237bSDimitry Andric     if (!HasNonScopeChildren) {
40139d628a0SDimitry Andric       FinalChildren.insert(FinalChildren.end(),
40239d628a0SDimitry Andric                            std::make_move_iterator(Children.begin()),
40339d628a0SDimitry Andric                            std::make_move_iterator(Children.end()));
40439d628a0SDimitry Andric       return;
40539d628a0SDimitry Andric     }
40639d628a0SDimitry Andric     ScopeDIE = constructLexicalScopeDIE(Scope);
40739d628a0SDimitry Andric     assert(ScopeDIE && "Scope DIE should not be null.");
40839d628a0SDimitry Andric   }
40939d628a0SDimitry Andric 
41039d628a0SDimitry Andric   // Add children
41139d628a0SDimitry Andric   for (auto &I : Children)
41239d628a0SDimitry Andric     ScopeDIE->addChild(std::move(I));
41339d628a0SDimitry Andric 
41439d628a0SDimitry Andric   FinalChildren.push_back(std::move(ScopeDIE));
41539d628a0SDimitry Andric }
41639d628a0SDimitry Andric 
addScopeRangeList(DIE & ScopeDIE,SmallVector<RangeSpan,2> Range)41739d628a0SDimitry Andric void DwarfCompileUnit::addScopeRangeList(DIE &ScopeDIE,
41839d628a0SDimitry Andric                                          SmallVector<RangeSpan, 2> Range) {
419ff0cc061SDimitry Andric   const TargetLoweringObjectFile &TLOF = Asm->getObjFileLowering();
420ff0cc061SDimitry Andric 
4214ba319b5SDimitry Andric   // Emit the offset into .debug_ranges or .debug_rnglists as a relocatable
4224ba319b5SDimitry Andric   // label. emitDIE() will handle emitting it appropriately.
423ff0cc061SDimitry Andric   const MCSymbol *RangeSectionSym =
4244ba319b5SDimitry Andric       DD->getDwarfVersion() >= 5
4254ba319b5SDimitry Andric           ? TLOF.getDwarfRnglistsSection()->getBeginSymbol()
4264ba319b5SDimitry Andric           : TLOF.getDwarfRangesSection()->getBeginSymbol();
42739d628a0SDimitry Andric 
428*b5893f02SDimitry Andric   HasRangeLists = true;
429*b5893f02SDimitry Andric 
430*b5893f02SDimitry Andric   // Add the range list to the set of ranges to be emitted.
431*b5893f02SDimitry Andric   auto IndexAndList =
432*b5893f02SDimitry Andric       (DD->getDwarfVersion() < 5 && Skeleton ? Skeleton->DU : DU)
433*b5893f02SDimitry Andric           ->addRange(*(Skeleton ? Skeleton : this), std::move(Range));
434*b5893f02SDimitry Andric 
435*b5893f02SDimitry Andric   uint32_t Index = IndexAndList.first;
436*b5893f02SDimitry Andric   auto &List = *IndexAndList.second;
43739d628a0SDimitry Andric 
43839d628a0SDimitry Andric   // Under fission, ranges are specified by constant offsets relative to the
43939d628a0SDimitry Andric   // CU's DW_AT_GNU_ranges_base.
4404ba319b5SDimitry Andric   // FIXME: For DWARF v5, do not generate the DW_AT_ranges attribute under
4414ba319b5SDimitry Andric   // fission until we support the forms using the .debug_addr section
4424ba319b5SDimitry Andric   // (DW_RLE_startx_endx etc.).
443*b5893f02SDimitry Andric   if (DD->getDwarfVersion() >= 5)
444*b5893f02SDimitry Andric     addUInt(ScopeDIE, dwarf::DW_AT_ranges, dwarf::DW_FORM_rnglistx, Index);
445*b5893f02SDimitry Andric   else if (isDwoUnit())
44639d628a0SDimitry Andric     addSectionDelta(ScopeDIE, dwarf::DW_AT_ranges, List.getSym(),
44739d628a0SDimitry Andric                     RangeSectionSym);
448*b5893f02SDimitry Andric   else
44939d628a0SDimitry Andric     addSectionLabel(ScopeDIE, dwarf::DW_AT_ranges, List.getSym(),
45039d628a0SDimitry Andric                     RangeSectionSym);
4514ba319b5SDimitry Andric }
45239d628a0SDimitry Andric 
attachRangesOrLowHighPC(DIE & Die,SmallVector<RangeSpan,2> Ranges)45339d628a0SDimitry Andric void DwarfCompileUnit::attachRangesOrLowHighPC(
45439d628a0SDimitry Andric     DIE &Die, SmallVector<RangeSpan, 2> Ranges) {
4554ba319b5SDimitry Andric   if (Ranges.size() == 1 || !DD->useRangesSection()) {
4564ba319b5SDimitry Andric     const RangeSpan &Front = Ranges.front();
4574ba319b5SDimitry Andric     const RangeSpan &Back = Ranges.back();
4584ba319b5SDimitry Andric     attachLowHighPC(Die, Front.getStart(), Back.getEnd());
45939d628a0SDimitry Andric   } else
46039d628a0SDimitry Andric     addScopeRangeList(Die, std::move(Ranges));
46139d628a0SDimitry Andric }
46239d628a0SDimitry Andric 
attachRangesOrLowHighPC(DIE & Die,const SmallVectorImpl<InsnRange> & Ranges)46339d628a0SDimitry Andric void DwarfCompileUnit::attachRangesOrLowHighPC(
46439d628a0SDimitry Andric     DIE &Die, const SmallVectorImpl<InsnRange> &Ranges) {
46539d628a0SDimitry Andric   SmallVector<RangeSpan, 2> List;
46639d628a0SDimitry Andric   List.reserve(Ranges.size());
46739d628a0SDimitry Andric   for (const InsnRange &R : Ranges)
46839d628a0SDimitry Andric     List.push_back(RangeSpan(DD->getLabelBeforeInsn(R.first),
46939d628a0SDimitry Andric                              DD->getLabelAfterInsn(R.second)));
47039d628a0SDimitry Andric   attachRangesOrLowHighPC(Die, std::move(List));
47139d628a0SDimitry Andric }
47239d628a0SDimitry Andric 
47339d628a0SDimitry Andric // This scope represents inlined body of a function. Construct DIE to
47439d628a0SDimitry Andric // represent this concrete inlined copy of the function.
constructInlinedScopeDIE(LexicalScope * Scope)4753dac3a9bSDimitry Andric DIE *DwarfCompileUnit::constructInlinedScopeDIE(LexicalScope *Scope) {
47639d628a0SDimitry Andric   assert(Scope->getScopeNode());
477ff0cc061SDimitry Andric   auto *DS = Scope->getScopeNode();
478ff0cc061SDimitry Andric   auto *InlinedSP = getDISubprogram(DS);
47939d628a0SDimitry Andric   // Find the subprogram's DwarfCompileUnit in the SPMap in case the subprogram
48039d628a0SDimitry Andric   // was inlined from another compile unit.
4815517e702SDimitry Andric   DIE *OriginDIE = getAbstractSPDies()[InlinedSP];
48239d628a0SDimitry Andric   assert(OriginDIE && "Unable to find original DIE for an inlined subprogram.");
48339d628a0SDimitry Andric 
4843dac3a9bSDimitry Andric   auto ScopeDIE = DIE::get(DIEValueAllocator, dwarf::DW_TAG_inlined_subroutine);
48539d628a0SDimitry Andric   addDIEEntry(*ScopeDIE, dwarf::DW_AT_abstract_origin, *OriginDIE);
48639d628a0SDimitry Andric 
48739d628a0SDimitry Andric   attachRangesOrLowHighPC(*ScopeDIE, Scope->getRanges());
48839d628a0SDimitry Andric 
48939d628a0SDimitry Andric   // Add the call site information to the DIE.
490ff0cc061SDimitry Andric   const DILocation *IA = Scope->getInlinedAt();
49139d628a0SDimitry Andric   addUInt(*ScopeDIE, dwarf::DW_AT_call_file, None,
4924ba319b5SDimitry Andric           getOrCreateSourceID(IA->getFile()));
493ff0cc061SDimitry Andric   addUInt(*ScopeDIE, dwarf::DW_AT_call_line, None, IA->getLine());
494d88c1a5aSDimitry Andric   if (IA->getDiscriminator() && DD->getDwarfVersion() >= 4)
4957d523365SDimitry Andric     addUInt(*ScopeDIE, dwarf::DW_AT_GNU_discriminator, None,
4967d523365SDimitry Andric             IA->getDiscriminator());
49739d628a0SDimitry Andric 
49839d628a0SDimitry Andric   // Add name to the name table, we do this here because we're guaranteed
49939d628a0SDimitry Andric   // to have concrete versions of our DW_TAG_inlined_subprogram nodes.
500*b5893f02SDimitry Andric   DD->addSubprogramNames(*CUNode, InlinedSP, *ScopeDIE);
50139d628a0SDimitry Andric 
50239d628a0SDimitry Andric   return ScopeDIE;
50339d628a0SDimitry Andric }
50439d628a0SDimitry Andric 
50539d628a0SDimitry Andric // Construct new DW_TAG_lexical_block for this scope and attach
50639d628a0SDimitry Andric // DW_AT_low_pc/DW_AT_high_pc labels.
constructLexicalScopeDIE(LexicalScope * Scope)5073dac3a9bSDimitry Andric DIE *DwarfCompileUnit::constructLexicalScopeDIE(LexicalScope *Scope) {
50839d628a0SDimitry Andric   if (DD->isLexicalScopeDIENull(Scope))
50939d628a0SDimitry Andric     return nullptr;
51039d628a0SDimitry Andric 
5113dac3a9bSDimitry Andric   auto ScopeDIE = DIE::get(DIEValueAllocator, dwarf::DW_TAG_lexical_block);
51239d628a0SDimitry Andric   if (Scope->isAbstractScope())
51339d628a0SDimitry Andric     return ScopeDIE;
51439d628a0SDimitry Andric 
51539d628a0SDimitry Andric   attachRangesOrLowHighPC(*ScopeDIE, Scope->getRanges());
51639d628a0SDimitry Andric 
51739d628a0SDimitry Andric   return ScopeDIE;
51839d628a0SDimitry Andric }
51939d628a0SDimitry Andric 
52039d628a0SDimitry Andric /// constructVariableDIE - Construct a DIE for the given DbgVariable.
constructVariableDIE(DbgVariable & DV,bool Abstract)5213dac3a9bSDimitry Andric DIE *DwarfCompileUnit::constructVariableDIE(DbgVariable &DV, bool Abstract) {
52239d628a0SDimitry Andric   auto D = constructVariableDIEImpl(DV, Abstract);
52339d628a0SDimitry Andric   DV.setDIE(*D);
52439d628a0SDimitry Andric   return D;
52539d628a0SDimitry Andric }
52639d628a0SDimitry Andric 
constructLabelDIE(DbgLabel & DL,const LexicalScope & Scope)527*b5893f02SDimitry Andric DIE *DwarfCompileUnit::constructLabelDIE(DbgLabel &DL,
528*b5893f02SDimitry Andric                                          const LexicalScope &Scope) {
529*b5893f02SDimitry Andric   auto LabelDie = DIE::get(DIEValueAllocator, DL.getTag());
530*b5893f02SDimitry Andric   insertDIE(DL.getLabel(), LabelDie);
531*b5893f02SDimitry Andric   DL.setDIE(*LabelDie);
532*b5893f02SDimitry Andric 
533*b5893f02SDimitry Andric   if (Scope.isAbstractScope())
534*b5893f02SDimitry Andric     applyLabelAttributes(DL, *LabelDie);
535*b5893f02SDimitry Andric 
536*b5893f02SDimitry Andric   return LabelDie;
537*b5893f02SDimitry Andric }
538*b5893f02SDimitry Andric 
constructVariableDIEImpl(const DbgVariable & DV,bool Abstract)5393dac3a9bSDimitry Andric DIE *DwarfCompileUnit::constructVariableDIEImpl(const DbgVariable &DV,
54039d628a0SDimitry Andric                                                 bool Abstract) {
54139d628a0SDimitry Andric   // Define variable debug information entry.
5423dac3a9bSDimitry Andric   auto VariableDie = DIE::get(DIEValueAllocator, DV.getTag());
5434ba319b5SDimitry Andric   insertDIE(DV.getVariable(), VariableDie);
54439d628a0SDimitry Andric 
54539d628a0SDimitry Andric   if (Abstract) {
54639d628a0SDimitry Andric     applyVariableAttributes(DV, *VariableDie);
54739d628a0SDimitry Andric     return VariableDie;
54839d628a0SDimitry Andric   }
54939d628a0SDimitry Andric 
55039d628a0SDimitry Andric   // Add variable address.
55139d628a0SDimitry Andric 
552ff0cc061SDimitry Andric   unsigned Offset = DV.getDebugLocListIndex();
55339d628a0SDimitry Andric   if (Offset != ~0U) {
55439d628a0SDimitry Andric     addLocationList(*VariableDie, dwarf::DW_AT_location, Offset);
55539d628a0SDimitry Andric     return VariableDie;
55639d628a0SDimitry Andric   }
55739d628a0SDimitry Andric 
55839d628a0SDimitry Andric   // Check if variable is described by a DBG_VALUE instruction.
55939d628a0SDimitry Andric   if (const MachineInstr *DVInsn = DV.getMInsn()) {
56039d628a0SDimitry Andric     assert(DVInsn->getNumOperands() == 4);
56139d628a0SDimitry Andric     if (DVInsn->getOperand(0).isReg()) {
5622cab237bSDimitry Andric       auto RegOp = DVInsn->getOperand(0);
5632cab237bSDimitry Andric       auto Op1 = DVInsn->getOperand(1);
56439d628a0SDimitry Andric       // If the second operand is an immediate, this is an indirect value.
5652cab237bSDimitry Andric       assert((!Op1.isImm() || (Op1.getImm() == 0)) && "unexpected offset");
5662cab237bSDimitry Andric       MachineLocation Location(RegOp.getReg(), Op1.isImm());
56739d628a0SDimitry Andric       addVariableAddress(DV, *VariableDie, Location);
5683ca95b02SDimitry Andric     } else if (DVInsn->getOperand(0).isImm()) {
5693ca95b02SDimitry Andric       // This variable is described by a single constant.
5703ca95b02SDimitry Andric       // Check whether it has a DIExpression.
5713ca95b02SDimitry Andric       auto *Expr = DV.getSingleExpression();
5723ca95b02SDimitry Andric       if (Expr && Expr->getNumElements()) {
5733ca95b02SDimitry Andric         DIELoc *Loc = new (DIEValueAllocator) DIELoc;
5743ca95b02SDimitry Andric         DIEDwarfExpression DwarfExpr(*Asm, *this, *Loc);
5753ca95b02SDimitry Andric         // If there is an expression, emit raw unsigned bytes.
576d88c1a5aSDimitry Andric         DwarfExpr.addFragmentOffset(Expr);
5777a7e6055SDimitry Andric         DwarfExpr.addUnsignedConstant(DVInsn->getOperand(0).getImm());
5787a7e6055SDimitry Andric         DwarfExpr.addExpression(Expr);
579d88c1a5aSDimitry Andric         addBlock(*VariableDie, dwarf::DW_AT_location, DwarfExpr.finalize());
5803ca95b02SDimitry Andric       } else
58139d628a0SDimitry Andric         addConstantValue(*VariableDie, DVInsn->getOperand(0), DV.getType());
5823ca95b02SDimitry Andric     } else if (DVInsn->getOperand(0).isFPImm())
58339d628a0SDimitry Andric       addConstantFPValue(*VariableDie, DVInsn->getOperand(0));
58439d628a0SDimitry Andric     else if (DVInsn->getOperand(0).isCImm())
58539d628a0SDimitry Andric       addConstantValue(*VariableDie, DVInsn->getOperand(0).getCImm(),
58639d628a0SDimitry Andric                        DV.getType());
58739d628a0SDimitry Andric 
58839d628a0SDimitry Andric     return VariableDie;
58939d628a0SDimitry Andric   }
59039d628a0SDimitry Andric 
59139d628a0SDimitry Andric   // .. else use frame index.
5925d193882SDimitry Andric   if (!DV.hasFrameIndexExprs())
593ff0cc061SDimitry Andric     return VariableDie;
594ff0cc061SDimitry Andric 
59597bc6c73SDimitry Andric   DIELoc *Loc = new (DIEValueAllocator) DIELoc;
596ff0cc061SDimitry Andric   DIEDwarfExpression DwarfExpr(*Asm, *this, *Loc);
5975d193882SDimitry Andric   for (auto &Fragment : DV.getFrameIndexExprs()) {
59839d628a0SDimitry Andric     unsigned FrameReg = 0;
5996bc11b14SDimitry Andric     const DIExpression *Expr = Fragment.Expr;
600ff0cc061SDimitry Andric     const TargetFrameLowering *TFI = Asm->MF->getSubtarget().getFrameLowering();
6015d193882SDimitry Andric     int Offset = TFI->getFrameIndexReference(*Asm->MF, Fragment.FI, FrameReg);
6026bc11b14SDimitry Andric     DwarfExpr.addFragmentOffset(Expr);
6037a7e6055SDimitry Andric     SmallVector<uint64_t, 8> Ops;
60424d58133SDimitry Andric     Ops.push_back(dwarf::DW_OP_plus_uconst);
6057a7e6055SDimitry Andric     Ops.push_back(Offset);
6066bc11b14SDimitry Andric     Ops.append(Expr->elements_begin(), Expr->elements_end());
6076bc11b14SDimitry Andric     DIExpressionCursor Cursor(Ops);
6086bc11b14SDimitry Andric     DwarfExpr.setMemoryLocationKind();
6094ba319b5SDimitry Andric     if (const MCSymbol *FrameSymbol = Asm->getFunctionFrameSymbol())
6104ba319b5SDimitry Andric       addOpAddress(*Loc, FrameSymbol);
6114ba319b5SDimitry Andric     else
6127a7e6055SDimitry Andric       DwarfExpr.addMachineRegExpression(
6136bc11b14SDimitry Andric           *Asm->MF->getSubtarget().getRegisterInfo(), Cursor, FrameReg);
6146bc11b14SDimitry Andric     DwarfExpr.addExpression(std::move(Cursor));
61539d628a0SDimitry Andric   }
616d88c1a5aSDimitry Andric   addBlock(*VariableDie, dwarf::DW_AT_location, DwarfExpr.finalize());
61739d628a0SDimitry Andric 
61839d628a0SDimitry Andric   return VariableDie;
61939d628a0SDimitry Andric }
62039d628a0SDimitry Andric 
constructVariableDIE(DbgVariable & DV,const LexicalScope & Scope,DIE * & ObjectPointer)6213dac3a9bSDimitry Andric DIE *DwarfCompileUnit::constructVariableDIE(DbgVariable &DV,
6223dac3a9bSDimitry Andric                                             const LexicalScope &Scope,
6233dac3a9bSDimitry Andric                                             DIE *&ObjectPointer) {
62439d628a0SDimitry Andric   auto Var = constructVariableDIE(DV, Scope.isAbstractScope());
62539d628a0SDimitry Andric   if (DV.isObjectPointer())
6263dac3a9bSDimitry Andric     ObjectPointer = Var;
62739d628a0SDimitry Andric   return Var;
62839d628a0SDimitry Andric }
62939d628a0SDimitry Andric 
6304ba319b5SDimitry Andric /// Return all DIVariables that appear in count: expressions.
dependencies(DbgVariable * Var)6314ba319b5SDimitry Andric static SmallVector<const DIVariable *, 2> dependencies(DbgVariable *Var) {
6324ba319b5SDimitry Andric   SmallVector<const DIVariable *, 2> Result;
6334ba319b5SDimitry Andric   auto *Array = dyn_cast<DICompositeType>(Var->getType());
6344ba319b5SDimitry Andric   if (!Array || Array->getTag() != dwarf::DW_TAG_array_type)
6354ba319b5SDimitry Andric     return Result;
6364ba319b5SDimitry Andric   for (auto *El : Array->getElements()) {
6374ba319b5SDimitry Andric     if (auto *Subrange = dyn_cast<DISubrange>(El)) {
6384ba319b5SDimitry Andric       auto Count = Subrange->getCount();
6394ba319b5SDimitry Andric       if (auto *Dependency = Count.dyn_cast<DIVariable *>())
6404ba319b5SDimitry Andric         Result.push_back(Dependency);
6414ba319b5SDimitry Andric     }
6424ba319b5SDimitry Andric   }
6434ba319b5SDimitry Andric   return Result;
6444ba319b5SDimitry Andric }
6454ba319b5SDimitry Andric 
6464ba319b5SDimitry Andric /// Sort local variables so that variables appearing inside of helper
6474ba319b5SDimitry Andric /// expressions come first.
6484ba319b5SDimitry Andric static SmallVector<DbgVariable *, 8>
sortLocalVars(SmallVectorImpl<DbgVariable * > & Input)6494ba319b5SDimitry Andric sortLocalVars(SmallVectorImpl<DbgVariable *> &Input) {
6504ba319b5SDimitry Andric   SmallVector<DbgVariable *, 8> Result;
6514ba319b5SDimitry Andric   SmallVector<PointerIntPair<DbgVariable *, 1>, 8> WorkList;
6524ba319b5SDimitry Andric   // Map back from a DIVariable to its containing DbgVariable.
6534ba319b5SDimitry Andric   SmallDenseMap<const DILocalVariable *, DbgVariable *> DbgVar;
6544ba319b5SDimitry Andric   // Set of DbgVariables in Result.
6554ba319b5SDimitry Andric   SmallDenseSet<DbgVariable *, 8> Visited;
6564ba319b5SDimitry Andric   // For cycle detection.
6574ba319b5SDimitry Andric   SmallDenseSet<DbgVariable *, 8> Visiting;
6584ba319b5SDimitry Andric 
6594ba319b5SDimitry Andric   // Initialize the worklist and the DIVariable lookup table.
6604ba319b5SDimitry Andric   for (auto Var : reverse(Input)) {
6614ba319b5SDimitry Andric     DbgVar.insert({Var->getVariable(), Var});
6624ba319b5SDimitry Andric     WorkList.push_back({Var, 0});
6634ba319b5SDimitry Andric   }
6644ba319b5SDimitry Andric 
6654ba319b5SDimitry Andric   // Perform a stable topological sort by doing a DFS.
6664ba319b5SDimitry Andric   while (!WorkList.empty()) {
6674ba319b5SDimitry Andric     auto Item = WorkList.back();
6684ba319b5SDimitry Andric     DbgVariable *Var = Item.getPointer();
6694ba319b5SDimitry Andric     bool visitedAllDependencies = Item.getInt();
6704ba319b5SDimitry Andric     WorkList.pop_back();
6714ba319b5SDimitry Andric 
6724ba319b5SDimitry Andric     // Dependency is in a different lexical scope or a global.
6734ba319b5SDimitry Andric     if (!Var)
6744ba319b5SDimitry Andric       continue;
6754ba319b5SDimitry Andric 
6764ba319b5SDimitry Andric     // Already handled.
6774ba319b5SDimitry Andric     if (Visited.count(Var))
6784ba319b5SDimitry Andric       continue;
6794ba319b5SDimitry Andric 
6804ba319b5SDimitry Andric     // Add to Result if all dependencies are visited.
6814ba319b5SDimitry Andric     if (visitedAllDependencies) {
6824ba319b5SDimitry Andric       Visited.insert(Var);
6834ba319b5SDimitry Andric       Result.push_back(Var);
6844ba319b5SDimitry Andric       continue;
6854ba319b5SDimitry Andric     }
6864ba319b5SDimitry Andric 
6874ba319b5SDimitry Andric     // Detect cycles.
6884ba319b5SDimitry Andric     auto Res = Visiting.insert(Var);
6894ba319b5SDimitry Andric     if (!Res.second) {
6904ba319b5SDimitry Andric       assert(false && "dependency cycle in local variables");
6914ba319b5SDimitry Andric       return Result;
6924ba319b5SDimitry Andric     }
6934ba319b5SDimitry Andric 
6944ba319b5SDimitry Andric     // Push dependencies and this node onto the worklist, so that this node is
6954ba319b5SDimitry Andric     // visited again after all of its dependencies are handled.
6964ba319b5SDimitry Andric     WorkList.push_back({Var, 1});
6974ba319b5SDimitry Andric     for (auto *Dependency : dependencies(Var)) {
6984ba319b5SDimitry Andric       auto Dep = dyn_cast_or_null<const DILocalVariable>(Dependency);
6994ba319b5SDimitry Andric       WorkList.push_back({DbgVar[Dep], 0});
7004ba319b5SDimitry Andric     }
7014ba319b5SDimitry Andric   }
7024ba319b5SDimitry Andric   return Result;
7034ba319b5SDimitry Andric }
7044ba319b5SDimitry Andric 
createScopeChildrenDIE(LexicalScope * Scope,SmallVectorImpl<DIE * > & Children,bool * HasNonScopeChildren)7053dac3a9bSDimitry Andric DIE *DwarfCompileUnit::createScopeChildrenDIE(LexicalScope *Scope,
7063dac3a9bSDimitry Andric                                               SmallVectorImpl<DIE *> &Children,
7072cab237bSDimitry Andric                                               bool *HasNonScopeChildren) {
7082cab237bSDimitry Andric   assert(Children.empty());
70939d628a0SDimitry Andric   DIE *ObjectPointer = nullptr;
71039d628a0SDimitry Andric 
7114ba319b5SDimitry Andric   // Emit function arguments (order is significant).
7124ba319b5SDimitry Andric   auto Vars = DU->getScopeVariables().lookup(Scope);
7134ba319b5SDimitry Andric   for (auto &DV : Vars.Args)
7144ba319b5SDimitry Andric     Children.push_back(constructVariableDIE(*DV.second, *Scope, ObjectPointer));
7154ba319b5SDimitry Andric 
7164ba319b5SDimitry Andric   // Emit local variables.
7174ba319b5SDimitry Andric   auto Locals = sortLocalVars(Vars.Locals);
7184ba319b5SDimitry Andric   for (DbgVariable *DV : Locals)
71939d628a0SDimitry Andric     Children.push_back(constructVariableDIE(*DV, *Scope, ObjectPointer));
72039d628a0SDimitry Andric 
7212cab237bSDimitry Andric   // Skip imported directives in gmlt-like data.
7222cab237bSDimitry Andric   if (!includeMinimalInlineScopes()) {
7232cab237bSDimitry Andric     // There is no need to emit empty lexical block DIE.
7242cab237bSDimitry Andric     for (const auto *IE : ImportedEntities[Scope->getScopeNode()])
7252cab237bSDimitry Andric       Children.push_back(
7262cab237bSDimitry Andric           constructImportedEntityDIE(cast<DIImportedEntity>(IE)));
7272cab237bSDimitry Andric   }
7282cab237bSDimitry Andric 
7292cab237bSDimitry Andric   if (HasNonScopeChildren)
7302cab237bSDimitry Andric     *HasNonScopeChildren = !Children.empty();
73139d628a0SDimitry Andric 
732*b5893f02SDimitry Andric   for (DbgLabel *DL : DU->getScopeLabels().lookup(Scope))
733*b5893f02SDimitry Andric     Children.push_back(constructLabelDIE(*DL, *Scope));
734*b5893f02SDimitry Andric 
73539d628a0SDimitry Andric   for (LexicalScope *LS : Scope->getChildren())
73639d628a0SDimitry Andric     constructScopeDIE(LS, Children);
73739d628a0SDimitry Andric 
73839d628a0SDimitry Andric   return ObjectPointer;
73939d628a0SDimitry Andric }
74039d628a0SDimitry Andric 
constructSubprogramScopeDIE(const DISubprogram * Sub,LexicalScope * Scope)741*b5893f02SDimitry Andric DIE &DwarfCompileUnit::constructSubprogramScopeDIE(const DISubprogram *Sub,
742*b5893f02SDimitry Andric                                                    LexicalScope *Scope) {
74339d628a0SDimitry Andric   DIE &ScopeDIE = updateSubprogramScopeDIE(Sub);
74439d628a0SDimitry Andric 
745d88c1a5aSDimitry Andric   if (Scope) {
746d88c1a5aSDimitry Andric     assert(!Scope->getInlinedAt());
747d88c1a5aSDimitry Andric     assert(!Scope->isAbstractScope());
74839d628a0SDimitry Andric     // Collect lexical scope children first.
74939d628a0SDimitry Andric     // ObjectPointer might be a local (non-argument) local variable if it's a
75039d628a0SDimitry Andric     // block's synthetic this pointer.
75139d628a0SDimitry Andric     if (DIE *ObjectPointer = createAndAddScopeChildren(Scope, ScopeDIE))
75239d628a0SDimitry Andric       addDIEEntry(ScopeDIE, dwarf::DW_AT_object_pointer, *ObjectPointer);
753d88c1a5aSDimitry Andric   }
754d88c1a5aSDimitry Andric 
755d88c1a5aSDimitry Andric   // If this is a variadic function, add an unspecified parameter.
756d88c1a5aSDimitry Andric   DITypeRefArray FnArgs = Sub->getType()->getTypeArray();
75739d628a0SDimitry Andric 
75839d628a0SDimitry Andric   // If we have a single element of null, it is a function that returns void.
75939d628a0SDimitry Andric   // If we have more than one elements and the last one is null, it is a
76039d628a0SDimitry Andric   // variadic function.
761ff0cc061SDimitry Andric   if (FnArgs.size() > 1 && !FnArgs[FnArgs.size() - 1] &&
76239d628a0SDimitry Andric       !includeMinimalInlineScopes())
7633dac3a9bSDimitry Andric     ScopeDIE.addChild(
7643dac3a9bSDimitry Andric         DIE::get(DIEValueAllocator, dwarf::DW_TAG_unspecified_parameters));
765*b5893f02SDimitry Andric 
766*b5893f02SDimitry Andric   return ScopeDIE;
76739d628a0SDimitry Andric }
76839d628a0SDimitry Andric 
createAndAddScopeChildren(LexicalScope * Scope,DIE & ScopeDIE)76939d628a0SDimitry Andric DIE *DwarfCompileUnit::createAndAddScopeChildren(LexicalScope *Scope,
77039d628a0SDimitry Andric                                                  DIE &ScopeDIE) {
77139d628a0SDimitry Andric   // We create children when the scope DIE is not null.
7723dac3a9bSDimitry Andric   SmallVector<DIE *, 8> Children;
77339d628a0SDimitry Andric   DIE *ObjectPointer = createScopeChildrenDIE(Scope, Children);
77439d628a0SDimitry Andric 
77539d628a0SDimitry Andric   // Add children
77639d628a0SDimitry Andric   for (auto &I : Children)
77739d628a0SDimitry Andric     ScopeDIE.addChild(std::move(I));
77839d628a0SDimitry Andric 
77939d628a0SDimitry Andric   return ObjectPointer;
78039d628a0SDimitry Andric }
78139d628a0SDimitry Andric 
constructAbstractSubprogramScopeDIE(LexicalScope * Scope)7827d523365SDimitry Andric void DwarfCompileUnit::constructAbstractSubprogramScopeDIE(
7837d523365SDimitry Andric     LexicalScope *Scope) {
7845517e702SDimitry Andric   DIE *&AbsDef = getAbstractSPDies()[Scope->getScopeNode()];
78539d628a0SDimitry Andric   if (AbsDef)
78639d628a0SDimitry Andric     return;
78739d628a0SDimitry Andric 
788ff0cc061SDimitry Andric   auto *SP = cast<DISubprogram>(Scope->getScopeNode());
78939d628a0SDimitry Andric 
79039d628a0SDimitry Andric   DIE *ContextDIE;
791d4419f6fSDimitry Andric   DwarfCompileUnit *ContextCU = this;
79239d628a0SDimitry Andric 
79339d628a0SDimitry Andric   if (includeMinimalInlineScopes())
79439d628a0SDimitry Andric     ContextDIE = &getUnitDie();
79539d628a0SDimitry Andric   // Some of this is duplicated from DwarfUnit::getOrCreateSubprogramDIE, with
796ff0cc061SDimitry Andric   // the important distinction that the debug node is not associated with the
797ff0cc061SDimitry Andric   // DIE (since the debug node will be associated with the concrete DIE, if
79839d628a0SDimitry Andric   // any). It could be refactored to some common utility function.
799ff0cc061SDimitry Andric   else if (auto *SPDecl = SP->getDeclaration()) {
80039d628a0SDimitry Andric     ContextDIE = &getUnitDie();
80139d628a0SDimitry Andric     getOrCreateSubprogramDIE(SPDecl);
802d4419f6fSDimitry Andric   } else {
803ff0cc061SDimitry Andric     ContextDIE = getOrCreateContextDIE(resolve(SP->getScope()));
804d4419f6fSDimitry Andric     // The scope may be shared with a subprogram that has already been
805d4419f6fSDimitry Andric     // constructed in another CU, in which case we need to construct this
806d4419f6fSDimitry Andric     // subprogram in the same CU.
807d4419f6fSDimitry Andric     ContextCU = DD->lookupCU(ContextDIE->getUnitDie());
808d4419f6fSDimitry Andric   }
80939d628a0SDimitry Andric 
810ff0cc061SDimitry Andric   // Passing null as the associated node because the abstract definition
81139d628a0SDimitry Andric   // shouldn't be found by lookup.
812d4419f6fSDimitry Andric   AbsDef = &ContextCU->createAndAddDIE(dwarf::DW_TAG_subprogram, *ContextDIE, nullptr);
813d4419f6fSDimitry Andric   ContextCU->applySubprogramAttributesToDefinition(SP, *AbsDef);
81439d628a0SDimitry Andric 
815d4419f6fSDimitry Andric   if (!ContextCU->includeMinimalInlineScopes())
816d4419f6fSDimitry Andric     ContextCU->addUInt(*AbsDef, dwarf::DW_AT_inline, None, dwarf::DW_INL_inlined);
817d4419f6fSDimitry Andric   if (DIE *ObjectPointer = ContextCU->createAndAddScopeChildren(Scope, *AbsDef))
818d4419f6fSDimitry Andric     ContextCU->addDIEEntry(*AbsDef, dwarf::DW_AT_object_pointer, *ObjectPointer);
81939d628a0SDimitry Andric }
82039d628a0SDimitry Andric 
constructCallSiteEntryDIE(DIE & ScopeDIE,const DISubprogram & CalleeSP,bool IsTail,const MCExpr * PCOffset)821*b5893f02SDimitry Andric DIE &DwarfCompileUnit::constructCallSiteEntryDIE(DIE &ScopeDIE,
822*b5893f02SDimitry Andric                                                  const DISubprogram &CalleeSP,
823*b5893f02SDimitry Andric                                                  bool IsTail,
824*b5893f02SDimitry Andric                                                  const MCExpr *PCOffset) {
825*b5893f02SDimitry Andric   // Insert a call site entry DIE within ScopeDIE.
826*b5893f02SDimitry Andric   DIE &CallSiteDIE =
827*b5893f02SDimitry Andric       createAndAddDIE(dwarf::DW_TAG_call_site, ScopeDIE, nullptr);
828*b5893f02SDimitry Andric 
829*b5893f02SDimitry Andric   // For the purposes of showing tail call frames in backtraces, a key piece of
830*b5893f02SDimitry Andric   // information is DW_AT_call_origin, a pointer to the callee DIE.
831*b5893f02SDimitry Andric   DIE *CalleeDIE = getOrCreateSubprogramDIE(&CalleeSP);
832*b5893f02SDimitry Andric   assert(CalleeDIE && "Could not create DIE for call site entry origin");
833*b5893f02SDimitry Andric   addDIEEntry(CallSiteDIE, dwarf::DW_AT_call_origin, *CalleeDIE);
834*b5893f02SDimitry Andric 
835*b5893f02SDimitry Andric   if (IsTail) {
836*b5893f02SDimitry Andric     // Attach DW_AT_call_tail_call to tail calls for standards compliance.
837*b5893f02SDimitry Andric     addFlag(CallSiteDIE, dwarf::DW_AT_call_tail_call);
838*b5893f02SDimitry Andric   } else {
839*b5893f02SDimitry Andric     // Attach the return PC to allow the debugger to disambiguate call paths
840*b5893f02SDimitry Andric     // from one function to another.
841*b5893f02SDimitry Andric     assert(PCOffset && "Missing return PC information for a call");
842*b5893f02SDimitry Andric     addAddressExpr(CallSiteDIE, dwarf::DW_AT_call_return_pc, PCOffset);
843*b5893f02SDimitry Andric   }
844*b5893f02SDimitry Andric   return CallSiteDIE;
845*b5893f02SDimitry Andric }
846*b5893f02SDimitry Andric 
constructImportedEntityDIE(const DIImportedEntity * Module)8473dac3a9bSDimitry Andric DIE *DwarfCompileUnit::constructImportedEntityDIE(
8483dac3a9bSDimitry Andric     const DIImportedEntity *Module) {
8493dac3a9bSDimitry Andric   DIE *IMDie = DIE::get(DIEValueAllocator, (dwarf::Tag)Module->getTag());
8503dac3a9bSDimitry Andric   insertDIE(Module, IMDie);
85139d628a0SDimitry Andric   DIE *EntityDie;
852ff0cc061SDimitry Andric   auto *Entity = resolve(Module->getEntity());
853ff0cc061SDimitry Andric   if (auto *NS = dyn_cast<DINamespace>(Entity))
854ff0cc061SDimitry Andric     EntityDie = getOrCreateNameSpace(NS);
8553dac3a9bSDimitry Andric   else if (auto *M = dyn_cast<DIModule>(Entity))
8563dac3a9bSDimitry Andric     EntityDie = getOrCreateModule(M);
857ff0cc061SDimitry Andric   else if (auto *SP = dyn_cast<DISubprogram>(Entity))
858ff0cc061SDimitry Andric     EntityDie = getOrCreateSubprogramDIE(SP);
859ff0cc061SDimitry Andric   else if (auto *T = dyn_cast<DIType>(Entity))
860ff0cc061SDimitry Andric     EntityDie = getOrCreateTypeDIE(T);
861ff0cc061SDimitry Andric   else if (auto *GV = dyn_cast<DIGlobalVariable>(Entity))
862d88c1a5aSDimitry Andric     EntityDie = getOrCreateGlobalVariableDIE(GV, {});
86339d628a0SDimitry Andric   else
86439d628a0SDimitry Andric     EntityDie = getDIE(Entity);
86539d628a0SDimitry Andric   assert(EntityDie);
8664ba319b5SDimitry Andric   addSourceLine(*IMDie, Module->getLine(), Module->getFile());
86739d628a0SDimitry Andric   addDIEEntry(*IMDie, dwarf::DW_AT_import, *EntityDie);
868ff0cc061SDimitry Andric   StringRef Name = Module->getName();
86939d628a0SDimitry Andric   if (!Name.empty())
87039d628a0SDimitry Andric     addString(*IMDie, dwarf::DW_AT_name, Name);
87139d628a0SDimitry Andric 
87239d628a0SDimitry Andric   return IMDie;
87339d628a0SDimitry Andric }
87439d628a0SDimitry Andric 
finishSubprogramDefinition(const DISubprogram * SP)875ff0cc061SDimitry Andric void DwarfCompileUnit::finishSubprogramDefinition(const DISubprogram *SP) {
87639d628a0SDimitry Andric   DIE *D = getDIE(SP);
8775517e702SDimitry Andric   if (DIE *AbsSPDIE = getAbstractSPDies().lookup(SP)) {
87839d628a0SDimitry Andric     if (D)
87939d628a0SDimitry Andric       // If this subprogram has an abstract definition, reference that
88039d628a0SDimitry Andric       addDIEEntry(*D, dwarf::DW_AT_abstract_origin, *AbsSPDIE);
88139d628a0SDimitry Andric   } else {
882d88c1a5aSDimitry Andric     assert(D || includeMinimalInlineScopes());
88339d628a0SDimitry Andric     if (D)
88439d628a0SDimitry Andric       // And attach the attributes
88539d628a0SDimitry Andric       applySubprogramAttributesToDefinition(SP, *D);
88639d628a0SDimitry Andric   }
88739d628a0SDimitry Andric }
88839d628a0SDimitry Andric 
finishEntityDefinition(const DbgEntity * Entity)889*b5893f02SDimitry Andric void DwarfCompileUnit::finishEntityDefinition(const DbgEntity *Entity) {
890*b5893f02SDimitry Andric   DbgEntity *AbsEntity = getExistingAbstractEntity(Entity->getEntity());
891*b5893f02SDimitry Andric 
892*b5893f02SDimitry Andric   auto *Die = Entity->getDIE();
893*b5893f02SDimitry Andric   /// Label may be used to generate DW_AT_low_pc, so put it outside
894*b5893f02SDimitry Andric   /// if/else block.
895*b5893f02SDimitry Andric   const DbgLabel *Label = nullptr;
896*b5893f02SDimitry Andric   if (AbsEntity && AbsEntity->getDIE()) {
897*b5893f02SDimitry Andric     addDIEEntry(*Die, dwarf::DW_AT_abstract_origin, *AbsEntity->getDIE());
898*b5893f02SDimitry Andric     Label = dyn_cast<const DbgLabel>(Entity);
899*b5893f02SDimitry Andric   } else {
900*b5893f02SDimitry Andric     if (const DbgVariable *Var = dyn_cast<const DbgVariable>(Entity))
901*b5893f02SDimitry Andric       applyVariableAttributes(*Var, *Die);
902*b5893f02SDimitry Andric     else if ((Label = dyn_cast<const DbgLabel>(Entity)))
903*b5893f02SDimitry Andric       applyLabelAttributes(*Label, *Die);
904*b5893f02SDimitry Andric     else
905*b5893f02SDimitry Andric       llvm_unreachable("DbgEntity must be DbgVariable or DbgLabel.");
9065517e702SDimitry Andric   }
9075517e702SDimitry Andric 
908*b5893f02SDimitry Andric   if (Label)
909*b5893f02SDimitry Andric     if (const auto *Sym = Label->getSymbol())
910*b5893f02SDimitry Andric       addLabelAddress(*Die, dwarf::DW_AT_low_pc, Sym);
9115517e702SDimitry Andric }
9125517e702SDimitry Andric 
getExistingAbstractEntity(const DINode * Node)913*b5893f02SDimitry Andric DbgEntity *DwarfCompileUnit::getExistingAbstractEntity(const DINode *Node) {
914*b5893f02SDimitry Andric   auto &AbstractEntities = getAbstractEntities();
915*b5893f02SDimitry Andric   auto I = AbstractEntities.find(Node);
916*b5893f02SDimitry Andric   if (I != AbstractEntities.end())
9175517e702SDimitry Andric     return I->second.get();
9185517e702SDimitry Andric   return nullptr;
9195517e702SDimitry Andric }
9205517e702SDimitry Andric 
createAbstractEntity(const DINode * Node,LexicalScope * Scope)921*b5893f02SDimitry Andric void DwarfCompileUnit::createAbstractEntity(const DINode *Node,
9225517e702SDimitry Andric                                             LexicalScope *Scope) {
9235517e702SDimitry Andric   assert(Scope && Scope->isAbstractScope());
924*b5893f02SDimitry Andric   auto &Entity = getAbstractEntities()[Node];
925*b5893f02SDimitry Andric   if (isa<const DILocalVariable>(Node)) {
926*b5893f02SDimitry Andric     Entity = llvm::make_unique<DbgVariable>(
927*b5893f02SDimitry Andric                         cast<const DILocalVariable>(Node), nullptr /* IA */);;
928*b5893f02SDimitry Andric     DU->addScopeVariable(Scope, cast<DbgVariable>(Entity.get()));
929*b5893f02SDimitry Andric   } else if (isa<const DILabel>(Node)) {
930*b5893f02SDimitry Andric     Entity = llvm::make_unique<DbgLabel>(
931*b5893f02SDimitry Andric                         cast<const DILabel>(Node), nullptr /* IA */);
932*b5893f02SDimitry Andric     DU->addScopeLabel(Scope, cast<DbgLabel>(Entity.get()));
933*b5893f02SDimitry Andric   }
9345517e702SDimitry Andric }
9355517e702SDimitry Andric 
emitHeader(bool UseOffsets)936ff0cc061SDimitry Andric void DwarfCompileUnit::emitHeader(bool UseOffsets) {
93739d628a0SDimitry Andric   // Don't bother labeling the .dwo unit, as its offset isn't used.
9384ba319b5SDimitry Andric   if (!Skeleton && !DD->useSectionsAsReferences()) {
939ff0cc061SDimitry Andric     LabelBegin = Asm->createTempSymbol("cu_begin");
940ff0cc061SDimitry Andric     Asm->OutStreamer->EmitLabel(LabelBegin);
941ff0cc061SDimitry Andric   }
94239d628a0SDimitry Andric 
9437a7e6055SDimitry Andric   dwarf::UnitType UT = Skeleton ? dwarf::DW_UT_split_compile
9447a7e6055SDimitry Andric                                 : DD->useSplitDwarf() ? dwarf::DW_UT_skeleton
9457a7e6055SDimitry Andric                                                       : dwarf::DW_UT_compile;
9467a7e6055SDimitry Andric   DwarfUnit::emitCommonHeader(UseOffsets, UT);
9474ba319b5SDimitry Andric   if (DD->getDwarfVersion() >= 5 && UT != dwarf::DW_UT_compile)
9484ba319b5SDimitry Andric     Asm->emitInt64(getDWOId());
94939d628a0SDimitry Andric }
95039d628a0SDimitry Andric 
hasDwarfPubSections() const9512cab237bSDimitry Andric bool DwarfCompileUnit::hasDwarfPubSections() const {
952*b5893f02SDimitry Andric   switch (CUNode->getNameTableKind()) {
953*b5893f02SDimitry Andric   case DICompileUnit::DebugNameTableKind::None:
954*b5893f02SDimitry Andric     return false;
9552cab237bSDimitry Andric     // Opting in to GNU Pubnames/types overrides the default to ensure these are
9562cab237bSDimitry Andric     // generated for things like Gold's gdb_index generation.
957*b5893f02SDimitry Andric   case DICompileUnit::DebugNameTableKind::GNU:
9582cab237bSDimitry Andric     return true;
959*b5893f02SDimitry Andric   case DICompileUnit::DebugNameTableKind::Default:
960*b5893f02SDimitry Andric     return DD->tuneForGDB() && !includeMinimalInlineScopes() &&
961*b5893f02SDimitry Andric            !CUNode->isDebugDirectivesOnly();
962*b5893f02SDimitry Andric   }
963*b5893f02SDimitry Andric   llvm_unreachable("Unhandled DICompileUnit::DebugNameTableKind enum");
9642cab237bSDimitry Andric }
9652cab237bSDimitry Andric 
96639d628a0SDimitry Andric /// addGlobalName - Add a new global name to the compile unit.
addGlobalName(StringRef Name,const DIE & Die,const DIScope * Context)9677a7e6055SDimitry Andric void DwarfCompileUnit::addGlobalName(StringRef Name, const DIE &Die,
968ff0cc061SDimitry Andric                                      const DIScope *Context) {
9692cab237bSDimitry Andric   if (!hasDwarfPubSections())
97039d628a0SDimitry Andric     return;
97139d628a0SDimitry Andric   std::string FullName = getParentContextString(Context) + Name.str();
97239d628a0SDimitry Andric   GlobalNames[FullName] = &Die;
97339d628a0SDimitry Andric }
97439d628a0SDimitry Andric 
addGlobalNameForTypeUnit(StringRef Name,const DIScope * Context)9757a7e6055SDimitry Andric void DwarfCompileUnit::addGlobalNameForTypeUnit(StringRef Name,
9767a7e6055SDimitry Andric                                                 const DIScope *Context) {
9772cab237bSDimitry Andric   if (!hasDwarfPubSections())
9787a7e6055SDimitry Andric     return;
9797a7e6055SDimitry Andric   std::string FullName = getParentContextString(Context) + Name.str();
9807a7e6055SDimitry Andric   // Insert, allowing the entry to remain as-is if it's already present
9817a7e6055SDimitry Andric   // This way the CU-level type DIE is preferred over the "can't describe this
9827a7e6055SDimitry Andric   // type as a unit offset because it's not really in the CU at all, it's only
9837a7e6055SDimitry Andric   // in a type unit"
9847a7e6055SDimitry Andric   GlobalNames.insert(std::make_pair(std::move(FullName), &getUnitDie()));
9857a7e6055SDimitry Andric }
9867a7e6055SDimitry Andric 
98739d628a0SDimitry Andric /// Add a new global type to the unit.
addGlobalType(const DIType * Ty,const DIE & Die,const DIScope * Context)988ff0cc061SDimitry Andric void DwarfCompileUnit::addGlobalType(const DIType *Ty, const DIE &Die,
989ff0cc061SDimitry Andric                                      const DIScope *Context) {
9902cab237bSDimitry Andric   if (!hasDwarfPubSections())
99139d628a0SDimitry Andric     return;
992ff0cc061SDimitry Andric   std::string FullName = getParentContextString(Context) + Ty->getName().str();
99339d628a0SDimitry Andric   GlobalTypes[FullName] = &Die;
99439d628a0SDimitry Andric }
99539d628a0SDimitry Andric 
addGlobalTypeUnitType(const DIType * Ty,const DIScope * Context)9967a7e6055SDimitry Andric void DwarfCompileUnit::addGlobalTypeUnitType(const DIType *Ty,
9977a7e6055SDimitry Andric                                              const DIScope *Context) {
9982cab237bSDimitry Andric   if (!hasDwarfPubSections())
9997a7e6055SDimitry Andric     return;
10007a7e6055SDimitry Andric   std::string FullName = getParentContextString(Context) + Ty->getName().str();
10017a7e6055SDimitry Andric   // Insert, allowing the entry to remain as-is if it's already present
10027a7e6055SDimitry Andric   // This way the CU-level type DIE is preferred over the "can't describe this
10037a7e6055SDimitry Andric   // type as a unit offset because it's not really in the CU at all, it's only
10047a7e6055SDimitry Andric   // in a type unit"
10057a7e6055SDimitry Andric   GlobalTypes.insert(std::make_pair(std::move(FullName), &getUnitDie()));
10067a7e6055SDimitry Andric }
10077a7e6055SDimitry Andric 
100839d628a0SDimitry Andric /// addVariableAddress - Add DW_AT_location attribute for a
100939d628a0SDimitry Andric /// DbgVariable based on provided MachineLocation.
addVariableAddress(const DbgVariable & DV,DIE & Die,MachineLocation Location)101039d628a0SDimitry Andric void DwarfCompileUnit::addVariableAddress(const DbgVariable &DV, DIE &Die,
101139d628a0SDimitry Andric                                           MachineLocation Location) {
10122cab237bSDimitry Andric   // addBlockByrefAddress is obsolete and will be removed soon.
10132cab237bSDimitry Andric   // The clang frontend always generates block byref variables with a
10142cab237bSDimitry Andric   // complex expression that encodes exactly what addBlockByrefAddress
10152cab237bSDimitry Andric   // would do.
10162cab237bSDimitry Andric   assert((!DV.isBlockByrefVariable() || DV.hasComplexAddress()) &&
10172cab237bSDimitry Andric          "block byref variable without a complex expression");
10183dac3a9bSDimitry Andric   if (DV.hasComplexAddress())
101939d628a0SDimitry Andric     addComplexAddress(DV, Die, dwarf::DW_AT_location, Location);
102039d628a0SDimitry Andric   else
1021ff0cc061SDimitry Andric     addAddress(Die, dwarf::DW_AT_location, Location);
102239d628a0SDimitry Andric }
102339d628a0SDimitry Andric 
102439d628a0SDimitry Andric /// Add an address attribute to a die based on the location provided.
addAddress(DIE & Die,dwarf::Attribute Attribute,const MachineLocation & Location)102539d628a0SDimitry Andric void DwarfCompileUnit::addAddress(DIE &Die, dwarf::Attribute Attribute,
1026ff0cc061SDimitry Andric                                   const MachineLocation &Location) {
102797bc6c73SDimitry Andric   DIELoc *Loc = new (DIEValueAllocator) DIELoc;
10287a7e6055SDimitry Andric   DIEDwarfExpression DwarfExpr(*Asm, *this, *Loc);
10296bc11b14SDimitry Andric   if (Location.isIndirect())
10306bc11b14SDimitry Andric     DwarfExpr.setMemoryLocationKind();
103139d628a0SDimitry Andric 
10322cab237bSDimitry Andric   DIExpressionCursor Cursor({});
10337a7e6055SDimitry Andric   const TargetRegisterInfo &TRI = *Asm->MF->getSubtarget().getRegisterInfo();
10347a7e6055SDimitry Andric   if (!DwarfExpr.addMachineRegExpression(TRI, Cursor, Location.getReg()))
103539d628a0SDimitry Andric     return;
10367a7e6055SDimitry Andric   DwarfExpr.addExpression(std::move(Cursor));
103739d628a0SDimitry Andric 
103839d628a0SDimitry Andric   // Now attach the location information to the DIE.
10397a7e6055SDimitry Andric   addBlock(Die, Attribute, DwarfExpr.finalize());
104039d628a0SDimitry Andric }
104139d628a0SDimitry Andric 
104239d628a0SDimitry Andric /// Start with the address based on the location provided, and generate the
104339d628a0SDimitry Andric /// DWARF information necessary to find the actual variable given the extra
104439d628a0SDimitry Andric /// address information encoded in the DbgVariable, starting from the starting
104539d628a0SDimitry Andric /// location.  Add the DWARF information to the die.
addComplexAddress(const DbgVariable & DV,DIE & Die,dwarf::Attribute Attribute,const MachineLocation & Location)104639d628a0SDimitry Andric void DwarfCompileUnit::addComplexAddress(const DbgVariable &DV, DIE &Die,
104739d628a0SDimitry Andric                                          dwarf::Attribute Attribute,
104839d628a0SDimitry Andric                                          const MachineLocation &Location) {
104997bc6c73SDimitry Andric   DIELoc *Loc = new (DIEValueAllocator) DIELoc;
105039d628a0SDimitry Andric   DIEDwarfExpression DwarfExpr(*Asm, *this, *Loc);
10517a7e6055SDimitry Andric   const DIExpression *DIExpr = DV.getSingleExpression();
10527a7e6055SDimitry Andric   DwarfExpr.addFragmentOffset(DIExpr);
10536bc11b14SDimitry Andric   if (Location.isIndirect())
10546bc11b14SDimitry Andric     DwarfExpr.setMemoryLocationKind();
10557a7e6055SDimitry Andric 
10562cab237bSDimitry Andric   DIExpressionCursor Cursor(DIExpr);
10573ca95b02SDimitry Andric   const TargetRegisterInfo &TRI = *Asm->MF->getSubtarget().getRegisterInfo();
10587a7e6055SDimitry Andric   if (!DwarfExpr.addMachineRegExpression(TRI, Cursor, Location.getReg()))
1059d88c1a5aSDimitry Andric     return;
10607a7e6055SDimitry Andric   DwarfExpr.addExpression(std::move(Cursor));
106139d628a0SDimitry Andric 
106239d628a0SDimitry Andric   // Now attach the location information to the DIE.
10637a7e6055SDimitry Andric   addBlock(Die, Attribute, DwarfExpr.finalize());
106439d628a0SDimitry Andric }
106539d628a0SDimitry Andric 
106639d628a0SDimitry Andric /// Add a Dwarf loclistptr attribute data and value.
addLocationList(DIE & Die,dwarf::Attribute Attribute,unsigned Index)106739d628a0SDimitry Andric void DwarfCompileUnit::addLocationList(DIE &Die, dwarf::Attribute Attribute,
106839d628a0SDimitry Andric                                        unsigned Index) {
106939d628a0SDimitry Andric   dwarf::Form Form = DD->getDwarfVersion() >= 4 ? dwarf::DW_FORM_sec_offset
107039d628a0SDimitry Andric                                                 : dwarf::DW_FORM_data4;
10713dac3a9bSDimitry Andric   Die.addValue(DIEValueAllocator, Attribute, Form, DIELocList(Index));
107239d628a0SDimitry Andric }
107339d628a0SDimitry Andric 
applyVariableAttributes(const DbgVariable & Var,DIE & VariableDie)107439d628a0SDimitry Andric void DwarfCompileUnit::applyVariableAttributes(const DbgVariable &Var,
107539d628a0SDimitry Andric                                                DIE &VariableDie) {
107639d628a0SDimitry Andric   StringRef Name = Var.getName();
107739d628a0SDimitry Andric   if (!Name.empty())
107839d628a0SDimitry Andric     addString(VariableDie, dwarf::DW_AT_name, Name);
1079d88c1a5aSDimitry Andric   const auto *DIVar = Var.getVariable();
1080d88c1a5aSDimitry Andric   if (DIVar)
1081d88c1a5aSDimitry Andric     if (uint32_t AlignInBytes = DIVar->getAlignInBytes())
1082d88c1a5aSDimitry Andric       addUInt(VariableDie, dwarf::DW_AT_alignment, dwarf::DW_FORM_udata,
1083d88c1a5aSDimitry Andric               AlignInBytes);
1084d88c1a5aSDimitry Andric 
1085d88c1a5aSDimitry Andric   addSourceLine(VariableDie, DIVar);
108639d628a0SDimitry Andric   addType(VariableDie, Var.getType());
108739d628a0SDimitry Andric   if (Var.isArtificial())
108839d628a0SDimitry Andric     addFlag(VariableDie, dwarf::DW_AT_artificial);
108939d628a0SDimitry Andric }
109039d628a0SDimitry Andric 
applyLabelAttributes(const DbgLabel & Label,DIE & LabelDie)1091*b5893f02SDimitry Andric void DwarfCompileUnit::applyLabelAttributes(const DbgLabel &Label,
1092*b5893f02SDimitry Andric                                             DIE &LabelDie) {
1093*b5893f02SDimitry Andric   StringRef Name = Label.getName();
1094*b5893f02SDimitry Andric   if (!Name.empty())
1095*b5893f02SDimitry Andric     addString(LabelDie, dwarf::DW_AT_name, Name);
1096*b5893f02SDimitry Andric   const auto *DILabel = Label.getLabel();
1097*b5893f02SDimitry Andric   addSourceLine(LabelDie, DILabel);
1098*b5893f02SDimitry Andric }
1099*b5893f02SDimitry Andric 
110039d628a0SDimitry Andric /// Add a Dwarf expression attribute data and value.
addExpr(DIELoc & Die,dwarf::Form Form,const MCExpr * Expr)110139d628a0SDimitry Andric void DwarfCompileUnit::addExpr(DIELoc &Die, dwarf::Form Form,
110239d628a0SDimitry Andric                                const MCExpr *Expr) {
11033dac3a9bSDimitry Andric   Die.addValue(DIEValueAllocator, (dwarf::Attribute)0, Form, DIEExpr(Expr));
110439d628a0SDimitry Andric }
110539d628a0SDimitry Andric 
addAddressExpr(DIE & Die,dwarf::Attribute Attribute,const MCExpr * Expr)1106*b5893f02SDimitry Andric void DwarfCompileUnit::addAddressExpr(DIE &Die, dwarf::Attribute Attribute,
1107*b5893f02SDimitry Andric                                       const MCExpr *Expr) {
1108*b5893f02SDimitry Andric   Die.addValue(DIEValueAllocator, Attribute, dwarf::DW_FORM_addr,
1109*b5893f02SDimitry Andric                DIEExpr(Expr));
1110*b5893f02SDimitry Andric }
1111*b5893f02SDimitry Andric 
applySubprogramAttributesToDefinition(const DISubprogram * SP,DIE & SPDie)1112ff0cc061SDimitry Andric void DwarfCompileUnit::applySubprogramAttributesToDefinition(
1113ff0cc061SDimitry Andric     const DISubprogram *SP, DIE &SPDie) {
1114ff0cc061SDimitry Andric   auto *SPDecl = SP->getDeclaration();
1115ff0cc061SDimitry Andric   auto *Context = resolve(SPDecl ? SPDecl->getScope() : SP->getScope());
111639d628a0SDimitry Andric   applySubprogramAttributes(SP, SPDie, includeMinimalInlineScopes());
1117ff0cc061SDimitry Andric   addGlobalName(SP->getName(), SPDie, Context);
111839d628a0SDimitry Andric }
111939d628a0SDimitry Andric 
isDwoUnit() const112039d628a0SDimitry Andric bool DwarfCompileUnit::isDwoUnit() const {
112139d628a0SDimitry Andric   return DD->useSplitDwarf() && Skeleton;
112239d628a0SDimitry Andric }
112339d628a0SDimitry Andric 
includeMinimalInlineScopes() const112439d628a0SDimitry Andric bool DwarfCompileUnit::includeMinimalInlineScopes() const {
11253ca95b02SDimitry Andric   return getCUNode()->getEmissionKind() == DICompileUnit::LineTablesOnly ||
112639d628a0SDimitry Andric          (DD->useSplitDwarf() && !Skeleton);
112739d628a0SDimitry Andric }
1128*b5893f02SDimitry Andric 
addAddrTableBase()1129*b5893f02SDimitry Andric void DwarfCompileUnit::addAddrTableBase() {
1130*b5893f02SDimitry Andric   const TargetLoweringObjectFile &TLOF = Asm->getObjFileLowering();
1131*b5893f02SDimitry Andric   MCSymbol *Label = DD->getAddressPool().getLabel();
1132*b5893f02SDimitry Andric   addSectionLabel(getUnitDie(),
1133*b5893f02SDimitry Andric                   getDwarfVersion() >= 5 ? dwarf::DW_AT_addr_base
1134*b5893f02SDimitry Andric                                          : dwarf::DW_AT_GNU_addr_base,
1135*b5893f02SDimitry Andric                   Label, TLOF.getDwarfAddrSection()->getBeginSymbol());
1136*b5893f02SDimitry Andric }
1137