xref: /freebsd-src/contrib/llvm-project/llvm/lib/CodeGen/AsmPrinter/DwarfUnit.cpp (revision 0fca6ea1d4eea4c934cfff25ac9ee8ad6fe95583)
10b57cec5SDimitry Andric //===-- llvm/CodeGen/DwarfUnit.cpp - Dwarf Type and 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 "DwarfUnit.h"
140b57cec5SDimitry Andric #include "AddressPool.h"
150b57cec5SDimitry Andric #include "DwarfCompileUnit.h"
160b57cec5SDimitry Andric #include "DwarfExpression.h"
170b57cec5SDimitry Andric #include "llvm/ADT/APFloat.h"
180b57cec5SDimitry Andric #include "llvm/ADT/APInt.h"
190b57cec5SDimitry Andric #include "llvm/CodeGen/TargetRegisterInfo.h"
200b57cec5SDimitry Andric #include "llvm/IR/Constants.h"
210b57cec5SDimitry Andric #include "llvm/IR/DataLayout.h"
220b57cec5SDimitry Andric #include "llvm/IR/GlobalValue.h"
230b57cec5SDimitry Andric #include "llvm/IR/Metadata.h"
240b57cec5SDimitry Andric #include "llvm/MC/MCAsmInfo.h"
250b57cec5SDimitry Andric #include "llvm/MC/MCContext.h"
260b57cec5SDimitry Andric #include "llvm/MC/MCDwarf.h"
270b57cec5SDimitry Andric #include "llvm/MC/MCSection.h"
280b57cec5SDimitry Andric #include "llvm/MC/MCStreamer.h"
290b57cec5SDimitry Andric #include "llvm/Support/Casting.h"
300b57cec5SDimitry Andric #include "llvm/Target/TargetLoweringObjectFile.h"
310b57cec5SDimitry Andric #include <cassert>
320b57cec5SDimitry Andric #include <cstdint>
33*0fca6ea1SDimitry Andric #include <limits>
340b57cec5SDimitry Andric #include <string>
350b57cec5SDimitry Andric #include <utility>
360b57cec5SDimitry Andric 
370b57cec5SDimitry Andric using namespace llvm;
380b57cec5SDimitry Andric 
390b57cec5SDimitry Andric #define DEBUG_TYPE "dwarfdebug"
400b57cec5SDimitry Andric 
410b57cec5SDimitry Andric DIEDwarfExpression::DIEDwarfExpression(const AsmPrinter &AP,
428bcb0991SDimitry Andric                                        DwarfCompileUnit &CU, DIELoc &DIE)
438bcb0991SDimitry Andric     : DwarfExpression(AP.getDwarfVersion(), CU), AP(AP), OutDIE(DIE) {}
440b57cec5SDimitry Andric 
450b57cec5SDimitry Andric void DIEDwarfExpression::emitOp(uint8_t Op, const char* Comment) {
468bcb0991SDimitry Andric   CU.addUInt(getActiveDIE(), dwarf::DW_FORM_data1, Op);
470b57cec5SDimitry Andric }
480b57cec5SDimitry Andric 
490b57cec5SDimitry Andric void DIEDwarfExpression::emitSigned(int64_t Value) {
508bcb0991SDimitry Andric   CU.addSInt(getActiveDIE(), dwarf::DW_FORM_sdata, Value);
510b57cec5SDimitry Andric }
520b57cec5SDimitry Andric 
530b57cec5SDimitry Andric void DIEDwarfExpression::emitUnsigned(uint64_t Value) {
548bcb0991SDimitry Andric   CU.addUInt(getActiveDIE(), dwarf::DW_FORM_udata, Value);
550b57cec5SDimitry Andric }
560b57cec5SDimitry Andric 
570b57cec5SDimitry Andric void DIEDwarfExpression::emitData1(uint8_t Value) {
588bcb0991SDimitry Andric   CU.addUInt(getActiveDIE(), dwarf::DW_FORM_data1, Value);
590b57cec5SDimitry Andric }
600b57cec5SDimitry Andric 
610b57cec5SDimitry Andric void DIEDwarfExpression::emitBaseTypeRef(uint64_t Idx) {
628bcb0991SDimitry Andric   CU.addBaseTypeRef(getActiveDIE(), Idx);
630b57cec5SDimitry Andric }
640b57cec5SDimitry Andric 
658bcb0991SDimitry Andric void DIEDwarfExpression::enableTemporaryBuffer() {
668bcb0991SDimitry Andric   assert(!IsBuffering && "Already buffering?");
678bcb0991SDimitry Andric   IsBuffering = true;
688bcb0991SDimitry Andric }
698bcb0991SDimitry Andric 
708bcb0991SDimitry Andric void DIEDwarfExpression::disableTemporaryBuffer() { IsBuffering = false; }
718bcb0991SDimitry Andric 
728bcb0991SDimitry Andric unsigned DIEDwarfExpression::getTemporaryBufferSize() {
7304eeddc0SDimitry Andric   return TmpDIE.computeSize(AP.getDwarfFormParams());
748bcb0991SDimitry Andric }
758bcb0991SDimitry Andric 
768bcb0991SDimitry Andric void DIEDwarfExpression::commitTemporaryBuffer() { OutDIE.takeValues(TmpDIE); }
778bcb0991SDimitry Andric 
780b57cec5SDimitry Andric bool DIEDwarfExpression::isFrameRegister(const TargetRegisterInfo &TRI,
79e8d8bef9SDimitry Andric                                          llvm::Register MachineReg) {
800b57cec5SDimitry Andric   return MachineReg == TRI.getFrameRegister(*AP.MF);
810b57cec5SDimitry Andric }
820b57cec5SDimitry Andric 
830b57cec5SDimitry Andric DwarfUnit::DwarfUnit(dwarf::Tag UnitTag, const DICompileUnit *Node,
845f757f3fSDimitry Andric                      AsmPrinter *A, DwarfDebug *DW, DwarfFile *DWU,
855f757f3fSDimitry Andric                      unsigned UniqueID)
865f757f3fSDimitry Andric     : DIEUnit(UnitTag), UniqueID(UniqueID), CUNode(Node), Asm(A), DD(DW),
875f757f3fSDimitry Andric       DU(DWU) {}
880b57cec5SDimitry Andric 
890b57cec5SDimitry Andric DwarfTypeUnit::DwarfTypeUnit(DwarfCompileUnit &CU, AsmPrinter *A,
905f757f3fSDimitry Andric                              DwarfDebug *DW, DwarfFile *DWU, unsigned UniqueID,
910b57cec5SDimitry Andric                              MCDwarfDwoLineTable *SplitLineTable)
925f757f3fSDimitry Andric     : DwarfUnit(dwarf::DW_TAG_type_unit, CU.getCUNode(), A, DW, DWU, UniqueID),
935f757f3fSDimitry Andric       CU(CU), SplitLineTable(SplitLineTable) {}
940b57cec5SDimitry Andric 
950b57cec5SDimitry Andric DwarfUnit::~DwarfUnit() {
96fe6060f1SDimitry Andric   for (DIEBlock *B : DIEBlocks)
97fe6060f1SDimitry Andric     B->~DIEBlock();
98fe6060f1SDimitry Andric   for (DIELoc *L : DIELocs)
99fe6060f1SDimitry Andric     L->~DIELoc();
1000b57cec5SDimitry Andric }
1010b57cec5SDimitry Andric 
1020b57cec5SDimitry Andric int64_t DwarfUnit::getDefaultLowerBound() const {
1030b57cec5SDimitry Andric   switch (getLanguage()) {
1040b57cec5SDimitry Andric   default:
1050b57cec5SDimitry Andric     break;
1060b57cec5SDimitry Andric 
1070b57cec5SDimitry Andric   // The languages below have valid values in all DWARF versions.
1080b57cec5SDimitry Andric   case dwarf::DW_LANG_C:
1090b57cec5SDimitry Andric   case dwarf::DW_LANG_C89:
1100b57cec5SDimitry Andric   case dwarf::DW_LANG_C_plus_plus:
1110b57cec5SDimitry Andric     return 0;
1120b57cec5SDimitry Andric 
1130b57cec5SDimitry Andric   case dwarf::DW_LANG_Fortran77:
1140b57cec5SDimitry Andric   case dwarf::DW_LANG_Fortran90:
1150b57cec5SDimitry Andric     return 1;
1160b57cec5SDimitry Andric 
1170b57cec5SDimitry Andric   // The languages below have valid values only if the DWARF version >= 3.
1180b57cec5SDimitry Andric   case dwarf::DW_LANG_C99:
1190b57cec5SDimitry Andric   case dwarf::DW_LANG_ObjC:
1200b57cec5SDimitry Andric   case dwarf::DW_LANG_ObjC_plus_plus:
1210b57cec5SDimitry Andric     if (DD->getDwarfVersion() >= 3)
1220b57cec5SDimitry Andric       return 0;
1230b57cec5SDimitry Andric     break;
1240b57cec5SDimitry Andric 
1250b57cec5SDimitry Andric   case dwarf::DW_LANG_Fortran95:
1260b57cec5SDimitry Andric     if (DD->getDwarfVersion() >= 3)
1270b57cec5SDimitry Andric       return 1;
1280b57cec5SDimitry Andric     break;
1290b57cec5SDimitry Andric 
1300b57cec5SDimitry Andric   // Starting with DWARF v4, all defined languages have valid values.
1310b57cec5SDimitry Andric   case dwarf::DW_LANG_D:
1320b57cec5SDimitry Andric   case dwarf::DW_LANG_Java:
1330b57cec5SDimitry Andric   case dwarf::DW_LANG_Python:
1340b57cec5SDimitry Andric   case dwarf::DW_LANG_UPC:
1350b57cec5SDimitry Andric     if (DD->getDwarfVersion() >= 4)
1360b57cec5SDimitry Andric       return 0;
1370b57cec5SDimitry Andric     break;
1380b57cec5SDimitry Andric 
1390b57cec5SDimitry Andric   case dwarf::DW_LANG_Ada83:
1400b57cec5SDimitry Andric   case dwarf::DW_LANG_Ada95:
1410b57cec5SDimitry Andric   case dwarf::DW_LANG_Cobol74:
1420b57cec5SDimitry Andric   case dwarf::DW_LANG_Cobol85:
1430b57cec5SDimitry Andric   case dwarf::DW_LANG_Modula2:
1440b57cec5SDimitry Andric   case dwarf::DW_LANG_Pascal83:
1450b57cec5SDimitry Andric   case dwarf::DW_LANG_PLI:
1460b57cec5SDimitry Andric     if (DD->getDwarfVersion() >= 4)
1470b57cec5SDimitry Andric       return 1;
1480b57cec5SDimitry Andric     break;
1490b57cec5SDimitry Andric 
1500b57cec5SDimitry Andric   // The languages below are new in DWARF v5.
1510b57cec5SDimitry Andric   case dwarf::DW_LANG_BLISS:
1520b57cec5SDimitry Andric   case dwarf::DW_LANG_C11:
1530b57cec5SDimitry Andric   case dwarf::DW_LANG_C_plus_plus_03:
1540b57cec5SDimitry Andric   case dwarf::DW_LANG_C_plus_plus_11:
1550b57cec5SDimitry Andric   case dwarf::DW_LANG_C_plus_plus_14:
1560b57cec5SDimitry Andric   case dwarf::DW_LANG_Dylan:
1570b57cec5SDimitry Andric   case dwarf::DW_LANG_Go:
1580b57cec5SDimitry Andric   case dwarf::DW_LANG_Haskell:
1590b57cec5SDimitry Andric   case dwarf::DW_LANG_OCaml:
1600b57cec5SDimitry Andric   case dwarf::DW_LANG_OpenCL:
1610b57cec5SDimitry Andric   case dwarf::DW_LANG_RenderScript:
1620b57cec5SDimitry Andric   case dwarf::DW_LANG_Rust:
1630b57cec5SDimitry Andric   case dwarf::DW_LANG_Swift:
1640b57cec5SDimitry Andric     if (DD->getDwarfVersion() >= 5)
1650b57cec5SDimitry Andric       return 0;
1660b57cec5SDimitry Andric     break;
1670b57cec5SDimitry Andric 
1680b57cec5SDimitry Andric   case dwarf::DW_LANG_Fortran03:
1690b57cec5SDimitry Andric   case dwarf::DW_LANG_Fortran08:
1700b57cec5SDimitry Andric   case dwarf::DW_LANG_Julia:
1710b57cec5SDimitry Andric   case dwarf::DW_LANG_Modula3:
1720b57cec5SDimitry Andric     if (DD->getDwarfVersion() >= 5)
1730b57cec5SDimitry Andric       return 1;
1740b57cec5SDimitry Andric     break;
1750b57cec5SDimitry Andric   }
1760b57cec5SDimitry Andric 
1770b57cec5SDimitry Andric   return -1;
1780b57cec5SDimitry Andric }
1790b57cec5SDimitry Andric 
1800b57cec5SDimitry Andric /// Check whether the DIE for this MDNode can be shared across CUs.
1810b57cec5SDimitry Andric bool DwarfUnit::isShareableAcrossCUs(const DINode *D) const {
18269ade1e0SDimitry Andric   // When the MDNode can be part of the type system, the DIE can be shared
18369ade1e0SDimitry Andric   // across CUs.
1840b57cec5SDimitry Andric   // Combining type units and cross-CU DIE sharing is lower value (since
1850b57cec5SDimitry Andric   // cross-CU DIE sharing is used in LTO and removes type redundancy at that
1860b57cec5SDimitry Andric   // level already) but may be implementable for some value in projects
1870b57cec5SDimitry Andric   // building multiple independent libraries with LTO and then linking those
1880b57cec5SDimitry Andric   // together.
1890b57cec5SDimitry Andric   if (isDwoUnit() && !DD->shareAcrossDWOCUs())
1900b57cec5SDimitry Andric     return false;
19169ade1e0SDimitry Andric   return (isa<DIType>(D) ||
19269ade1e0SDimitry Andric           (isa<DISubprogram>(D) && !cast<DISubprogram>(D)->isDefinition())) &&
19369ade1e0SDimitry Andric          !DD->generateTypeUnits();
1940b57cec5SDimitry Andric }
1950b57cec5SDimitry Andric 
1960b57cec5SDimitry Andric DIE *DwarfUnit::getDIE(const DINode *D) const {
1970b57cec5SDimitry Andric   if (isShareableAcrossCUs(D))
1980b57cec5SDimitry Andric     return DU->getDIE(D);
1990b57cec5SDimitry Andric   return MDNodeToDieMap.lookup(D);
2000b57cec5SDimitry Andric }
2010b57cec5SDimitry Andric 
2020b57cec5SDimitry Andric void DwarfUnit::insertDIE(const DINode *Desc, DIE *D) {
2030b57cec5SDimitry Andric   if (isShareableAcrossCUs(Desc)) {
2040b57cec5SDimitry Andric     DU->insertDIE(Desc, D);
2050b57cec5SDimitry Andric     return;
2060b57cec5SDimitry Andric   }
2070b57cec5SDimitry Andric   MDNodeToDieMap.insert(std::make_pair(Desc, D));
2080b57cec5SDimitry Andric }
2090b57cec5SDimitry Andric 
2108bcb0991SDimitry Andric void DwarfUnit::insertDIE(DIE *D) {
2118bcb0991SDimitry Andric   MDNodeToDieMap.insert(std::make_pair(nullptr, D));
2128bcb0991SDimitry Andric }
2138bcb0991SDimitry Andric 
2140b57cec5SDimitry Andric void DwarfUnit::addFlag(DIE &Die, dwarf::Attribute Attribute) {
2150b57cec5SDimitry Andric   if (DD->getDwarfVersion() >= 4)
216fe6060f1SDimitry Andric     addAttribute(Die, Attribute, dwarf::DW_FORM_flag_present, DIEInteger(1));
2170b57cec5SDimitry Andric   else
218fe6060f1SDimitry Andric     addAttribute(Die, Attribute, dwarf::DW_FORM_flag, DIEInteger(1));
2190b57cec5SDimitry Andric }
2200b57cec5SDimitry Andric 
2210b57cec5SDimitry Andric void DwarfUnit::addUInt(DIEValueList &Die, dwarf::Attribute Attribute,
222bdd1243dSDimitry Andric                         std::optional<dwarf::Form> Form, uint64_t Integer) {
2230b57cec5SDimitry Andric   if (!Form)
2240b57cec5SDimitry Andric     Form = DIEInteger::BestForm(false, Integer);
2250b57cec5SDimitry Andric   assert(Form != dwarf::DW_FORM_implicit_const &&
2260b57cec5SDimitry Andric          "DW_FORM_implicit_const is used only for signed integers");
227fe6060f1SDimitry Andric   addAttribute(Die, Attribute, *Form, DIEInteger(Integer));
2280b57cec5SDimitry Andric }
2290b57cec5SDimitry Andric 
2300b57cec5SDimitry Andric void DwarfUnit::addUInt(DIEValueList &Block, dwarf::Form Form,
2310b57cec5SDimitry Andric                         uint64_t Integer) {
2320b57cec5SDimitry Andric   addUInt(Block, (dwarf::Attribute)0, Form, Integer);
2330b57cec5SDimitry Andric }
2340b57cec5SDimitry Andric 
2350b57cec5SDimitry Andric void DwarfUnit::addSInt(DIEValueList &Die, dwarf::Attribute Attribute,
236bdd1243dSDimitry Andric                         std::optional<dwarf::Form> Form, int64_t Integer) {
2370b57cec5SDimitry Andric   if (!Form)
2380b57cec5SDimitry Andric     Form = DIEInteger::BestForm(true, Integer);
239fe6060f1SDimitry Andric   addAttribute(Die, Attribute, *Form, DIEInteger(Integer));
2400b57cec5SDimitry Andric }
2410b57cec5SDimitry Andric 
242bdd1243dSDimitry Andric void DwarfUnit::addSInt(DIELoc &Die, std::optional<dwarf::Form> Form,
2430b57cec5SDimitry Andric                         int64_t Integer) {
2440b57cec5SDimitry Andric   addSInt(Die, (dwarf::Attribute)0, Form, Integer);
2450b57cec5SDimitry Andric }
2460b57cec5SDimitry Andric 
2470b57cec5SDimitry Andric void DwarfUnit::addString(DIE &Die, dwarf::Attribute Attribute,
2480b57cec5SDimitry Andric                           StringRef String) {
2490b57cec5SDimitry Andric   if (CUNode->isDebugDirectivesOnly())
2500b57cec5SDimitry Andric     return;
2510b57cec5SDimitry Andric 
2520b57cec5SDimitry Andric   if (DD->useInlineStrings()) {
253fe6060f1SDimitry Andric     addAttribute(Die, Attribute, dwarf::DW_FORM_string,
2540b57cec5SDimitry Andric                  new (DIEValueAllocator)
2550b57cec5SDimitry Andric                      DIEInlineString(String, DIEValueAllocator));
2560b57cec5SDimitry Andric     return;
2570b57cec5SDimitry Andric   }
2580b57cec5SDimitry Andric   dwarf::Form IxForm =
2590b57cec5SDimitry Andric       isDwoUnit() ? dwarf::DW_FORM_GNU_str_index : dwarf::DW_FORM_strp;
2600b57cec5SDimitry Andric 
2610b57cec5SDimitry Andric   auto StringPoolEntry =
2620b57cec5SDimitry Andric       useSegmentedStringOffsetsTable() || IxForm == dwarf::DW_FORM_GNU_str_index
2630b57cec5SDimitry Andric           ? DU->getStringPool().getIndexedEntry(*Asm, String)
2640b57cec5SDimitry Andric           : DU->getStringPool().getEntry(*Asm, String);
2650b57cec5SDimitry Andric 
2660b57cec5SDimitry Andric   // For DWARF v5 and beyond, use the smallest strx? form possible.
2670b57cec5SDimitry Andric   if (useSegmentedStringOffsetsTable()) {
2680b57cec5SDimitry Andric     IxForm = dwarf::DW_FORM_strx1;
2690b57cec5SDimitry Andric     unsigned Index = StringPoolEntry.getIndex();
2700b57cec5SDimitry Andric     if (Index > 0xffffff)
2710b57cec5SDimitry Andric       IxForm = dwarf::DW_FORM_strx4;
2720b57cec5SDimitry Andric     else if (Index > 0xffff)
2730b57cec5SDimitry Andric       IxForm = dwarf::DW_FORM_strx3;
2740b57cec5SDimitry Andric     else if (Index > 0xff)
2750b57cec5SDimitry Andric       IxForm = dwarf::DW_FORM_strx2;
2760b57cec5SDimitry Andric   }
277fe6060f1SDimitry Andric   addAttribute(Die, Attribute, IxForm, DIEString(StringPoolEntry));
2780b57cec5SDimitry Andric }
2790b57cec5SDimitry Andric 
280fe6060f1SDimitry Andric void DwarfUnit::addLabel(DIEValueList &Die, dwarf::Attribute Attribute,
281fe6060f1SDimitry Andric                          dwarf::Form Form, const MCSymbol *Label) {
282fe6060f1SDimitry Andric   addAttribute(Die, Attribute, Form, DIELabel(Label));
2830b57cec5SDimitry Andric }
2840b57cec5SDimitry Andric 
2850b57cec5SDimitry Andric void DwarfUnit::addLabel(DIELoc &Die, dwarf::Form Form, const MCSymbol *Label) {
2860b57cec5SDimitry Andric   addLabel(Die, (dwarf::Attribute)0, Form, Label);
2870b57cec5SDimitry Andric }
2880b57cec5SDimitry Andric 
2890b57cec5SDimitry Andric void DwarfUnit::addSectionOffset(DIE &Die, dwarf::Attribute Attribute,
2900b57cec5SDimitry Andric                                  uint64_t Integer) {
291e8d8bef9SDimitry Andric   addUInt(Die, Attribute, DD->getDwarfSectionOffsetForm(), Integer);
2920b57cec5SDimitry Andric }
2930b57cec5SDimitry Andric 
2940b57cec5SDimitry Andric unsigned DwarfTypeUnit::getOrCreateSourceID(const DIFile *File) {
2950b57cec5SDimitry Andric   if (!SplitLineTable)
2960b57cec5SDimitry Andric     return getCU().getOrCreateSourceID(File);
2970b57cec5SDimitry Andric   if (!UsedLineTable) {
2980b57cec5SDimitry Andric     UsedLineTable = true;
2990b57cec5SDimitry Andric     // This is a split type unit that needs a line table.
3000b57cec5SDimitry Andric     addSectionOffset(getUnitDie(), dwarf::DW_AT_stmt_list, 0);
3010b57cec5SDimitry Andric   }
302e8d8bef9SDimitry Andric   return SplitLineTable->getFile(
303e8d8bef9SDimitry Andric       File->getDirectory(), File->getFilename(), DD->getMD5AsBytes(File),
304e8d8bef9SDimitry Andric       Asm->OutContext.getDwarfVersion(), File->getSource());
3050b57cec5SDimitry Andric }
3060b57cec5SDimitry Andric 
307fe6060f1SDimitry Andric void DwarfUnit::addPoolOpAddress(DIEValueList &Die, const MCSymbol *Label) {
308fe6060f1SDimitry Andric   bool UseAddrOffsetFormOrExpressions =
309fe6060f1SDimitry Andric       DD->useAddrOffsetForm() || DD->useAddrOffsetExpressions();
310fe6060f1SDimitry Andric 
311fe6060f1SDimitry Andric   const MCSymbol *Base = nullptr;
312fe6060f1SDimitry Andric   if (Label->isInSection() && UseAddrOffsetFormOrExpressions)
313fe6060f1SDimitry Andric     Base = DD->getSectionLabel(&Label->getSection());
314fe6060f1SDimitry Andric 
315fe6060f1SDimitry Andric   uint32_t Index = DD->getAddressPool().getIndex(Base ? Base : Label);
316fe6060f1SDimitry Andric 
3170b57cec5SDimitry Andric   if (DD->getDwarfVersion() >= 5) {
3180b57cec5SDimitry Andric     addUInt(Die, dwarf::DW_FORM_data1, dwarf::DW_OP_addrx);
319fe6060f1SDimitry Andric     addUInt(Die, dwarf::DW_FORM_addrx, Index);
320fe6060f1SDimitry Andric   } else {
321fe6060f1SDimitry Andric     addUInt(Die, dwarf::DW_FORM_data1, dwarf::DW_OP_GNU_addr_index);
322fe6060f1SDimitry Andric     addUInt(Die, dwarf::DW_FORM_GNU_addr_index, Index);
323fe6060f1SDimitry Andric   }
324fe6060f1SDimitry Andric 
325fe6060f1SDimitry Andric   if (Base && Base != Label) {
326fe6060f1SDimitry Andric     addUInt(Die, dwarf::DW_FORM_data1, dwarf::DW_OP_const4u);
327fe6060f1SDimitry Andric     addLabelDelta(Die, (dwarf::Attribute)0, Label, Base);
328fe6060f1SDimitry Andric     addUInt(Die, dwarf::DW_FORM_data1, dwarf::DW_OP_plus);
329fe6060f1SDimitry Andric   }
330fe6060f1SDimitry Andric }
331fe6060f1SDimitry Andric 
332fe6060f1SDimitry Andric void DwarfUnit::addOpAddress(DIELoc &Die, const MCSymbol *Sym) {
333fe6060f1SDimitry Andric   if (DD->getDwarfVersion() >= 5) {
334fe6060f1SDimitry Andric     addPoolOpAddress(Die, Sym);
3350b57cec5SDimitry Andric     return;
3360b57cec5SDimitry Andric   }
3370b57cec5SDimitry Andric 
3380b57cec5SDimitry Andric   if (DD->useSplitDwarf()) {
339fe6060f1SDimitry Andric     addPoolOpAddress(Die, Sym);
3400b57cec5SDimitry Andric     return;
3410b57cec5SDimitry Andric   }
3420b57cec5SDimitry Andric 
3430b57cec5SDimitry Andric   addUInt(Die, dwarf::DW_FORM_data1, dwarf::DW_OP_addr);
344e8d8bef9SDimitry Andric   addLabel(Die, dwarf::DW_FORM_addr, Sym);
3450b57cec5SDimitry Andric }
3460b57cec5SDimitry Andric 
347fe6060f1SDimitry Andric void DwarfUnit::addLabelDelta(DIEValueList &Die, dwarf::Attribute Attribute,
3480b57cec5SDimitry Andric                               const MCSymbol *Hi, const MCSymbol *Lo) {
349fe6060f1SDimitry Andric   addAttribute(Die, Attribute, dwarf::DW_FORM_data4,
3500b57cec5SDimitry Andric                new (DIEValueAllocator) DIEDelta(Hi, Lo));
3510b57cec5SDimitry Andric }
3520b57cec5SDimitry Andric 
3530b57cec5SDimitry Andric void DwarfUnit::addDIEEntry(DIE &Die, dwarf::Attribute Attribute, DIE &Entry) {
3540b57cec5SDimitry Andric   addDIEEntry(Die, Attribute, DIEEntry(Entry));
3550b57cec5SDimitry Andric }
3560b57cec5SDimitry Andric 
3570b57cec5SDimitry Andric void DwarfUnit::addDIETypeSignature(DIE &Die, uint64_t Signature) {
3580b57cec5SDimitry Andric   // Flag the type unit reference as a declaration so that if it contains
3590b57cec5SDimitry Andric   // members (implicit special members, static data member definitions, member
3600b57cec5SDimitry Andric   // declarations for definitions in this CU, etc) consumers don't get confused
3610b57cec5SDimitry Andric   // and think this is a full definition.
3620b57cec5SDimitry Andric   addFlag(Die, dwarf::DW_AT_declaration);
3630b57cec5SDimitry Andric 
364fe6060f1SDimitry Andric   addAttribute(Die, dwarf::DW_AT_signature, dwarf::DW_FORM_ref_sig8,
365fe6060f1SDimitry Andric                DIEInteger(Signature));
3660b57cec5SDimitry Andric }
3670b57cec5SDimitry Andric 
3680b57cec5SDimitry Andric void DwarfUnit::addDIEEntry(DIE &Die, dwarf::Attribute Attribute,
3690b57cec5SDimitry Andric                             DIEEntry Entry) {
3700b57cec5SDimitry Andric   const DIEUnit *CU = Die.getUnit();
3710b57cec5SDimitry Andric   const DIEUnit *EntryCU = Entry.getEntry().getUnit();
3720b57cec5SDimitry Andric   if (!CU)
3730b57cec5SDimitry Andric     // We assume that Die belongs to this CU, if it is not linked to any CU yet.
3740b57cec5SDimitry Andric     CU = getUnitDie().getUnit();
3750b57cec5SDimitry Andric   if (!EntryCU)
3760b57cec5SDimitry Andric     EntryCU = getUnitDie().getUnit();
37781ad6265SDimitry Andric   assert(EntryCU == CU || !DD->useSplitDwarf() || DD->shareAcrossDWOCUs() ||
37881ad6265SDimitry Andric          !static_cast<const DwarfUnit*>(CU)->isDwoUnit());
379fe6060f1SDimitry Andric   addAttribute(Die, Attribute,
3800b57cec5SDimitry Andric                EntryCU == CU ? dwarf::DW_FORM_ref4 : dwarf::DW_FORM_ref_addr,
3810b57cec5SDimitry Andric                Entry);
3820b57cec5SDimitry Andric }
3830b57cec5SDimitry Andric 
384fe6060f1SDimitry Andric DIE &DwarfUnit::createAndAddDIE(dwarf::Tag Tag, DIE &Parent, const DINode *N) {
385fe6060f1SDimitry Andric   DIE &Die = Parent.addChild(DIE::get(DIEValueAllocator, Tag));
3860b57cec5SDimitry Andric   if (N)
3870b57cec5SDimitry Andric     insertDIE(N, &Die);
3880b57cec5SDimitry Andric   return Die;
3890b57cec5SDimitry Andric }
3900b57cec5SDimitry Andric 
3910b57cec5SDimitry Andric void DwarfUnit::addBlock(DIE &Die, dwarf::Attribute Attribute, DIELoc *Loc) {
39204eeddc0SDimitry Andric   Loc->computeSize(Asm->getDwarfFormParams());
3930b57cec5SDimitry Andric   DIELocs.push_back(Loc); // Memoize so we can call the destructor later on.
394fe6060f1SDimitry Andric   addAttribute(Die, Attribute, Loc->BestForm(DD->getDwarfVersion()), Loc);
395fe6060f1SDimitry Andric }
396fe6060f1SDimitry Andric 
397fe6060f1SDimitry Andric void DwarfUnit::addBlock(DIE &Die, dwarf::Attribute Attribute, dwarf::Form Form,
398fe6060f1SDimitry Andric                          DIEBlock *Block) {
39904eeddc0SDimitry Andric   Block->computeSize(Asm->getDwarfFormParams());
400fe6060f1SDimitry Andric   DIEBlocks.push_back(Block); // Memoize so we can call the destructor later on.
401fe6060f1SDimitry Andric   addAttribute(Die, Attribute, Form, Block);
4020b57cec5SDimitry Andric }
4030b57cec5SDimitry Andric 
4040b57cec5SDimitry Andric void DwarfUnit::addBlock(DIE &Die, dwarf::Attribute Attribute,
4050b57cec5SDimitry Andric                          DIEBlock *Block) {
406fe6060f1SDimitry Andric   addBlock(Die, Attribute, Block->BestForm(), Block);
4070b57cec5SDimitry Andric }
4080b57cec5SDimitry Andric 
4090b57cec5SDimitry Andric void DwarfUnit::addSourceLine(DIE &Die, unsigned Line, const DIFile *File) {
4100b57cec5SDimitry Andric   if (Line == 0)
4110b57cec5SDimitry Andric     return;
4120b57cec5SDimitry Andric 
4130b57cec5SDimitry Andric   unsigned FileID = getOrCreateSourceID(File);
414bdd1243dSDimitry Andric   addUInt(Die, dwarf::DW_AT_decl_file, std::nullopt, FileID);
415bdd1243dSDimitry Andric   addUInt(Die, dwarf::DW_AT_decl_line, std::nullopt, Line);
4160b57cec5SDimitry Andric }
4170b57cec5SDimitry Andric 
4180b57cec5SDimitry Andric void DwarfUnit::addSourceLine(DIE &Die, const DILocalVariable *V) {
4190b57cec5SDimitry Andric   assert(V);
4200b57cec5SDimitry Andric 
4210b57cec5SDimitry Andric   addSourceLine(Die, V->getLine(), V->getFile());
4220b57cec5SDimitry Andric }
4230b57cec5SDimitry Andric 
4240b57cec5SDimitry Andric void DwarfUnit::addSourceLine(DIE &Die, const DIGlobalVariable *G) {
4250b57cec5SDimitry Andric   assert(G);
4260b57cec5SDimitry Andric 
4270b57cec5SDimitry Andric   addSourceLine(Die, G->getLine(), G->getFile());
4280b57cec5SDimitry Andric }
4290b57cec5SDimitry Andric 
4300b57cec5SDimitry Andric void DwarfUnit::addSourceLine(DIE &Die, const DISubprogram *SP) {
4310b57cec5SDimitry Andric   assert(SP);
4320b57cec5SDimitry Andric 
4330b57cec5SDimitry Andric   addSourceLine(Die, SP->getLine(), SP->getFile());
4340b57cec5SDimitry Andric }
4350b57cec5SDimitry Andric 
4360b57cec5SDimitry Andric void DwarfUnit::addSourceLine(DIE &Die, const DILabel *L) {
4370b57cec5SDimitry Andric   assert(L);
4380b57cec5SDimitry Andric 
4390b57cec5SDimitry Andric   addSourceLine(Die, L->getLine(), L->getFile());
4400b57cec5SDimitry Andric }
4410b57cec5SDimitry Andric 
4420b57cec5SDimitry Andric void DwarfUnit::addSourceLine(DIE &Die, const DIType *Ty) {
4430b57cec5SDimitry Andric   assert(Ty);
4440b57cec5SDimitry Andric 
4450b57cec5SDimitry Andric   addSourceLine(Die, Ty->getLine(), Ty->getFile());
4460b57cec5SDimitry Andric }
4470b57cec5SDimitry Andric 
4480b57cec5SDimitry Andric void DwarfUnit::addSourceLine(DIE &Die, const DIObjCProperty *Ty) {
4490b57cec5SDimitry Andric   assert(Ty);
4500b57cec5SDimitry Andric 
4510b57cec5SDimitry Andric   addSourceLine(Die, Ty->getLine(), Ty->getFile());
4520b57cec5SDimitry Andric }
4530b57cec5SDimitry Andric 
4540b57cec5SDimitry Andric void DwarfUnit::addConstantFPValue(DIE &Die, const ConstantFP *CFP) {
4550b57cec5SDimitry Andric   // Pass this down to addConstantValue as an unsigned bag of bits.
4560b57cec5SDimitry Andric   addConstantValue(Die, CFP->getValueAPF().bitcastToAPInt(), true);
4570b57cec5SDimitry Andric }
4580b57cec5SDimitry Andric 
4590b57cec5SDimitry Andric void DwarfUnit::addConstantValue(DIE &Die, const ConstantInt *CI,
4600b57cec5SDimitry Andric                                  const DIType *Ty) {
4610b57cec5SDimitry Andric   addConstantValue(Die, CI->getValue(), Ty);
4620b57cec5SDimitry Andric }
4630b57cec5SDimitry Andric 
4640b57cec5SDimitry Andric void DwarfUnit::addConstantValue(DIE &Die, uint64_t Val, const DIType *Ty) {
465e8d8bef9SDimitry Andric   addConstantValue(Die, DD->isUnsignedDIType(Ty), Val);
4660b57cec5SDimitry Andric }
4670b57cec5SDimitry Andric 
4680b57cec5SDimitry Andric void DwarfUnit::addConstantValue(DIE &Die, bool Unsigned, uint64_t Val) {
4690b57cec5SDimitry Andric   // FIXME: This is a bit conservative/simple - it emits negative values always
4700b57cec5SDimitry Andric   // sign extended to 64 bits rather than minimizing the number of bytes.
4710b57cec5SDimitry Andric   addUInt(Die, dwarf::DW_AT_const_value,
4720b57cec5SDimitry Andric           Unsigned ? dwarf::DW_FORM_udata : dwarf::DW_FORM_sdata, Val);
4730b57cec5SDimitry Andric }
4740b57cec5SDimitry Andric 
4750b57cec5SDimitry Andric void DwarfUnit::addConstantValue(DIE &Die, const APInt &Val, const DIType *Ty) {
476e8d8bef9SDimitry Andric   addConstantValue(Die, Val, DD->isUnsignedDIType(Ty));
4770b57cec5SDimitry Andric }
4780b57cec5SDimitry Andric 
4790b57cec5SDimitry Andric void DwarfUnit::addConstantValue(DIE &Die, const APInt &Val, bool Unsigned) {
4800b57cec5SDimitry Andric   unsigned CIBitWidth = Val.getBitWidth();
4810b57cec5SDimitry Andric   if (CIBitWidth <= 64) {
4820b57cec5SDimitry Andric     addConstantValue(Die, Unsigned,
4830b57cec5SDimitry Andric                      Unsigned ? Val.getZExtValue() : Val.getSExtValue());
4840b57cec5SDimitry Andric     return;
4850b57cec5SDimitry Andric   }
4860b57cec5SDimitry Andric 
4870b57cec5SDimitry Andric   DIEBlock *Block = new (DIEValueAllocator) DIEBlock;
4880b57cec5SDimitry Andric 
4890b57cec5SDimitry Andric   // Get the raw data form of the large APInt.
4900b57cec5SDimitry Andric   const uint64_t *Ptr64 = Val.getRawData();
4910b57cec5SDimitry Andric 
4920b57cec5SDimitry Andric   int NumBytes = Val.getBitWidth() / 8; // 8 bits per byte.
4930b57cec5SDimitry Andric   bool LittleEndian = Asm->getDataLayout().isLittleEndian();
4940b57cec5SDimitry Andric 
4950b57cec5SDimitry Andric   // Output the constant to DWARF one byte at a time.
4960b57cec5SDimitry Andric   for (int i = 0; i < NumBytes; i++) {
4970b57cec5SDimitry Andric     uint8_t c;
4980b57cec5SDimitry Andric     if (LittleEndian)
4990b57cec5SDimitry Andric       c = Ptr64[i / 8] >> (8 * (i & 7));
5000b57cec5SDimitry Andric     else
5010b57cec5SDimitry Andric       c = Ptr64[(NumBytes - 1 - i) / 8] >> (8 * ((NumBytes - 1 - i) & 7));
5020b57cec5SDimitry Andric     addUInt(*Block, dwarf::DW_FORM_data1, c);
5030b57cec5SDimitry Andric   }
5040b57cec5SDimitry Andric 
5050b57cec5SDimitry Andric   addBlock(Die, dwarf::DW_AT_const_value, Block);
5060b57cec5SDimitry Andric }
5070b57cec5SDimitry Andric 
5080b57cec5SDimitry Andric void DwarfUnit::addLinkageName(DIE &Die, StringRef LinkageName) {
5090b57cec5SDimitry Andric   if (!LinkageName.empty())
5100b57cec5SDimitry Andric     addString(Die,
5110b57cec5SDimitry Andric               DD->getDwarfVersion() >= 4 ? dwarf::DW_AT_linkage_name
5120b57cec5SDimitry Andric                                          : dwarf::DW_AT_MIPS_linkage_name,
5130b57cec5SDimitry Andric               GlobalValue::dropLLVMManglingEscape(LinkageName));
5140b57cec5SDimitry Andric }
5150b57cec5SDimitry Andric 
5160b57cec5SDimitry Andric void DwarfUnit::addTemplateParams(DIE &Buffer, DINodeArray TParams) {
5170b57cec5SDimitry Andric   // Add template parameters.
5180b57cec5SDimitry Andric   for (const auto *Element : TParams) {
5190b57cec5SDimitry Andric     if (auto *TTP = dyn_cast<DITemplateTypeParameter>(Element))
5200b57cec5SDimitry Andric       constructTemplateTypeParameterDIE(Buffer, TTP);
5210b57cec5SDimitry Andric     else if (auto *TVP = dyn_cast<DITemplateValueParameter>(Element))
5220b57cec5SDimitry Andric       constructTemplateValueParameterDIE(Buffer, TVP);
5230b57cec5SDimitry Andric   }
5240b57cec5SDimitry Andric }
5250b57cec5SDimitry Andric 
5260b57cec5SDimitry Andric /// Add thrown types.
5270b57cec5SDimitry Andric void DwarfUnit::addThrownTypes(DIE &Die, DINodeArray ThrownTypes) {
5280b57cec5SDimitry Andric   for (const auto *Ty : ThrownTypes) {
5290b57cec5SDimitry Andric     DIE &TT = createAndAddDIE(dwarf::DW_TAG_thrown_type, Die);
5300b57cec5SDimitry Andric     addType(TT, cast<DIType>(Ty));
5310b57cec5SDimitry Andric   }
5320b57cec5SDimitry Andric }
5330b57cec5SDimitry Andric 
5340eae32dcSDimitry Andric void DwarfUnit::addAccess(DIE &Die, DINode::DIFlags Flags) {
5350eae32dcSDimitry Andric   if ((Flags & DINode::FlagAccessibility) == DINode::FlagProtected)
5360eae32dcSDimitry Andric     addUInt(Die, dwarf::DW_AT_accessibility, dwarf::DW_FORM_data1,
5370eae32dcSDimitry Andric             dwarf::DW_ACCESS_protected);
5380eae32dcSDimitry Andric   else if ((Flags & DINode::FlagAccessibility) == DINode::FlagPrivate)
5390eae32dcSDimitry Andric     addUInt(Die, dwarf::DW_AT_accessibility, dwarf::DW_FORM_data1,
5400eae32dcSDimitry Andric             dwarf::DW_ACCESS_private);
5410eae32dcSDimitry Andric   else if ((Flags & DINode::FlagAccessibility) == DINode::FlagPublic)
5420eae32dcSDimitry Andric     addUInt(Die, dwarf::DW_AT_accessibility, dwarf::DW_FORM_data1,
5430eae32dcSDimitry Andric             dwarf::DW_ACCESS_public);
5440eae32dcSDimitry Andric }
5450eae32dcSDimitry Andric 
5460b57cec5SDimitry Andric DIE *DwarfUnit::getOrCreateContextDIE(const DIScope *Context) {
54706c3fb27SDimitry Andric   if (!Context || isa<DIFile>(Context) || isa<DICompileUnit>(Context))
5480b57cec5SDimitry Andric     return &getUnitDie();
5490b57cec5SDimitry Andric   if (auto *T = dyn_cast<DIType>(Context))
5500b57cec5SDimitry Andric     return getOrCreateTypeDIE(T);
5510b57cec5SDimitry Andric   if (auto *NS = dyn_cast<DINamespace>(Context))
5520b57cec5SDimitry Andric     return getOrCreateNameSpace(NS);
5530b57cec5SDimitry Andric   if (auto *SP = dyn_cast<DISubprogram>(Context))
5540b57cec5SDimitry Andric     return getOrCreateSubprogramDIE(SP);
5550b57cec5SDimitry Andric   if (auto *M = dyn_cast<DIModule>(Context))
5560b57cec5SDimitry Andric     return getOrCreateModule(M);
5570b57cec5SDimitry Andric   return getDIE(Context);
5580b57cec5SDimitry Andric }
5590b57cec5SDimitry Andric 
5600b57cec5SDimitry Andric DIE *DwarfUnit::createTypeDIE(const DICompositeType *Ty) {
5610b57cec5SDimitry Andric   auto *Context = Ty->getScope();
5620b57cec5SDimitry Andric   DIE *ContextDIE = getOrCreateContextDIE(Context);
5630b57cec5SDimitry Andric 
5640b57cec5SDimitry Andric   if (DIE *TyDIE = getDIE(Ty))
5650b57cec5SDimitry Andric     return TyDIE;
5660b57cec5SDimitry Andric 
5670b57cec5SDimitry Andric   // Create new type.
5680b57cec5SDimitry Andric   DIE &TyDIE = createAndAddDIE(Ty->getTag(), *ContextDIE, Ty);
5690b57cec5SDimitry Andric 
5700b57cec5SDimitry Andric   constructTypeDIE(TyDIE, cast<DICompositeType>(Ty));
5710b57cec5SDimitry Andric 
5720b57cec5SDimitry Andric   updateAcceleratorTables(Context, Ty, TyDIE);
5730b57cec5SDimitry Andric   return &TyDIE;
5740b57cec5SDimitry Andric }
5750b57cec5SDimitry Andric 
5760b57cec5SDimitry Andric DIE *DwarfUnit::createTypeDIE(const DIScope *Context, DIE &ContextDIE,
5770b57cec5SDimitry Andric                               const DIType *Ty) {
5780b57cec5SDimitry Andric   // Create new type.
5790b57cec5SDimitry Andric   DIE &TyDIE = createAndAddDIE(Ty->getTag(), ContextDIE, Ty);
5800b57cec5SDimitry Andric 
581*0fca6ea1SDimitry Andric   auto construct = [&](const auto *Ty) {
5820b57cec5SDimitry Andric     updateAcceleratorTables(Context, Ty, TyDIE);
583*0fca6ea1SDimitry Andric     constructTypeDIE(TyDIE, Ty);
584*0fca6ea1SDimitry Andric   };
5850b57cec5SDimitry Andric 
586*0fca6ea1SDimitry Andric   if (auto *CTy = dyn_cast<DICompositeType>(Ty)) {
5870b57cec5SDimitry Andric     if (DD->generateTypeUnits() && !Ty->isForwardDecl() &&
5880b57cec5SDimitry Andric         (Ty->getRawName() || CTy->getRawIdentifier())) {
5890b57cec5SDimitry Andric       // Skip updating the accelerator tables since this is not the full type.
590*0fca6ea1SDimitry Andric       if (MDString *TypeId = CTy->getRawIdentifier()) {
591*0fca6ea1SDimitry Andric         addGlobalType(Ty, TyDIE, Context);
5920b57cec5SDimitry Andric         DD->addDwarfTypeUnitType(getCU(), TypeId->getString(), TyDIE, CTy);
593*0fca6ea1SDimitry Andric       } else {
594*0fca6ea1SDimitry Andric         updateAcceleratorTables(Context, Ty, TyDIE);
5950b57cec5SDimitry Andric         finishNonUnitTypeDIE(TyDIE, CTy);
596*0fca6ea1SDimitry Andric       }
5970b57cec5SDimitry Andric       return &TyDIE;
5980b57cec5SDimitry Andric     }
599*0fca6ea1SDimitry Andric     construct(CTy);
600*0fca6ea1SDimitry Andric   } else if (auto *BT = dyn_cast<DIBasicType>(Ty))
601*0fca6ea1SDimitry Andric     construct(BT);
602*0fca6ea1SDimitry Andric   else if (auto *ST = dyn_cast<DIStringType>(Ty))
603*0fca6ea1SDimitry Andric     construct(ST);
604*0fca6ea1SDimitry Andric   else if (auto *STy = dyn_cast<DISubroutineType>(Ty))
605*0fca6ea1SDimitry Andric     construct(STy);
606*0fca6ea1SDimitry Andric   else
607*0fca6ea1SDimitry Andric     construct(cast<DIDerivedType>(Ty));
6080b57cec5SDimitry Andric 
6090b57cec5SDimitry Andric   return &TyDIE;
6100b57cec5SDimitry Andric }
6110b57cec5SDimitry Andric 
6120b57cec5SDimitry Andric DIE *DwarfUnit::getOrCreateTypeDIE(const MDNode *TyNode) {
6130b57cec5SDimitry Andric   if (!TyNode)
6140b57cec5SDimitry Andric     return nullptr;
6150b57cec5SDimitry Andric 
6160b57cec5SDimitry Andric   auto *Ty = cast<DIType>(TyNode);
6170b57cec5SDimitry Andric 
6180b57cec5SDimitry Andric   // DW_TAG_restrict_type is not supported in DWARF2
6190b57cec5SDimitry Andric   if (Ty->getTag() == dwarf::DW_TAG_restrict_type && DD->getDwarfVersion() <= 2)
6200b57cec5SDimitry Andric     return getOrCreateTypeDIE(cast<DIDerivedType>(Ty)->getBaseType());
6210b57cec5SDimitry Andric 
6220b57cec5SDimitry Andric   // DW_TAG_atomic_type is not supported in DWARF < 5
6230b57cec5SDimitry Andric   if (Ty->getTag() == dwarf::DW_TAG_atomic_type && DD->getDwarfVersion() < 5)
6240b57cec5SDimitry Andric     return getOrCreateTypeDIE(cast<DIDerivedType>(Ty)->getBaseType());
6250b57cec5SDimitry Andric 
6260b57cec5SDimitry Andric   // Construct the context before querying for the existence of the DIE in case
6270b57cec5SDimitry Andric   // such construction creates the DIE.
6280b57cec5SDimitry Andric   auto *Context = Ty->getScope();
6290b57cec5SDimitry Andric   DIE *ContextDIE = getOrCreateContextDIE(Context);
6300b57cec5SDimitry Andric   assert(ContextDIE);
6310b57cec5SDimitry Andric 
6320b57cec5SDimitry Andric   if (DIE *TyDIE = getDIE(Ty))
6330b57cec5SDimitry Andric     return TyDIE;
6340b57cec5SDimitry Andric 
6350b57cec5SDimitry Andric   return static_cast<DwarfUnit *>(ContextDIE->getUnit())
6360b57cec5SDimitry Andric       ->createTypeDIE(Context, *ContextDIE, Ty);
6370b57cec5SDimitry Andric }
6380b57cec5SDimitry Andric 
6390b57cec5SDimitry Andric void DwarfUnit::updateAcceleratorTables(const DIScope *Context,
6400b57cec5SDimitry Andric                                         const DIType *Ty, const DIE &TyDIE) {
641*0fca6ea1SDimitry Andric   if (Ty->getName().empty())
642*0fca6ea1SDimitry Andric     return;
643*0fca6ea1SDimitry Andric   if (Ty->isForwardDecl())
644*0fca6ea1SDimitry Andric     return;
645*0fca6ea1SDimitry Andric 
646*0fca6ea1SDimitry Andric   // add temporary record for this type to be added later
647*0fca6ea1SDimitry Andric 
6480b57cec5SDimitry Andric   bool IsImplementation = false;
6490b57cec5SDimitry Andric   if (auto *CT = dyn_cast<DICompositeType>(Ty)) {
6500b57cec5SDimitry Andric     // A runtime language of 0 actually means C/C++ and that any
6510b57cec5SDimitry Andric     // non-negative value is some version of Objective-C/C++.
6520b57cec5SDimitry Andric     IsImplementation = CT->getRuntimeLang() == 0 || CT->isObjcClassComplete();
6530b57cec5SDimitry Andric   }
6540b57cec5SDimitry Andric   unsigned Flags = IsImplementation ? dwarf::DW_FLAG_type_implementation : 0;
6555f757f3fSDimitry Andric   DD->addAccelType(*this, CUNode->getNameTableKind(), Ty->getName(), TyDIE,
6565f757f3fSDimitry Andric                    Flags);
6570b57cec5SDimitry Andric 
6580b57cec5SDimitry Andric   addGlobalType(Ty, TyDIE, Context);
6590b57cec5SDimitry Andric }
660*0fca6ea1SDimitry Andric 
661*0fca6ea1SDimitry Andric void DwarfUnit::addGlobalType(const DIType *Ty, const DIE &TyDIE,
662*0fca6ea1SDimitry Andric                               const DIScope *Context) {
663*0fca6ea1SDimitry Andric   if (!Context || isa<DICompileUnit>(Context) || isa<DIFile>(Context) ||
664*0fca6ea1SDimitry Andric       isa<DINamespace>(Context) || isa<DICommonBlock>(Context))
665*0fca6ea1SDimitry Andric     addGlobalTypeImpl(Ty, TyDIE, Context);
6660b57cec5SDimitry Andric }
6670b57cec5SDimitry Andric 
6680b57cec5SDimitry Andric void DwarfUnit::addType(DIE &Entity, const DIType *Ty,
6690b57cec5SDimitry Andric                         dwarf::Attribute Attribute) {
6700b57cec5SDimitry Andric   assert(Ty && "Trying to add a type that doesn't exist?");
6710b57cec5SDimitry Andric   addDIEEntry(Entity, Attribute, DIEEntry(*getOrCreateTypeDIE(Ty)));
6720b57cec5SDimitry Andric }
6730b57cec5SDimitry Andric 
6740b57cec5SDimitry Andric std::string DwarfUnit::getParentContextString(const DIScope *Context) const {
6750b57cec5SDimitry Andric   if (!Context)
6760b57cec5SDimitry Andric     return "";
6770b57cec5SDimitry Andric 
6780b57cec5SDimitry Andric   // FIXME: Decide whether to implement this for non-C++ languages.
6798bcb0991SDimitry Andric   if (!dwarf::isCPlusPlus((dwarf::SourceLanguage)getLanguage()))
6800b57cec5SDimitry Andric     return "";
6810b57cec5SDimitry Andric 
6820b57cec5SDimitry Andric   std::string CS;
6830b57cec5SDimitry Andric   SmallVector<const DIScope *, 1> Parents;
6840b57cec5SDimitry Andric   while (!isa<DICompileUnit>(Context)) {
6850b57cec5SDimitry Andric     Parents.push_back(Context);
6860b57cec5SDimitry Andric     if (const DIScope *S = Context->getScope())
6870b57cec5SDimitry Andric       Context = S;
6880b57cec5SDimitry Andric     else
6890b57cec5SDimitry Andric       // Structure, etc types will have a NULL context if they're at the top
6900b57cec5SDimitry Andric       // level.
6910b57cec5SDimitry Andric       break;
6920b57cec5SDimitry Andric   }
6930b57cec5SDimitry Andric 
6940b57cec5SDimitry Andric   // Reverse iterate over our list to go from the outermost construct to the
6950b57cec5SDimitry Andric   // innermost.
696349cc55cSDimitry Andric   for (const DIScope *Ctx : llvm::reverse(Parents)) {
6970b57cec5SDimitry Andric     StringRef Name = Ctx->getName();
6980b57cec5SDimitry Andric     if (Name.empty() && isa<DINamespace>(Ctx))
6990b57cec5SDimitry Andric       Name = "(anonymous namespace)";
7000b57cec5SDimitry Andric     if (!Name.empty()) {
7010b57cec5SDimitry Andric       CS += Name;
7020b57cec5SDimitry Andric       CS += "::";
7030b57cec5SDimitry Andric     }
7040b57cec5SDimitry Andric   }
7050b57cec5SDimitry Andric   return CS;
7060b57cec5SDimitry Andric }
7070b57cec5SDimitry Andric 
7080b57cec5SDimitry Andric void DwarfUnit::constructTypeDIE(DIE &Buffer, const DIBasicType *BTy) {
7090b57cec5SDimitry Andric   // Get core information.
7100b57cec5SDimitry Andric   StringRef Name = BTy->getName();
7110b57cec5SDimitry Andric   // Add name if not anonymous or intermediate type.
7120b57cec5SDimitry Andric   if (!Name.empty())
7130b57cec5SDimitry Andric     addString(Buffer, dwarf::DW_AT_name, Name);
7140b57cec5SDimitry Andric 
7150b57cec5SDimitry Andric   // An unspecified type only has a name attribute.
7160b57cec5SDimitry Andric   if (BTy->getTag() == dwarf::DW_TAG_unspecified_type)
7170b57cec5SDimitry Andric     return;
7180b57cec5SDimitry Andric 
719e8d8bef9SDimitry Andric   if (BTy->getTag() != dwarf::DW_TAG_string_type)
7200b57cec5SDimitry Andric     addUInt(Buffer, dwarf::DW_AT_encoding, dwarf::DW_FORM_data1,
7210b57cec5SDimitry Andric             BTy->getEncoding());
7220b57cec5SDimitry Andric 
7230b57cec5SDimitry Andric   uint64_t Size = BTy->getSizeInBits() >> 3;
724bdd1243dSDimitry Andric   addUInt(Buffer, dwarf::DW_AT_byte_size, std::nullopt, Size);
7250b57cec5SDimitry Andric 
7260b57cec5SDimitry Andric   if (BTy->isBigEndian())
727bdd1243dSDimitry Andric     addUInt(Buffer, dwarf::DW_AT_endianity, std::nullopt, dwarf::DW_END_big);
7280b57cec5SDimitry Andric   else if (BTy->isLittleEndian())
729bdd1243dSDimitry Andric     addUInt(Buffer, dwarf::DW_AT_endianity, std::nullopt, dwarf::DW_END_little);
7300b57cec5SDimitry Andric }
7310b57cec5SDimitry Andric 
732e8d8bef9SDimitry Andric void DwarfUnit::constructTypeDIE(DIE &Buffer, const DIStringType *STy) {
733e8d8bef9SDimitry Andric   // Get core information.
734e8d8bef9SDimitry Andric   StringRef Name = STy->getName();
735e8d8bef9SDimitry Andric   // Add name if not anonymous or intermediate type.
736e8d8bef9SDimitry Andric   if (!Name.empty())
737e8d8bef9SDimitry Andric     addString(Buffer, dwarf::DW_AT_name, Name);
738e8d8bef9SDimitry Andric 
739e8d8bef9SDimitry Andric   if (DIVariable *Var = STy->getStringLength()) {
740e8d8bef9SDimitry Andric     if (auto *VarDIE = getDIE(Var))
741e8d8bef9SDimitry Andric       addDIEEntry(Buffer, dwarf::DW_AT_string_length, *VarDIE);
742e8d8bef9SDimitry Andric   } else if (DIExpression *Expr = STy->getStringLengthExp()) {
743e8d8bef9SDimitry Andric     DIELoc *Loc = new (DIEValueAllocator) DIELoc;
744e8d8bef9SDimitry Andric     DIEDwarfExpression DwarfExpr(*Asm, getCU(), *Loc);
745e8d8bef9SDimitry Andric     // This is to describe the memory location of the
746e8d8bef9SDimitry Andric     // length of a Fortran deferred length string, so
747e8d8bef9SDimitry Andric     // lock it down as such.
748e8d8bef9SDimitry Andric     DwarfExpr.setMemoryLocationKind();
749e8d8bef9SDimitry Andric     DwarfExpr.addExpression(Expr);
750e8d8bef9SDimitry Andric     addBlock(Buffer, dwarf::DW_AT_string_length, DwarfExpr.finalize());
751e8d8bef9SDimitry Andric   } else {
752e8d8bef9SDimitry Andric     uint64_t Size = STy->getSizeInBits() >> 3;
753bdd1243dSDimitry Andric     addUInt(Buffer, dwarf::DW_AT_byte_size, std::nullopt, Size);
754e8d8bef9SDimitry Andric   }
755e8d8bef9SDimitry Andric 
75604eeddc0SDimitry Andric   if (DIExpression *Expr = STy->getStringLocationExp()) {
75704eeddc0SDimitry Andric     DIELoc *Loc = new (DIEValueAllocator) DIELoc;
75804eeddc0SDimitry Andric     DIEDwarfExpression DwarfExpr(*Asm, getCU(), *Loc);
75904eeddc0SDimitry Andric     // This is to describe the memory location of the
76004eeddc0SDimitry Andric     // string, so lock it down as such.
76104eeddc0SDimitry Andric     DwarfExpr.setMemoryLocationKind();
76204eeddc0SDimitry Andric     DwarfExpr.addExpression(Expr);
76304eeddc0SDimitry Andric     addBlock(Buffer, dwarf::DW_AT_data_location, DwarfExpr.finalize());
76404eeddc0SDimitry Andric   }
76504eeddc0SDimitry Andric 
766e8d8bef9SDimitry Andric   if (STy->getEncoding()) {
767e8d8bef9SDimitry Andric     // For eventual Unicode support.
768e8d8bef9SDimitry Andric     addUInt(Buffer, dwarf::DW_AT_encoding, dwarf::DW_FORM_data1,
769e8d8bef9SDimitry Andric             STy->getEncoding());
770e8d8bef9SDimitry Andric   }
771e8d8bef9SDimitry Andric }
772e8d8bef9SDimitry Andric 
7730b57cec5SDimitry Andric void DwarfUnit::constructTypeDIE(DIE &Buffer, const DIDerivedType *DTy) {
7740b57cec5SDimitry Andric   // Get core information.
7750b57cec5SDimitry Andric   StringRef Name = DTy->getName();
7760b57cec5SDimitry Andric   uint64_t Size = DTy->getSizeInBits() >> 3;
7770b57cec5SDimitry Andric   uint16_t Tag = Buffer.getTag();
7780b57cec5SDimitry Andric 
7790b57cec5SDimitry Andric   // Map to main type, void will not have a type.
7800b57cec5SDimitry Andric   const DIType *FromTy = DTy->getBaseType();
7810b57cec5SDimitry Andric   if (FromTy)
7820b57cec5SDimitry Andric     addType(Buffer, FromTy);
7830b57cec5SDimitry Andric 
7840b57cec5SDimitry Andric   // Add name if not anonymous or intermediate type.
7850b57cec5SDimitry Andric   if (!Name.empty())
7860b57cec5SDimitry Andric     addString(Buffer, dwarf::DW_AT_name, Name);
7870b57cec5SDimitry Andric 
788349cc55cSDimitry Andric   addAnnotation(Buffer, DTy->getAnnotations());
789349cc55cSDimitry Andric 
790480093f4SDimitry Andric   // If alignment is specified for a typedef , create and insert DW_AT_alignment
791480093f4SDimitry Andric   // attribute in DW_TAG_typedef DIE.
792480093f4SDimitry Andric   if (Tag == dwarf::DW_TAG_typedef && DD->getDwarfVersion() >= 5) {
793480093f4SDimitry Andric     uint32_t AlignInBytes = DTy->getAlignInBytes();
794480093f4SDimitry Andric     if (AlignInBytes > 0)
795480093f4SDimitry Andric       addUInt(Buffer, dwarf::DW_AT_alignment, dwarf::DW_FORM_udata,
796480093f4SDimitry Andric               AlignInBytes);
797480093f4SDimitry Andric   }
798480093f4SDimitry Andric 
7990b57cec5SDimitry Andric   // Add size if non-zero (derived types might be zero-sized.)
8000b57cec5SDimitry Andric   if (Size && Tag != dwarf::DW_TAG_pointer_type
8010b57cec5SDimitry Andric            && Tag != dwarf::DW_TAG_ptr_to_member_type
8020b57cec5SDimitry Andric            && Tag != dwarf::DW_TAG_reference_type
8030b57cec5SDimitry Andric            && Tag != dwarf::DW_TAG_rvalue_reference_type)
804bdd1243dSDimitry Andric     addUInt(Buffer, dwarf::DW_AT_byte_size, std::nullopt, Size);
8050b57cec5SDimitry Andric 
8060b57cec5SDimitry Andric   if (Tag == dwarf::DW_TAG_ptr_to_member_type)
8070b57cec5SDimitry Andric     addDIEEntry(Buffer, dwarf::DW_AT_containing_type,
8080b57cec5SDimitry Andric                 *getOrCreateTypeDIE(cast<DIDerivedType>(DTy)->getClassType()));
809bdd1243dSDimitry Andric 
810bdd1243dSDimitry Andric   addAccess(Buffer, DTy->getFlags());
811bdd1243dSDimitry Andric 
8120b57cec5SDimitry Andric   // Add source line info if available and TyDesc is not a forward declaration.
8130b57cec5SDimitry Andric   if (!DTy->isForwardDecl())
8140b57cec5SDimitry Andric     addSourceLine(Buffer, DTy);
8150b57cec5SDimitry Andric 
8160b57cec5SDimitry Andric   // If DWARF address space value is other than None, add it.  The IR
8170b57cec5SDimitry Andric   // verifier checks that DWARF address space only exists for pointer
8180b57cec5SDimitry Andric   // or reference types.
8190b57cec5SDimitry Andric   if (DTy->getDWARFAddressSpace())
8200b57cec5SDimitry Andric     addUInt(Buffer, dwarf::DW_AT_address_class, dwarf::DW_FORM_data4,
82181ad6265SDimitry Andric             *DTy->getDWARFAddressSpace());
822*0fca6ea1SDimitry Andric 
823*0fca6ea1SDimitry Andric   // Add template alias template parameters.
824*0fca6ea1SDimitry Andric   if (Tag == dwarf::DW_TAG_template_alias)
825*0fca6ea1SDimitry Andric     addTemplateParams(Buffer, DTy->getTemplateParams());
826*0fca6ea1SDimitry Andric 
827*0fca6ea1SDimitry Andric   if (auto PtrAuthData = DTy->getPtrAuthData()) {
828*0fca6ea1SDimitry Andric     addUInt(Buffer, dwarf::DW_AT_LLVM_ptrauth_key, dwarf::DW_FORM_data1,
829*0fca6ea1SDimitry Andric             PtrAuthData->key());
830*0fca6ea1SDimitry Andric     if (PtrAuthData->isAddressDiscriminated())
831*0fca6ea1SDimitry Andric       addFlag(Buffer, dwarf::DW_AT_LLVM_ptrauth_address_discriminated);
832*0fca6ea1SDimitry Andric     addUInt(Buffer, dwarf::DW_AT_LLVM_ptrauth_extra_discriminator,
833*0fca6ea1SDimitry Andric             dwarf::DW_FORM_data2, PtrAuthData->extraDiscriminator());
834*0fca6ea1SDimitry Andric     if (PtrAuthData->isaPointer())
835*0fca6ea1SDimitry Andric       addFlag(Buffer, dwarf::DW_AT_LLVM_ptrauth_isa_pointer);
836*0fca6ea1SDimitry Andric     if (PtrAuthData->authenticatesNullValues())
837*0fca6ea1SDimitry Andric       addFlag(Buffer, dwarf::DW_AT_LLVM_ptrauth_authenticates_null_values);
838*0fca6ea1SDimitry Andric   }
8390b57cec5SDimitry Andric }
8400b57cec5SDimitry Andric 
8410b57cec5SDimitry Andric void DwarfUnit::constructSubprogramArguments(DIE &Buffer, DITypeRefArray Args) {
8420b57cec5SDimitry Andric   for (unsigned i = 1, N = Args.size(); i < N; ++i) {
8430b57cec5SDimitry Andric     const DIType *Ty = Args[i];
8440b57cec5SDimitry Andric     if (!Ty) {
8450b57cec5SDimitry Andric       assert(i == N-1 && "Unspecified parameter must be the last argument");
8460b57cec5SDimitry Andric       createAndAddDIE(dwarf::DW_TAG_unspecified_parameters, Buffer);
8470b57cec5SDimitry Andric     } else {
8480b57cec5SDimitry Andric       DIE &Arg = createAndAddDIE(dwarf::DW_TAG_formal_parameter, Buffer);
8490b57cec5SDimitry Andric       addType(Arg, Ty);
8500b57cec5SDimitry Andric       if (Ty->isArtificial())
8510b57cec5SDimitry Andric         addFlag(Arg, dwarf::DW_AT_artificial);
8520b57cec5SDimitry Andric     }
8530b57cec5SDimitry Andric   }
8540b57cec5SDimitry Andric }
8550b57cec5SDimitry Andric 
8560b57cec5SDimitry Andric void DwarfUnit::constructTypeDIE(DIE &Buffer, const DISubroutineType *CTy) {
8570b57cec5SDimitry Andric   // Add return type.  A void return won't have a type.
8580b57cec5SDimitry Andric   auto Elements = cast<DISubroutineType>(CTy)->getTypeArray();
8590b57cec5SDimitry Andric   if (Elements.size())
8600b57cec5SDimitry Andric     if (auto RTy = Elements[0])
8610b57cec5SDimitry Andric       addType(Buffer, RTy);
8620b57cec5SDimitry Andric 
8630b57cec5SDimitry Andric   bool isPrototyped = true;
8640b57cec5SDimitry Andric   if (Elements.size() == 2 && !Elements[1])
8650b57cec5SDimitry Andric     isPrototyped = false;
8660b57cec5SDimitry Andric 
8670b57cec5SDimitry Andric   constructSubprogramArguments(Buffer, Elements);
8680b57cec5SDimitry Andric 
8690b57cec5SDimitry Andric   // Add prototype flag if we're dealing with a C language and the function has
8700b57cec5SDimitry Andric   // been prototyped.
871bdd1243dSDimitry Andric   if (isPrototyped && dwarf::isC((dwarf::SourceLanguage)getLanguage()))
8720b57cec5SDimitry Andric     addFlag(Buffer, dwarf::DW_AT_prototyped);
8730b57cec5SDimitry Andric 
8740b57cec5SDimitry Andric   // Add a DW_AT_calling_convention if this has an explicit convention.
8750b57cec5SDimitry Andric   if (CTy->getCC() && CTy->getCC() != dwarf::DW_CC_normal)
8760b57cec5SDimitry Andric     addUInt(Buffer, dwarf::DW_AT_calling_convention, dwarf::DW_FORM_data1,
8770b57cec5SDimitry Andric             CTy->getCC());
8780b57cec5SDimitry Andric 
8790b57cec5SDimitry Andric   if (CTy->isLValueReference())
8800b57cec5SDimitry Andric     addFlag(Buffer, dwarf::DW_AT_reference);
8810b57cec5SDimitry Andric 
8820b57cec5SDimitry Andric   if (CTy->isRValueReference())
8830b57cec5SDimitry Andric     addFlag(Buffer, dwarf::DW_AT_rvalue_reference);
8840b57cec5SDimitry Andric }
8850b57cec5SDimitry Andric 
886349cc55cSDimitry Andric void DwarfUnit::addAnnotation(DIE &Buffer, DINodeArray Annotations) {
887349cc55cSDimitry Andric   if (!Annotations)
888349cc55cSDimitry Andric     return;
889349cc55cSDimitry Andric 
890349cc55cSDimitry Andric   for (const Metadata *Annotation : Annotations->operands()) {
891349cc55cSDimitry Andric     const MDNode *MD = cast<MDNode>(Annotation);
892349cc55cSDimitry Andric     const MDString *Name = cast<MDString>(MD->getOperand(0));
8930eae32dcSDimitry Andric     const auto &Value = MD->getOperand(1);
894349cc55cSDimitry Andric 
895349cc55cSDimitry Andric     DIE &AnnotationDie = createAndAddDIE(dwarf::DW_TAG_LLVM_annotation, Buffer);
896349cc55cSDimitry Andric     addString(AnnotationDie, dwarf::DW_AT_name, Name->getString());
8970eae32dcSDimitry Andric     if (const auto *Data = dyn_cast<MDString>(Value))
8980eae32dcSDimitry Andric       addString(AnnotationDie, dwarf::DW_AT_const_value, Data->getString());
8990eae32dcSDimitry Andric     else if (const auto *Data = dyn_cast<ConstantAsMetadata>(Value))
9000eae32dcSDimitry Andric       addConstantValue(AnnotationDie, Data->getValue()->getUniqueInteger(),
9010eae32dcSDimitry Andric                        /*Unsigned=*/true);
9020eae32dcSDimitry Andric     else
9030eae32dcSDimitry Andric       assert(false && "Unsupported annotation value type");
904349cc55cSDimitry Andric   }
905349cc55cSDimitry Andric }
906349cc55cSDimitry Andric 
9070b57cec5SDimitry Andric void DwarfUnit::constructTypeDIE(DIE &Buffer, const DICompositeType *CTy) {
9080b57cec5SDimitry Andric   // Add name if not anonymous or intermediate type.
9090b57cec5SDimitry Andric   StringRef Name = CTy->getName();
9100b57cec5SDimitry Andric 
9110b57cec5SDimitry Andric   uint64_t Size = CTy->getSizeInBits() >> 3;
9120b57cec5SDimitry Andric   uint16_t Tag = Buffer.getTag();
9130b57cec5SDimitry Andric 
9140b57cec5SDimitry Andric   switch (Tag) {
9150b57cec5SDimitry Andric   case dwarf::DW_TAG_array_type:
9160b57cec5SDimitry Andric     constructArrayTypeDIE(Buffer, CTy);
9170b57cec5SDimitry Andric     break;
9180b57cec5SDimitry Andric   case dwarf::DW_TAG_enumeration_type:
9190b57cec5SDimitry Andric     constructEnumTypeDIE(Buffer, CTy);
9200b57cec5SDimitry Andric     break;
9210b57cec5SDimitry Andric   case dwarf::DW_TAG_variant_part:
9220b57cec5SDimitry Andric   case dwarf::DW_TAG_structure_type:
9230b57cec5SDimitry Andric   case dwarf::DW_TAG_union_type:
924349cc55cSDimitry Andric   case dwarf::DW_TAG_class_type:
925349cc55cSDimitry Andric   case dwarf::DW_TAG_namelist: {
9260b57cec5SDimitry Andric     // Emit the discriminator for a variant part.
9270b57cec5SDimitry Andric     DIDerivedType *Discriminator = nullptr;
9280b57cec5SDimitry Andric     if (Tag == dwarf::DW_TAG_variant_part) {
9290b57cec5SDimitry Andric       Discriminator = CTy->getDiscriminator();
9300b57cec5SDimitry Andric       if (Discriminator) {
9310b57cec5SDimitry Andric         // DWARF says:
9320b57cec5SDimitry Andric         //    If the variant part has a discriminant, the discriminant is
9330b57cec5SDimitry Andric         //    represented by a separate debugging information entry which is
9340b57cec5SDimitry Andric         //    a child of the variant part entry.
9350b57cec5SDimitry Andric         DIE &DiscMember = constructMemberDIE(Buffer, Discriminator);
9360b57cec5SDimitry Andric         addDIEEntry(Buffer, dwarf::DW_AT_discr, DiscMember);
9370b57cec5SDimitry Andric       }
9380b57cec5SDimitry Andric     }
9390b57cec5SDimitry Andric 
940e8d8bef9SDimitry Andric     // Add template parameters to a class, structure or union types.
941e8d8bef9SDimitry Andric     if (Tag == dwarf::DW_TAG_class_type ||
942e8d8bef9SDimitry Andric         Tag == dwarf::DW_TAG_structure_type || Tag == dwarf::DW_TAG_union_type)
943e8d8bef9SDimitry Andric       addTemplateParams(Buffer, CTy->getTemplateParams());
944e8d8bef9SDimitry Andric 
9450b57cec5SDimitry Andric     // Add elements to structure type.
9460b57cec5SDimitry Andric     DINodeArray Elements = CTy->getElements();
9470b57cec5SDimitry Andric     for (const auto *Element : Elements) {
9480b57cec5SDimitry Andric       if (!Element)
9490b57cec5SDimitry Andric         continue;
9500b57cec5SDimitry Andric       if (auto *SP = dyn_cast<DISubprogram>(Element))
9510b57cec5SDimitry Andric         getOrCreateSubprogramDIE(SP);
9520b57cec5SDimitry Andric       else if (auto *DDTy = dyn_cast<DIDerivedType>(Element)) {
9530b57cec5SDimitry Andric         if (DDTy->getTag() == dwarf::DW_TAG_friend) {
9540b57cec5SDimitry Andric           DIE &ElemDie = createAndAddDIE(dwarf::DW_TAG_friend, Buffer);
9550b57cec5SDimitry Andric           addType(ElemDie, DDTy->getBaseType(), dwarf::DW_AT_friend);
9560b57cec5SDimitry Andric         } else if (DDTy->isStaticMember()) {
9570b57cec5SDimitry Andric           getOrCreateStaticMemberDIE(DDTy);
9580b57cec5SDimitry Andric         } else if (Tag == dwarf::DW_TAG_variant_part) {
9590b57cec5SDimitry Andric           // When emitting a variant part, wrap each member in
9600b57cec5SDimitry Andric           // DW_TAG_variant.
9610b57cec5SDimitry Andric           DIE &Variant = createAndAddDIE(dwarf::DW_TAG_variant, Buffer);
9620b57cec5SDimitry Andric           if (const ConstantInt *CI =
9630b57cec5SDimitry Andric               dyn_cast_or_null<ConstantInt>(DDTy->getDiscriminantValue())) {
964e8d8bef9SDimitry Andric             if (DD->isUnsignedDIType(Discriminator->getBaseType()))
965bdd1243dSDimitry Andric               addUInt(Variant, dwarf::DW_AT_discr_value, std::nullopt,
966bdd1243dSDimitry Andric                       CI->getZExtValue());
9670b57cec5SDimitry Andric             else
968bdd1243dSDimitry Andric               addSInt(Variant, dwarf::DW_AT_discr_value, std::nullopt,
969bdd1243dSDimitry Andric                       CI->getSExtValue());
9700b57cec5SDimitry Andric           }
9710b57cec5SDimitry Andric           constructMemberDIE(Variant, DDTy);
9720b57cec5SDimitry Andric         } else {
9730b57cec5SDimitry Andric           constructMemberDIE(Buffer, DDTy);
9740b57cec5SDimitry Andric         }
9750b57cec5SDimitry Andric       } else if (auto *Property = dyn_cast<DIObjCProperty>(Element)) {
9760b57cec5SDimitry Andric         DIE &ElemDie = createAndAddDIE(Property->getTag(), Buffer);
9770b57cec5SDimitry Andric         StringRef PropertyName = Property->getName();
9780b57cec5SDimitry Andric         addString(ElemDie, dwarf::DW_AT_APPLE_property_name, PropertyName);
9790b57cec5SDimitry Andric         if (Property->getType())
9800b57cec5SDimitry Andric           addType(ElemDie, Property->getType());
9810b57cec5SDimitry Andric         addSourceLine(ElemDie, Property);
9820b57cec5SDimitry Andric         StringRef GetterName = Property->getGetterName();
9830b57cec5SDimitry Andric         if (!GetterName.empty())
9840b57cec5SDimitry Andric           addString(ElemDie, dwarf::DW_AT_APPLE_property_getter, GetterName);
9850b57cec5SDimitry Andric         StringRef SetterName = Property->getSetterName();
9860b57cec5SDimitry Andric         if (!SetterName.empty())
9870b57cec5SDimitry Andric           addString(ElemDie, dwarf::DW_AT_APPLE_property_setter, SetterName);
9880b57cec5SDimitry Andric         if (unsigned PropertyAttributes = Property->getAttributes())
989bdd1243dSDimitry Andric           addUInt(ElemDie, dwarf::DW_AT_APPLE_property_attribute, std::nullopt,
9900b57cec5SDimitry Andric                   PropertyAttributes);
9910b57cec5SDimitry Andric       } else if (auto *Composite = dyn_cast<DICompositeType>(Element)) {
9920b57cec5SDimitry Andric         if (Composite->getTag() == dwarf::DW_TAG_variant_part) {
9930b57cec5SDimitry Andric           DIE &VariantPart = createAndAddDIE(Composite->getTag(), Buffer);
9940b57cec5SDimitry Andric           constructTypeDIE(VariantPart, Composite);
9950b57cec5SDimitry Andric         }
996349cc55cSDimitry Andric       } else if (Tag == dwarf::DW_TAG_namelist) {
997349cc55cSDimitry Andric         auto *Var = dyn_cast<DINode>(Element);
998349cc55cSDimitry Andric         auto *VarDIE = getDIE(Var);
999349cc55cSDimitry Andric         if (VarDIE) {
1000349cc55cSDimitry Andric           DIE &ItemDie = createAndAddDIE(dwarf::DW_TAG_namelist_item, Buffer);
1001349cc55cSDimitry Andric           addDIEEntry(ItemDie, dwarf::DW_AT_namelist_item, *VarDIE);
1002349cc55cSDimitry Andric         }
10030b57cec5SDimitry Andric       }
10040b57cec5SDimitry Andric     }
10050b57cec5SDimitry Andric 
10060b57cec5SDimitry Andric     if (CTy->isAppleBlockExtension())
10070b57cec5SDimitry Andric       addFlag(Buffer, dwarf::DW_AT_APPLE_block);
10080b57cec5SDimitry Andric 
10098bcb0991SDimitry Andric     if (CTy->getExportSymbols())
10108bcb0991SDimitry Andric       addFlag(Buffer, dwarf::DW_AT_export_symbols);
10118bcb0991SDimitry Andric 
10120b57cec5SDimitry Andric     // This is outside the DWARF spec, but GDB expects a DW_AT_containing_type
10130b57cec5SDimitry Andric     // inside C++ composite types to point to the base class with the vtable.
10140b57cec5SDimitry Andric     // Rust uses DW_AT_containing_type to link a vtable to the type
10150b57cec5SDimitry Andric     // for which it was created.
10160b57cec5SDimitry Andric     if (auto *ContainingType = CTy->getVTableHolder())
10170b57cec5SDimitry Andric       addDIEEntry(Buffer, dwarf::DW_AT_containing_type,
10180b57cec5SDimitry Andric                   *getOrCreateTypeDIE(ContainingType));
10190b57cec5SDimitry Andric 
10200b57cec5SDimitry Andric     if (CTy->isObjcClassComplete())
10210b57cec5SDimitry Andric       addFlag(Buffer, dwarf::DW_AT_APPLE_objc_complete_type);
10220b57cec5SDimitry Andric 
10230b57cec5SDimitry Andric     // Add the type's non-standard calling convention.
1024fe6060f1SDimitry Andric     // DW_CC_pass_by_value/DW_CC_pass_by_reference are introduced in DWARF 5.
1025fe6060f1SDimitry Andric     if (!Asm->TM.Options.DebugStrictDwarf || DD->getDwarfVersion() >= 5) {
10260b57cec5SDimitry Andric       uint8_t CC = 0;
10270b57cec5SDimitry Andric       if (CTy->isTypePassByValue())
10280b57cec5SDimitry Andric         CC = dwarf::DW_CC_pass_by_value;
10290b57cec5SDimitry Andric       else if (CTy->isTypePassByReference())
10300b57cec5SDimitry Andric         CC = dwarf::DW_CC_pass_by_reference;
10310b57cec5SDimitry Andric       if (CC)
10320b57cec5SDimitry Andric         addUInt(Buffer, dwarf::DW_AT_calling_convention, dwarf::DW_FORM_data1,
10330b57cec5SDimitry Andric                 CC);
1034fe6060f1SDimitry Andric     }
10350b57cec5SDimitry Andric     break;
10360b57cec5SDimitry Andric   }
10370b57cec5SDimitry Andric   default:
10380b57cec5SDimitry Andric     break;
10390b57cec5SDimitry Andric   }
10400b57cec5SDimitry Andric 
10410b57cec5SDimitry Andric   // Add name if not anonymous or intermediate type.
10420b57cec5SDimitry Andric   if (!Name.empty())
10430b57cec5SDimitry Andric     addString(Buffer, dwarf::DW_AT_name, Name);
10440b57cec5SDimitry Andric 
1045349cc55cSDimitry Andric   addAnnotation(Buffer, CTy->getAnnotations());
1046349cc55cSDimitry Andric 
10470b57cec5SDimitry Andric   if (Tag == dwarf::DW_TAG_enumeration_type ||
10480b57cec5SDimitry Andric       Tag == dwarf::DW_TAG_class_type || Tag == dwarf::DW_TAG_structure_type ||
10490b57cec5SDimitry Andric       Tag == dwarf::DW_TAG_union_type) {
10500b57cec5SDimitry Andric     // Add size if non-zero (derived types might be zero-sized.)
1051e8d8bef9SDimitry Andric     // Ignore the size if it's a non-enum forward decl.
10520b57cec5SDimitry Andric     // TODO: Do we care about size for enum forward declarations?
1053e8d8bef9SDimitry Andric     if (Size &&
1054e8d8bef9SDimitry Andric         (!CTy->isForwardDecl() || Tag == dwarf::DW_TAG_enumeration_type))
1055bdd1243dSDimitry Andric       addUInt(Buffer, dwarf::DW_AT_byte_size, std::nullopt, Size);
10560b57cec5SDimitry Andric     else if (!CTy->isForwardDecl())
10570b57cec5SDimitry Andric       // Add zero size if it is not a forward declaration.
1058bdd1243dSDimitry Andric       addUInt(Buffer, dwarf::DW_AT_byte_size, std::nullopt, 0);
10590b57cec5SDimitry Andric 
10600b57cec5SDimitry Andric     // If we're a forward decl, say so.
10610b57cec5SDimitry Andric     if (CTy->isForwardDecl())
10620b57cec5SDimitry Andric       addFlag(Buffer, dwarf::DW_AT_declaration);
10630b57cec5SDimitry Andric 
10640eae32dcSDimitry Andric     // Add accessibility info if available.
10650eae32dcSDimitry Andric     addAccess(Buffer, CTy->getFlags());
10660eae32dcSDimitry Andric 
10670b57cec5SDimitry Andric     // Add source line info if available.
10680b57cec5SDimitry Andric     if (!CTy->isForwardDecl())
10690b57cec5SDimitry Andric       addSourceLine(Buffer, CTy);
10700b57cec5SDimitry Andric 
10710b57cec5SDimitry Andric     // No harm in adding the runtime language to the declaration.
10720b57cec5SDimitry Andric     unsigned RLang = CTy->getRuntimeLang();
10730b57cec5SDimitry Andric     if (RLang)
10740b57cec5SDimitry Andric       addUInt(Buffer, dwarf::DW_AT_APPLE_runtime_class, dwarf::DW_FORM_data1,
10750b57cec5SDimitry Andric               RLang);
10760b57cec5SDimitry Andric 
10770b57cec5SDimitry Andric     // Add align info if available.
10780b57cec5SDimitry Andric     if (uint32_t AlignInBytes = CTy->getAlignInBytes())
10790b57cec5SDimitry Andric       addUInt(Buffer, dwarf::DW_AT_alignment, dwarf::DW_FORM_udata,
10800b57cec5SDimitry Andric               AlignInBytes);
10810b57cec5SDimitry Andric   }
10820b57cec5SDimitry Andric }
10830b57cec5SDimitry Andric 
10840b57cec5SDimitry Andric void DwarfUnit::constructTemplateTypeParameterDIE(
10850b57cec5SDimitry Andric     DIE &Buffer, const DITemplateTypeParameter *TP) {
10860b57cec5SDimitry Andric   DIE &ParamDIE =
10870b57cec5SDimitry Andric       createAndAddDIE(dwarf::DW_TAG_template_type_parameter, Buffer);
10880b57cec5SDimitry Andric   // Add the type if it exists, it could be void and therefore no type.
10890b57cec5SDimitry Andric   if (TP->getType())
10900b57cec5SDimitry Andric     addType(ParamDIE, TP->getType());
10910b57cec5SDimitry Andric   if (!TP->getName().empty())
10920b57cec5SDimitry Andric     addString(ParamDIE, dwarf::DW_AT_name, TP->getName());
1093bdd1243dSDimitry Andric   if (TP->isDefault() && isCompatibleWithVersion(5))
10945ffd83dbSDimitry Andric     addFlag(ParamDIE, dwarf::DW_AT_default_value);
10950b57cec5SDimitry Andric }
10960b57cec5SDimitry Andric 
10970b57cec5SDimitry Andric void DwarfUnit::constructTemplateValueParameterDIE(
10980b57cec5SDimitry Andric     DIE &Buffer, const DITemplateValueParameter *VP) {
10990b57cec5SDimitry Andric   DIE &ParamDIE = createAndAddDIE(VP->getTag(), Buffer);
11000b57cec5SDimitry Andric 
11010b57cec5SDimitry Andric   // Add the type if there is one, template template and template parameter
11020b57cec5SDimitry Andric   // packs will not have a type.
11030b57cec5SDimitry Andric   if (VP->getTag() == dwarf::DW_TAG_template_value_parameter)
11040b57cec5SDimitry Andric     addType(ParamDIE, VP->getType());
11050b57cec5SDimitry Andric   if (!VP->getName().empty())
11060b57cec5SDimitry Andric     addString(ParamDIE, dwarf::DW_AT_name, VP->getName());
1107bdd1243dSDimitry Andric   if (VP->isDefault() && isCompatibleWithVersion(5))
11085ffd83dbSDimitry Andric     addFlag(ParamDIE, dwarf::DW_AT_default_value);
11090b57cec5SDimitry Andric   if (Metadata *Val = VP->getValue()) {
11100b57cec5SDimitry Andric     if (ConstantInt *CI = mdconst::dyn_extract<ConstantInt>(Val))
11110b57cec5SDimitry Andric       addConstantValue(ParamDIE, CI, VP->getType());
11120b57cec5SDimitry Andric     else if (GlobalValue *GV = mdconst::dyn_extract<GlobalValue>(Val)) {
11130b57cec5SDimitry Andric       // We cannot describe the location of dllimport'd entities: the
11140b57cec5SDimitry Andric       // computation of their address requires loads from the IAT.
11150b57cec5SDimitry Andric       if (!GV->hasDLLImportStorageClass()) {
11160b57cec5SDimitry Andric         // For declaration non-type template parameters (such as global values
11170b57cec5SDimitry Andric         // and functions)
11180b57cec5SDimitry Andric         DIELoc *Loc = new (DIEValueAllocator) DIELoc;
11190b57cec5SDimitry Andric         addOpAddress(*Loc, Asm->getSymbol(GV));
11200b57cec5SDimitry Andric         // Emit DW_OP_stack_value to use the address as the immediate value of
11210b57cec5SDimitry Andric         // the parameter, rather than a pointer to it.
11220b57cec5SDimitry Andric         addUInt(*Loc, dwarf::DW_FORM_data1, dwarf::DW_OP_stack_value);
11230b57cec5SDimitry Andric         addBlock(ParamDIE, dwarf::DW_AT_location, Loc);
11240b57cec5SDimitry Andric       }
11250b57cec5SDimitry Andric     } else if (VP->getTag() == dwarf::DW_TAG_GNU_template_template_param) {
11260b57cec5SDimitry Andric       assert(isa<MDString>(Val));
11270b57cec5SDimitry Andric       addString(ParamDIE, dwarf::DW_AT_GNU_template_name,
11280b57cec5SDimitry Andric                 cast<MDString>(Val)->getString());
11290b57cec5SDimitry Andric     } else if (VP->getTag() == dwarf::DW_TAG_GNU_template_parameter_pack) {
11300b57cec5SDimitry Andric       addTemplateParams(ParamDIE, cast<MDTuple>(Val));
11310b57cec5SDimitry Andric     }
11320b57cec5SDimitry Andric   }
11330b57cec5SDimitry Andric }
11340b57cec5SDimitry Andric 
11350b57cec5SDimitry Andric DIE *DwarfUnit::getOrCreateNameSpace(const DINamespace *NS) {
11360b57cec5SDimitry Andric   // Construct the context before querying for the existence of the DIE in case
11370b57cec5SDimitry Andric   // such construction creates the DIE.
11380b57cec5SDimitry Andric   DIE *ContextDIE = getOrCreateContextDIE(NS->getScope());
11390b57cec5SDimitry Andric 
11400b57cec5SDimitry Andric   if (DIE *NDie = getDIE(NS))
11410b57cec5SDimitry Andric     return NDie;
11420b57cec5SDimitry Andric   DIE &NDie = createAndAddDIE(dwarf::DW_TAG_namespace, *ContextDIE, NS);
11430b57cec5SDimitry Andric 
11440b57cec5SDimitry Andric   StringRef Name = NS->getName();
11450b57cec5SDimitry Andric   if (!Name.empty())
11460b57cec5SDimitry Andric     addString(NDie, dwarf::DW_AT_name, NS->getName());
11470b57cec5SDimitry Andric   else
11480b57cec5SDimitry Andric     Name = "(anonymous namespace)";
11495f757f3fSDimitry Andric   DD->addAccelNamespace(*this, CUNode->getNameTableKind(), Name, NDie);
11500b57cec5SDimitry Andric   addGlobalName(Name, NDie, NS->getScope());
11510b57cec5SDimitry Andric   if (NS->getExportSymbols())
11520b57cec5SDimitry Andric     addFlag(NDie, dwarf::DW_AT_export_symbols);
11530b57cec5SDimitry Andric   return &NDie;
11540b57cec5SDimitry Andric }
11550b57cec5SDimitry Andric 
11560b57cec5SDimitry Andric DIE *DwarfUnit::getOrCreateModule(const DIModule *M) {
11570b57cec5SDimitry Andric   // Construct the context before querying for the existence of the DIE in case
11580b57cec5SDimitry Andric   // such construction creates the DIE.
11590b57cec5SDimitry Andric   DIE *ContextDIE = getOrCreateContextDIE(M->getScope());
11600b57cec5SDimitry Andric 
11610b57cec5SDimitry Andric   if (DIE *MDie = getDIE(M))
11620b57cec5SDimitry Andric     return MDie;
11630b57cec5SDimitry Andric   DIE &MDie = createAndAddDIE(dwarf::DW_TAG_module, *ContextDIE, M);
11640b57cec5SDimitry Andric 
11650b57cec5SDimitry Andric   if (!M->getName().empty()) {
11660b57cec5SDimitry Andric     addString(MDie, dwarf::DW_AT_name, M->getName());
11670b57cec5SDimitry Andric     addGlobalName(M->getName(), MDie, M->getScope());
11680b57cec5SDimitry Andric   }
11690b57cec5SDimitry Andric   if (!M->getConfigurationMacros().empty())
11700b57cec5SDimitry Andric     addString(MDie, dwarf::DW_AT_LLVM_config_macros,
11710b57cec5SDimitry Andric               M->getConfigurationMacros());
11720b57cec5SDimitry Andric   if (!M->getIncludePath().empty())
11730b57cec5SDimitry Andric     addString(MDie, dwarf::DW_AT_LLVM_include_path, M->getIncludePath());
11745ffd83dbSDimitry Andric   if (!M->getAPINotesFile().empty())
11755ffd83dbSDimitry Andric     addString(MDie, dwarf::DW_AT_LLVM_apinotes, M->getAPINotesFile());
11765ffd83dbSDimitry Andric   if (M->getFile())
1177bdd1243dSDimitry Andric     addUInt(MDie, dwarf::DW_AT_decl_file, std::nullopt,
11785ffd83dbSDimitry Andric             getOrCreateSourceID(M->getFile()));
11795ffd83dbSDimitry Andric   if (M->getLineNo())
1180bdd1243dSDimitry Andric     addUInt(MDie, dwarf::DW_AT_decl_line, std::nullopt, M->getLineNo());
1181e8d8bef9SDimitry Andric   if (M->getIsDecl())
1182e8d8bef9SDimitry Andric     addFlag(MDie, dwarf::DW_AT_declaration);
11830b57cec5SDimitry Andric 
11840b57cec5SDimitry Andric   return &MDie;
11850b57cec5SDimitry Andric }
11860b57cec5SDimitry Andric 
11870b57cec5SDimitry Andric DIE *DwarfUnit::getOrCreateSubprogramDIE(const DISubprogram *SP, bool Minimal) {
11880b57cec5SDimitry Andric   // Construct the context before querying for the existence of the DIE in case
11890b57cec5SDimitry Andric   // such construction creates the DIE (as is the case for member function
11900b57cec5SDimitry Andric   // declarations).
11910b57cec5SDimitry Andric   DIE *ContextDIE =
11920b57cec5SDimitry Andric       Minimal ? &getUnitDie() : getOrCreateContextDIE(SP->getScope());
11930b57cec5SDimitry Andric 
11940b57cec5SDimitry Andric   if (DIE *SPDie = getDIE(SP))
11950b57cec5SDimitry Andric     return SPDie;
11960b57cec5SDimitry Andric 
11970b57cec5SDimitry Andric   if (auto *SPDecl = SP->getDeclaration()) {
11980b57cec5SDimitry Andric     if (!Minimal) {
11990b57cec5SDimitry Andric       // Add subprogram definitions to the CU die directly.
12000b57cec5SDimitry Andric       ContextDIE = &getUnitDie();
12010b57cec5SDimitry Andric       // Build the decl now to ensure it precedes the definition.
12020b57cec5SDimitry Andric       getOrCreateSubprogramDIE(SPDecl);
12030b57cec5SDimitry Andric     }
12040b57cec5SDimitry Andric   }
12050b57cec5SDimitry Andric 
12060b57cec5SDimitry Andric   // DW_TAG_inlined_subroutine may refer to this DIE.
12070b57cec5SDimitry Andric   DIE &SPDie = createAndAddDIE(dwarf::DW_TAG_subprogram, *ContextDIE, SP);
12080b57cec5SDimitry Andric 
12090b57cec5SDimitry Andric   // Stop here and fill this in later, depending on whether or not this
12100b57cec5SDimitry Andric   // subprogram turns out to have inlined instances or not.
12110b57cec5SDimitry Andric   if (SP->isDefinition())
12120b57cec5SDimitry Andric     return &SPDie;
12130b57cec5SDimitry Andric 
12140b57cec5SDimitry Andric   static_cast<DwarfUnit *>(SPDie.getUnit())
12150b57cec5SDimitry Andric       ->applySubprogramAttributes(SP, SPDie);
12160b57cec5SDimitry Andric   return &SPDie;
12170b57cec5SDimitry Andric }
12180b57cec5SDimitry Andric 
12190b57cec5SDimitry Andric bool DwarfUnit::applySubprogramDefinitionAttributes(const DISubprogram *SP,
1220fe6060f1SDimitry Andric                                                     DIE &SPDie, bool Minimal) {
12210b57cec5SDimitry Andric   DIE *DeclDie = nullptr;
12220b57cec5SDimitry Andric   StringRef DeclLinkageName;
12230b57cec5SDimitry Andric   if (auto *SPDecl = SP->getDeclaration()) {
1224fe6060f1SDimitry Andric     if (!Minimal) {
12255ffd83dbSDimitry Andric       DITypeRefArray DeclArgs, DefinitionArgs;
12265ffd83dbSDimitry Andric       DeclArgs = SPDecl->getType()->getTypeArray();
12275ffd83dbSDimitry Andric       DefinitionArgs = SP->getType()->getTypeArray();
12285ffd83dbSDimitry Andric 
12295ffd83dbSDimitry Andric       if (DeclArgs.size() && DefinitionArgs.size())
123004eeddc0SDimitry Andric         if (DefinitionArgs[0] != nullptr && DeclArgs[0] != DefinitionArgs[0])
12315ffd83dbSDimitry Andric           addType(SPDie, DefinitionArgs[0]);
12325ffd83dbSDimitry Andric 
12330b57cec5SDimitry Andric       DeclDie = getDIE(SPDecl);
12340b57cec5SDimitry Andric       assert(DeclDie && "This DIE should've already been constructed when the "
12350b57cec5SDimitry Andric                         "definition DIE was created in "
12360b57cec5SDimitry Andric                         "getOrCreateSubprogramDIE");
12370b57cec5SDimitry Andric       // Look at the Decl's linkage name only if we emitted it.
12380b57cec5SDimitry Andric       if (DD->useAllLinkageNames())
12390b57cec5SDimitry Andric         DeclLinkageName = SPDecl->getLinkageName();
12400b57cec5SDimitry Andric       unsigned DeclID = getOrCreateSourceID(SPDecl->getFile());
12410b57cec5SDimitry Andric       unsigned DefID = getOrCreateSourceID(SP->getFile());
12420b57cec5SDimitry Andric       if (DeclID != DefID)
1243bdd1243dSDimitry Andric         addUInt(SPDie, dwarf::DW_AT_decl_file, std::nullopt, DefID);
12440b57cec5SDimitry Andric 
12450b57cec5SDimitry Andric       if (SP->getLine() != SPDecl->getLine())
1246bdd1243dSDimitry Andric         addUInt(SPDie, dwarf::DW_AT_decl_line, std::nullopt, SP->getLine());
12470b57cec5SDimitry Andric     }
1248fe6060f1SDimitry Andric   }
12490b57cec5SDimitry Andric 
12500b57cec5SDimitry Andric   // Add function template parameters.
12510b57cec5SDimitry Andric   addTemplateParams(SPDie, SP->getTemplateParams());
12520b57cec5SDimitry Andric 
12530b57cec5SDimitry Andric   // Add the linkage name if we have one and it isn't in the Decl.
12540b57cec5SDimitry Andric   StringRef LinkageName = SP->getLinkageName();
12550b57cec5SDimitry Andric   assert(((LinkageName.empty() || DeclLinkageName.empty()) ||
12560b57cec5SDimitry Andric           LinkageName == DeclLinkageName) &&
12570b57cec5SDimitry Andric          "decl has a linkage name and it is different");
12580b57cec5SDimitry Andric   if (DeclLinkageName.empty() &&
12590b57cec5SDimitry Andric       // Always emit it for abstract subprograms.
126006c3fb27SDimitry Andric       (DD->useAllLinkageNames() || DU->getAbstractScopeDIEs().lookup(SP)))
12610b57cec5SDimitry Andric     addLinkageName(SPDie, LinkageName);
12620b57cec5SDimitry Andric 
12630b57cec5SDimitry Andric   if (!DeclDie)
12640b57cec5SDimitry Andric     return false;
12650b57cec5SDimitry Andric 
12660b57cec5SDimitry Andric   // Refer to the function declaration where all the other attributes will be
12670b57cec5SDimitry Andric   // found.
12680b57cec5SDimitry Andric   addDIEEntry(SPDie, dwarf::DW_AT_specification, *DeclDie);
12690b57cec5SDimitry Andric   return true;
12700b57cec5SDimitry Andric }
12710b57cec5SDimitry Andric 
12720b57cec5SDimitry Andric void DwarfUnit::applySubprogramAttributes(const DISubprogram *SP, DIE &SPDie,
12730b57cec5SDimitry Andric                                           bool SkipSPAttributes) {
12740b57cec5SDimitry Andric   // If -fdebug-info-for-profiling is enabled, need to emit the subprogram
12750b57cec5SDimitry Andric   // and its source location.
12760b57cec5SDimitry Andric   bool SkipSPSourceLocation = SkipSPAttributes &&
12770b57cec5SDimitry Andric                               !CUNode->getDebugInfoForProfiling();
12780b57cec5SDimitry Andric   if (!SkipSPSourceLocation)
1279fe6060f1SDimitry Andric     if (applySubprogramDefinitionAttributes(SP, SPDie, SkipSPAttributes))
12800b57cec5SDimitry Andric       return;
12810b57cec5SDimitry Andric 
12820b57cec5SDimitry Andric   // Constructors and operators for anonymous aggregates do not have names.
12830b57cec5SDimitry Andric   if (!SP->getName().empty())
12840b57cec5SDimitry Andric     addString(SPDie, dwarf::DW_AT_name, SP->getName());
12850b57cec5SDimitry Andric 
1286349cc55cSDimitry Andric   addAnnotation(SPDie, SP->getAnnotations());
1287349cc55cSDimitry Andric 
12880b57cec5SDimitry Andric   if (!SkipSPSourceLocation)
12890b57cec5SDimitry Andric     addSourceLine(SPDie, SP);
12900b57cec5SDimitry Andric 
12910b57cec5SDimitry Andric   // Skip the rest of the attributes under -gmlt to save space.
12920b57cec5SDimitry Andric   if (SkipSPAttributes)
12930b57cec5SDimitry Andric     return;
12940b57cec5SDimitry Andric 
12950b57cec5SDimitry Andric   // Add the prototype if we have a prototype and we have a C like
12960b57cec5SDimitry Andric   // language.
1297bdd1243dSDimitry Andric   if (SP->isPrototyped() && dwarf::isC((dwarf::SourceLanguage)getLanguage()))
12980b57cec5SDimitry Andric     addFlag(SPDie, dwarf::DW_AT_prototyped);
12990b57cec5SDimitry Andric 
1300480093f4SDimitry Andric   if (SP->isObjCDirect())
1301480093f4SDimitry Andric     addFlag(SPDie, dwarf::DW_AT_APPLE_objc_direct);
1302480093f4SDimitry Andric 
13030b57cec5SDimitry Andric   unsigned CC = 0;
13040b57cec5SDimitry Andric   DITypeRefArray Args;
13050b57cec5SDimitry Andric   if (const DISubroutineType *SPTy = SP->getType()) {
13060b57cec5SDimitry Andric     Args = SPTy->getTypeArray();
13070b57cec5SDimitry Andric     CC = SPTy->getCC();
13080b57cec5SDimitry Andric   }
13090b57cec5SDimitry Andric 
13100b57cec5SDimitry Andric   // Add a DW_AT_calling_convention if this has an explicit convention.
13110b57cec5SDimitry Andric   if (CC && CC != dwarf::DW_CC_normal)
13120b57cec5SDimitry Andric     addUInt(SPDie, dwarf::DW_AT_calling_convention, dwarf::DW_FORM_data1, CC);
13130b57cec5SDimitry Andric 
13140b57cec5SDimitry Andric   // Add a return type. If this is a type like a C/C++ void type we don't add a
13150b57cec5SDimitry Andric   // return type.
13160b57cec5SDimitry Andric   if (Args.size())
13170b57cec5SDimitry Andric     if (auto Ty = Args[0])
13180b57cec5SDimitry Andric       addType(SPDie, Ty);
13190b57cec5SDimitry Andric 
13200b57cec5SDimitry Andric   unsigned VK = SP->getVirtuality();
13210b57cec5SDimitry Andric   if (VK) {
13220b57cec5SDimitry Andric     addUInt(SPDie, dwarf::DW_AT_virtuality, dwarf::DW_FORM_data1, VK);
13230b57cec5SDimitry Andric     if (SP->getVirtualIndex() != -1u) {
13240b57cec5SDimitry Andric       DIELoc *Block = getDIELoc();
13250b57cec5SDimitry Andric       addUInt(*Block, dwarf::DW_FORM_data1, dwarf::DW_OP_constu);
13260b57cec5SDimitry Andric       addUInt(*Block, dwarf::DW_FORM_udata, SP->getVirtualIndex());
13270b57cec5SDimitry Andric       addBlock(SPDie, dwarf::DW_AT_vtable_elem_location, Block);
13280b57cec5SDimitry Andric     }
13290b57cec5SDimitry Andric     ContainingTypeMap.insert(std::make_pair(&SPDie, SP->getContainingType()));
13300b57cec5SDimitry Andric   }
13310b57cec5SDimitry Andric 
13320b57cec5SDimitry Andric   if (!SP->isDefinition()) {
13330b57cec5SDimitry Andric     addFlag(SPDie, dwarf::DW_AT_declaration);
13340b57cec5SDimitry Andric 
13350b57cec5SDimitry Andric     // Add arguments. Do not add arguments for subprogram definition. They will
13360b57cec5SDimitry Andric     // be handled while processing variables.
13370b57cec5SDimitry Andric     constructSubprogramArguments(SPDie, Args);
13380b57cec5SDimitry Andric   }
13390b57cec5SDimitry Andric 
13400b57cec5SDimitry Andric   addThrownTypes(SPDie, SP->getThrownTypes());
13410b57cec5SDimitry Andric 
13420b57cec5SDimitry Andric   if (SP->isArtificial())
13430b57cec5SDimitry Andric     addFlag(SPDie, dwarf::DW_AT_artificial);
13440b57cec5SDimitry Andric 
13450b57cec5SDimitry Andric   if (!SP->isLocalToUnit())
13460b57cec5SDimitry Andric     addFlag(SPDie, dwarf::DW_AT_external);
13470b57cec5SDimitry Andric 
13480b57cec5SDimitry Andric   if (DD->useAppleExtensionAttributes()) {
13490b57cec5SDimitry Andric     if (SP->isOptimized())
13500b57cec5SDimitry Andric       addFlag(SPDie, dwarf::DW_AT_APPLE_optimized);
13510b57cec5SDimitry Andric 
13520b57cec5SDimitry Andric     if (unsigned isa = Asm->getISAEncoding())
13530b57cec5SDimitry Andric       addUInt(SPDie, dwarf::DW_AT_APPLE_isa, dwarf::DW_FORM_flag, isa);
13540b57cec5SDimitry Andric   }
13550b57cec5SDimitry Andric 
13560b57cec5SDimitry Andric   if (SP->isLValueReference())
13570b57cec5SDimitry Andric     addFlag(SPDie, dwarf::DW_AT_reference);
13580b57cec5SDimitry Andric 
13590b57cec5SDimitry Andric   if (SP->isRValueReference())
13600b57cec5SDimitry Andric     addFlag(SPDie, dwarf::DW_AT_rvalue_reference);
13610b57cec5SDimitry Andric 
13620b57cec5SDimitry Andric   if (SP->isNoReturn())
13630b57cec5SDimitry Andric     addFlag(SPDie, dwarf::DW_AT_noreturn);
13640b57cec5SDimitry Andric 
13650eae32dcSDimitry Andric   addAccess(SPDie, SP->getFlags());
13660b57cec5SDimitry Andric 
13670b57cec5SDimitry Andric   if (SP->isExplicit())
13680b57cec5SDimitry Andric     addFlag(SPDie, dwarf::DW_AT_explicit);
13690b57cec5SDimitry Andric 
13700b57cec5SDimitry Andric   if (SP->isMainSubprogram())
13710b57cec5SDimitry Andric     addFlag(SPDie, dwarf::DW_AT_main_subprogram);
13720b57cec5SDimitry Andric   if (SP->isPure())
13730b57cec5SDimitry Andric     addFlag(SPDie, dwarf::DW_AT_pure);
13740b57cec5SDimitry Andric   if (SP->isElemental())
13750b57cec5SDimitry Andric     addFlag(SPDie, dwarf::DW_AT_elemental);
13760b57cec5SDimitry Andric   if (SP->isRecursive())
13770b57cec5SDimitry Andric     addFlag(SPDie, dwarf::DW_AT_recursive);
1378480093f4SDimitry Andric 
137981ad6265SDimitry Andric   if (!SP->getTargetFuncName().empty())
138081ad6265SDimitry Andric     addString(SPDie, dwarf::DW_AT_trampoline, SP->getTargetFuncName());
138181ad6265SDimitry Andric 
1382480093f4SDimitry Andric   if (DD->getDwarfVersion() >= 5 && SP->isDeleted())
1383480093f4SDimitry Andric     addFlag(SPDie, dwarf::DW_AT_deleted);
13840b57cec5SDimitry Andric }
13850b57cec5SDimitry Andric 
13860b57cec5SDimitry Andric void DwarfUnit::constructSubrangeDIE(DIE &Buffer, const DISubrange *SR,
13870b57cec5SDimitry Andric                                      DIE *IndexTy) {
13880b57cec5SDimitry Andric   DIE &DW_Subrange = createAndAddDIE(dwarf::DW_TAG_subrange_type, Buffer);
13890b57cec5SDimitry Andric   addDIEEntry(DW_Subrange, dwarf::DW_AT_type, *IndexTy);
13900b57cec5SDimitry Andric 
13910b57cec5SDimitry Andric   // The LowerBound value defines the lower bounds which is typically zero for
13920b57cec5SDimitry Andric   // C/C++. The Count value is the number of elements.  Values are 64 bit. If
13930b57cec5SDimitry Andric   // Count == -1 then the array is unbounded and we do not emit
13940b57cec5SDimitry Andric   // DW_AT_lower_bound and DW_AT_count attributes.
13950b57cec5SDimitry Andric   int64_t DefaultLowerBound = getDefaultLowerBound();
13960b57cec5SDimitry Andric 
1397e8d8bef9SDimitry Andric   auto AddBoundTypeEntry = [&](dwarf::Attribute Attr,
13985ffd83dbSDimitry Andric                                DISubrange::BoundType Bound) -> void {
139906c3fb27SDimitry Andric     if (auto *BV = dyn_cast_if_present<DIVariable *>(Bound)) {
14005ffd83dbSDimitry Andric       if (auto *VarDIE = getDIE(BV))
14015ffd83dbSDimitry Andric         addDIEEntry(DW_Subrange, Attr, *VarDIE);
140206c3fb27SDimitry Andric     } else if (auto *BE = dyn_cast_if_present<DIExpression *>(Bound)) {
14035ffd83dbSDimitry Andric       DIELoc *Loc = new (DIEValueAllocator) DIELoc;
14045ffd83dbSDimitry Andric       DIEDwarfExpression DwarfExpr(*Asm, getCU(), *Loc);
14055ffd83dbSDimitry Andric       DwarfExpr.setMemoryLocationKind();
14065ffd83dbSDimitry Andric       DwarfExpr.addExpression(BE);
14075ffd83dbSDimitry Andric       addBlock(DW_Subrange, Attr, DwarfExpr.finalize());
140806c3fb27SDimitry Andric     } else if (auto *BI = dyn_cast_if_present<ConstantInt *>(Bound)) {
1409fe6060f1SDimitry Andric       if (Attr == dwarf::DW_AT_count) {
1410fe6060f1SDimitry Andric         if (BI->getSExtValue() != -1)
1411bdd1243dSDimitry Andric           addUInt(DW_Subrange, Attr, std::nullopt, BI->getSExtValue());
1412fe6060f1SDimitry Andric       } else if (Attr != dwarf::DW_AT_lower_bound || DefaultLowerBound == -1 ||
14135ffd83dbSDimitry Andric                  BI->getSExtValue() != DefaultLowerBound)
14145ffd83dbSDimitry Andric         addSInt(DW_Subrange, Attr, dwarf::DW_FORM_sdata, BI->getSExtValue());
14155ffd83dbSDimitry Andric     }
14165ffd83dbSDimitry Andric   };
14175ffd83dbSDimitry Andric 
1418e8d8bef9SDimitry Andric   AddBoundTypeEntry(dwarf::DW_AT_lower_bound, SR->getLowerBound());
14190b57cec5SDimitry Andric 
1420fe6060f1SDimitry Andric   AddBoundTypeEntry(dwarf::DW_AT_count, SR->getCount());
14215ffd83dbSDimitry Andric 
1422e8d8bef9SDimitry Andric   AddBoundTypeEntry(dwarf::DW_AT_upper_bound, SR->getUpperBound());
14235ffd83dbSDimitry Andric 
1424e8d8bef9SDimitry Andric   AddBoundTypeEntry(dwarf::DW_AT_byte_stride, SR->getStride());
1425e8d8bef9SDimitry Andric }
1426e8d8bef9SDimitry Andric 
1427e8d8bef9SDimitry Andric void DwarfUnit::constructGenericSubrangeDIE(DIE &Buffer,
1428e8d8bef9SDimitry Andric                                             const DIGenericSubrange *GSR,
1429e8d8bef9SDimitry Andric                                             DIE *IndexTy) {
1430e8d8bef9SDimitry Andric   DIE &DwGenericSubrange =
1431e8d8bef9SDimitry Andric       createAndAddDIE(dwarf::DW_TAG_generic_subrange, Buffer);
1432e8d8bef9SDimitry Andric   addDIEEntry(DwGenericSubrange, dwarf::DW_AT_type, *IndexTy);
1433e8d8bef9SDimitry Andric 
1434e8d8bef9SDimitry Andric   int64_t DefaultLowerBound = getDefaultLowerBound();
1435e8d8bef9SDimitry Andric 
1436e8d8bef9SDimitry Andric   auto AddBoundTypeEntry = [&](dwarf::Attribute Attr,
1437e8d8bef9SDimitry Andric                                DIGenericSubrange::BoundType Bound) -> void {
143806c3fb27SDimitry Andric     if (auto *BV = dyn_cast_if_present<DIVariable *>(Bound)) {
1439e8d8bef9SDimitry Andric       if (auto *VarDIE = getDIE(BV))
1440e8d8bef9SDimitry Andric         addDIEEntry(DwGenericSubrange, Attr, *VarDIE);
144106c3fb27SDimitry Andric     } else if (auto *BE = dyn_cast_if_present<DIExpression *>(Bound)) {
1442fe6060f1SDimitry Andric       if (BE->isConstant() &&
1443fe6060f1SDimitry Andric           DIExpression::SignedOrUnsignedConstant::SignedConstant ==
1444fe6060f1SDimitry Andric               *BE->isConstant()) {
1445e8d8bef9SDimitry Andric         if (Attr != dwarf::DW_AT_lower_bound || DefaultLowerBound == -1 ||
1446e8d8bef9SDimitry Andric             static_cast<int64_t>(BE->getElement(1)) != DefaultLowerBound)
1447e8d8bef9SDimitry Andric           addSInt(DwGenericSubrange, Attr, dwarf::DW_FORM_sdata,
1448e8d8bef9SDimitry Andric                   BE->getElement(1));
1449e8d8bef9SDimitry Andric       } else {
1450e8d8bef9SDimitry Andric         DIELoc *Loc = new (DIEValueAllocator) DIELoc;
1451e8d8bef9SDimitry Andric         DIEDwarfExpression DwarfExpr(*Asm, getCU(), *Loc);
1452e8d8bef9SDimitry Andric         DwarfExpr.setMemoryLocationKind();
1453e8d8bef9SDimitry Andric         DwarfExpr.addExpression(BE);
1454e8d8bef9SDimitry Andric         addBlock(DwGenericSubrange, Attr, DwarfExpr.finalize());
1455e8d8bef9SDimitry Andric       }
1456e8d8bef9SDimitry Andric     }
1457e8d8bef9SDimitry Andric   };
1458e8d8bef9SDimitry Andric 
1459e8d8bef9SDimitry Andric   AddBoundTypeEntry(dwarf::DW_AT_lower_bound, GSR->getLowerBound());
1460e8d8bef9SDimitry Andric   AddBoundTypeEntry(dwarf::DW_AT_count, GSR->getCount());
1461e8d8bef9SDimitry Andric   AddBoundTypeEntry(dwarf::DW_AT_upper_bound, GSR->getUpperBound());
1462e8d8bef9SDimitry Andric   AddBoundTypeEntry(dwarf::DW_AT_byte_stride, GSR->getStride());
14630b57cec5SDimitry Andric }
14640b57cec5SDimitry Andric 
14650b57cec5SDimitry Andric DIE *DwarfUnit::getIndexTyDie() {
14660b57cec5SDimitry Andric   if (IndexTyDie)
14670b57cec5SDimitry Andric     return IndexTyDie;
14680b57cec5SDimitry Andric   // Construct an integer type to use for indexes.
14690b57cec5SDimitry Andric   IndexTyDie = &createAndAddDIE(dwarf::DW_TAG_base_type, getUnitDie());
14700b57cec5SDimitry Andric   StringRef Name = "__ARRAY_SIZE_TYPE__";
14710b57cec5SDimitry Andric   addString(*IndexTyDie, dwarf::DW_AT_name, Name);
1472bdd1243dSDimitry Andric   addUInt(*IndexTyDie, dwarf::DW_AT_byte_size, std::nullopt, sizeof(int64_t));
14730b57cec5SDimitry Andric   addUInt(*IndexTyDie, dwarf::DW_AT_encoding, dwarf::DW_FORM_data1,
147481ad6265SDimitry Andric           dwarf::getArrayIndexTypeEncoding(
147581ad6265SDimitry Andric               (dwarf::SourceLanguage)getLanguage()));
14765f757f3fSDimitry Andric   DD->addAccelType(*this, CUNode->getNameTableKind(), Name, *IndexTyDie,
14775f757f3fSDimitry Andric                    /*Flags*/ 0);
14780b57cec5SDimitry Andric   return IndexTyDie;
14790b57cec5SDimitry Andric }
14800b57cec5SDimitry Andric 
14810b57cec5SDimitry Andric /// Returns true if the vector's size differs from the sum of sizes of elements
14820b57cec5SDimitry Andric /// the user specified.  This can occur if the vector has been rounded up to
14830b57cec5SDimitry Andric /// fit memory alignment constraints.
14840b57cec5SDimitry Andric static bool hasVectorBeenPadded(const DICompositeType *CTy) {
14850b57cec5SDimitry Andric   assert(CTy && CTy->isVector() && "Composite type is not a vector");
14860b57cec5SDimitry Andric   const uint64_t ActualSize = CTy->getSizeInBits();
14870b57cec5SDimitry Andric 
14880b57cec5SDimitry Andric   // Obtain the size of each element in the vector.
14890b57cec5SDimitry Andric   DIType *BaseTy = CTy->getBaseType();
14900b57cec5SDimitry Andric   assert(BaseTy && "Unknown vector element type.");
14910b57cec5SDimitry Andric   const uint64_t ElementSize = BaseTy->getSizeInBits();
14920b57cec5SDimitry Andric 
14930b57cec5SDimitry Andric   // Locate the number of elements in the vector.
14940b57cec5SDimitry Andric   const DINodeArray Elements = CTy->getElements();
14950b57cec5SDimitry Andric   assert(Elements.size() == 1 &&
14960b57cec5SDimitry Andric          Elements[0]->getTag() == dwarf::DW_TAG_subrange_type &&
14970b57cec5SDimitry Andric          "Invalid vector element array, expected one element of type subrange");
14980b57cec5SDimitry Andric   const auto Subrange = cast<DISubrange>(Elements[0]);
149916d6b3b3SDimitry Andric   const auto NumVecElements =
150016d6b3b3SDimitry Andric       Subrange->getCount()
150106c3fb27SDimitry Andric           ? cast<ConstantInt *>(Subrange->getCount())->getSExtValue()
150216d6b3b3SDimitry Andric           : 0;
15030b57cec5SDimitry Andric 
15040b57cec5SDimitry Andric   // Ensure we found the element count and that the actual size is wide
15050b57cec5SDimitry Andric   // enough to contain the requested size.
15060b57cec5SDimitry Andric   assert(ActualSize >= (NumVecElements * ElementSize) && "Invalid vector size");
15070b57cec5SDimitry Andric   return ActualSize != (NumVecElements * ElementSize);
15080b57cec5SDimitry Andric }
15090b57cec5SDimitry Andric 
15100b57cec5SDimitry Andric void DwarfUnit::constructArrayTypeDIE(DIE &Buffer, const DICompositeType *CTy) {
15110b57cec5SDimitry Andric   if (CTy->isVector()) {
15120b57cec5SDimitry Andric     addFlag(Buffer, dwarf::DW_AT_GNU_vector);
15130b57cec5SDimitry Andric     if (hasVectorBeenPadded(CTy))
1514bdd1243dSDimitry Andric       addUInt(Buffer, dwarf::DW_AT_byte_size, std::nullopt,
15150b57cec5SDimitry Andric               CTy->getSizeInBits() / CHAR_BIT);
15160b57cec5SDimitry Andric   }
15170b57cec5SDimitry Andric 
15185ffd83dbSDimitry Andric   if (DIVariable *Var = CTy->getDataLocation()) {
15195ffd83dbSDimitry Andric     if (auto *VarDIE = getDIE(Var))
15205ffd83dbSDimitry Andric       addDIEEntry(Buffer, dwarf::DW_AT_data_location, *VarDIE);
15215ffd83dbSDimitry Andric   } else if (DIExpression *Expr = CTy->getDataLocationExp()) {
15225ffd83dbSDimitry Andric     DIELoc *Loc = new (DIEValueAllocator) DIELoc;
15235ffd83dbSDimitry Andric     DIEDwarfExpression DwarfExpr(*Asm, getCU(), *Loc);
15245ffd83dbSDimitry Andric     DwarfExpr.setMemoryLocationKind();
15255ffd83dbSDimitry Andric     DwarfExpr.addExpression(Expr);
15265ffd83dbSDimitry Andric     addBlock(Buffer, dwarf::DW_AT_data_location, DwarfExpr.finalize());
15275ffd83dbSDimitry Andric   }
15285ffd83dbSDimitry Andric 
1529e8d8bef9SDimitry Andric   if (DIVariable *Var = CTy->getAssociated()) {
1530e8d8bef9SDimitry Andric     if (auto *VarDIE = getDIE(Var))
1531e8d8bef9SDimitry Andric       addDIEEntry(Buffer, dwarf::DW_AT_associated, *VarDIE);
1532e8d8bef9SDimitry Andric   } else if (DIExpression *Expr = CTy->getAssociatedExp()) {
1533e8d8bef9SDimitry Andric     DIELoc *Loc = new (DIEValueAllocator) DIELoc;
1534e8d8bef9SDimitry Andric     DIEDwarfExpression DwarfExpr(*Asm, getCU(), *Loc);
1535e8d8bef9SDimitry Andric     DwarfExpr.setMemoryLocationKind();
1536e8d8bef9SDimitry Andric     DwarfExpr.addExpression(Expr);
1537e8d8bef9SDimitry Andric     addBlock(Buffer, dwarf::DW_AT_associated, DwarfExpr.finalize());
1538e8d8bef9SDimitry Andric   }
1539e8d8bef9SDimitry Andric 
1540e8d8bef9SDimitry Andric   if (DIVariable *Var = CTy->getAllocated()) {
1541e8d8bef9SDimitry Andric     if (auto *VarDIE = getDIE(Var))
1542e8d8bef9SDimitry Andric       addDIEEntry(Buffer, dwarf::DW_AT_allocated, *VarDIE);
1543e8d8bef9SDimitry Andric   } else if (DIExpression *Expr = CTy->getAllocatedExp()) {
1544e8d8bef9SDimitry Andric     DIELoc *Loc = new (DIEValueAllocator) DIELoc;
1545e8d8bef9SDimitry Andric     DIEDwarfExpression DwarfExpr(*Asm, getCU(), *Loc);
1546e8d8bef9SDimitry Andric     DwarfExpr.setMemoryLocationKind();
1547e8d8bef9SDimitry Andric     DwarfExpr.addExpression(Expr);
1548e8d8bef9SDimitry Andric     addBlock(Buffer, dwarf::DW_AT_allocated, DwarfExpr.finalize());
1549e8d8bef9SDimitry Andric   }
1550e8d8bef9SDimitry Andric 
1551e8d8bef9SDimitry Andric   if (auto *RankConst = CTy->getRankConst()) {
1552e8d8bef9SDimitry Andric     addSInt(Buffer, dwarf::DW_AT_rank, dwarf::DW_FORM_sdata,
1553e8d8bef9SDimitry Andric             RankConst->getSExtValue());
1554e8d8bef9SDimitry Andric   } else if (auto *RankExpr = CTy->getRankExp()) {
1555e8d8bef9SDimitry Andric     DIELoc *Loc = new (DIEValueAllocator) DIELoc;
1556e8d8bef9SDimitry Andric     DIEDwarfExpression DwarfExpr(*Asm, getCU(), *Loc);
1557e8d8bef9SDimitry Andric     DwarfExpr.setMemoryLocationKind();
1558e8d8bef9SDimitry Andric     DwarfExpr.addExpression(RankExpr);
1559e8d8bef9SDimitry Andric     addBlock(Buffer, dwarf::DW_AT_rank, DwarfExpr.finalize());
1560e8d8bef9SDimitry Andric   }
1561e8d8bef9SDimitry Andric 
15620b57cec5SDimitry Andric   // Emit the element type.
15630b57cec5SDimitry Andric   addType(Buffer, CTy->getBaseType());
15640b57cec5SDimitry Andric 
15650b57cec5SDimitry Andric   // Get an anonymous type for index type.
15660b57cec5SDimitry Andric   // FIXME: This type should be passed down from the front end
15670b57cec5SDimitry Andric   // as different languages may have different sizes for indexes.
15680b57cec5SDimitry Andric   DIE *IdxTy = getIndexTyDie();
15690b57cec5SDimitry Andric 
15700b57cec5SDimitry Andric   // Add subranges to array type.
15710b57cec5SDimitry Andric   DINodeArray Elements = CTy->getElements();
1572fe6060f1SDimitry Andric   for (DINode *E : Elements) {
15730b57cec5SDimitry Andric     // FIXME: Should this really be such a loose cast?
1574fe6060f1SDimitry Andric     if (auto *Element = dyn_cast_or_null<DINode>(E)) {
15750b57cec5SDimitry Andric       if (Element->getTag() == dwarf::DW_TAG_subrange_type)
15760b57cec5SDimitry Andric         constructSubrangeDIE(Buffer, cast<DISubrange>(Element), IdxTy);
1577e8d8bef9SDimitry Andric       else if (Element->getTag() == dwarf::DW_TAG_generic_subrange)
1578e8d8bef9SDimitry Andric         constructGenericSubrangeDIE(Buffer, cast<DIGenericSubrange>(Element),
1579e8d8bef9SDimitry Andric                                     IdxTy);
1580e8d8bef9SDimitry Andric     }
15810b57cec5SDimitry Andric   }
15820b57cec5SDimitry Andric }
15830b57cec5SDimitry Andric 
15840b57cec5SDimitry Andric void DwarfUnit::constructEnumTypeDIE(DIE &Buffer, const DICompositeType *CTy) {
15850b57cec5SDimitry Andric   const DIType *DTy = CTy->getBaseType();
1586e8d8bef9SDimitry Andric   bool IsUnsigned = DTy && DD->isUnsignedDIType(DTy);
15870b57cec5SDimitry Andric   if (DTy) {
1588*0fca6ea1SDimitry Andric     if (!Asm->TM.Options.DebugStrictDwarf || DD->getDwarfVersion() >= 3)
15890b57cec5SDimitry Andric       addType(Buffer, DTy);
15900b57cec5SDimitry Andric     if (DD->getDwarfVersion() >= 4 && (CTy->getFlags() & DINode::FlagEnumClass))
15910b57cec5SDimitry Andric       addFlag(Buffer, dwarf::DW_AT_enum_class);
15920b57cec5SDimitry Andric   }
15930b57cec5SDimitry Andric 
15940b57cec5SDimitry Andric   auto *Context = CTy->getScope();
15950b57cec5SDimitry Andric   bool IndexEnumerators = !Context || isa<DICompileUnit>(Context) || isa<DIFile>(Context) ||
15960b57cec5SDimitry Andric       isa<DINamespace>(Context) || isa<DICommonBlock>(Context);
15970b57cec5SDimitry Andric   DINodeArray Elements = CTy->getElements();
15980b57cec5SDimitry Andric 
15990b57cec5SDimitry Andric   // Add enumerators to enumeration type.
1600fe6060f1SDimitry Andric   for (const DINode *E : Elements) {
1601fe6060f1SDimitry Andric     auto *Enum = dyn_cast_or_null<DIEnumerator>(E);
16020b57cec5SDimitry Andric     if (Enum) {
16030b57cec5SDimitry Andric       DIE &Enumerator = createAndAddDIE(dwarf::DW_TAG_enumerator, Buffer);
16040b57cec5SDimitry Andric       StringRef Name = Enum->getName();
16050b57cec5SDimitry Andric       addString(Enumerator, dwarf::DW_AT_name, Name);
16065ffd83dbSDimitry Andric       addConstantValue(Enumerator, Enum->getValue(), IsUnsigned);
16070b57cec5SDimitry Andric       if (IndexEnumerators)
16080b57cec5SDimitry Andric         addGlobalName(Name, Enumerator, Context);
16090b57cec5SDimitry Andric     }
16100b57cec5SDimitry Andric   }
16110b57cec5SDimitry Andric }
16120b57cec5SDimitry Andric 
16130b57cec5SDimitry Andric void DwarfUnit::constructContainingTypeDIEs() {
1614fe6060f1SDimitry Andric   for (auto &P : ContainingTypeMap) {
1615fe6060f1SDimitry Andric     DIE &SPDie = *P.first;
1616fe6060f1SDimitry Andric     const DINode *D = P.second;
16170b57cec5SDimitry Andric     if (!D)
16180b57cec5SDimitry Andric       continue;
16190b57cec5SDimitry Andric     DIE *NDie = getDIE(D);
16200b57cec5SDimitry Andric     if (!NDie)
16210b57cec5SDimitry Andric       continue;
16220b57cec5SDimitry Andric     addDIEEntry(SPDie, dwarf::DW_AT_containing_type, *NDie);
16230b57cec5SDimitry Andric   }
16240b57cec5SDimitry Andric }
16250b57cec5SDimitry Andric 
16260b57cec5SDimitry Andric DIE &DwarfUnit::constructMemberDIE(DIE &Buffer, const DIDerivedType *DT) {
16270b57cec5SDimitry Andric   DIE &MemberDie = createAndAddDIE(DT->getTag(), Buffer);
16280b57cec5SDimitry Andric   StringRef Name = DT->getName();
16290b57cec5SDimitry Andric   if (!Name.empty())
16300b57cec5SDimitry Andric     addString(MemberDie, dwarf::DW_AT_name, Name);
16310b57cec5SDimitry Andric 
1632349cc55cSDimitry Andric   addAnnotation(MemberDie, DT->getAnnotations());
1633349cc55cSDimitry Andric 
16340b57cec5SDimitry Andric   if (DIType *Resolved = DT->getBaseType())
16350b57cec5SDimitry Andric     addType(MemberDie, Resolved);
16360b57cec5SDimitry Andric 
16370b57cec5SDimitry Andric   addSourceLine(MemberDie, DT);
16380b57cec5SDimitry Andric 
16390b57cec5SDimitry Andric   if (DT->getTag() == dwarf::DW_TAG_inheritance && DT->isVirtual()) {
16400b57cec5SDimitry Andric 
16410b57cec5SDimitry Andric     // For C++, virtual base classes are not at fixed offset. Use following
16420b57cec5SDimitry Andric     // expression to extract appropriate offset from vtable.
16430b57cec5SDimitry Andric     // BaseAddr = ObAddr + *((*ObAddr) - Offset)
16440b57cec5SDimitry Andric 
16450b57cec5SDimitry Andric     DIELoc *VBaseLocationDie = new (DIEValueAllocator) DIELoc;
16460b57cec5SDimitry Andric     addUInt(*VBaseLocationDie, dwarf::DW_FORM_data1, dwarf::DW_OP_dup);
16470b57cec5SDimitry Andric     addUInt(*VBaseLocationDie, dwarf::DW_FORM_data1, dwarf::DW_OP_deref);
16480b57cec5SDimitry Andric     addUInt(*VBaseLocationDie, dwarf::DW_FORM_data1, dwarf::DW_OP_constu);
16490b57cec5SDimitry Andric     addUInt(*VBaseLocationDie, dwarf::DW_FORM_udata, DT->getOffsetInBits());
16500b57cec5SDimitry Andric     addUInt(*VBaseLocationDie, dwarf::DW_FORM_data1, dwarf::DW_OP_minus);
16510b57cec5SDimitry Andric     addUInt(*VBaseLocationDie, dwarf::DW_FORM_data1, dwarf::DW_OP_deref);
16520b57cec5SDimitry Andric     addUInt(*VBaseLocationDie, dwarf::DW_FORM_data1, dwarf::DW_OP_plus);
16530b57cec5SDimitry Andric 
16540b57cec5SDimitry Andric     addBlock(MemberDie, dwarf::DW_AT_data_member_location, VBaseLocationDie);
16550b57cec5SDimitry Andric   } else {
16560b57cec5SDimitry Andric     uint64_t Size = DT->getSizeInBits();
16570b57cec5SDimitry Andric     uint64_t FieldSize = DD->getBaseTypeSize(DT);
16580b57cec5SDimitry Andric     uint32_t AlignInBytes = DT->getAlignInBytes();
16590b57cec5SDimitry Andric     uint64_t OffsetInBytes;
16600b57cec5SDimitry Andric 
1661bdd1243dSDimitry Andric     bool IsBitfield = DT->isBitField();
16620b57cec5SDimitry Andric     if (IsBitfield) {
16630b57cec5SDimitry Andric       // Handle bitfield, assume bytes are 8 bits.
16640b57cec5SDimitry Andric       if (DD->useDWARF2Bitfields())
1665bdd1243dSDimitry Andric         addUInt(MemberDie, dwarf::DW_AT_byte_size, std::nullopt, FieldSize / 8);
1666bdd1243dSDimitry Andric       addUInt(MemberDie, dwarf::DW_AT_bit_size, std::nullopt, Size);
16670b57cec5SDimitry Andric 
1668*0fca6ea1SDimitry Andric       assert(DT->getOffsetInBits() <=
1669*0fca6ea1SDimitry Andric              (uint64_t)std::numeric_limits<int64_t>::max());
1670*0fca6ea1SDimitry Andric       int64_t Offset = DT->getOffsetInBits();
16710b57cec5SDimitry Andric       // We can't use DT->getAlignInBits() here: AlignInBits for member type
16720b57cec5SDimitry Andric       // is non-zero if and only if alignment was forced (e.g. _Alignas()),
16730b57cec5SDimitry Andric       // which can't be done with bitfields. Thus we use FieldSize here.
16740b57cec5SDimitry Andric       uint32_t AlignInBits = FieldSize;
16750b57cec5SDimitry Andric       uint32_t AlignMask = ~(AlignInBits - 1);
16760b57cec5SDimitry Andric       // The bits from the start of the storage unit to the start of the field.
16770b57cec5SDimitry Andric       uint64_t StartBitOffset = Offset - (Offset & AlignMask);
16780b57cec5SDimitry Andric       // The byte offset of the field's aligned storage unit inside the struct.
16790b57cec5SDimitry Andric       OffsetInBytes = (Offset - StartBitOffset) / 8;
16800b57cec5SDimitry Andric 
16810b57cec5SDimitry Andric       if (DD->useDWARF2Bitfields()) {
16820b57cec5SDimitry Andric         uint64_t HiMark = (Offset + FieldSize) & AlignMask;
16830b57cec5SDimitry Andric         uint64_t FieldOffset = (HiMark - FieldSize);
16840b57cec5SDimitry Andric         Offset -= FieldOffset;
16850b57cec5SDimitry Andric 
16860b57cec5SDimitry Andric         // Maybe we need to work from the other end.
16870b57cec5SDimitry Andric         if (Asm->getDataLayout().isLittleEndian())
16880b57cec5SDimitry Andric           Offset = FieldSize - (Offset + Size);
16890b57cec5SDimitry Andric 
1690*0fca6ea1SDimitry Andric         if (Offset < 0)
1691*0fca6ea1SDimitry Andric           addSInt(MemberDie, dwarf::DW_AT_bit_offset, dwarf::DW_FORM_sdata,
1692*0fca6ea1SDimitry Andric                   Offset);
1693*0fca6ea1SDimitry Andric         else
1694*0fca6ea1SDimitry Andric           addUInt(MemberDie, dwarf::DW_AT_bit_offset, std::nullopt,
1695*0fca6ea1SDimitry Andric                   (uint64_t)Offset);
16960b57cec5SDimitry Andric         OffsetInBytes = FieldOffset >> 3;
16970b57cec5SDimitry Andric       } else {
1698bdd1243dSDimitry Andric         addUInt(MemberDie, dwarf::DW_AT_data_bit_offset, std::nullopt, Offset);
16990b57cec5SDimitry Andric       }
17000b57cec5SDimitry Andric     } else {
17010b57cec5SDimitry Andric       // This is not a bitfield.
17020b57cec5SDimitry Andric       OffsetInBytes = DT->getOffsetInBits() / 8;
17030b57cec5SDimitry Andric       if (AlignInBytes)
17040b57cec5SDimitry Andric         addUInt(MemberDie, dwarf::DW_AT_alignment, dwarf::DW_FORM_udata,
17050b57cec5SDimitry Andric                 AlignInBytes);
17060b57cec5SDimitry Andric     }
17070b57cec5SDimitry Andric 
17080b57cec5SDimitry Andric     if (DD->getDwarfVersion() <= 2) {
17090b57cec5SDimitry Andric       DIELoc *MemLocationDie = new (DIEValueAllocator) DIELoc;
17100b57cec5SDimitry Andric       addUInt(*MemLocationDie, dwarf::DW_FORM_data1, dwarf::DW_OP_plus_uconst);
17110b57cec5SDimitry Andric       addUInt(*MemLocationDie, dwarf::DW_FORM_udata, OffsetInBytes);
17120b57cec5SDimitry Andric       addBlock(MemberDie, dwarf::DW_AT_data_member_location, MemLocationDie);
1713fe6060f1SDimitry Andric     } else if (!IsBitfield || DD->useDWARF2Bitfields()) {
1714fe6060f1SDimitry Andric       // In DWARF v3, DW_FORM_data4/8 in DW_AT_data_member_location are
1715fe6060f1SDimitry Andric       // interpreted as location-list pointers. Interpreting constants as
1716fe6060f1SDimitry Andric       // pointers is not expected, so we use DW_FORM_udata to encode the
1717fe6060f1SDimitry Andric       // constants here.
1718fe6060f1SDimitry Andric       if (DD->getDwarfVersion() == 3)
1719fe6060f1SDimitry Andric         addUInt(MemberDie, dwarf::DW_AT_data_member_location,
1720fe6060f1SDimitry Andric                 dwarf::DW_FORM_udata, OffsetInBytes);
1721fe6060f1SDimitry Andric       else
1722bdd1243dSDimitry Andric         addUInt(MemberDie, dwarf::DW_AT_data_member_location, std::nullopt,
17230b57cec5SDimitry Andric                 OffsetInBytes);
17240b57cec5SDimitry Andric     }
1725fe6060f1SDimitry Andric   }
17260b57cec5SDimitry Andric 
17270eae32dcSDimitry Andric   addAccess(MemberDie, DT->getFlags());
17280eae32dcSDimitry Andric 
17290b57cec5SDimitry Andric   if (DT->isVirtual())
17300b57cec5SDimitry Andric     addUInt(MemberDie, dwarf::DW_AT_virtuality, dwarf::DW_FORM_data1,
17310b57cec5SDimitry Andric             dwarf::DW_VIRTUALITY_virtual);
17320b57cec5SDimitry Andric 
17330b57cec5SDimitry Andric   // Objective-C properties.
17340b57cec5SDimitry Andric   if (DINode *PNode = DT->getObjCProperty())
17350b57cec5SDimitry Andric     if (DIE *PDie = getDIE(PNode))
1736fe6060f1SDimitry Andric       addAttribute(MemberDie, dwarf::DW_AT_APPLE_property,
17370b57cec5SDimitry Andric                    dwarf::DW_FORM_ref4, DIEEntry(*PDie));
17380b57cec5SDimitry Andric 
17390b57cec5SDimitry Andric   if (DT->isArtificial())
17400b57cec5SDimitry Andric     addFlag(MemberDie, dwarf::DW_AT_artificial);
17410b57cec5SDimitry Andric 
17420b57cec5SDimitry Andric   return MemberDie;
17430b57cec5SDimitry Andric }
17440b57cec5SDimitry Andric 
17450b57cec5SDimitry Andric DIE *DwarfUnit::getOrCreateStaticMemberDIE(const DIDerivedType *DT) {
17460b57cec5SDimitry Andric   if (!DT)
17470b57cec5SDimitry Andric     return nullptr;
17480b57cec5SDimitry Andric 
17490b57cec5SDimitry Andric   // Construct the context before querying for the existence of the DIE in case
17500b57cec5SDimitry Andric   // such construction creates the DIE.
17510b57cec5SDimitry Andric   DIE *ContextDIE = getOrCreateContextDIE(DT->getScope());
17520b57cec5SDimitry Andric   assert(dwarf::isType(ContextDIE->getTag()) &&
17530b57cec5SDimitry Andric          "Static member should belong to a type.");
17540b57cec5SDimitry Andric 
17550b57cec5SDimitry Andric   if (DIE *StaticMemberDIE = getDIE(DT))
17560b57cec5SDimitry Andric     return StaticMemberDIE;
17570b57cec5SDimitry Andric 
17580b57cec5SDimitry Andric   DIE &StaticMemberDIE = createAndAddDIE(DT->getTag(), *ContextDIE, DT);
17590b57cec5SDimitry Andric 
17600b57cec5SDimitry Andric   const DIType *Ty = DT->getBaseType();
17610b57cec5SDimitry Andric 
17620b57cec5SDimitry Andric   addString(StaticMemberDIE, dwarf::DW_AT_name, DT->getName());
17630b57cec5SDimitry Andric   addType(StaticMemberDIE, Ty);
17640b57cec5SDimitry Andric   addSourceLine(StaticMemberDIE, DT);
17650b57cec5SDimitry Andric   addFlag(StaticMemberDIE, dwarf::DW_AT_external);
17660b57cec5SDimitry Andric   addFlag(StaticMemberDIE, dwarf::DW_AT_declaration);
17670b57cec5SDimitry Andric 
17680b57cec5SDimitry Andric   // FIXME: We could omit private if the parent is a class_type, and
17690b57cec5SDimitry Andric   // public if the parent is something else.
17700eae32dcSDimitry Andric   addAccess(StaticMemberDIE, DT->getFlags());
17710b57cec5SDimitry Andric 
17720b57cec5SDimitry Andric   if (const ConstantInt *CI = dyn_cast_or_null<ConstantInt>(DT->getConstant()))
17730b57cec5SDimitry Andric     addConstantValue(StaticMemberDIE, CI, Ty);
17740b57cec5SDimitry Andric   if (const ConstantFP *CFP = dyn_cast_or_null<ConstantFP>(DT->getConstant()))
17750b57cec5SDimitry Andric     addConstantFPValue(StaticMemberDIE, CFP);
17760b57cec5SDimitry Andric 
17770b57cec5SDimitry Andric   if (uint32_t AlignInBytes = DT->getAlignInBytes())
17780b57cec5SDimitry Andric     addUInt(StaticMemberDIE, dwarf::DW_AT_alignment, dwarf::DW_FORM_udata,
17790b57cec5SDimitry Andric             AlignInBytes);
17800b57cec5SDimitry Andric 
17810b57cec5SDimitry Andric   return &StaticMemberDIE;
17820b57cec5SDimitry Andric }
17830b57cec5SDimitry Andric 
17840b57cec5SDimitry Andric void DwarfUnit::emitCommonHeader(bool UseOffsets, dwarf::UnitType UT) {
17850b57cec5SDimitry Andric   // Emit size of content not including length itself
1786fe6060f1SDimitry Andric   if (!DD->useSectionsAsReferences())
1787fe6060f1SDimitry Andric     EndLabel = Asm->emitDwarfUnitLength(
1788fe6060f1SDimitry Andric         isDwoUnit() ? "debug_info_dwo" : "debug_info", "Length of Unit");
1789fe6060f1SDimitry Andric   else
1790e8d8bef9SDimitry Andric     Asm->emitDwarfUnitLength(getHeaderSize() + getUnitDie().getSize(),
1791e8d8bef9SDimitry Andric                              "Length of Unit");
17920b57cec5SDimitry Andric 
17930b57cec5SDimitry Andric   Asm->OutStreamer->AddComment("DWARF version number");
17940b57cec5SDimitry Andric   unsigned Version = DD->getDwarfVersion();
17950b57cec5SDimitry Andric   Asm->emitInt16(Version);
17960b57cec5SDimitry Andric 
17970b57cec5SDimitry Andric   // DWARF v5 reorders the address size and adds a unit type.
17980b57cec5SDimitry Andric   if (Version >= 5) {
17990b57cec5SDimitry Andric     Asm->OutStreamer->AddComment("DWARF Unit Type");
18000b57cec5SDimitry Andric     Asm->emitInt8(UT);
18010b57cec5SDimitry Andric     Asm->OutStreamer->AddComment("Address Size (in bytes)");
18020b57cec5SDimitry Andric     Asm->emitInt8(Asm->MAI->getCodePointerSize());
18030b57cec5SDimitry Andric   }
18040b57cec5SDimitry Andric 
18050b57cec5SDimitry Andric   // We share one abbreviations table across all units so it's always at the
18060b57cec5SDimitry Andric   // start of the section. Use a relocatable offset where needed to ensure
18070b57cec5SDimitry Andric   // linking doesn't invalidate that offset.
18080b57cec5SDimitry Andric   Asm->OutStreamer->AddComment("Offset Into Abbrev. Section");
18090b57cec5SDimitry Andric   const TargetLoweringObjectFile &TLOF = Asm->getObjFileLowering();
18100b57cec5SDimitry Andric   if (UseOffsets)
1811e8d8bef9SDimitry Andric     Asm->emitDwarfLengthOrOffset(0);
18120b57cec5SDimitry Andric   else
18130b57cec5SDimitry Andric     Asm->emitDwarfSymbolReference(
18140b57cec5SDimitry Andric         TLOF.getDwarfAbbrevSection()->getBeginSymbol(), false);
18150b57cec5SDimitry Andric 
18160b57cec5SDimitry Andric   if (Version <= 4) {
18170b57cec5SDimitry Andric     Asm->OutStreamer->AddComment("Address Size (in bytes)");
18180b57cec5SDimitry Andric     Asm->emitInt8(Asm->MAI->getCodePointerSize());
18190b57cec5SDimitry Andric   }
18200b57cec5SDimitry Andric }
18210b57cec5SDimitry Andric 
18220b57cec5SDimitry Andric void DwarfTypeUnit::emitHeader(bool UseOffsets) {
18235f757f3fSDimitry Andric   if (!DD->useSplitDwarf()) {
18245f757f3fSDimitry Andric     LabelBegin = Asm->createTempSymbol("tu_begin");
18255f757f3fSDimitry Andric     Asm->OutStreamer->emitLabel(LabelBegin);
18265f757f3fSDimitry Andric   }
18270b57cec5SDimitry Andric   DwarfUnit::emitCommonHeader(UseOffsets,
18280b57cec5SDimitry Andric                               DD->useSplitDwarf() ? dwarf::DW_UT_split_type
18290b57cec5SDimitry Andric                                                   : dwarf::DW_UT_type);
18300b57cec5SDimitry Andric   Asm->OutStreamer->AddComment("Type Signature");
18315ffd83dbSDimitry Andric   Asm->OutStreamer->emitIntValue(TypeSignature, sizeof(TypeSignature));
18320b57cec5SDimitry Andric   Asm->OutStreamer->AddComment("Type DIE Offset");
18330b57cec5SDimitry Andric   // In a skeleton type unit there is no type DIE so emit a zero offset.
1834e8d8bef9SDimitry Andric   Asm->emitDwarfLengthOrOffset(Ty ? Ty->getOffset() : 0);
18350b57cec5SDimitry Andric }
18360b57cec5SDimitry Andric 
1837fe6060f1SDimitry Andric void DwarfUnit::addSectionDelta(DIE &Die, dwarf::Attribute Attribute,
18380b57cec5SDimitry Andric                                 const MCSymbol *Hi, const MCSymbol *Lo) {
1839fe6060f1SDimitry Andric   addAttribute(Die, Attribute, DD->getDwarfSectionOffsetForm(),
18400b57cec5SDimitry Andric                new (DIEValueAllocator) DIEDelta(Hi, Lo));
18410b57cec5SDimitry Andric }
18420b57cec5SDimitry Andric 
1843fe6060f1SDimitry Andric void DwarfUnit::addSectionLabel(DIE &Die, dwarf::Attribute Attribute,
18440b57cec5SDimitry Andric                                 const MCSymbol *Label, const MCSymbol *Sec) {
1845bdd1243dSDimitry Andric   if (Asm->doesDwarfUseRelocationsAcrossSections())
1846fe6060f1SDimitry Andric     addLabel(Die, Attribute, DD->getDwarfSectionOffsetForm(), Label);
1847fe6060f1SDimitry Andric   else
1848fe6060f1SDimitry Andric     addSectionDelta(Die, Attribute, Label, Sec);
18490b57cec5SDimitry Andric }
18500b57cec5SDimitry Andric 
18510b57cec5SDimitry Andric bool DwarfTypeUnit::isDwoUnit() const {
18520b57cec5SDimitry Andric   // Since there are no skeleton type units, all type units are dwo type units
18530b57cec5SDimitry Andric   // when split DWARF is being used.
18540b57cec5SDimitry Andric   return DD->useSplitDwarf();
18550b57cec5SDimitry Andric }
18560b57cec5SDimitry Andric 
18570b57cec5SDimitry Andric void DwarfTypeUnit::addGlobalName(StringRef Name, const DIE &Die,
18580b57cec5SDimitry Andric                                   const DIScope *Context) {
18590b57cec5SDimitry Andric   getCU().addGlobalNameForTypeUnit(Name, Context);
18600b57cec5SDimitry Andric }
18610b57cec5SDimitry Andric 
1862*0fca6ea1SDimitry Andric void DwarfTypeUnit::addGlobalTypeImpl(const DIType *Ty, const DIE &Die,
18630b57cec5SDimitry Andric                                       const DIScope *Context) {
18640b57cec5SDimitry Andric   getCU().addGlobalTypeUnitType(Ty, Context);
18650b57cec5SDimitry Andric }
18660b57cec5SDimitry Andric 
18670b57cec5SDimitry Andric const MCSymbol *DwarfUnit::getCrossSectionRelativeBaseAddress() const {
1868bdd1243dSDimitry Andric   if (!Asm->doesDwarfUseRelocationsAcrossSections())
18690b57cec5SDimitry Andric     return nullptr;
18700b57cec5SDimitry Andric   if (isDwoUnit())
18710b57cec5SDimitry Andric     return nullptr;
18720b57cec5SDimitry Andric   return getSection()->getBeginSymbol();
18730b57cec5SDimitry Andric }
18740b57cec5SDimitry Andric 
18750b57cec5SDimitry Andric void DwarfUnit::addStringOffsetsStart() {
18760b57cec5SDimitry Andric   const TargetLoweringObjectFile &TLOF = Asm->getObjFileLowering();
18770b57cec5SDimitry Andric   addSectionLabel(getUnitDie(), dwarf::DW_AT_str_offsets_base,
18780b57cec5SDimitry Andric                   DU->getStringOffsetsStartSym(),
18790b57cec5SDimitry Andric                   TLOF.getDwarfStrOffSection()->getBeginSymbol());
18800b57cec5SDimitry Andric }
18810b57cec5SDimitry Andric 
18820b57cec5SDimitry Andric void DwarfUnit::addRnglistsBase() {
18830b57cec5SDimitry Andric   assert(DD->getDwarfVersion() >= 5 &&
18840b57cec5SDimitry Andric          "DW_AT_rnglists_base requires DWARF version 5 or later");
18850b57cec5SDimitry Andric   const TargetLoweringObjectFile &TLOF = Asm->getObjFileLowering();
18860b57cec5SDimitry Andric   addSectionLabel(getUnitDie(), dwarf::DW_AT_rnglists_base,
18870b57cec5SDimitry Andric                   DU->getRnglistsTableBaseSym(),
18880b57cec5SDimitry Andric                   TLOF.getDwarfRnglistsSection()->getBeginSymbol());
18890b57cec5SDimitry Andric }
18900b57cec5SDimitry Andric 
18910b57cec5SDimitry Andric void DwarfTypeUnit::finishNonUnitTypeDIE(DIE& D, const DICompositeType *CTy) {
189281ad6265SDimitry Andric   DD->getAddressPool().resetUsedFlag(true);
18930b57cec5SDimitry Andric }
1894bdd1243dSDimitry Andric 
1895bdd1243dSDimitry Andric bool DwarfUnit::isCompatibleWithVersion(uint16_t Version) const {
1896bdd1243dSDimitry Andric   return !Asm->TM.Options.DebugStrictDwarf || DD->getDwarfVersion() >= Version;
1897bdd1243dSDimitry Andric }
1898