From 90e3e3a429e75a7d3671afcc30ed376b6186fd58 Mon Sep 17 00:00:00 2001 From: Daniel Dunbar Date: Sat, 27 Nov 2010 13:39:48 +0000 Subject: [PATCH] macho-dump: Add support for dumping relocation entries. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@120216 91177308-0d34-0410-b5e6-96231b3b80d8 --- include/llvm/Object/MachOFormat.h | 9 +++++ include/llvm/Object/MachOObject.h | 3 ++ lib/MC/MachObjectWriter.cpp | 23 +++++------- lib/Object/MachOObject.cpp | 13 +++++++ tools/macho-dump/macho-dump.cpp | 61 +++++++++++++++++++++---------- 5 files changed, 76 insertions(+), 33 deletions(-) diff --git a/include/llvm/Object/MachOFormat.h b/include/llvm/Object/MachOFormat.h index 320140773d4..0a2cceccb83 100644 --- a/include/llvm/Object/MachOFormat.h +++ b/include/llvm/Object/MachOFormat.h @@ -258,6 +258,15 @@ namespace macho { uint32_t Index; }; + /// @} + /// @name Relocation Data + /// @{ + + struct RelocationEntry { + uint32_t Word0; + uint32_t Word1; + }; + /// @} // See . diff --git a/include/llvm/Object/MachOObject.h b/include/llvm/Object/MachOObject.h index 77a8d3592e4..53c7abf34a4 100644 --- a/include/llvm/Object/MachOObject.h +++ b/include/llvm/Object/MachOObject.h @@ -137,6 +137,9 @@ public: const LoadCommandInfo &LCI, unsigned Index, InMemoryStruct &Res) const; + void ReadRelocationEntry( + uint64_t RelocationTableOffset, unsigned Index, + InMemoryStruct &Res) const; /// @} }; diff --git a/lib/MC/MachObjectWriter.cpp b/lib/MC/MachObjectWriter.cpp index 1213de0f002..a70f1c3d224 100644 --- a/lib/MC/MachObjectWriter.cpp +++ b/lib/MC/MachObjectWriter.cpp @@ -177,13 +177,8 @@ class MachObjectWriter : public MCObjectWriter { /// @name Relocation Data /// @{ - struct MachRelocationEntry { - uint32_t Word0; - uint32_t Word1; - }; - llvm::DenseMap > Relocations; + std::vector > Relocations; llvm::DenseMap IndirectSymBase; /// @} @@ -551,7 +546,7 @@ public: } Type = macho::RIT_X86_64_Unsigned; - MachRelocationEntry MRE; + macho::RelocationEntry MRE; MRE.Word0 = FixupOffset; MRE.Word1 = ((Index << 0) | (IsPCRel << 24) | @@ -676,7 +671,7 @@ public: FixedValue = Value; // struct relocation_info (8 bytes) - MachRelocationEntry MRE; + macho::RelocationEntry MRE; MRE.Word0 = FixupOffset; MRE.Word1 = ((Index << 0) | (IsPCRel << 24) | @@ -726,7 +721,7 @@ public: // Relocations are written out in reverse order, so the PAIR comes first. if (Type == macho::RIT_Difference || Type == macho::RIT_LocalDifference) { - MachRelocationEntry MRE; + macho::RelocationEntry MRE; MRE.Word0 = ((0 << 0) | (macho::RIT_Pair << 24) | (Log2Size << 28) | @@ -736,7 +731,7 @@ public: Relocations[Fragment->getParent()].push_back(MRE); } - MachRelocationEntry MRE; + macho::RelocationEntry MRE; MRE.Word0 = ((FixupOffset << 0) | (Type << 24) | (Log2Size << 28) | @@ -781,7 +776,7 @@ public: } // struct relocation_info (8 bytes) - MachRelocationEntry MRE; + macho::RelocationEntry MRE; MRE.Word0 = Value; MRE.Word1 = ((Index << 0) | (IsPCRel << 24) | @@ -861,7 +856,7 @@ public: } // struct relocation_info (8 bytes) - MachRelocationEntry MRE; + macho::RelocationEntry MRE; MRE.Word0 = FixupOffset; MRE.Word1 = ((Index << 0) | (IsPCRel << 24) | @@ -1138,7 +1133,7 @@ public: uint64_t RelocTableEnd = SectionDataStart + SectionDataFileSize; for (MCAssembler::const_iterator it = Asm.begin(), ie = Asm.end(); it != ie; ++it) { - std::vector &Relocs = Relocations[it]; + std::vector &Relocs = Relocations[it]; unsigned NumRelocs = Relocs.size(); uint64_t SectionStart = SectionDataStart + Layout.getSectionAddress(it); WriteSection(Asm, Layout, *it, SectionStart, RelocTableEnd, NumRelocs); @@ -1192,7 +1187,7 @@ public: ie = Asm.end(); it != ie; ++it) { // Write the section relocation entries, in reverse order to match 'as' // (approximately, the exact algorithm is more complicated than this). - std::vector &Relocs = Relocations[it]; + std::vector &Relocs = Relocations[it]; for (unsigned i = 0, e = Relocs.size(); i != e; ++i) { Write32(Relocs[e - i - 1].Word0); Write32(Relocs[e - i - 1].Word1); diff --git a/lib/Object/MachOObject.cpp b/lib/Object/MachOObject.cpp index 1e9ec70d422..f5bc73ada71 100644 --- a/lib/Object/MachOObject.cpp +++ b/lib/Object/MachOObject.cpp @@ -289,3 +289,16 @@ void MachOObject::ReadSection64(const LoadCommandInfo &LCI, Index * sizeof(macho::Section64)); ReadInMemoryStruct(*this, Buffer->getBuffer(), Offset, Res); } + +template<> +void SwapStruct(macho::RelocationEntry &Value) { + SwapValue(Value.Word0); + SwapValue(Value.Word1); +} +void MachOObject::ReadRelocationEntry(uint64_t RelocationTableOffset, + unsigned Index, + InMemoryStruct &Res) const { + uint64_t Offset = (RelocationTableOffset + + Index * sizeof(macho::RelocationEntry)); + ReadInMemoryStruct(*this, Buffer->getBuffer(), Offset, Res); +} diff --git a/tools/macho-dump/macho-dump.cpp b/tools/macho-dump/macho-dump.cpp index 68e61ba8d66..274c41bd25c 100644 --- a/tools/macho-dump/macho-dump.cpp +++ b/tools/macho-dump/macho-dump.cpp @@ -83,13 +83,13 @@ static void DumpSegmentCommandData(StringRef Name, outs() << " ('flags', " << Flags << ")\n"; } -static void DumpSectionData(unsigned Index, StringRef Name, - StringRef SegmentName, uint64_t Address, - uint64_t Size, uint32_t Offset, - uint32_t Align, uint32_t RelocationTableOffset, - uint32_t NumRelocationTableEntries, - uint32_t Flags, uint32_t Reserved1, - uint32_t Reserved2, uint64_t Reserved3 = ~0ULL) { +static int DumpSectionData(MachOObject &Obj, unsigned Index, StringRef Name, + StringRef SegmentName, uint64_t Address, + uint64_t Size, uint32_t Offset, + uint32_t Align, uint32_t RelocationTableOffset, + uint32_t NumRelocationTableEntries, + uint32_t Flags, uint32_t Reserved1, + uint32_t Reserved2, uint64_t Reserved3 = ~0ULL) { outs() << " # Section " << Index << "\n"; outs() << " (('section_name', '"; outs().write_escaped(Name, /*UseHexEscapes=*/true) << "')\n"; @@ -106,6 +106,26 @@ static void DumpSectionData(unsigned Index, StringRef Name, outs() << " ('reserved2', " << Reserved2 << ")\n"; if (Reserved3 != ~0ULL) outs() << " ('reserved3', " << Reserved3 << ")\n"; + outs() << " ),\n"; + + // Dump the relocation entries. + int Res = 0; + outs() << " ('_relocations', [\n"; + for (unsigned i = 0; i != NumRelocationTableEntries; ++i) { + InMemoryStruct RE; + Obj.ReadRelocationEntry(RelocationTableOffset, i, RE); + if (!RE) { + Res = Error("unable to read relocation table entry '" + Twine(i) + "'"); + break; + } + + outs() << " # Relocation " << i << "\n"; + outs() << " (('word-0', " << format("%#x", RE->Word0) << "),\n"; + outs() << " ('word-1', " << format("%#x", RE->Word1) << ")),\n"; + } + outs() << " ])\n"; + + return Res; } static int DumpSegmentCommand(MachOObject &Obj, @@ -131,12 +151,13 @@ static int DumpSegmentCommand(MachOObject &Obj, break; } - DumpSectionData(i, StringRef(Sect->Name, 16), - StringRef(Sect->SegmentName, 16), Sect->Address, Sect->Size, - Sect->Offset, Sect->Align, Sect->RelocationTableOffset, - Sect->NumRelocationTableEntries, Sect->Flags, - Sect->Reserved1, Sect->Reserved2); - outs() << " ),\n"; + if ((Res = DumpSectionData(Obj, i, StringRef(Sect->Name, 16), + StringRef(Sect->SegmentName, 16), Sect->Address, + Sect->Size, Sect->Offset, Sect->Align, + Sect->RelocationTableOffset, + Sect->NumRelocationTableEntries, Sect->Flags, + Sect->Reserved1, Sect->Reserved2))) + break; } outs() << " ])\n"; @@ -166,12 +187,14 @@ static int DumpSegment64Command(MachOObject &Obj, break; } - DumpSectionData(i, StringRef(Sect->Name, 16), - StringRef(Sect->SegmentName, 16), Sect->Address, Sect->Size, - Sect->Offset, Sect->Align, Sect->RelocationTableOffset, - Sect->NumRelocationTableEntries, Sect->Flags, - Sect->Reserved1, Sect->Reserved2, Sect->Reserved3); - outs() << " ),\n"; + if ((Res = DumpSectionData(Obj, i, StringRef(Sect->Name, 16), + StringRef(Sect->SegmentName, 16), Sect->Address, + Sect->Size, Sect->Offset, Sect->Align, + Sect->RelocationTableOffset, + Sect->NumRelocationTableEntries, Sect->Flags, + Sect->Reserved1, Sect->Reserved2, + Sect->Reserved3))) + break; } outs() << " ])\n"; -- 2.34.1