Index: include/llvm/CodeGen/DIE.h =================================================================== --- include/llvm/CodeGen/DIE.h +++ include/llvm/CodeGen/DIE.h @@ -16,6 +16,8 @@ #include "llvm/ADT/FoldingSet.h" #include "llvm/ADT/SmallVector.h" +#include "llvm/ADT/ilist_node.h" +#include "llvm/ADT/ilist.h" #include "llvm/Support/Dwarf.h" #include @@ -26,6 +28,20 @@ class raw_ostream; class DwarfTypeUnit; +class DIE; + +template<> +struct ilist_traits : public ilist_default_traits { + mutable ilist_half_node Sentinel; + + DIE *createSentinel() const; + void destroySentinel(DIE *) const {} + + DIE *provideInitialHead() const { return createSentinel(); } + DIE *ensureHead(DIE*) const { return createSentinel(); } + static void noteHead(DIE*, DIE*) {} +}; + //===--------------------------------------------------------------------===// /// DIEAbbrevData - Dwarf abbreviation data, describes one attribute of a /// Dwarf abbreviation. @@ -54,6 +70,14 @@ /// DIEAbbrev - Dwarf abbreviation, describes the organization of a debug /// information object. class DIEAbbrev : public FoldingSetNode { +public: + // Number of inline elements in the SmallVector containing the + // AbbrevData elements. This needs to be the same as used inside DIE + // for the DIEValue lists so that we do not leak memory (see + // DIE::addValue()). + static const unsigned NumInlineAttributes = 12; + +private: /// Unique number for node. /// unsigned Number; @@ -70,7 +94,7 @@ /// Data - Raw data bytes for abbreviation. /// - SmallVector Data; + SmallVector Data; public: DIEAbbrev(dwarf::Tag T, bool C) : Tag(T), Children(C), Data() {} @@ -108,7 +132,7 @@ /// describes its organization. class DIEValue; -class DIE { +class DIE : public ilist_node { protected: /// Offset - Offset in debug info section. /// @@ -130,13 +154,13 @@ // the object has been added to any child list // (eg: DwarfUnit::constructVariableDIE). These aren't insurmountable, but may // be more convoluted than beneficial. - std::vector> Children; + ilist Children; DIE *Parent; /// Attribute values. /// - SmallVector Values; + SmallVector Values; protected: DIE() @@ -155,7 +179,10 @@ dwarf::Tag getTag() const { return Abbrev.getTag(); } unsigned getOffset() const { return Offset; } unsigned getSize() const { return Size; } - const std::vector> &getChildren() const { + const ilist &getChildren() const { + return Children; + } + ilist &getChildren() { return Children; } const SmallVectorImpl &getValues() const { return Values; } @@ -169,16 +196,24 @@ void setOffset(unsigned O) { Offset = O; } void setSize(unsigned S) { Size = S; } - /// addValue - Add a value and attributes to a DIE. + /// \brief Add a value and attributes to a DIE. /// - void addValue(dwarf::Attribute Attribute, dwarf::Form Form, DIEValue *Value) { + /// \param DIEsToDelete If not null, the DIEs which contain + /// SmallVectors that needed to allocate out-of-line storage for + /// their elements are stored in this list. This allows to allocate + /// everything DIE-related from a BumpPtrAllocator while still + /// keeping track of the DIEs that need their destructors called so + /// that we don't leak their external memory. + void addValue(dwarf::Attribute Attribute, dwarf::Form Form, DIEValue *Value, std::vector *DIEsToDelete = nullptr) { Abbrev.AddAttribute(Attribute, Form); Values.push_back(Value); + if (DIEsToDelete && Values.size() == DIEAbbrev::NumInlineAttributes + 1) + DIEsToDelete->push_back(this); } /// addChild - Add a child to the DIE. /// - void addChild(std::unique_ptr Child) { + void addChild(DIE* Child) { assert(!Child->getParent()); Abbrev.setChildrenFlag(dwarf::DW_CHILDREN_yes); Child->Parent = this; @@ -195,6 +230,11 @@ #endif }; +inline DIE * +ilist_traits::createSentinel() const { + return static_cast(&Sentinel); +} + //===--------------------------------------------------------------------===// /// DIEValue - A debug information entry value. Some of these roughly correlate /// to DWARF attribute classes. Index: lib/CodeGen/AsmPrinter/DIE.cpp =================================================================== --- lib/CodeGen/AsmPrinter/DIE.cpp +++ lib/CodeGen/AsmPrinter/DIE.cpp @@ -178,8 +178,8 @@ } IndentCount -= 2; - for (unsigned j = 0, M = Children.size(); j < M; ++j) { - Children[j]->print(O, IndentCount+4); + for (const auto &Child : Children) { + Child.print(O, IndentCount+4); } if (!isBlock) O << "\n"; Index: lib/CodeGen/AsmPrinter/DIEHash.cpp =================================================================== --- lib/CodeGen/AsmPrinter/DIEHash.cpp +++ lib/CodeGen/AsmPrinter/DIEHash.cpp @@ -466,15 +466,15 @@ for (auto &C : Die.getChildren()) { // 7.27 Step 7 // If C is a nested type entry or a member function entry, ... - if (isType(C->getTag()) || C->getTag() == dwarf::DW_TAG_subprogram) { - StringRef Name = getDIEStringAttr(*C, dwarf::DW_AT_name); + if (isType(C.getTag()) || C.getTag() == dwarf::DW_TAG_subprogram) { + StringRef Name = getDIEStringAttr(C, dwarf::DW_AT_name); // ... and has a DW_AT_name attribute if (!Name.empty()) { - hashNestedType(*C, Name); + hashNestedType(C, Name); continue; } } - computeHash(*C); + computeHash(C); } // Following the last (or if there are no children), append a zero byte. Index: lib/CodeGen/AsmPrinter/DwarfCompileUnit.h =================================================================== --- lib/CodeGen/AsmPrinter/DwarfCompileUnit.h +++ lib/CodeGen/AsmPrinter/DwarfCompileUnit.h @@ -61,7 +61,7 @@ /// \brief Construct a DIE for the given DbgVariable without initializing the /// DbgVariable's DIE reference. - std::unique_ptr constructVariableDIEImpl(const DbgVariable &DV, + DIE *constructVariableDIEImpl(const DbgVariable &DV, bool Abstract); bool isDwoUnit() const override; @@ -119,7 +119,7 @@ DIE &updateSubprogramScopeDIE(DISubprogram SP); void constructScopeDIE(LexicalScope *Scope, - SmallVectorImpl> &FinalChildren); + SmallVectorImpl &FinalChildren); /// \brief A helper function to construct a RangeSpanList for a given /// lexical scope. @@ -131,23 +131,23 @@ const SmallVectorImpl &Ranges); /// \brief This scope represents inlined body of a function. Construct /// DIE to represent this concrete inlined copy of the function. - std::unique_ptr constructInlinedScopeDIE(LexicalScope *Scope); + DIE *constructInlinedScopeDIE(LexicalScope *Scope); /// \brief Construct new DW_TAG_lexical_block for this scope and /// attach DW_AT_low_pc/DW_AT_high_pc labels. - std::unique_ptr constructLexicalScopeDIE(LexicalScope *Scope); + DIE *constructLexicalScopeDIE(LexicalScope *Scope); /// constructVariableDIE - Construct a DIE for the given DbgVariable. - std::unique_ptr constructVariableDIE(DbgVariable &DV, - bool Abstract = false); + DIE *constructVariableDIE(DbgVariable &DV, + bool Abstract = false); - std::unique_ptr constructVariableDIE(DbgVariable &DV, - const LexicalScope &Scope, - DIE *&ObjectPointer); + DIE *constructVariableDIE(DbgVariable &DV, + const LexicalScope &Scope, + DIE *&ObjectPointer); /// A helper function to create children of a Scope DIE. DIE *createScopeChildrenDIE(LexicalScope *Scope, - SmallVectorImpl> &Children, + SmallVectorImpl &Children, unsigned *ChildScopeCount = nullptr); /// \brief Construct a DIE for this subprogram scope. @@ -158,7 +158,7 @@ void constructAbstractSubprogramScopeDIE(LexicalScope *Scope); /// \brief Construct import_module DIE. - std::unique_ptr + DIE * constructImportedEntityDIE(const DIImportedEntity &Module); void finishSubprogramDefinition(DISubprogram SP); @@ -188,7 +188,7 @@ unsigned getLength() { return sizeof(uint32_t) + // Length field - getHeaderSize() + UnitDie.getSize(); + getHeaderSize() + UnitDie->getSize(); } void emitHeader(const MCSymbol *ASectionSym) const override; Index: lib/CodeGen/AsmPrinter/DwarfCompileUnit.cpp =================================================================== --- lib/CodeGen/AsmPrinter/DwarfCompileUnit.cpp +++ lib/CodeGen/AsmPrinter/DwarfCompileUnit.cpp @@ -42,7 +42,7 @@ unsigned idx = DD->getAddressPool().getIndex(Label); DIEValue *Value = new (DIEValueAllocator) DIEInteger(idx); - Die.addValue(Attribute, dwarf::DW_FORM_GNU_addr_index, Value); + Die.addValue(Attribute, dwarf::DW_FORM_GNU_addr_index, Value, &DIEsToDelete); } void DwarfCompileUnit::addLocalLabelAddress(DIE &Die, @@ -53,7 +53,8 @@ Die.addValue(Attribute, dwarf::DW_FORM_addr, Label ? (DIEValue *)new (DIEValueAllocator) DIELabel(Label) - : new (DIEValueAllocator) DIEInteger(0)); + : new (DIEValueAllocator) DIEInteger(0), + &DIEsToDelete); } unsigned DwarfCompileUnit::getOrCreateSourceID(StringRef FileName, @@ -248,21 +249,22 @@ MCSymbol *LineTableStartSym = Asm->OutStreamer.getDwarfLineTableSymbol(getUniqueID()); - stmtListIndex = UnitDie.getValues().size(); + stmtListIndex = UnitDie->getValues().size(); // DW_AT_stmt_list is a offset of line number information for this // compile unit in debug_line section. For split dwarf this is // left in the skeleton CU and so not included. // The line table entries are not always emitted in assembly, so it // is not okay to use line_table_start here. - addSectionLabel(UnitDie, dwarf::DW_AT_stmt_list, LineTableStartSym, + addSectionLabel(*UnitDie, dwarf::DW_AT_stmt_list, LineTableStartSym, DwarfLineSectionSym); } void DwarfCompileUnit::applyStmtList(DIE &D) { D.addValue(dwarf::DW_AT_stmt_list, - UnitDie.getAbbrev().getData()[stmtListIndex].getForm(), - UnitDie.getValues()[stmtListIndex]); + UnitDie->getAbbrev().getData()[stmtListIndex].getForm(), + UnitDie->getValues()[stmtListIndex], + &DIEsToDelete); } void DwarfCompileUnit::attachLowHighPC(DIE &D, const MCSymbol *Begin, @@ -308,7 +310,7 @@ // Construct a DIE for this scope. void DwarfCompileUnit::constructScopeDIE( - LexicalScope *Scope, SmallVectorImpl> &FinalChildren) { + LexicalScope *Scope, SmallVectorImpl &FinalChildren) { if (!Scope || !Scope->getScopeNode()) return; @@ -319,12 +321,12 @@ "constructSubprogramScopeDIE for non-inlined " "subprograms"); - SmallVector, 8> Children; + SmallVector Children; // We try to create the scope DIE first, then the children DIEs. This will // avoid creating un-used children then removing them later when we find out // the scope DIE is null. - std::unique_ptr ScopeDIE; + DIE *ScopeDIE; if (Scope->getParent() && DS.isSubprogram()) { ScopeDIE = constructInlinedScopeDIE(Scope); if (!ScopeDIE) @@ -374,7 +376,7 @@ DIEValue *Value = new (DIEValueAllocator) DIEDelta(Hi, Lo); Die.addValue(Attribute, DD->getDwarfVersion() >= 4 ? dwarf::DW_FORM_sec_offset : dwarf::DW_FORM_data4, - Value); + Value, &DIEsToDelete); } void DwarfCompileUnit::addScopeRangeList(DIE &ScopeDIE, @@ -421,7 +423,7 @@ // This scope represents inlined body of a function. Construct DIE to // represent this concrete inlined copy of the function. -std::unique_ptr +DIE * DwarfCompileUnit::constructInlinedScopeDIE(LexicalScope *Scope) { assert(Scope->getScopeNode()); DIScope DS(Scope->getScopeNode()); @@ -431,7 +433,7 @@ DIE *OriginDIE = DU->getAbstractSPDies()[InlinedSP]; assert(OriginDIE && "Unable to find original DIE for an inlined subprogram."); - auto ScopeDIE = make_unique(dwarf::DW_TAG_inlined_subroutine); + auto ScopeDIE = new (DIEValueAllocator) DIE(dwarf::DW_TAG_inlined_subroutine); addDIEEntry(*ScopeDIE, dwarf::DW_AT_abstract_origin, *OriginDIE); attachRangesOrLowHighPC(*ScopeDIE, Scope->getRanges()); @@ -451,12 +453,12 @@ // Construct new DW_TAG_lexical_block for this scope and attach // DW_AT_low_pc/DW_AT_high_pc labels. -std::unique_ptr +DIE * DwarfCompileUnit::constructLexicalScopeDIE(LexicalScope *Scope) { if (DD->isLexicalScopeDIENull(Scope)) return nullptr; - auto ScopeDIE = make_unique(dwarf::DW_TAG_lexical_block); + auto ScopeDIE = new (DIEValueAllocator) DIE(dwarf::DW_TAG_lexical_block); if (Scope->isAbstractScope()) return ScopeDIE; @@ -466,18 +468,18 @@ } /// constructVariableDIE - Construct a DIE for the given DbgVariable. -std::unique_ptr DwarfCompileUnit::constructVariableDIE(DbgVariable &DV, - bool Abstract) { +DIE *DwarfCompileUnit::constructVariableDIE(DbgVariable &DV, + bool Abstract) { auto D = constructVariableDIEImpl(DV, Abstract); DV.setDIE(*D); return D; } -std::unique_ptr +DIE * DwarfCompileUnit::constructVariableDIEImpl(const DbgVariable &DV, bool Abstract) { // Define variable debug information entry. - auto VariableDie = make_unique(DV.getTag()); + auto *VariableDie = new (DIEValueAllocator) DIE(DV.getTag()); if (Abstract) { applyVariableAttributes(DV, *VariableDie); @@ -529,16 +531,16 @@ return VariableDie; } -std::unique_ptr DwarfCompileUnit::constructVariableDIE( +DIE *DwarfCompileUnit::constructVariableDIE( DbgVariable &DV, const LexicalScope &Scope, DIE *&ObjectPointer) { auto Var = constructVariableDIE(DV, Scope.isAbstractScope()); if (DV.isObjectPointer()) - ObjectPointer = Var.get(); + ObjectPointer = Var; return Var; } DIE *DwarfCompileUnit::createScopeChildrenDIE( - LexicalScope *Scope, SmallVectorImpl> &Children, + LexicalScope *Scope, SmallVectorImpl &Children, unsigned *ChildScopeCount) { DIE *ObjectPointer = nullptr; @@ -583,13 +585,13 @@ if (FnArgs.getNumElements() > 1 && !FnArgs.getElement(FnArgs.getNumElements() - 1) && !includeMinimalInlineScopes()) - ScopeDIE.addChild(make_unique(dwarf::DW_TAG_unspecified_parameters)); + ScopeDIE.addChild(new (DIEValueAllocator) DIE(dwarf::DW_TAG_unspecified_parameters)); } DIE *DwarfCompileUnit::createAndAddScopeChildren(LexicalScope *Scope, DIE &ScopeDIE) { // We create children when the scope DIE is not null. - SmallVector, 8> Children; + SmallVector Children; DIE *ObjectPointer = createScopeChildrenDIE(Scope, Children); // Add children @@ -633,12 +635,12 @@ addDIEEntry(*AbsDef, dwarf::DW_AT_object_pointer, *ObjectPointer); } -std::unique_ptr +DIE * DwarfCompileUnit::constructImportedEntityDIE(const DIImportedEntity &Module) { assert(Module.Verify() && "Use one of the MDNode * overloads to handle invalid metadata"); - std::unique_ptr IMDie = make_unique((dwarf::Tag)Module.getTag()); - insertDIE(Module, IMDie.get()); + DIE *IMDie = new (DIEValueAllocator) DIE((dwarf::Tag)Module.getTag()); + insertDIE(Module, IMDie); DIE *EntityDie; DIDescriptor Entity = resolve(Module.getEntity()); if (Entity.isNameSpace()) @@ -785,7 +787,7 @@ DIEValue *Value = new (DIEValueAllocator) DIELocList(Index); dwarf::Form Form = DD->getDwarfVersion() >= 4 ? dwarf::DW_FORM_sec_offset : dwarf::DW_FORM_data4; - Die.addValue(Attribute, Form, Value); + Die.addValue(Attribute, Form, Value, &DIEsToDelete); } void DwarfCompileUnit::applyVariableAttributes(const DbgVariable &Var, @@ -803,7 +805,7 @@ void DwarfCompileUnit::addExpr(DIELoc &Die, dwarf::Form Form, const MCExpr *Expr) { DIEValue *Value = new (DIEValueAllocator) DIEExpr(Expr); - Die.addValue((dwarf::Attribute)0, Form, Value); + Die.addValue((dwarf::Attribute)0, Form, Value, &DIEsToDelete); } void DwarfCompileUnit::applySubprogramAttributesToDefinition(DISubprogram SP, Index: lib/CodeGen/AsmPrinter/DwarfDebug.cpp =================================================================== --- lib/CodeGen/AsmPrinter/DwarfDebug.cpp +++ lib/CodeGen/AsmPrinter/DwarfDebug.cpp @@ -1431,7 +1431,7 @@ // Emit the DIE children if any. if (Abbrev.hasChildren()) { for (auto &Child : Die.getChildren()) - emitDIE(*Child); + emitDIE(Child); Asm->OutStreamer.AddComment("End Of Children Mark"); Asm->EmitInt8(0); Index: lib/CodeGen/AsmPrinter/DwarfFile.cpp =================================================================== --- lib/CodeGen/AsmPrinter/DwarfFile.cpp +++ lib/CodeGen/AsmPrinter/DwarfFile.cpp @@ -104,14 +104,14 @@ Offset += Values[i]->SizeOf(Asm, AbbrevData[i].getForm()); // Get the children. - const auto &Children = Die.getChildren(); + auto &Children = Die.getChildren(); // Size the DIE children if any. if (!Children.empty()) { assert(Abbrev.hasChildren() && "Children flag not set"); for (auto &Child : Children) - Offset = computeSizeAndOffset(*Child, Offset); + Offset = computeSizeAndOffset(Child, Offset); // End of children marker. Offset += sizeof(int8_t); Index: lib/CodeGen/AsmPrinter/DwarfUnit.h =================================================================== --- lib/CodeGen/AsmPrinter/DwarfUnit.h +++ lib/CodeGen/AsmPrinter/DwarfUnit.h @@ -74,7 +74,7 @@ DICompileUnit CUNode; /// Unit debug information entry. - DIE UnitDie; + DIE *UnitDie; /// Offset of the UnitDie from beginning of debug info section. unsigned DebugInfoOffset; @@ -98,10 +98,10 @@ DenseMap MDNodeToDIEEntryMap; /// DIEBlocks - A list of all the DIEBlocks in use. - std::vector DIEBlocks; + // std::vector DIEBlocks; /// DIELocs - A list of all the DIELocs in use. - std::vector DIELocs; + // std::vector DIELocs; /// ContainingTypeMap - This map is used to keep track of subprogram DIEs that /// need DW_AT_containing_type attribute. This attribute points to a DIE that @@ -110,6 +110,10 @@ // DIEValueAllocator - All DIEValues are allocated through this allocator. BumpPtrAllocator DIEValueAllocator; + // Contains the DIEs that have had more attributes added that their + // inline SmallVector can contain. Their destructor needs to be + // called so that the SmallVector's memory isn't leaked. + std::vector DIEsToDelete; // DIEIntegerOne - A preallocated DIEValue because 1 is used frequently. DIEInteger *DIEIntegerOne; @@ -142,13 +146,13 @@ unsigned getUniqueID() const { return UniqueID; } uint16_t getLanguage() const { return CUNode.getLanguage(); } DICompileUnit getCUNode() const { return CUNode; } - DIE &getUnitDie() { return UnitDie; } + DIE &getUnitDie() { return *UnitDie; } unsigned getDebugInfoOffset() const { return DebugInfoOffset; } void setDebugInfoOffset(unsigned DbgInfoOff) { DebugInfoOffset = DbgInfoOff; } /// hasContent - Return true if this compile unit has something to write out. - bool hasContent() const { return !UnitDie.getChildren().empty(); } + bool hasContent() const { return !UnitDie->getChildren().empty(); } /// getParentContextString - Get a string containing the language specific /// context for a global name. Index: lib/CodeGen/AsmPrinter/DwarfUnit.cpp =================================================================== --- lib/CodeGen/AsmPrinter/DwarfUnit.cpp +++ lib/CodeGen/AsmPrinter/DwarfUnit.cpp @@ -60,10 +60,11 @@ /// Unit - Unit constructor. DwarfUnit::DwarfUnit(unsigned UID, dwarf::Tag UnitTag, DICompileUnit Node, AsmPrinter *A, DwarfDebug *DW, DwarfFile *DWU) - : UniqueID(UID), CUNode(Node), UnitDie(UnitTag), DebugInfoOffset(0), Asm(A), + : UniqueID(UID), CUNode(Node), DebugInfoOffset(0), Asm(A), DD(DW), DU(DWU), IndexTyDie(nullptr), Section(nullptr) { assert(UnitTag == dwarf::DW_TAG_compile_unit || UnitTag == dwarf::DW_TAG_type_unit); + UnitDie = new (DIEValueAllocator) DIE(UnitTag); DIEIntegerOne = new (DIEValueAllocator) DIEInteger(1); } @@ -73,15 +74,21 @@ : DwarfUnit(UID, dwarf::DW_TAG_type_unit, CU.getCUNode(), A, DW, DWU), CU(CU), SplitLineTable(SplitLineTable) { if (SplitLineTable) - addSectionOffset(UnitDie, dwarf::DW_AT_stmt_list, 0); + addSectionOffset(*UnitDie, dwarf::DW_AT_stmt_list, 0); } /// ~Unit - Destructor for compile unit. DwarfUnit::~DwarfUnit() { - for (unsigned j = 0, M = DIEBlocks.size(); j < M; ++j) - DIEBlocks[j]->~DIEBlock(); - for (unsigned j = 0, M = DIELocs.size(); j < M; ++j) - DIELocs[j]->~DIELoc(); + // The BumpPtrAllocator we have used for everything DIE related will + // be destroyed. Free the AbbrevData/DIEValue SmallVectors that have + // grown over their inline size(). + for (unsigned j = 0, M = DIEsToDelete.size(); j < M; ++j) { + // Prevent the list of children from being deleted with the + // DIE. They have been allocated through the BumpPtrAllocator, we + // must not destroy the list elements. + DIEsToDelete[j]->getChildren().clearAndLeakNodesUnsafely(); + DIEsToDelete[j]->~DIE(); + } } /// createDIEEntry - Creates a new DIEEntry to be a proxy for a debug @@ -173,9 +180,10 @@ /// addFlag - Add a flag that is true. void DwarfUnit::addFlag(DIE &Die, dwarf::Attribute Attribute) { if (DD->getDwarfVersion() >= 4) - Die.addValue(Attribute, dwarf::DW_FORM_flag_present, DIEIntegerOne); + Die.addValue(Attribute, dwarf::DW_FORM_flag_present, DIEIntegerOne, + &DIEsToDelete); else - Die.addValue(Attribute, dwarf::DW_FORM_flag, DIEIntegerOne); + Die.addValue(Attribute, dwarf::DW_FORM_flag, DIEIntegerOne, &DIEsToDelete); } /// addUInt - Add an unsigned integer attribute data and value. @@ -186,7 +194,7 @@ Form = DIEInteger::BestForm(false, Integer); DIEValue *Value = Integer == 1 ? DIEIntegerOne : new (DIEValueAllocator) DIEInteger(Integer); - Die.addValue(Attribute, *Form, Value); + Die.addValue(Attribute, *Form, Value, &DIEsToDelete); } void DwarfUnit::addUInt(DIE &Block, dwarf::Form Form, uint64_t Integer) { @@ -200,7 +208,7 @@ if (!Form) Form = DIEInteger::BestForm(true, Integer); DIEValue *Value = new (DIEValueAllocator) DIEInteger(Integer); - Die.addValue(Attribute, *Form, Value); + Die.addValue(Attribute, *Form, Value, &DIEsToDelete); } void DwarfUnit::addSInt(DIELoc &Die, Optional Form, @@ -226,7 +234,7 @@ unsigned idx = DU->getStringPool().getIndex(*Asm, String); DIEValue *Value = new (DIEValueAllocator) DIEInteger(idx); DIEValue *Str = new (DIEValueAllocator) DIEString(Value, String); - Die.addValue(Attribute, dwarf::DW_FORM_GNU_str_index, Str); + Die.addValue(Attribute, dwarf::DW_FORM_GNU_str_index, Str, &DIEsToDelete); } /// addLocalString - Add a string attribute data and value. This is guaranteed @@ -240,7 +248,7 @@ else Value = new (DIEValueAllocator) DIEDelta(Symb, DD->getDebugStrSym()); DIEValue *Str = new (DIEValueAllocator) DIEString(Value, String); - Die.addValue(Attribute, dwarf::DW_FORM_strp, Str); + Die.addValue(Attribute, dwarf::DW_FORM_strp, Str, &DIEsToDelete); } /// addLabel - Add a Dwarf label attribute data and value. @@ -248,7 +256,7 @@ void DwarfUnit::addLabel(DIE &Die, dwarf::Attribute Attribute, dwarf::Form Form, const MCSymbol *Label) { DIEValue *Value = new (DIEValueAllocator) DIELabel(Label); - Die.addValue(Attribute, Form, Value); + Die.addValue(Attribute, Form, Value, &DIEsToDelete); } void DwarfUnit::addLabel(DIELoc &Die, dwarf::Form Form, const MCSymbol *Label) { @@ -287,7 +295,7 @@ void DwarfUnit::addLabelDelta(DIE &Die, dwarf::Attribute Attribute, const MCSymbol *Hi, const MCSymbol *Lo) { DIEValue *Value = new (DIEValueAllocator) DIEDelta(Hi, Lo); - Die.addValue(Attribute, dwarf::DW_FORM_data4, Value); + Die.addValue(Attribute, dwarf::DW_FORM_data4, Value, &DIEsToDelete); } /// addDIEEntry - Add a DIE attribute data and value. @@ -304,7 +312,7 @@ addFlag(Die, dwarf::DW_AT_declaration); Die.addValue(dwarf::DW_AT_signature, dwarf::DW_FORM_ref_sig8, - new (DIEValueAllocator) DIETypeSignature(Type)); + new (DIEValueAllocator) DIETypeSignature(Type), &DIEsToDelete); } void DwarfUnit::addDIEEntry(DIE &Die, dwarf::Attribute Attribute, @@ -318,7 +326,7 @@ EntryCU = &getUnitDie(); Die.addValue(Attribute, EntryCU == DieCU ? dwarf::DW_FORM_ref4 : dwarf::DW_FORM_ref_addr, - Entry); + Entry, &DIEsToDelete); } /// Create a DIE with the given Tag, add the DIE to its parent, and @@ -326,8 +334,8 @@ DIE &DwarfUnit::createAndAddDIE(unsigned Tag, DIE &Parent, DIDescriptor N) { assert(Tag != dwarf::DW_TAG_auto_variable && Tag != dwarf::DW_TAG_arg_variable); - Parent.addChild(make_unique((dwarf::Tag)Tag)); - DIE &Die = *Parent.getChildren().back(); + Parent.addChild(new (DIEValueAllocator) DIE((dwarf::Tag)Tag)); + DIE &Die = Parent.getChildren().back(); if (N) insertDIE(N, &Die); return Die; @@ -337,15 +345,14 @@ /// void DwarfUnit::addBlock(DIE &Die, dwarf::Attribute Attribute, DIELoc *Loc) { Loc->ComputeSize(Asm); - DIELocs.push_back(Loc); // Memoize so we can call the destructor later on. - Die.addValue(Attribute, Loc->BestForm(DD->getDwarfVersion()), Loc); + Die.addValue(Attribute, Loc->BestForm(DD->getDwarfVersion()), Loc, + &DIEsToDelete); } void DwarfUnit::addBlock(DIE &Die, dwarf::Attribute Attribute, DIEBlock *Block) { Block->ComputeSize(Asm); - DIEBlocks.push_back(Block); // Memoize so we can call the destructor later on. - Die.addValue(Attribute, Block->BestForm(), Block); + Die.addValue(Attribute, Block->BestForm(), Block, &DIEsToDelete); } /// addSourceLine - Add location information to specified debug information @@ -526,7 +533,7 @@ // Decode the original location, and use that as the start of the byref // variable's location. - DIELoc *Loc = new (DIEValueAllocator) DIELoc(); + DIELoc *Loc = new DIELoc(); bool validReg; if (Location.isReg()) @@ -647,7 +654,7 @@ /// addConstantFPValue - Add constant value entry in variable DIE. void DwarfUnit::addConstantFPValue(DIE &Die, const MachineOperand &MO) { assert(MO.isFPImm() && "Invalid machine operand!"); - DIEBlock *Block = new (DIEValueAllocator) DIEBlock(); + DIEBlock *Block = new DIEBlock(); APFloat FPImm = MO.getFPImm()->getValueAPF(); // Get the raw data form of the floating point. @@ -706,7 +713,7 @@ return; } - DIEBlock *Block = new (DIEValueAllocator) DIEBlock(); + DIEBlock *Block = new DIEBlock(); // Get the raw data form of the large APInt. const uint64_t *Ptr64 = Val.getRawData(); @@ -1155,7 +1162,7 @@ else if (GlobalValue *GV = mdconst::dyn_extract(Val)) { // For declaration non-type template parameters (such as global values and // functions) - DIELoc *Loc = new (DIEValueAllocator) DIELoc(); + DIELoc *Loc = new DIELoc(); addOpAddress(*Loc, Asm->getSymbol(GV)); // Emit DW_OP_stack_value to use the address as the immediate value of the // parameter, rather than a pointer to it. @@ -1371,7 +1378,7 @@ if (IndexTyDie) return IndexTyDie; // Construct an integer type to use for indexes. - IndexTyDie = &createAndAddDIE(dwarf::DW_TAG_base_type, UnitDie); + IndexTyDie = &createAndAddDIE(dwarf::DW_TAG_base_type, *UnitDie); addString(*IndexTyDie, dwarf::DW_AT_name, "sizetype"); addUInt(*IndexTyDie, dwarf::DW_AT_byte_size, None, sizeof(int64_t)); addUInt(*IndexTyDie, dwarf::DW_AT_encoding, dwarf::DW_FORM_data1, @@ -1458,7 +1465,7 @@ // expression to extract appropriate offset from vtable. // BaseAddr = ObAddr + *((*ObAddr) - Offset) - DIELoc *VBaseLocationDie = new (DIEValueAllocator) DIELoc(); + DIELoc *VBaseLocationDie = new DIELoc(); addUInt(*VBaseLocationDie, dwarf::DW_FORM_data1, dwarf::DW_OP_dup); addUInt(*VBaseLocationDie, dwarf::DW_FORM_data1, dwarf::DW_OP_deref); addUInt(*VBaseLocationDie, dwarf::DW_FORM_data1, dwarf::DW_OP_constu); @@ -1497,7 +1504,7 @@ OffsetInBytes = DT.getOffsetInBits() >> 3; if (DD->getDwarfVersion() <= 2) { - DIELoc *MemLocationDie = new (DIEValueAllocator) DIELoc(); + DIELoc *MemLocationDie = new DIELoc(); addUInt(*MemLocationDie, dwarf::DW_FORM_data1, dwarf::DW_OP_plus_uconst); addUInt(*MemLocationDie, dwarf::DW_FORM_udata, OffsetInBytes); addBlock(MemberDie, dwarf::DW_AT_data_member_location, MemLocationDie); @@ -1524,7 +1531,7 @@ if (MDNode *PNode = DT.getObjCProperty()) if (DIEEntry *PropertyDie = getDIEEntry(PNode)) MemberDie.addValue(dwarf::DW_AT_APPLE_property, dwarf::DW_FORM_ref4, - PropertyDie); + PropertyDie, &DIEsToDelete); if (DT.isArtificial()) addFlag(MemberDie, dwarf::DW_AT_artificial); @@ -1577,7 +1584,7 @@ void DwarfUnit::emitHeader(const MCSymbol *ASectionSym) const { // Emit size of content not including length itself Asm->OutStreamer.AddComment("Length of Unit"); - Asm->EmitInt32(getHeaderSize() + UnitDie.getSize()); + Asm->EmitInt32(getHeaderSize() + UnitDie->getSize()); Asm->OutStreamer.AddComment("DWARF version number"); Asm->EmitInt16(DD->getDwarfVersion()); Index: unittests/CodeGen/DIEHashTest.cpp =================================================================== --- unittests/CodeGen/DIEHashTest.cpp +++ unittests/CodeGen/DIEHashTest.cpp @@ -60,7 +60,7 @@ TEST(DIEHashTest, NamespacedType) { DIE CU(dwarf::DW_TAG_compile_unit); - auto Space = make_unique(dwarf::DW_TAG_namespace); + DIE *Space = new DIE(dwarf::DW_TAG_namespace); DIEInteger One(1); DIEString SpaceStr(&One, "space"); Space->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &SpaceStr); @@ -68,14 +68,14 @@ Space->addValue(dwarf::DW_AT_declaration, dwarf::DW_FORM_flag_present, &One); // sibling? - auto Foo = make_unique(dwarf::DW_TAG_structure_type); + DIE *Foo = new DIE(dwarf::DW_TAG_structure_type); DIEString FooStr(&One, "foo"); Foo->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &FooStr); Foo->addValue(dwarf::DW_AT_byte_size, dwarf::DW_FORM_data1, &One); DIE &N = *Foo; - Space->addChild(std::move(Foo)); - CU.addChild(std::move(Space)); + Space->addChild(Foo); + CU.addChild(Space); uint64_t MD5Res = DIEHash().computeTypeSignature(N); @@ -98,7 +98,7 @@ DIEEntry IntRef(Int); - auto Member = make_unique(dwarf::DW_TAG_member); + DIE *Member = new DIE(dwarf::DW_TAG_member); DIEString MemberStr(&Four, "member"); Member->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &MemberStr); DIEInteger Zero(0); @@ -106,7 +106,7 @@ &Zero); Member->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, &IntRef); - Unnamed.addChild(std::move(Member)); + Unnamed.addChild(Member); uint64_t MD5Res = DIEHash().computeTypeSignature(Unnamed); @@ -129,7 +129,7 @@ DIEEntry IntRef(Int); - auto Mem1 = make_unique(dwarf::DW_TAG_member); + DIE *Mem1 = new DIE(dwarf::DW_TAG_member); DIEString Mem1Str(&Four, "mem1"); Mem1->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &Mem1Str); DIEInteger Zero(0); @@ -137,16 +137,16 @@ &Zero); Mem1->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, &IntRef); - Unnamed.addChild(std::move(Mem1)); + Unnamed.addChild(Mem1); - auto Mem2 = make_unique(dwarf::DW_TAG_member); + DIE *Mem2 = new DIE(dwarf::DW_TAG_member); DIEString Mem2Str(&Four, "mem2"); Mem2->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &Mem2Str); Mem2->addValue(dwarf::DW_AT_data_member_location, dwarf::DW_FORM_data1, &Four); Mem2->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, &IntRef); - Unnamed.addChild(std::move(Mem2)); + Unnamed.addChild(Mem2); uint64_t MD5Res = DIEHash().computeTypeSignature(Unnamed); @@ -161,14 +161,14 @@ DIEString FooStr(&One, "foo"); Foo.addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &FooStr); - auto Mem = make_unique(dwarf::DW_TAG_member); + DIE *Mem = new DIE(dwarf::DW_TAG_member); DIEString MemStr(&One, "mem"); Mem->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &MemStr); DIEEntry FooRef(Foo); Mem->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, &FooRef); // DW_AT_external and DW_AT_declaration are ignored anyway, so skip them. - Foo.addChild(std::move(Mem)); + Foo.addChild(Mem); uint64_t MD5Res = DIEHash().computeTypeSignature(Foo); @@ -183,7 +183,7 @@ DIEString FooStr(&Eight, "foo"); Foo.addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &FooStr); - auto Mem = make_unique(dwarf::DW_TAG_member); + DIE *Mem = new DIE(dwarf::DW_TAG_member); DIEString MemStr(&Eight, "mem"); Mem->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &MemStr); DIEInteger Zero(0); @@ -197,7 +197,7 @@ DIEEntry FooPtrRef(FooPtr); Mem->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, &FooPtrRef); - Foo.addChild(std::move(Mem)); + Foo.addChild(Mem); uint64_t MD5Res = DIEHash().computeTypeSignature(Foo); @@ -212,7 +212,7 @@ DIEString FooStr(&Eight, "foo"); Foo.addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &FooStr); - auto Mem = make_unique(dwarf::DW_TAG_member); + DIE *Mem = new DIE(dwarf::DW_TAG_member); DIEString MemStr(&Eight, "mem"); Mem->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &MemStr); DIEInteger Zero(0); @@ -230,7 +230,7 @@ DIEEntry FooRefConstRef(FooRefConst); Mem->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, &FooRefConstRef); - Foo.addChild(std::move(Mem)); + Foo.addChild(Mem); uint64_t MD5Res = DIEHash().computeTypeSignature(Foo); @@ -245,7 +245,7 @@ DIEString FooStr(&Eight, "foo"); Foo.addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &FooStr); - auto Mem = make_unique(dwarf::DW_TAG_member); + DIE *Mem = new DIE(dwarf::DW_TAG_member); DIEString MemStr(&Eight, "mem"); Mem->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &MemStr); DIEInteger Zero(0); @@ -263,7 +263,7 @@ DIEEntry FooRefConstRef(FooRefConst); Mem->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, &FooRefConstRef); - Foo.addChild(std::move(Mem)); + Foo.addChild(Mem); uint64_t MD5Res = DIEHash().computeTypeSignature(Foo); @@ -278,7 +278,7 @@ DIEString FooStr(&Eight, "foo"); Foo.addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &FooStr); - auto Mem = make_unique(dwarf::DW_TAG_member); + DIE *Mem = new DIE(dwarf::DW_TAG_member); DIEString MemStr(&Eight, "mem"); Mem->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &MemStr); DIEInteger Zero(0); @@ -293,7 +293,7 @@ DIEEntry PtrToFooMemRef(PtrToFooMem); Mem->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, &PtrToFooMemRef); - Foo.addChild(std::move(Mem)); + Foo.addChild(Mem); uint64_t MD5Res = DIEHash().computeTypeSignature(Foo); @@ -322,7 +322,7 @@ Foo.addValue(dwarf::DW_AT_byte_size, dwarf::DW_FORM_data1, &Eight); Foo.addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &FooStr); - auto Mem = make_unique(dwarf::DW_TAG_member); + DIE *Mem = new DIE(dwarf::DW_TAG_member); Mem->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &MemStr); Mem->addValue(dwarf::DW_AT_data_member_location, dwarf::DW_FORM_data1, &Zero); @@ -337,7 +337,7 @@ DIEEntry PtrToFooMemRef(PtrToFooMem); Mem->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, &PtrToFooMemRef); - Foo.addChild(std::move(Mem)); + Foo.addChild(Mem); MD5ResDecl = DIEHash().computeTypeSignature(Foo); } @@ -351,7 +351,7 @@ Foo.addValue(dwarf::DW_AT_byte_size, dwarf::DW_FORM_data1, &Eight); Foo.addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &FooStr); - auto Mem = make_unique(dwarf::DW_TAG_member); + DIE *Mem = new DIE(dwarf::DW_TAG_member); Mem->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &MemStr); Mem->addValue(dwarf::DW_AT_data_member_location, dwarf::DW_FORM_data1, &Zero); @@ -366,7 +366,7 @@ DIEEntry PtrToFooMemRef(PtrToFooMem); Mem->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, &PtrToFooMemRef); - Foo.addChild(std::move(Mem)); + Foo.addChild(Mem); MD5ResDef = DIEHash().computeTypeSignature(Foo); } @@ -395,7 +395,7 @@ Foo.addValue(dwarf::DW_AT_byte_size, dwarf::DW_FORM_data1, &Eight); Foo.addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &FooStr); - auto Mem = make_unique(dwarf::DW_TAG_member); + DIE *Mem = new DIE(dwarf::DW_TAG_member); Mem->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &MemStr); Mem->addValue(dwarf::DW_AT_data_member_location, dwarf::DW_FORM_data1, &Zero); @@ -409,7 +409,7 @@ DIEEntry PtrToFooMemRef(PtrToFooMem); Mem->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, &PtrToFooMemRef); - Foo.addChild(std::move(Mem)); + Foo.addChild(Mem); MD5ResDecl = DIEHash().computeTypeSignature(Foo); } @@ -423,7 +423,7 @@ Foo.addValue(dwarf::DW_AT_byte_size, dwarf::DW_FORM_data1, &Eight); Foo.addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &FooStr); - auto Mem = make_unique(dwarf::DW_TAG_member); + DIE *Mem = new DIE(dwarf::DW_TAG_member); Mem->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &MemStr); Mem->addValue(dwarf::DW_AT_data_member_location, dwarf::DW_FORM_data1, &Zero); @@ -437,7 +437,7 @@ DIEEntry PtrToFooMemRef(PtrToFooMem); Mem->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, &PtrToFooMemRef); - Foo.addChild(std::move(Mem)); + Foo.addChild(Mem); MD5ResDef = DIEHash().computeTypeSignature(Foo); } @@ -465,7 +465,7 @@ Foo.addValue(dwarf::DW_AT_byte_size, dwarf::DW_FORM_data1, &Eight); Foo.addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &FooStr); - auto Mem = make_unique(dwarf::DW_TAG_member); + DIE *Mem = new DIE(dwarf::DW_TAG_member); Mem->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &MemStr); Mem->addValue(dwarf::DW_AT_data_member_location, dwarf::DW_FORM_data1, &Zero); @@ -477,7 +477,7 @@ DIEEntry UnnamedPtrRef(UnnamedPtr); Mem->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, &UnnamedPtrRef); - Foo.addChild(std::move(Mem)); + Foo.addChild(Mem); uint64_t MD5Res = DIEHash().computeTypeSignature(Foo); @@ -490,12 +490,12 @@ DIEInteger One(1); Unnamed.addValue(dwarf::DW_AT_byte_size, dwarf::DW_FORM_data1, &One); - auto Foo = make_unique(dwarf::DW_TAG_structure_type); + DIE *Foo = new DIE(dwarf::DW_TAG_structure_type); DIEString FooStr(&One, "foo"); Foo->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &FooStr); Foo->addValue(dwarf::DW_AT_byte_size, dwarf::DW_FORM_data1, &One); - Unnamed.addChild(std::move(Foo)); + Unnamed.addChild(Foo); uint64_t MD5Res = DIEHash().computeTypeSignature(Unnamed); @@ -509,11 +509,11 @@ DIEInteger One(1); Unnamed.addValue(dwarf::DW_AT_byte_size, dwarf::DW_FORM_data1, &One); - auto Func = make_unique(dwarf::DW_TAG_subprogram); + DIE *Func = new DIE(dwarf::DW_TAG_subprogram); DIEString FuncStr(&One, "func"); Func->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &FuncStr); - Unnamed.addChild(std::move(Func)); + Unnamed.addChild(Func); uint64_t MD5Res = DIEHash().computeTypeSignature(Unnamed); @@ -533,7 +533,7 @@ A.addValue(dwarf::DW_AT_decl_file, dwarf::DW_FORM_data1, &One); A.addValue(dwarf::DW_AT_decl_line, dwarf::DW_FORM_data1, &One); - auto Func = make_unique(dwarf::DW_TAG_subprogram); + DIE *Func = new DIE(dwarf::DW_TAG_subprogram); DIEString FuncStr(&One, "func"); DIEString FuncLinkage(&One, "_ZN1A4funcEv"); DIEInteger Two(2); @@ -544,7 +544,7 @@ Func->addValue(dwarf::DW_AT_linkage_name, dwarf::DW_FORM_strp, &FuncLinkage); Func->addValue(dwarf::DW_AT_declaration, dwarf::DW_FORM_flag_present, &One); - A.addChild(std::move(Func)); + A.addChild(Func); uint64_t MD5Res = DIEHash().computeTypeSignature(A); @@ -579,7 +579,7 @@ PITyDIE->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, &IntTy); DIEEntry PITy(*PITyDIE); - auto PI = make_unique(dwarf::DW_TAG_member); + DIE *PI = new DIE(dwarf::DW_TAG_member); DIEString PIStr(&One, "PI"); DIEInteger Two(2); DIEInteger NegThree(-3); @@ -591,7 +591,7 @@ PI->addValue(dwarf::DW_AT_declaration, dwarf::DW_FORM_flag_present, &One); PI->addValue(dwarf::DW_AT_const_value, dwarf::DW_FORM_sdata, &NegThree); - A.addChild(std::move(PI)); + A.addChild(PI); uint64_t MD5Res = DIEHash().computeTypeSignature(A); ASSERT_EQ(0x9a216000dd3788a7ULL, MD5Res); @@ -623,7 +623,7 @@ PITyDIE->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, &FloatTy); DIEEntry PITy(*PITyDIE); - auto PI = make_unique(dwarf::DW_TAG_member); + DIE *PI = new DIE(dwarf::DW_TAG_member); DIEString PIStr(&One, "PI"); DIEInteger Two(2); PI->addValue(dwarf::DW_AT_name, dwarf::DW_FORM_strp, &PIStr); @@ -646,7 +646,7 @@ PI->addValue(dwarf::DW_AT_const_value, dwarf::DW_FORM_block1, &PIBlock); - A.addChild(std::move(PI)); + A.addChild(PI); uint64_t MD5Res = DIEHash().computeTypeSignature(A); ASSERT_EQ(0x493af53ad3d3f651ULL, MD5Res);