Index: llvm/include/llvm/DWARFLinker/DWARFLinker.h =================================================================== --- llvm/include/llvm/DWARFLinker/DWARFLinker.h +++ llvm/include/llvm/DWARFLinker/DWARFLinker.h @@ -75,6 +75,25 @@ using Offset2UnitMap = DenseMap; +struct DebugAddrPool { + DenseMap AddrIndexMap; + SmallVector Addrs; + + uint64_t getAddrIndex(uint64_t Addr) { + DenseMap::iterator It = AddrIndexMap.find(Addr); + if (It == AddrIndexMap.end()) { + It = AddrIndexMap.insert(std::make_pair(Addr, Addrs.size())).first; + Addrs.push_back(Addr); + } + return It->second; + } + + void clear() { + AddrIndexMap.clear(); + Addrs.clear(); + } +}; + /// DwarfEmitter presents interface to generate all debug info tables. class DwarfEmitter { public: @@ -137,7 +156,7 @@ virtual void emitDwarfDebugLocListFragment( const CompileUnit &Unit, const DWARFLocationExpressionsVector &LinkedLocationExpression, - PatchLocation Patch) = 0; + PatchLocation Patch, DebugAddrPool &AddrPool) = 0; /// Emit debug locations (.debug_loc, .debug_loclists) footer. virtual void emitDwarfDebugLocListFooter(const CompileUnit &Unit, @@ -639,27 +658,6 @@ DWARFFile &ObjFile; OffsetsStringPool &DebugStrPool; OffsetsStringPool &DebugLineStrPool; - - struct DebugAddrPool { - DenseMap AddrIndexMap; - SmallVector Addrs; - - uint64_t getAddrIndex(uint64_t Addr) { - DenseMap::iterator It = AddrIndexMap.find(Addr); - if (It == AddrIndexMap.end()) { - It = AddrIndexMap.insert(std::make_pair(Addr, Addrs.size())).first; - Addrs.push_back(Addr); - } - return It->second; - } - - void clear() { - AddrIndexMap.clear(); - Addrs.clear(); - } - - }; - DebugAddrPool AddrPool; /// Allocator used for all the DIEValue objects. @@ -708,6 +706,15 @@ void emitDebugAddrSection(CompileUnit &Unit, const uint16_t DwarfVersion) const; + using ExpressionHandlerRef = function_ref &, SmallVectorImpl &, + int64_t AddrRelocAdjustment)>; + + /// Compute and emit debug locations (.debug_loc, .debug_loclists) + /// for \p Unit, patch the attributes referencing it. + void generateUnitLocations(CompileUnit &Unit, const DWARFFile &File, + ExpressionHandlerRef ExprHandler); + private: using AttributeSpec = DWARFAbbreviationDeclaration::AttributeSpec; @@ -823,15 +830,6 @@ /// .debug_rnglists) for \p Unit, patch the attributes referencing it. void generateUnitRanges(CompileUnit &Unit, const DWARFFile &File) const; - using ExpressionHandlerRef = - function_ref &, SmallVectorImpl &, - int64_t AddrRelocAdjustment)>; - - /// Compute and emit debug locations (.debug_loc, .debug_loclists) - /// for \p Unit, patch the attributes referencing it. - void generateUnitLocations(CompileUnit &Unit, const DWARFFile &File, - ExpressionHandlerRef ExprHandler) const; - /// Emit the accelerator entries for \p Unit. void emitAcceleratorEntriesForUnit(CompileUnit &Unit); Index: llvm/include/llvm/DWARFLinker/DWARFStreamer.h =================================================================== --- llvm/include/llvm/DWARFLinker/DWARFStreamer.h +++ llvm/include/llvm/DWARFLinker/DWARFStreamer.h @@ -122,7 +122,7 @@ void emitDwarfDebugLocListFragment( const CompileUnit &Unit, const DWARFLocationExpressionsVector &LinkedLocationExpression, - PatchLocation Patch) override; + PatchLocation Patch, DebugAddrPool &AddrPool) override; /// Emit debug ranges(.debug_loc, .debug_loclists) footer. void emitDwarfDebugLocListFooter(const CompileUnit &Unit, @@ -232,7 +232,7 @@ void emitDwarfDebugLocListsTableFragment( const CompileUnit &Unit, const DWARFLocationExpressionsVector &LinkedLocationExpression, - PatchLocation Patch); + PatchLocation Patch, DebugAddrPool &AddrPool); /// \defgroup Line table emission /// @{ Index: llvm/lib/DWARFLinker/DWARFLinker.cpp =================================================================== --- llvm/lib/DWARFLinker/DWARFLinker.cpp +++ llvm/lib/DWARFLinker/DWARFLinker.cpp @@ -1942,10 +1942,10 @@ } } -void DWARFLinker::generateUnitLocations( +void DWARFLinker::DIECloner::generateUnitLocations( CompileUnit &Unit, const DWARFFile &File, - ExpressionHandlerRef ExprHandler) const { - if (LLVM_UNLIKELY(Options.Update)) + ExpressionHandlerRef ExprHandler) { + if (LLVM_UNLIKELY(Linker.Options.Update)) return; const LocListAttributesTy &AllLocListAttributes = @@ -1955,7 +1955,7 @@ return; // Emit locations list table header. - MCSymbol *EndLabel = TheDwarfEmitter->emitDwarfDebugLocListHeader(Unit); + MCSymbol *EndLabel = Emitter->emitDwarfDebugLocListHeader(Unit); for (auto &CurLocAttr : AllLocListAttributes) { // Get location expressions vector corresponding to the current attribute @@ -1965,7 +1965,7 @@ if (!OriginalLocations) { llvm::consumeError(OriginalLocations.takeError()); - reportWarning("Invalid location attribute ignored.", File); + Linker.reportWarning("Invalid location attribute ignored.", File); continue; } @@ -1989,12 +1989,12 @@ } // Emit locations list table fragment corresponding to the CurLocAttr. - TheDwarfEmitter->emitDwarfDebugLocListFragment( - Unit, LinkedLocationExpressions, CurLocAttr); + Emitter->emitDwarfDebugLocListFragment(Unit, LinkedLocationExpressions, + CurLocAttr, AddrPool); } // Emit locations list table footer. - TheDwarfEmitter->emitDwarfDebugLocListFooter(Unit, EndLabel); + Emitter->emitDwarfDebugLocListFooter(Unit, EndLabel); } static void patchAddrBase(DIE &Die, DIEInteger Offset) { @@ -2591,7 +2591,7 @@ File, *CurrentUnit, OutBytes, RelocAdjustment, IsLittleEndian); }; - Linker.generateUnitLocations(*CurrentUnit, File, ProcessExpr); + generateUnitLocations(*CurrentUnit, File, ProcessExpr); if (!AddrPool.Addrs.empty()) emitDebugAddrSection(*CurrentUnit, DwarfVersion); } Index: llvm/lib/DWARFLinker/DWARFStreamer.cpp =================================================================== --- llvm/lib/DWARFLinker/DWARFStreamer.cpp +++ llvm/lib/DWARFLinker/DWARFStreamer.cpp @@ -544,13 +544,14 @@ void DwarfStreamer::emitDwarfDebugLocListFragment( const CompileUnit &Unit, const DWARFLocationExpressionsVector &LinkedLocationExpression, - PatchLocation Patch) { + PatchLocation Patch, DebugAddrPool &AddrPool) { if (Unit.getOrigUnit().getVersion() < 5) { emitDwarfDebugLocTableFragment(Unit, LinkedLocationExpression, Patch); return; } - emitDwarfDebugLocListsTableFragment(Unit, LinkedLocationExpression, Patch); + emitDwarfDebugLocListsTableFragment(Unit, LinkedLocationExpression, Patch, + AddrPool); } /// Emit debug locations(.debug_loc, .debug_loclists) footer. @@ -661,7 +662,7 @@ void DwarfStreamer::emitDwarfDebugLocListsTableFragment( const CompileUnit &Unit, const DWARFLocationExpressionsVector &LinkedLocationExpression, - PatchLocation Patch) { + PatchLocation Patch, DebugAddrPool &AddrPool) { Patch.set(LocListsSectionSize); // Make .debug_loclists the current section. @@ -677,11 +678,10 @@ BaseAddress = LocExpression.Range->LowPC; // Emit base address. - MS->emitInt8(dwarf::DW_LLE_base_address); + MS->emitInt8(dwarf::DW_LLE_base_addressx); LocListsSectionSize += 1; - unsigned AddressSize = Unit.getOrigUnit().getAddressByteSize(); - MS->emitIntValue(*BaseAddress, AddressSize); - LocListsSectionSize += AddressSize; + LocListsSectionSize += + MS->emitULEB128IntValue(AddrPool.getAddrIndex(*BaseAddress)); } // Emit type of entry. Index: llvm/test/tools/dsymutil/ARM/dwarf5-dwarf4-combination-macho.test =================================================================== --- llvm/test/tools/dsymutil/ARM/dwarf5-dwarf4-combination-macho.test +++ llvm/test/tools/dsymutil/ARM/dwarf5-dwarf4-combination-macho.test @@ -67,13 +67,11 @@ CHECK-NEXT: (0x[[#sub(LOC_PAIR_START2,LOC_LOWPC)]], 0x[[#sub(LOC_PAIR_END2,LOC_LOWPC)]]): [[LOC_EXPR2:.*]] CHECK: .debug_loclists contents: -CHECK-NEXT: 0x00000000: locations list header: length = 0x0000001f, format = DWARF32, version = 0x0005, addr_size = 0x08, seg_size = 0x00, offset_entry_count = 0x00000000 +CHECK-NEXT: 0x00000000: locations list header: length = 0x00000018, format = DWARF32, version = 0x0005, addr_size = 0x08, seg_size = 0x00, offset_entry_count = 0x00000000 CHECK-NEXT: 0x[[LOCLIST_OFFSET]]: -CHECK-NEXT: DW_LLE_base_address (0x[[#LOCLIST_LOWPC]]) +CHECK-NEXT: DW_LLE_base_addressx (0x0000000000000000) CHECK-NEXT: DW_LLE_offset_pair (0x[[#sub(LOCLIST_PAIR_START,LOCLIST_LOWPC)]], 0x[[#sub(LOCLIST_PAIR_END,LOCLIST_LOWPC)]]) -CHECK-NEXT: => [0x[[#LOCLIST_PAIR_START]], 0x[[#LOCLIST_PAIR_END]]): [[LOCLIST_EXPR]] CHECK-NEXT: DW_LLE_offset_pair (0x[[#sub(LOCLIST_PAIR_START2,LOCLIST_LOWPC)]], 0x[[#sub(LOCLIST_PAIR_END2,LOCLIST_LOWPC)]]) -CHECK-NEXT: => [0x[[#LOCLIST_PAIR_START2]], 0x[[#LOCLIST_PAIR_END2]]): [[LOCLIST_EXPR2]] CHECK-NEXT: DW_LLE_end_of_list () CHECK: .debug_line contents: Index: llvm/test/tools/dsymutil/ARM/dwarf5-macho.test =================================================================== --- llvm/test/tools/dsymutil/ARM/dwarf5-macho.test +++ llvm/test/tools/dsymutil/ARM/dwarf5-macho.test @@ -37,13 +37,11 @@ CHECK-NEXT: [0x[[#%.16x,LOCLIST_PAIR_START2:]], 0x[[#%.16x,LOCLIST_PAIR_END2:]]): [[LOCLIST_EXPR2:.*]]) CHECK: .debug_loclists contents: -CHECK-NEXT: locations list header: length = 0x0000001f, format = DWARF32, version = 0x0005, addr_size = 0x08, seg_size = 0x00, offset_entry_count = 0x00000000 +CHECK-NEXT: 0x00000000: locations list header: length = 0x00000018, format = DWARF32, version = 0x0005, addr_size = 0x08, seg_size = 0x00, offset_entry_count = 0x00000000 CHECK-NEXT: 0x[[LOC_OFFSET]]: -CHECK-NEXT: DW_LLE_base_address (0x[[#LOCLIST_LOWPC]]) +CHECK-NEXT: DW_LLE_base_addressx (0x0000000000000000) CHECK-NEXT: DW_LLE_offset_pair (0x[[#sub(LOCLIST_PAIR_START,LOCLIST_LOWPC)]], 0x[[#sub(LOCLIST_PAIR_END,LOCLIST_LOWPC)]]) -CHECK-NEXT: => [0x[[#LOCLIST_PAIR_START]], 0x[[#LOCLIST_PAIR_END]]): [[LOCLIST_EXPR]] CHECK-NEXT: DW_LLE_offset_pair (0x[[#sub(LOCLIST_PAIR_START2,LOCLIST_LOWPC)]], 0x[[#sub(LOCLIST_PAIR_END2,LOCLIST_LOWPC)]]) -CHECK-NEXT: => [0x[[#LOCLIST_PAIR_START2]], 0x[[#LOCLIST_PAIR_END2]]): [[LOCLIST_EXPR2]] CHECK-NEXT: DW_LLE_end_of_list () CHECK: .debug_line contents: Index: llvm/test/tools/dsymutil/X86/dwarf5-loclists.test =================================================================== --- llvm/test/tools/dsymutil/X86/dwarf5-loclists.test +++ llvm/test/tools/dsymutil/X86/dwarf5-loclists.test @@ -38,31 +38,24 @@ #DWARF-CHECK: [0x0000000100000fa3, 0x0000000100000fbc): DW_OP_breg6 RBP-20) #DWARF-CHECK: DW_AT_name {{.*}} "argv" #DWARF-CHECK: DW_TAG_formal_parameter -#DWARF-CHECK: DW_AT_location [DW_FORM_sec_offset] (0x00000030: +#DWARF-CHECK: DW_AT_location [DW_FORM_sec_offset] (0x00000029: #DWARF-CHECK: [0x0000000100000f70, 0x0000000100000f89): DW_OP_reg4 RSI #DWARF-CHECK: [0x0000000100000f89, 0x0000000100000fbc): DW_OP_entry_value(DW_OP_reg4 RSI), DW_OP_stack_value) #DWARF-CHECK: DW_AT_name {{.*}} "argc" #DWARF-CHECK: .debug_loclists contents: -#DWARF-CHECK: 0x00000000: locations list header: length = 0x00000043, format = DWARF32, version = 0x0005, addr_size = 0x08, seg_size = 0x00, offset_entry_count = 0x00000000 +#DWARF-CHECK: 0x00000000: locations list header: length = 0x00000035, format = DWARF32, version = 0x0005, addr_size = 0x08, seg_size = 0x00, offset_entry_count = 0x00000000 #DWARF-CHECK: 0x0000000c: -#DWARF-CHECK: DW_LLE_base_address (0x0000000100000f70) -#DWARF-CHECK: DW_LLE_offset_pair (0x0000000000000000, 0x0000000000000017) -#DWARF-CHECK: => [0x0000000100000f70, 0x0000000100000f87): DW_OP_reg5 RDI -#DWARF-CHECK: DW_LLE_offset_pair (0x0000000000000017, 0x0000000000000023) -#DWARF-CHECK: => [0x0000000100000f87, 0x0000000100000f93): DW_OP_reg3 RBX -#DWARF-CHECK: DW_LLE_offset_pair (0x0000000000000023, 0x000000000000002d) -#DWARF-CHECK: => [0x0000000100000f93, 0x0000000100000f9d): DW_OP_reg4 RSI -#DWARF-CHECK: DW_LLE_offset_pair (0x0000000000000030, 0x0000000000000033) -#DWARF-CHECK: => [0x0000000100000fa0, 0x0000000100000fa3): DW_OP_reg3 RBX -#DWARF-CHECK: DW_LLE_offset_pair (0x0000000000000033, 0x000000000000004c) -#DWARF-CHECK: => [0x0000000100000fa3, 0x0000000100000fbc): DW_OP_breg6 RBP-20 +#DWARF-CHECK: DW_LLE_base_addressx (0x0000000000000000) +#DWARF-CHECK: DW_LLE_offset_pair (0x0000000000000000, 0x0000000000000017): DW_OP_reg5 RDI +#DWARF-CHECK: DW_LLE_offset_pair (0x0000000000000017, 0x0000000000000023): DW_OP_reg3 RBX +#DWARF-CHECK: DW_LLE_offset_pair (0x0000000000000023, 0x000000000000002d): DW_OP_reg4 RSI +#DWARF-CHECK: DW_LLE_offset_pair (0x0000000000000030, 0x0000000000000033): DW_OP_reg3 RBX +#DWARF-CHECK: DW_LLE_offset_pair (0x0000000000000033, 0x000000000000004c): DW_OP_breg6 RBP-20 #DWARF-CHECK: DW_LLE_end_of_list () -#DWARF-CHECK: 0x00000030: -#DWARF-CHECK: DW_LLE_base_address (0x0000000100000f70) -#DWARF-CHECK: DW_LLE_offset_pair (0x0000000000000000, 0x0000000000000019) -#DWARF-CHECK: => [0x0000000100000f70, 0x0000000100000f89): DW_OP_reg4 RSI -#DWARF-CHECK: DW_LLE_offset_pair (0x0000000000000019, 0x000000000000004c) -#DWARF-CHECK: => [0x0000000100000f89, 0x0000000100000fbc): DW_OP_entry_value(DW_OP_reg4 RSI), DW_OP_stack_value +#DWARF-CHECK: 0x00000029: +#DWARF-CHECK: DW_LLE_base_addressx (0x0000000000000000) +#DWARF-CHECK: DW_LLE_offset_pair (0x0000000000000000, 0x0000000000000019): DW_OP_reg4 RSI +#DWARF-CHECK: DW_LLE_offset_pair (0x0000000000000019, 0x000000000000004c): DW_OP_entry_value(DW_OP_reg4 RSI), DW_OP_stack_value #DWARF-CHECK: DW_LLE_end_of_list () Index: llvm/test/tools/llvm-dwarfutil/ELF/X86/dwarf5-loclists.test =================================================================== --- llvm/test/tools/llvm-dwarfutil/ELF/X86/dwarf5-loclists.test +++ llvm/test/tools/llvm-dwarfutil/ELF/X86/dwarf5-loclists.test @@ -26,11 +26,11 @@ #DWARF-CHECK: DW_AT_location [DW_FORM_sec_offset] (0x0000000c: #DWARF-CHECK: [0x0000000000001130, 0x0000000000001140): DW_OP_reg5 RDI) #DWARF-CHECK: DW_AT_name {{.*}}"var2" -#DWARF-CHECK: DW_AT_location [DW_FORM_sec_offset] (0x0000001b: +#DWARF-CHECK: DW_AT_location [DW_FORM_sec_offset] (0x00000014: #DWARF-CHECK: : DW_OP_reg5 RDI) #DWARF-CHECK: DW_TAG_variable #DWARF-CHECK: DW_AT_name {{.*}}"var3" -#DWARF-CHECK: DW_AT_location [DW_FORM_sec_offset] (0x0000001f: +#DWARF-CHECK: DW_AT_location [DW_FORM_sec_offset] (0x00000018: #DWARF-CHECK: [0x0000000000001140, 0x0000000000001150): DW_OP_reg5 RDI #DWARF-CHECK: [0x0000000000001160, 0x0000000000001170): DW_OP_reg6 RBP)