diff options
author | Sterling Augustine <saugustine@google.com> | 2018-06-28 18:57:13 +0000 |
---|---|---|
committer | Sterling Augustine <saugustine@google.com> | 2018-06-28 18:57:13 +0000 |
commit | 3605e121fbd4283246005545767fa4583f8f297a (patch) | |
tree | a9a9649783e705174c83c1693d693f7b7a770b90 /tools/llvm-objdump/llvm-objdump.cpp | |
parent | 822461008d345c56a1e3a17a0e3a74af3e4b84f2 (diff) |
Handle absolute symbols as branch targets in disassembly.
https://reviews.llvm.org/D48554
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@335903 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'tools/llvm-objdump/llvm-objdump.cpp')
-rw-r--r-- | tools/llvm-objdump/llvm-objdump.cpp | 56 |
1 files changed, 35 insertions, 21 deletions
diff --git a/tools/llvm-objdump/llvm-objdump.cpp b/tools/llvm-objdump/llvm-objdump.cpp index 2edd65be2ed..2598d930417 100644 --- a/tools/llvm-objdump/llvm-objdump.cpp +++ b/tools/llvm-objdump/llvm-objdump.cpp @@ -1282,6 +1282,7 @@ static void DisassembleObject(const ObjectFile *Obj, bool InlineRelocs) { // Create a mapping from virtual address to symbol name. This is used to // pretty print the symbols while disassembling. std::map<SectionRef, SectionSymbolsTy> AllSymbols; + SectionSymbolsTy AbsoluteSymbols; for (const SymbolRef &Symbol : Obj->symbols()) { Expected<uint64_t> AddressOrErr = Symbol.getAddress(); if (!AddressOrErr) @@ -1297,15 +1298,17 @@ static void DisassembleObject(const ObjectFile *Obj, bool InlineRelocs) { Expected<section_iterator> SectionOrErr = Symbol.getSection(); if (!SectionOrErr) report_error(Obj->getFileName(), SectionOrErr.takeError()); - section_iterator SecI = *SectionOrErr; - if (SecI == Obj->section_end()) - continue; uint8_t SymbolType = ELF::STT_NOTYPE; if (Obj->isELF()) SymbolType = getElfSymbolType(Obj, Symbol); - AllSymbols[*SecI].emplace_back(Address, *Name, SymbolType); + section_iterator SecI = *SectionOrErr; + if (SecI != Obj->section_end()) + AllSymbols[*SecI].emplace_back(Address, *Name, SymbolType); + else + AbsoluteSymbols.emplace_back(Address, *Name, SymbolType); + } if (AllSymbols.empty() && Obj->isELF()) @@ -1341,6 +1344,8 @@ static void DisassembleObject(const ObjectFile *Obj, bool InlineRelocs) { if (Sec != SectionAddresses.end()) AllSymbols[Sec->second].emplace_back(VA, Name, ELF::STT_NOTYPE); + else + AbsoluteSymbols.emplace_back(VA, Name, ELF::STT_NOTYPE); } } @@ -1348,6 +1353,7 @@ static void DisassembleObject(const ObjectFile *Obj, bool InlineRelocs) { // a symbol near an address. for (std::pair<const SectionRef, SectionSymbolsTy> &SecSyms : AllSymbols) array_pod_sort(SecSyms.second.begin(), SecSyms.second.end()); + array_pod_sort(AbsoluteSymbols.begin(), AbsoluteSymbols.end()); for (const SectionRef &Section : ToolSectionFilter(*Obj)) { if (!DisassembleAll && (!Section.isText() || Section.isVirtual())) @@ -1662,29 +1668,37 @@ static void DisassembleObject(const ObjectFile *Obj, bool InlineRelocs) { --SectionAddress; TargetSectionSymbols = &AllSymbols[SectionAddress->second]; } else { - TargetSectionSymbols = nullptr; + TargetSectionSymbols = &AbsoluteSymbols; } } // Find the first symbol in the section whose offset is less than - // or equal to the target. - if (TargetSectionSymbols) { - auto TargetSym = std::upper_bound( - TargetSectionSymbols->begin(), TargetSectionSymbols->end(), + // or equal to the target. If there isn't a section that contains + // the target, find the nearest preceding absolute symbol. + auto TargetSym = std::upper_bound( + TargetSectionSymbols->begin(), TargetSectionSymbols->end(), + Target, [](uint64_t LHS, + const std::tuple<uint64_t, StringRef, uint8_t> &RHS) { + return LHS < std::get<0>(RHS); + }); + if (TargetSym == TargetSectionSymbols->begin()) { + TargetSectionSymbols = &AbsoluteSymbols; + TargetSym = std::upper_bound( + AbsoluteSymbols.begin(), AbsoluteSymbols.end(), Target, [](uint64_t LHS, const std::tuple<uint64_t, StringRef, uint8_t> &RHS) { - return LHS < std::get<0>(RHS); - }); - if (TargetSym != TargetSectionSymbols->begin()) { - --TargetSym; - uint64_t TargetAddress = std::get<0>(*TargetSym); - StringRef TargetName = std::get<1>(*TargetSym); - outs() << " <" << TargetName; - uint64_t Disp = Target - TargetAddress; - if (Disp) - outs() << "+0x" << Twine::utohexstr(Disp); - outs() << '>'; - } + return LHS < std::get<0>(RHS); + }); + } + if (TargetSym != TargetSectionSymbols->begin()) { + --TargetSym; + uint64_t TargetAddress = std::get<0>(*TargetSym); + StringRef TargetName = std::get<1>(*TargetSym); + outs() << " <" << TargetName; + uint64_t Disp = Target - TargetAddress; + if (Disp) + outs() << "+0x" << Twine::utohexstr(Disp); + outs() << '>'; } } } |