diff options
| author | George Rimar <grimar@accesssoftek.com> | 2019-10-03 14:52:33 +0000 |
|---|---|---|
| committer | George Rimar <grimar@accesssoftek.com> | 2019-10-03 14:52:33 +0000 |
| commit | fc9104d42a777540984c7f43f5f12f635ebc5098 (patch) | |
| tree | bae019618dcd2cb1b90398f54e8138edf65e071e /llvm/tools | |
| parent | 2c9c7d680974d4d6f39a7df52268b8e308a5b50c (diff) | |
| download | bcm5719-llvm-fc9104d42a777540984c7f43f5f12f635ebc5098.tar.gz bcm5719-llvm-fc9104d42a777540984c7f43f5f12f635ebc5098.zip | |
Recommit r373598 "[yaml2obj/obj2yaml] - Add support for SHT_LLVM_ADDRSIG sections."
Fix: call `consumeError()` for a case missed.
Original commit message:
SHT_LLVM_ADDRSIG is described here:
https://llvm.org/docs/Extensions.html#sht-llvm-addrsig-section-address-significance-table
This patch teaches tools to dump them and to parse the YAML declarations of such sections.
Differential revision: https://reviews.llvm.org/D68333
llvm-svn: 373606
Diffstat (limited to 'llvm/tools')
| -rw-r--r-- | llvm/tools/obj2yaml/elf2yaml.cpp | 75 |
1 files changed, 65 insertions, 10 deletions
diff --git a/llvm/tools/obj2yaml/elf2yaml.cpp b/llvm/tools/obj2yaml/elf2yaml.cpp index c4b6eb79d18..2c17b9570e1 100644 --- a/llvm/tools/obj2yaml/elf2yaml.cpp +++ b/llvm/tools/obj2yaml/elf2yaml.cpp @@ -41,6 +41,7 @@ class ELFDumper { Expected<StringRef> getUniquedSymbolName(const Elf_Sym *Sym, StringRef StrTable, const Elf_Shdr *SymTab); + Expected<StringRef> getSymbolName(uint32_t SymtabNdx, uint32_t SymbolNdx); const object::ELFFile<ELFT> &Obj; ArrayRef<Elf_Word> ShndxTable; @@ -56,6 +57,7 @@ class ELFDumper { Error dumpRelocation(const RelT *Rel, const Elf_Shdr *SymTab, ELFYAML::Relocation &R); + Expected<ELFYAML::AddrsigSection *> dumpAddrsigSection(const Elf_Shdr *Shdr); Expected<ELFYAML::DynamicSection *> dumpDynamicSection(const Elf_Shdr *Shdr); Expected<ELFYAML::RelocationSection *> dumpRelocSection(const Elf_Shdr *Shdr); Expected<ELFYAML::RawContentSection *> @@ -284,6 +286,13 @@ template <class ELFT> Expected<ELFYAML::Object *> ELFDumper<ELFT>::dump() { Y->Sections.emplace_back(*SecOrErr); break; } + case ELF::SHT_LLVM_ADDRSIG: { + Expected<ELFYAML::AddrsigSection *> SecOrErr = dumpAddrsigSection(&Sec); + if (!SecOrErr) + return SecOrErr.takeError(); + Y->Sections.emplace_back(*SecOrErr); + break; + } case ELF::SHT_NULL: { // We only dump the SHT_NULL section at index 0 when it // has at least one non-null field, because yaml2obj @@ -520,6 +529,46 @@ ELFDumper<ELFT>::dumpStackSizesSection(const Elf_Shdr *Shdr) { } template <class ELFT> +Expected<ELFYAML::AddrsigSection *> +ELFDumper<ELFT>::dumpAddrsigSection(const Elf_Shdr *Shdr) { + auto S = std::make_unique<ELFYAML::AddrsigSection>(); + if (Error E = dumpCommonSection(Shdr, *S)) + return std::move(E); + + auto ContentOrErr = Obj.getSectionContents(Shdr); + if (!ContentOrErr) + return ContentOrErr.takeError(); + + ArrayRef<uint8_t> Content = *ContentOrErr; + DataExtractor::Cursor Cur(0); + DataExtractor Data(Content, Obj.isLE(), /*AddressSize=*/0); + std::vector<ELFYAML::AddrsigSymbol> Symbols; + while (Cur && Cur.tell() < Content.size()) { + uint64_t SymNdx = Data.getULEB128(Cur); + if (!Cur) + break; + + Expected<StringRef> SymbolName = getSymbolName(Shdr->sh_link, SymNdx); + if (!SymbolName || SymbolName->empty()) { + consumeError(SymbolName.takeError()); + Symbols.emplace_back(SymNdx); + continue; + } + + Symbols.emplace_back(*SymbolName); + } + + if (Cur) { + S->Symbols = std::move(Symbols); + return S.release(); + } + + consumeError(Cur.takeError()); + S->Content = yaml::BinaryRef(Content); + return S.release(); +} + +template <class ELFT> Expected<ELFYAML::DynamicSection *> ELFDumper<ELFT>::dumpDynamicSection(const Elf_Shdr *Shdr) { auto S = std::make_unique<ELFYAML::DynamicSection>(); @@ -791,25 +840,31 @@ ELFDumper<ELFT>::dumpVerneedSection(const Elf_Shdr *Shdr) { } template <class ELFT> -Expected<ELFYAML::Group *> ELFDumper<ELFT>::dumpGroup(const Elf_Shdr *Shdr) { - auto S = std::make_unique<ELFYAML::Group>(); - if (Error E = dumpCommonSection(Shdr, *S)) - return std::move(E); - - auto SymtabOrErr = Obj.getSection(Shdr->sh_link); +Expected<StringRef> ELFDumper<ELFT>::getSymbolName(uint32_t SymtabNdx, + uint32_t SymbolNdx) { + auto SymtabOrErr = Obj.getSection(SymtabNdx); if (!SymtabOrErr) return SymtabOrErr.takeError(); - // Get symbol with index sh_info which name is the signature of the group. + const Elf_Shdr *Symtab = *SymtabOrErr; - auto SymOrErr = Obj.getSymbol(Symtab, Shdr->sh_info); + auto SymOrErr = Obj.getSymbol(Symtab, SymbolNdx); if (!SymOrErr) return SymOrErr.takeError(); + auto StrTabOrErr = Obj.getStringTableForSymtab(*Symtab); if (!StrTabOrErr) return StrTabOrErr.takeError(); + return getUniquedSymbolName(*SymOrErr, *StrTabOrErr, Symtab); +} + +template <class ELFT> +Expected<ELFYAML::Group *> ELFDumper<ELFT>::dumpGroup(const Elf_Shdr *Shdr) { + auto S = std::make_unique<ELFYAML::Group>(); + if (Error E = dumpCommonSection(Shdr, *S)) + return std::move(E); - Expected<StringRef> SymbolName = - getUniquedSymbolName(*SymOrErr, *StrTabOrErr, Symtab); + // Get symbol with index sh_info. This symbol's name is the signature of the group. + Expected<StringRef> SymbolName = getSymbolName(Shdr->sh_link, Shdr->sh_info); if (!SymbolName) return SymbolName.takeError(); S->Signature = *SymbolName; |

