[yaml2obj] - Lookup relocation symbols in dynamic symbol when .dynsym referenced.
This fixes https://bugs.llvm.org/show_bug.cgi?id=40337. Previously, it was always assumed that relocations referenced symbols in the static symbol table. Now, if the Link field references a section called ".dynsym" it will look up these symbols in the dynamic symbol table. This patch is heavily based on D59097 by James Henderson Differential revision: https://reviews.llvm.org/D66532 llvm-svn: 369645
This commit is contained in:
parent
c2ca965c89
commit
91208447d0
|
@ -111,10 +111,11 @@ template <class ELFT> class ELFState {
|
|||
|
||||
NameToIdxMap SN2I;
|
||||
NameToIdxMap SymN2I;
|
||||
NameToIdxMap DynSymN2I;
|
||||
ELFYAML::Object &Doc;
|
||||
|
||||
bool buildSectionIndex();
|
||||
bool buildSymbolIndex(ArrayRef<ELFYAML::Symbol> Symbols);
|
||||
bool buildSymbolIndexes();
|
||||
void initELFHeader(Elf_Ehdr &Header);
|
||||
void initProgramHeaders(std::vector<Elf_Phdr> &PHeaders);
|
||||
bool initImplicitHeader(ELFState<ELFT> &State, ContiguousBlobAccumulator &CBA,
|
||||
|
@ -717,11 +718,12 @@ bool ELFState<ELFT>::writeSectionContent(
|
|||
|
||||
auto &OS = CBA.getOSAndAlignedOffset(SHeader.sh_offset, SHeader.sh_addralign);
|
||||
|
||||
const NameToIdxMap &SymMap = Section.Link == ".dynsym" ? DynSymN2I : SymN2I;
|
||||
for (const auto &Rel : Section.Relocations) {
|
||||
unsigned SymIdx = 0;
|
||||
// If a relocation references a symbol, try to look one up in the symbol
|
||||
// table. If it is not there, treat the value as a symbol index.
|
||||
if (Rel.Symbol && !SymN2I.lookup(*Rel.Symbol, SymIdx) &&
|
||||
if (Rel.Symbol && !SymMap.lookup(*Rel.Symbol, SymIdx) &&
|
||||
!to_integer(*Rel.Symbol, SymIdx)) {
|
||||
WithColor::error() << "Unknown symbol referenced: '" << *Rel.Symbol
|
||||
<< "' at YAML section '" << Section.Name << "'.\n";
|
||||
|
@ -987,11 +989,10 @@ template <class ELFT> bool ELFState<ELFT>::buildSectionIndex() {
|
|||
return true;
|
||||
}
|
||||
|
||||
template <class ELFT>
|
||||
bool ELFState<ELFT>::buildSymbolIndex(ArrayRef<ELFYAML::Symbol> Symbols) {
|
||||
static bool buildSymbolsMap(ArrayRef<ELFYAML::Symbol> V, NameToIdxMap &Map) {
|
||||
bool GlobalSymbolSeen = false;
|
||||
std::size_t I = 0;
|
||||
for (const auto &Sym : Symbols) {
|
||||
for (const ELFYAML::Symbol &Sym : V) {
|
||||
++I;
|
||||
|
||||
StringRef Name = Sym.Name;
|
||||
|
@ -1003,7 +1004,7 @@ bool ELFState<ELFT>::buildSymbolIndex(ArrayRef<ELFYAML::Symbol> Symbols) {
|
|||
if (Sym.Binding.value != ELF::STB_LOCAL)
|
||||
GlobalSymbolSeen = true;
|
||||
|
||||
if (!Name.empty() && !SymN2I.addName(Name, I)) {
|
||||
if (!Name.empty() && !Map.addName(Name, I)) {
|
||||
WithColor::error() << "Repeated symbol name: '" << Name << "'.\n";
|
||||
return false;
|
||||
}
|
||||
|
@ -1011,6 +1012,11 @@ bool ELFState<ELFT>::buildSymbolIndex(ArrayRef<ELFYAML::Symbol> Symbols) {
|
|||
return true;
|
||||
}
|
||||
|
||||
template <class ELFT> bool ELFState<ELFT>::buildSymbolIndexes() {
|
||||
return buildSymbolsMap(Doc.Symbols, SymN2I) &&
|
||||
buildSymbolsMap(Doc.DynamicSymbols, DynSymN2I);
|
||||
}
|
||||
|
||||
template <class ELFT> void ELFState<ELFT>::finalizeStrings() {
|
||||
// Add the regular symbol names to .strtab section.
|
||||
for (const ELFYAML::Symbol &Sym : Doc.Symbols)
|
||||
|
@ -1049,10 +1055,7 @@ int ELFState<ELFT>::writeELF(raw_ostream &OS, ELFYAML::Object &Doc) {
|
|||
// sections that might want to use them.
|
||||
State.finalizeStrings();
|
||||
|
||||
if (!State.buildSectionIndex())
|
||||
return 1;
|
||||
|
||||
if (!State.buildSymbolIndex(Doc.Symbols))
|
||||
if (!State.buildSectionIndex() || !State.buildSymbolIndexes())
|
||||
return 1;
|
||||
|
||||
Elf_Ehdr Header;
|
||||
|
|
|
@ -139,9 +139,7 @@ Sections:
|
|||
EntSize: 0x18
|
||||
Relocations:
|
||||
- Offset: 0x10
|
||||
## FIXME: This should be a lookup in the corresponding symbol table, not necessarily the static symbol table.
|
||||
## See https://bugs.llvm.org/show_bug.cgi?id=40337.
|
||||
Symbol: _Z3fooc
|
||||
Symbol: _Z3fooi
|
||||
Type: R_X86_64_PC32
|
||||
Addend: 0x4
|
||||
- Name: .dynamic
|
||||
|
|
|
@ -0,0 +1,65 @@
|
|||
## Show that yaml2obj uses the correct set of symbols for relocation sections
|
||||
## referencing the dynamic symbol table.
|
||||
|
||||
# RUN: yaml2obj %s -o %t
|
||||
# RUN: llvm-readelf -r %t | FileCheck %s
|
||||
|
||||
# CHECK: Relocation section '.rela.dyn' at offset {{.*}} contains 2 entries:
|
||||
# CHECK-NEXT: Offset Info Type Symbol's Value Symbol's Name
|
||||
# CHECK-NEXT: 0000000000000000 0000000100000000 R_X86_64_NONE 0000000012345678 dynamic
|
||||
# CHECK-NEXT: 0000000000000008 0000000200000000 R_X86_64_NONE 0000000087654321 both
|
||||
# CHECK-EMPTY:
|
||||
# CHECK-NEXT: Relocation section '.rela.data' at offset {{.*}} contains 2 entries:
|
||||
# CHECK-NEXT: Offset Info Type Symbol's Value Symbol's Name
|
||||
# CHECK-NEXT: 0000000000000010 0000000200000000 R_X86_64_NONE 0000000011223344 static
|
||||
# CHECK-NEXT: 0000000000000018 0000000100000000 R_X86_64_NONE 0000000088776655 both
|
||||
|
||||
!ELF
|
||||
FileHeader:
|
||||
Class: ELFCLASS64
|
||||
Data: ELFDATA2LSB
|
||||
Type: ET_DYN
|
||||
Machine: EM_X86_64
|
||||
Sections:
|
||||
- Name: .data
|
||||
Type: SHT_PROGBITS
|
||||
- Name: .rela.dyn
|
||||
Type: SHT_REL
|
||||
Link: .dynsym
|
||||
Info: .data
|
||||
Relocations:
|
||||
- Offset: 0
|
||||
Type: R_X86_64_NONE
|
||||
Symbol: dynamic
|
||||
- Offset: 8
|
||||
Type: R_X86_64_NONE
|
||||
Symbol: both
|
||||
- Name: .rela.data
|
||||
Type: SHT_REL
|
||||
Link: .symtab
|
||||
Info: .data
|
||||
Relocations:
|
||||
- Offset: 16
|
||||
Type: R_X86_64_NONE
|
||||
Symbol: static
|
||||
- Offset: 24
|
||||
Type: R_X86_64_NONE
|
||||
Symbol: both
|
||||
Symbols:
|
||||
- Name: both
|
||||
Section: .data
|
||||
Value: 0x88776655
|
||||
Binding: STB_GLOBAL
|
||||
- Name: static
|
||||
Section: .data
|
||||
Value: 0x11223344
|
||||
Binding: STB_GLOBAL
|
||||
DynamicSymbols:
|
||||
- Name: dynamic
|
||||
Section: .data
|
||||
Value: 0x12345678
|
||||
Binding: STB_GLOBAL
|
||||
- Name: both
|
||||
Section: .data
|
||||
Value: 0x87654321
|
||||
Binding: STB_GLOBAL
|
|
@ -14,6 +14,10 @@ Sections:
|
|||
Type: SHT_PROGBITS
|
||||
Flags: [ SHF_ALLOC, SHF_WRITE ]
|
||||
DynamicSymbols:
|
||||
- Name: dynlocal
|
||||
Type: STT_OBJECT
|
||||
Section: .data
|
||||
Binding: STB_LOCAL
|
||||
- Name: dynglobal
|
||||
Type: STT_OBJECT
|
||||
Section: .data
|
||||
|
@ -22,10 +26,6 @@ DynamicSymbols:
|
|||
Type: STT_OBJECT
|
||||
Section: .data
|
||||
Binding: STB_WEAK
|
||||
- Name: dynlocal
|
||||
Type: STT_OBJECT
|
||||
Section: .data
|
||||
Binding: STB_LOCAL
|
||||
|
||||
# SECTION: Name: .dynsym
|
||||
# SECTION-NEXT: Type: SHT_DYNSYM
|
||||
|
@ -36,6 +36,6 @@ DynamicSymbols:
|
|||
# SECTION-NEXT: Flags
|
||||
# SECTION-NEXT: SHF_ALLOC
|
||||
|
||||
# SYMBOL-DAG: d dynlocal
|
||||
# SYMBOL-DAG: D dynglobal
|
||||
# SYMBOL-DAG: V dynweak
|
||||
# SYMBOL-DAG: d dynlocal
|
||||
|
|
Loading…
Reference in New Issue