mirror of
https://github.com/RPCS3/llvm-mirror.git
synced 2025-02-01 05:01:59 +01:00
[llvm-readelf] - Make GNU style dumping of invalid SHT_GNU_verdef be consistent with LLVM style.
When we dump SHT_GNU_verdef section that has sh_link that references a non-existent section, llvm-readobj reports a warning and continues dump, but llvm-readelf fails with a error. This patch fixes the issue and opens road for futher follow-ups for improving the printGNUVersionSectionProlog(). Differential revision: https://reviews.llvm.org/D70776
This commit is contained in:
parent
4ff57b80e1
commit
63432001d0
@ -3,14 +3,14 @@
|
||||
## Check that we report a warning when sh_link references a non-existent section.
|
||||
|
||||
# RUN: yaml2obj %s --docnum=1 -o %t1
|
||||
# RUN: llvm-readobj -V %t1 2>&1 | FileCheck %s --check-prefix=INVALID-LINK-LLVM -DFILE=%t1
|
||||
# RUN: not llvm-readelf -V %t1 2>&1 | FileCheck %s --check-prefix=INVALID-LINK-GNU -DFILE=%t1
|
||||
# RUN: llvm-readobj -V %t1 2>&1 | FileCheck %s --check-prefix=INVALID-LINK-LLVM --implicit-check-not="warning:" -DFILE=%t1
|
||||
# RUN: llvm-readelf -V %t1 2>&1 | FileCheck %s --check-prefix=INVALID-LINK-GNU --implicit-check-not="warning:" -DFILE=%t1
|
||||
|
||||
# INVALID-LINK-LLVM: warning: '[[FILE]]': invalid section linked to SHT_GNU_verdef section with index 1: invalid section index: 255
|
||||
|
||||
## TODO: llvm-readelf should also report a meaningful warning instead of an error.
|
||||
# INVALID-LINK-GNU: Version definition
|
||||
# INVALID-LINK-GNU: error: '[[FILE]]': invalid section index: 255
|
||||
# INVALID-LINK-GNU: Version definition section '.gnu.version_d' contains 0 entries:
|
||||
# INVALID-LINK-GNU: warning: '[[FILE]]': invalid section linked to SHT_GNU_verdef section with index 1: invalid section index: 255
|
||||
# INVALID-LINK-GNU-NEXT: Addr: 0000000000000000 Offset: 0x000040 Link: 255 (<corrupt>)
|
||||
|
||||
--- !ELF
|
||||
FileHeader:
|
||||
|
@ -672,6 +672,9 @@ private:
|
||||
bool checkPTDynamic(const Elf_Phdr &Phdr, const Elf_Shdr &Sec);
|
||||
void printProgramHeaders(const ELFO *Obj);
|
||||
void printSectionMapping(const ELFO *Obj);
|
||||
void printGNUVersionSectionProlog(const ELFFile<ELFT> *Obj,
|
||||
const typename ELFT::Shdr *Sec,
|
||||
const Twine &Label, unsigned EntriesNum);
|
||||
};
|
||||
|
||||
template <class ELFT>
|
||||
@ -3921,18 +3924,26 @@ void GNUStyle<ELFT>::printDynamicRelocations(const ELFO *Obj) {
|
||||
}
|
||||
|
||||
template <class ELFT>
|
||||
static void printGNUVersionSectionProlog(formatted_raw_ostream &OS,
|
||||
const Twine &Name, unsigned EntriesNum,
|
||||
const ELFFile<ELFT> *Obj,
|
||||
const typename ELFT::Shdr *Sec,
|
||||
StringRef FileName) {
|
||||
StringRef SecName = unwrapOrError(FileName, Obj->getSectionName(Sec));
|
||||
OS << Name << " section '" << SecName << "' "
|
||||
void GNUStyle<ELFT>::printGNUVersionSectionProlog(
|
||||
const ELFFile<ELFT> *Obj, const typename ELFT::Shdr *Sec,
|
||||
const Twine &Label, unsigned EntriesNum) {
|
||||
StringRef SecName = unwrapOrError(this->FileName, Obj->getSectionName(Sec));
|
||||
OS << Label << " section '" << SecName << "' "
|
||||
<< "contains " << EntriesNum << " entries:\n";
|
||||
|
||||
const typename ELFT::Shdr *SymTab =
|
||||
unwrapOrError(FileName, Obj->getSection(Sec->sh_link));
|
||||
StringRef SymTabName = unwrapOrError(FileName, Obj->getSectionName(SymTab));
|
||||
unsigned SecNdx = Sec - &cantFail(Obj->sections()).front();
|
||||
StringRef SymTabName = "<corrupt>";
|
||||
|
||||
Expected<const typename ELFT::Shdr *> SymTabOrErr =
|
||||
Obj->getSection(Sec->sh_link);
|
||||
if (SymTabOrErr)
|
||||
SymTabName =
|
||||
unwrapOrError(this->FileName, Obj->getSectionName(*SymTabOrErr));
|
||||
else
|
||||
this->reportUniqueWarning(createError(
|
||||
"invalid section linked to SHT_GNU_verdef section with index " +
|
||||
Twine(SecNdx) + ": " + toString(SymTabOrErr.takeError())));
|
||||
|
||||
OS << " Addr: " << format_hex_no_prefix(Sec->sh_addr, 16)
|
||||
<< " Offset: " << format_hex(Sec->sh_offset, 8)
|
||||
<< " Link: " << Sec->sh_link << " (" << SymTabName << ")\n";
|
||||
@ -3945,8 +3956,7 @@ void GNUStyle<ELFT>::printVersionSymbolSection(const ELFFile<ELFT> *Obj,
|
||||
return;
|
||||
|
||||
unsigned Entries = Sec->sh_size / sizeof(Elf_Versym);
|
||||
printGNUVersionSectionProlog(OS, "Version symbols", Entries, Obj, Sec,
|
||||
this->FileName);
|
||||
printGNUVersionSectionProlog(Obj, Sec, "Version symbols", Entries);
|
||||
|
||||
const uint8_t *VersymBuf =
|
||||
reinterpret_cast<const uint8_t *>(Obj->base() + Sec->sh_offset);
|
||||
@ -4017,8 +4027,7 @@ void GNUStyle<ELFT>::printVersionDefinitionSection(const ELFFile<ELFT> *Obj,
|
||||
if (!Sec)
|
||||
return;
|
||||
|
||||
printGNUVersionSectionProlog(OS, "Version definition", Sec->sh_info, Obj, Sec,
|
||||
this->FileName);
|
||||
printGNUVersionSectionProlog(Obj, Sec, "Version definition", Sec->sh_info);
|
||||
|
||||
Expected<std::vector<VerDef>> V = this->dumper()->getVersionDefinitions(Sec);
|
||||
if (!V) {
|
||||
@ -4047,8 +4056,7 @@ void GNUStyle<ELFT>::printVersionDependencySection(const ELFFile<ELFT> *Obj,
|
||||
return;
|
||||
|
||||
unsigned VerneedNum = Sec->sh_info;
|
||||
printGNUVersionSectionProlog(OS, "Version needs", VerneedNum, Obj, Sec,
|
||||
this->FileName);
|
||||
printGNUVersionSectionProlog(Obj, Sec, "Version needs", VerneedNum);
|
||||
|
||||
ArrayRef<uint8_t> SecData =
|
||||
unwrapOrError(this->FileName, Obj->getSectionContents(Sec));
|
||||
|
Loading…
x
Reference in New Issue
Block a user