From: George Rimar Date: Thu, 30 May 2019 10:36:52 +0000 (+0000) Subject: [llvm-readobj/llvm-readelf] - Implement GNU style dumper of the SHT_GNU_verdef section. X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=ec36578fd8c8655bd1b9d22e7edb6e1516f80cc9;p=llvm [llvm-readobj/llvm-readelf] - Implement GNU style dumper of the SHT_GNU_verdef section. It was not implemented yet, we had only LLVM style dumper implemented. Section description is here: https://refspecs.linuxfoundation.org/LSB_5.0.0/LSB-Core-generic/LSB-Core-generic/symversion.html Differential revision: https://reviews.llvm.org/D62520 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@362082 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/test/tools/llvm-readobj/elf-versioninfo.test b/test/tools/llvm-readobj/elf-versioninfo.test index cca5bb1b409..ba48e91b21c 100644 --- a/test/tools/llvm-readobj/elf-versioninfo.test +++ b/test/tools/llvm-readobj/elf-versioninfo.test @@ -30,7 +30,7 @@ Sections: Flags: 0 VersionNdx: 2 Hash: 175630257 - Names: + Names: - VERSION1 - Version: 1 Flags: 0 @@ -64,7 +64,7 @@ Sections: Hash: 1937 Flags: 0 Other: 6 -DynamicSymbols: +DynamicSymbols: - Name: sym1 Binding: STB_GLOBAL - Name: sym2 @@ -174,7 +174,13 @@ DynamicSymbols: # GNU-NEXT: 000: 0 (*local*) 2 (VERSION1) 3 (VERSION2) 4 (v1) # GNU-NEXT: 004: 5 (v2) 6 (v3) # GNU-EMPTY: -# GNU-NEXT: Dumper for .gnu.version_d is not implemented +# GNU-NEXT: Version definition section '.gnu.version_d' contains 3 entries: +# GNU-NEXT: Addr: 0000000000000000 Offset: 0x00028c Link: 8 (.dynstr) +# GNU-NEXT: 0x0000: Rev: 1 Flags: none Index: 2 Cnt: 1 Name: VERSION1 +# GNU-NEXT: 0x001c: Rev: 1 Flags: none Index: 3 Cnt: 2 Name: VERSION2 +# GNU-NEXT: 0x0038: Parent 1: VERSION1 +# GNU-NEXT: 0x001c: Rev: 1 Flags: none Index: 3 Cnt: 2 Name: VERSION2 +# GNU-NEXT: 0x0038: Parent 1: VERSION1 # GNU-EMPTY: # GNU-NEXT: Version needs section '.gnu.version_r' contains 2 entries: # GNU-NEXT: Addr: 0000000000000000 Offset: 0x0002cc Link: 8 (.dynstr) diff --git a/tools/llvm-readobj/ELFDumper.cpp b/tools/llvm-readobj/ELFDumper.cpp index fdef4b79ebf..1aea4935da6 100644 --- a/tools/llvm-readobj/ELFDumper.cpp +++ b/tools/llvm-readobj/ELFDumper.cpp @@ -3491,18 +3491,7 @@ void GNUStyle::printVersionSymbolSection(const ELFFile *Obj, OS << '\n'; } -template -void GNUStyle::printVersionDefinitionSection(const ELFFile *Obj, - const Elf_Shdr *Sec) { - if (!Sec) - return; - - StringRef SecName = unwrapOrError(Obj->getSectionName(Sec)); - OS << "Dumper for " << SecName << " is not implemented\n"; - OS << '\n'; -} - -static std::string verNeedFlagToString(unsigned Flags) { +static std::string versionFlagToString(unsigned Flags) { if (Flags == 0) return "none"; @@ -3523,6 +3512,48 @@ static std::string verNeedFlagToString(unsigned Flags) { return Ret; } +template +void GNUStyle::printVersionDefinitionSection(const ELFFile *Obj, + const Elf_Shdr *Sec) { + if (!Sec) + return; + + unsigned VerDefsNum = Sec->sh_info; + printGNUVersionSectionProlog(OS, "Version definition", VerDefsNum, Obj, Sec); + + const Elf_Shdr *StrTabSec = unwrapOrError(Obj->getSection(Sec->sh_link)); + StringRef StringTable( + reinterpret_cast(Obj->base() + StrTabSec->sh_offset), + StrTabSec->sh_size); + + const uint8_t *VerdefBuf = unwrapOrError(Obj->getSectionContents(Sec)).data(); + const uint8_t *Begin = VerdefBuf; + + while (VerDefsNum--) { + const Elf_Verdef *Verdef = reinterpret_cast(VerdefBuf); + OS << format(" 0x%04x: Rev: %u Flags: %s Index: %u Cnt: %u", + VerdefBuf - Begin, (unsigned)Verdef->vd_version, + versionFlagToString(Verdef->vd_flags).c_str(), + (unsigned)Verdef->vd_ndx, (unsigned)Verdef->vd_cnt); + + const uint8_t *VerdauxBuf = VerdefBuf + Verdef->vd_aux; + const Elf_Verdaux *Verdaux = + reinterpret_cast(VerdauxBuf); + OS << format(" Name: %s\n", + StringTable.drop_front(Verdaux->vda_name).data()); + + for (unsigned I = 1; I < Verdef->vd_cnt; ++I) { + VerdauxBuf += Verdaux->vda_next; + Verdaux = reinterpret_cast(VerdauxBuf); + OS << format(" 0x%04x: Parent %u: %s\n", VerdauxBuf - Begin, I, + StringTable.drop_front(Verdaux->vda_name).data()); + } + + VerdefBuf += Verdef->vd_next; + } + OS << '\n'; +} + template void GNUStyle::printVersionDependencySection(const ELFFile *Obj, const Elf_Shdr *Sec) { @@ -3558,7 +3589,7 @@ void GNUStyle::printVersionDependencySection(const ELFFile *Obj, OS << format(" 0x%04x: Name: %s Flags: %s Version: %u\n", reinterpret_cast(Vernaux) - SecData.begin(), StringTable.drop_front(Vernaux->vna_name).data(), - verNeedFlagToString(Vernaux->vna_flags).c_str(), + versionFlagToString(Vernaux->vna_flags).c_str(), (unsigned)Vernaux->vna_other); VernauxBuf += Vernaux->vna_next; }