Index: llvm/include/llvm/DWARFLinker/DWARFLinker.h =================================================================== --- llvm/include/llvm/DWARFLinker/DWARFLinker.h +++ llvm/include/llvm/DWARFLinker/DWARFLinker.h @@ -85,8 +85,8 @@ virtual bool applyValidRelocs(MutableArrayRef Data, uint64_t BaseOffset, bool IsLittleEndian) = 0; - /// Apply the valid reloctions tot he index address. - virtual uint64_t relocateIndexedAddr(uint64_t Addr) = 0; + /// Relocate the given address offset if a valid relocation exists. + virtual uint64_t relocateIndexedAddr(uint64_t Offset) = 0; /// Returns all valid functions address ranges(i.e., those ranges /// which points to sections with code). Index: llvm/lib/DWARFLinker/DWARFLinker.cpp =================================================================== --- llvm/lib/DWARFLinker/DWARFLinker.cpp +++ llvm/lib/DWARFLinker/DWARFLinker.cpp @@ -2143,10 +2143,10 @@ uint64_t OutputDebugInfoSize = Linker.Options.NoOutput ? 0 : Emitter->getDebugInfoSectionSize(); const uint64_t StartOutputDebugInfoSize = OutputDebugInfoSize; - const uint16_t DwarfVersion = Linker.MaxDwarfVersion; - const uint32_t UnitHeaderSize = DwarfVersion >= 5 ? 12 : 11; for (auto &CurrentUnit : CompileUnits) { + const uint16_t DwarfVersion = CurrentUnit->getOrigUnit().getVersion(); + const uint32_t UnitHeaderSize = DwarfVersion >= 5 ? 12 : 11; auto InputDIE = CurrentUnit->getOrigUnit().getUnitDIE(); CurrentUnit->setStartOffset(OutputDebugInfoSize); if (!InputDIE) { @@ -2203,6 +2203,8 @@ if (!CurrentUnit->getOutputUnitDIE()) continue; + unsigned DwarfVersion = CurrentUnit->getOrigUnit().getVersion(); + assert(Emitter->getDebugInfoSectionSize() == CurrentUnit->getStartOffset()); Emitter->emitCompileUnitHeader(*CurrentUnit, DwarfVersion); Index: llvm/tools/dsymutil/DwarfLinkerForBinary.h =================================================================== --- llvm/tools/dsymutil/DwarfLinkerForBinary.h +++ llvm/tools/dsymutil/DwarfLinkerForBinary.h @@ -149,8 +149,18 @@ std::vector &ValidRelocs); /// @} - bool hasValidRelocationAt(uint64_t StartOffset, uint64_t EndOffset, - CompileUnit::DIEInfo &Info); + /// Checks that there is a relocation in the debug_addr section against a + /// debug map entry between \p StartOffset and \p NextOffset. + bool hasValidDebugInfoRelocationAt(uint64_t StartOffset, uint64_t EndOffset, + CompileUnit::DIEInfo &Info); + + /// Checks that there is a relocation in the debug_addr section against a + /// debug map entry at the given offset. + /// + /// This function must be called with offsets in strictly ascending order + /// because it never looks back at relocations it already 'went past'. + /// \returns true and sets Info.InDebugMap if it is the case. + bool hasValidDebugAddrRelocationAt(uint64_t Offset); bool hasLiveMemoryLocation(const DWARFDie &DIE, CompileUnit::DIEInfo &Info) override; @@ -160,7 +170,7 @@ bool applyValidRelocs(MutableArrayRef Data, uint64_t BaseOffset, bool IsLittleEndian) override; - uint64_t relocateIndexedAddr(uint64_t Addr) override; + uint64_t relocateIndexedAddr(uint64_t Offset) override; RangesTy &getValidAddressRanges() override { return AddressRanges; } Index: llvm/tools/dsymutil/DwarfLinkerForBinary.cpp =================================================================== --- llvm/tools/dsymutil/DwarfLinkerForBinary.cpp +++ llvm/tools/dsymutil/DwarfLinkerForBinary.cpp @@ -610,13 +610,14 @@ return FoundValidRelocs; } -/// Checks that there is a relocation against an actual debug -/// map entry between \p StartOffset and \p NextOffset. -/// -/// This function must be called with offsets in strictly ascending -/// order because it never looks back at relocations it already 'went past'. -/// \returns true and sets Info.InDebugMap if it is the case. -bool DwarfLinkerForBinary::AddressManager::hasValidRelocationAt( +bool DwarfLinkerForBinary::AddressManager::hasValidDebugAddrRelocationAt( + uint64_t Offset) { + auto It = std::lower_bound(ValidDebugAddrRelocs.begin(), + ValidDebugAddrRelocs.end(), Offset); + return It != ValidDebugAddrRelocs.end(); +} + +bool DwarfLinkerForBinary::AddressManager::hasValidDebugInfoRelocationAt( uint64_t StartOffset, uint64_t EndOffset, CompileUnit::DIEInfo &Info) { assert(NextValidReloc == 0 || StartOffset > ValidDebugInfoRelocs[NextValidReloc - 1].Offset); @@ -690,7 +691,9 @@ std::tie(LocationOffset, LocationEndOffset) = getAttributeOffsets(Abbrev, *LocationIdx, Offset, *DIE.getDwarfUnit()); - return hasValidRelocationAt(LocationOffset, LocationEndOffset, MyInfo); + // FIXME: Support relocations debug_addr. + return hasValidDebugInfoRelocationAt(LocationOffset, LocationEndOffset, + MyInfo); } bool DwarfLinkerForBinary::AddressManager::hasLiveAddressRange( @@ -708,15 +711,12 @@ uint64_t LowPcOffset, LowPcEndOffset; std::tie(LowPcOffset, LowPcEndOffset) = getAttributeOffsets(Abbrev, *LowPcIdx, Offset, *DIE.getDwarfUnit()); - return hasValidRelocationAt(LowPcOffset, LowPcEndOffset, MyInfo); + return hasValidDebugInfoRelocationAt(LowPcOffset, LowPcEndOffset, MyInfo); } if (Form == dwarf::DW_FORM_addrx) { - Optional OffsetValue = DIE.find(dwarf::DW_AT_low_pc); - uint64_t LowPcOffset = *OffsetValue->getAsAddress(); - auto It = std::lower_bound(ValidDebugAddrRelocs.begin(), - ValidDebugAddrRelocs.end(), LowPcOffset); - return It != ValidDebugAddrRelocs.end(); + Optional AddrValue = DIE.find(dwarf::DW_AT_low_pc); + return hasValidDebugAddrRelocationAt(*AddrValue->getAsAddress()); } return false; @@ -767,11 +767,11 @@ } uint64_t -DwarfLinkerForBinary::AddressManager::relocateIndexedAddr(uint64_t Addr) { +DwarfLinkerForBinary::AddressManager::relocateIndexedAddr(uint64_t Offset) { auto It = std::lower_bound(ValidDebugAddrRelocs.begin(), - ValidDebugAddrRelocs.end(), Addr); + ValidDebugAddrRelocs.end(), Offset); if (It == ValidDebugAddrRelocs.end()) - return Addr; + return Offset; return It->Mapping->getValue().BinaryAddress; }