diff options
author | George Rimar <grimar@accesssoftek.com> | 2019-01-28 10:44:01 +0000 |
---|---|---|
committer | George Rimar <grimar@accesssoftek.com> | 2019-01-28 10:44:01 +0000 |
commit | 4c3b2976216b197fd62d21663e6b81706dd698cb (patch) | |
tree | 52bfec0de0826c799cd5b3b0f2301f5eb8f4e112 /llvm/tools/llvm-objdump/llvm-objdump.cpp | |
parent | 574e0c5e328b89c598d31a243c5587a7ba5176c1 (diff) | |
download | llvm-4c3b2976216b197fd62d21663e6b81706dd698cb.zip llvm-4c3b2976216b197fd62d21663e6b81706dd698cb.tar.gz llvm-4c3b2976216b197fd62d21663e6b81706dd698cb.tar.bz2 |
[llvm-objdump] - Implement the --adjust-vma option.
GNU objdump's help says: "--adjust-vma: Add OFFSET to all displayed section addresses"
In real life what it does is a bit more complicated
(and IMO not always reasonable. For example, GNU objdump prints not only VMA, but also LMA
for sections. And with --adjust-vma it adjusts LMA, but only when a section has relocations.
llvm-objsump does not seem to support printing LMAs yet, but GNU's logic anyways does not
make sense for me here).
This patch tries to adjust VMA. I tried to implement a reasonable approach.
I am not adjusting sections that are not allocatable. As, for example, adjusting debug sections
VA's and rel[a] sections VA's should not make sense. This behavior seems to be GNU compatible.
Differential revision: https://reviews.llvm.org/D57051
llvm-svn: 352347
Diffstat (limited to 'llvm/tools/llvm-objdump/llvm-objdump.cpp')
-rw-r--r-- | llvm/tools/llvm-objdump/llvm-objdump.cpp | 42 |
1 files changed, 38 insertions, 4 deletions
diff --git a/llvm/tools/llvm-objdump/llvm-objdump.cpp b/llvm/tools/llvm-objdump/llvm-objdump.cpp index 9ac5266..8241765 100644 --- a/llvm/tools/llvm-objdump/llvm-objdump.cpp +++ b/llvm/tools/llvm-objdump/llvm-objdump.cpp @@ -70,6 +70,11 @@ using namespace llvm; using namespace object; +cl::opt<unsigned long long> AdjustVMA( + "adjust-vma", + cl::desc("Increase the displayed address by the specified offset"), + cl::value_desc("offset"), cl::init(0)); + cl::opt<bool> llvm::AllHeaders("all-headers", cl::desc("Display all available header information")); @@ -890,6 +895,18 @@ getRelocsMap(llvm::object::ObjectFile const &Obj) { return Ret; } +// Used for --adjust-vma to check if address should be adjusted by the +// specified value for a given section. +// For ELF we do not adjust non-allocatable sections like debug ones, +// because they are not loadable. +// TODO: implement for other file formats. +static bool shouldAdjustVA(const SectionRef &Section) { + const ObjectFile *Obj = Section.getObject(); + if (isa<object::ELFObjectFileBase>(Obj)) + return ELFSectionRef(Section).getFlags() & ELF::SHF_ALLOC; + return false; +} + static void disassembleObject(const Target *TheTarget, const ObjectFile *Obj, MCContext &Ctx, MCDisassembler *DisAsm, const MCInstrAnalysis *MIA, MCInstPrinter *IP, @@ -1046,6 +1063,10 @@ static void disassembleObject(const Target *TheTarget, const ObjectFile *Obj, ArrayRef<uint8_t> Bytes(reinterpret_cast<const uint8_t *>(BytesStr.data()), BytesStr.size()); + uint64_t VMAAdjustment = 0; + if (shouldAdjustVA(Section)) + VMAAdjustment = AdjustVMA; + uint64_t Size; uint64_t Index; bool PrintedSection = false; @@ -1110,7 +1131,8 @@ static void disassembleObject(const Target *TheTarget, const ObjectFile *Obj, outs() << '\n'; if (!NoLeadingAddr) - outs() << format("%016" PRIx64 " ", SectionAddr + Start); + outs() << format("%016" PRIx64 " ", + SectionAddr + Start + VMAAdjustment); StringRef SymbolName = std::get<1>(Symbols[SI]); if (Demangle) @@ -1271,9 +1293,9 @@ static void disassembleObject(const Target *TheTarget, const ObjectFile *Obj, if (Size == 0) Size = 1; - PIP.printInst(*IP, Disassembled ? &Inst : nullptr, - Bytes.slice(Index, Size), SectionAddr + Index, outs(), "", - *STI, &SP, &Rels); + PIP.printInst( + *IP, Disassembled ? &Inst : nullptr, Bytes.slice(Index, Size), + SectionAddr + Index + VMAAdjustment, outs(), "", *STI, &SP, &Rels); outs() << CommentStream.str(); Comments.clear(); @@ -1353,6 +1375,15 @@ static void disassembleObject(const Target *TheTarget, const ObjectFile *Obj, if (Offset >= Index + Size) break; + // When --adjust-vma is used, update the address printed. + if (RelCur->getSymbol() != Obj->symbol_end()) { + Expected<section_iterator> SymSI = + RelCur->getSymbol()->getSection(); + if (SymSI && *SymSI != Obj->section_end() && + (shouldAdjustVA(**SymSI))) + Offset += AdjustVMA; + } + printRelocation(*RelCur, SectionAddr + Offset, Obj->getBytesInAddress()); ++RelCur; @@ -1493,6 +1524,9 @@ void llvm::printSectionHeaders(const ObjectFile *Obj) { StringRef Name; error(Section.getName(Name)); uint64_t Address = Section.getAddress(); + if (shouldAdjustVA(Section)) + Address += AdjustVMA; + uint64_t Size = Section.getSize(); bool Text = Section.isText(); bool Data = Section.isData(); |