[ELF] - Check that .dynsym is present in DSO if SHT_GNU_versym section is.

When we have SHT_GNU_versym section, it is should be associated with symbol table
section. Usually (and in out implementation) it is .dynsym.
In case when .dynsym is absent (due to broken object for example), 
lld crashes in parseVerdefs() when accesses null pointer:

Versym = reinterpret_cast<const Elf_Versym *>(this->ELFObj.base() +
                                              VersymSec->sh_offset) +
         this->Symtab->sh_info;

DIfferential revision: https://reviews.llvm.org/D25553

llvm-svn: 285796
This commit is contained in:
George Rimar 2016-11-02 10:16:25 +00:00
parent 5cddd608cd
commit bcba39ab9c
3 changed files with 30 additions and 1 deletions

View File

@ -610,6 +610,9 @@ template <class ELFT> void SharedFile<ELFT>::parseSoName() {
}
}
if (this->VersymSec && !this->Symtab)
error("SHT_GNU_versym should be associated with symbol table");
this->initStringTable();
// DSOs are identified by soname, and they usually contain

View File

@ -77,7 +77,7 @@ template <class ELFT> void SymbolTable<ELFT>::addFile(InputFile *File) {
if (auto *F = dyn_cast<SharedFile<ELFT>>(File)) {
// DSOs are uniquified not by filename but by soname.
F->parseSoName();
if (!SoNames.insert(F->getSoName()).second)
if (HasError || !SoNames.insert(F->getSoName()).second)
return;
SharedFiles.push_back(F);
F->parseRest();

View File

@ -0,0 +1,26 @@
# RUN: yaml2obj %s -o %t
# RUN: not ld.lld %t -o %tout 2>&1 | FileCheck %s
## When we have SHT_GNU_versym section, it is should be associated
## with symbol table section.
--- !ELF
FileHeader:
Class: ELFCLASS64
Data: ELFDATA2LSB
Type: ET_DYN
Machine: EM_X86_64
Sections:
- Name: .versym
Type: SHT_GNU_versym
Flags: [ SHF_ALLOC, SHF_EXECINSTR ]
AddressAlign: 0x1
Content: "00000000"
- Name: .verdef
Type: SHT_GNU_verdef
Flags: [ SHF_ALLOC, SHF_EXECINSTR ]
AddressAlign: 0x1
Content: "00000000"
# CHECK: SHT_GNU_versym should be associated with symbol table