From 3ff62ade384d5b1dfd33eb0978e17cbc643b49e3 Mon Sep 17 00:00:00 2001 From: Shankar Easwaran Date: Tue, 5 Mar 2013 14:52:48 +0000 Subject: [PATCH] [ELF] add dynamic library support llvm-svn: 176483 --- lld/lib/ReaderWriter/ELF/SectionChunks.h | 36 +++++++++++++++++++----- lld/test/elf/Hexagon/dynlib.test | 11 ++++++++ 2 files changed, 40 insertions(+), 7 deletions(-) create mode 100644 lld/test/elf/Hexagon/dynlib.test diff --git a/lld/lib/ReaderWriter/ELF/SectionChunks.h b/lld/lib/ReaderWriter/ELF/SectionChunks.h index 94f465d7a0f9..12f1c20d6ae9 100644 --- a/lld/lib/ReaderWriter/ELF/SectionChunks.h +++ b/lld/lib/ReaderWriter/ELF/SectionChunks.h @@ -584,18 +584,21 @@ class SymbolTable : public Section { typedef llvm::object::Elf_Sym_Impl Elf_Sym; struct SymbolEntry { - SymbolEntry(const Atom *a, const Elf_Sym &sym) : _atom(a), _symbol(sym) {} - + SymbolEntry(const Atom *a, const Elf_Sym &sym, + const AtomLayout *layout) : _atom(a), _symbol(sym), + _atomLayout(layout) {} SymbolEntry() : _atom(nullptr) {} const Atom *_atom; Elf_Sym _symbol; + const AtomLayout *_atomLayout; }; public: SymbolTable(const ELFTargetInfo &ti, const char *str, int32_t order); - void addSymbol(const Atom *atom, int32_t sectionIndex, uint64_t addr = 0); + void addSymbol(const Atom *atom, int32_t sectionIndex, + uint64_t addr = 0, const AtomLayout *layout=nullptr); /// \brief Get the symbol table index for an Atom. If it's not in the symbol /// table, return STN_UNDEF. @@ -617,7 +620,7 @@ public: StringTable *getStringTable() const { return _stringSection; } -private: +protected: llvm::BumpPtrAllocator _symbolAllocate; StringTable *_stringSection; std::vector _symbolTable; @@ -631,16 +634,21 @@ SymbolTable::SymbolTable(const ELFTargetInfo &ti, const char *str, this->setOrder(order); Elf_Sym symbol; std::memset(&symbol, 0, sizeof(Elf_Sym)); - _symbolTable.push_back(SymbolEntry(nullptr, symbol)); + _symbolTable.push_back(SymbolEntry(nullptr, symbol, nullptr)); this->_entSize = sizeof(Elf_Sym); this->_fsize = sizeof(Elf_Sym); this->_align2 = sizeof(Elf_Addr); this->_type = SHT_SYMTAB; } +/// Add a symbol to the symbol Table, definedAtoms which get added to the symbol +/// section dont have their virtual addresses set at the time of adding the +/// symbol to the symbol table(Example: dynamic symbols), the addresses needs +/// to be updated in the table before writing the dynamic symbol table +/// information template void SymbolTable::addSymbol(const Atom *atom, int32_t sectionIndex, - uint64_t addr) { + uint64_t addr, const AtomLayout *atomLayout) { Elf_Sym symbol; unsigned char binding = 0, type = 0; symbol.st_name = _stringSection->addString(atom->name()); @@ -711,7 +719,7 @@ void SymbolTable::addSymbol(const Atom *atom, int32_t sectionIndex, binding = llvm::ELF::STB_WEAK; } symbol.setBindingAndType(binding, type); - _symbolTable.push_back(SymbolEntry(atom, symbol)); + _symbolTable.push_back(SymbolEntry(atom, symbol, atomLayout)); this->_fsize += sizeof(Elf_Sym); if (this->_flags & SHF_ALLOC) this->_msize = this->_fsize; @@ -757,6 +765,20 @@ public: this->_flags = SHF_ALLOC; this->_msize = this->_fsize; } + + virtual void finalize() { + // Defined symbols which have been added into the dynamic symbol table + // dont have their addresses known until addresses have been assigned + // so lets update the symbol values after they have got assigned + for (auto &ste: this->_symbolTable) { + const AtomLayout *atomLayout = ste._atomLayout; + if (!atomLayout) + continue; + ste._symbol.st_value = atomLayout->_virtualAddr; + } + SymbolTable::finalize(); + } + }; template class RelocationTable : public Section { diff --git a/lld/test/elf/Hexagon/dynlib.test b/lld/test/elf/Hexagon/dynlib.test new file mode 100644 index 000000000000..a0764e2d68ed --- /dev/null +++ b/lld/test/elf/Hexagon/dynlib.test @@ -0,0 +1,11 @@ +RUN: lld -core -target hexagon %p/Inputs/use-shared.hexagon \ +RUN: -output=%t1 -output-type=shared +RUN: llvm-readobj %t2 > %t3 +RUN: FileCheck -check-prefix=DYNSYMS %s < %t3 + +DYNSYMS: Dynamic Symbols: +DYNSYMS: Name Type Address Size FileOffset Flags +DYNSYMS: fn2 FUNC 148 c 21c global +DYNSYMS: fn1 FUNC 154 c 228 global +DYNSYMS: fn3 FUNC 160 14 234 global +DYNSYMS: Total: 3