diff --git a/lib/ExecutionEngine/RuntimeDyld/DyldELFObject.h b/lib/ExecutionEngine/RuntimeDyld/DyldELFObject.h deleted file mode 100644 index 2d777dac07d..00000000000 --- a/lib/ExecutionEngine/RuntimeDyld/DyldELFObject.h +++ /dev/null @@ -1,388 +0,0 @@ -//===-- DyldELFObject.h - Dynamically loaded ELF object ----0---*- C++ -*-===// -// -// The LLVM Compiler Infrastructure -// -// This file is distributed under the University of Illinois Open Source -// License. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// -// -// Dynamically loaded ELF object class, a subclass of ELFObjectFile. Used -// to represent a loadable ELF image. -// -//===----------------------------------------------------------------------===// - -#ifndef LLVM_RUNTIMEDYLD_DYLDELFOBJECT_H -#define LLVM_RUNTIMEDYLD_DYLDELFOBJECT_H - -#include "llvm/Object/ELF.h" - - -namespace llvm { - -using support::endianness; -using namespace llvm::object; - -template -class DyldELFObject : public ELFObjectFile { - LLVM_ELF_IMPORT_TYPES(target_endianness, is64Bits) - - typedef Elf_Shdr_Impl Elf_Shdr; - typedef Elf_Sym_Impl Elf_Sym; - typedef Elf_Rel_Impl Elf_Rel; - typedef Elf_Rel_Impl Elf_Rela; - - typedef typename ELFObjectFile:: - Elf_Ehdr Elf_Ehdr; - Elf_Ehdr *Header; - - // Update section headers according to the current location in memory - virtual void rebaseObject(std::vector *MemoryMap); - // Record memory addresses for cleanup - virtual void saveAddress(std::vector *MemoryMap, uint8_t *addr); - -protected: - virtual error_code getSymbolAddress(DataRefImpl Symb, uint64_t &Res) const; - -public: - DyldELFObject(MemoryBuffer *Object, std::vector *MemoryMap, - error_code &ec); - - // Methods for type inquiry through isa, cast, and dyn_cast - static inline bool classof(const Binary *v) { - return (isa >(v) - && classof(cast >(v))); - } - static inline bool classof( - const ELFObjectFile *v) { - return v->isDyldType(); - } - static inline bool classof(const DyldELFObject *v) { - return true; - } -}; - -template -DyldELFObject::DyldELFObject(MemoryBuffer *Object, - std::vector *MemoryMap, error_code &ec) - : ELFObjectFile(Object, ec) - , Header(0) { - this->isDyldELFObject = true; - Header = const_cast( - reinterpret_cast(this->base())); - if (Header->e_shoff == 0) - return; - - // Mark the image as a dynamic shared library - Header->e_type = ELF::ET_DYN; - - rebaseObject(MemoryMap); -} - -// Walk through the ELF headers, updating virtual addresses to reflect where -// the object is currently loaded in memory -template -void DyldELFObject::rebaseObject( - std::vector *MemoryMap) { - typedef typename ELFDataTypeTypedefHelper< - target_endianness, is64Bits>::value_type addr_type; - - uint8_t *base_p = const_cast(this->base()); - Elf_Shdr *sectionTable = - reinterpret_cast(base_p + Header->e_shoff); - uint64_t numSections = this->getNumSections(); - - // Allocate memory space for NOBITS sections (such as .bss), which only exist - // in memory, but don't occupy space in the object file. - // Update the address in the section headers to reflect this allocation. - for (uint64_t index = 0; index < numSections; index++) { - Elf_Shdr *sec = reinterpret_cast( - reinterpret_cast(sectionTable) + index * Header->e_shentsize); - - // Only update sections that are meant to be present in program memory - if (sec->sh_flags & ELF::SHF_ALLOC) { - uint8_t *addr = base_p + sec->sh_offset; - if (sec->sh_type == ELF::SHT_NOBITS) { - addr = static_cast(calloc(sec->sh_size, 1)); - saveAddress(MemoryMap, addr); - } - else { - // FIXME: Currently memory with RWX permissions is allocated. In the - // future, make sure that permissions are as necessary - if (sec->sh_flags & ELF::SHF_WRITE) { - // see FIXME above - } - if (sec->sh_flags & ELF::SHF_EXECINSTR) { - // see FIXME above - } - } - assert(sizeof(addr_type) == sizeof(intptr_t) && - "Cross-architecture ELF dy-load is not supported!"); - sec->sh_addr = static_cast(intptr_t(addr)); - } - } - - // Now allocate actual space for COMMON symbols, which also don't occupy - // space in the object file. - // We want to allocate space for all COMMON symbols at once, so the flow is: - // 1. Go over all symbols, find those that are in COMMON. For each such - // symbol, record its size and the value field in its symbol header in a - // special vector. - // 2. Allocate memory for all COMMON symbols in one fell swoop. - // 3. Using the recorded information from (1), update the address fields in - // the symbol headers of the COMMON symbols to reflect their allocated - // address. - uint64_t TotalSize = 0; - std::vector > SymbAddrInfo; - error_code ec = object_error::success; - for (symbol_iterator si = this->begin_symbols(), - se = this->end_symbols(); si != se; si.increment(ec)) { - uint64_t Size = 0; - ec = si->getSize(Size); - Elf_Sym* symb = const_cast( - this->getSymbol(si->getRawDataRefImpl())); - if (ec == object_error::success && - this->getSymbolTableIndex(symb) == ELF::SHN_COMMON && Size > 0) { - SymbAddrInfo.push_back(std::make_pair(&(symb->st_value), Size)); - TotalSize += Size; - } - } - - uint8_t* SectionPtr = (uint8_t *)calloc(TotalSize, 1); - saveAddress(MemoryMap, SectionPtr); - - typedef typename std::vector >::iterator - AddrInfoIterator; - AddrInfoIterator EndIter = SymbAddrInfo.end(); - for (AddrInfoIterator AddrIter = SymbAddrInfo.begin(); - AddrIter != EndIter; ++AddrIter) { - assert(sizeof(addr_type) == sizeof(intptr_t) && - "Cross-architecture ELF dy-load is not supported!"); - *(AddrIter->first) = static_cast(intptr_t(SectionPtr)); - SectionPtr += AddrIter->second; - } -} - -// Record memory addresses for callers -template -void DyldELFObject::saveAddress( - std::vector *MemoryMap, uint8_t* addr) { - if (MemoryMap) - MemoryMap->push_back(addr); - else - errs() << "WARNING: Memory leak - cannot record memory for ELF dyld."; -} - -template -error_code DyldELFObject::getSymbolAddress( - DataRefImpl Symb, uint64_t &Result) const { - this->validateSymbol(Symb); - const Elf_Sym *symb = this->getSymbol(Symb); - if (this->getSymbolTableIndex(symb) == ELF::SHN_COMMON) { - Result = symb->st_value; - return object_error::success; - } - else { - return ELFObjectFile::getSymbolAddress( - Symb, Result); - } -} - -} - -#endif - -//===-- DyldELFObject.h - Dynamically loaded ELF object ----0---*- C++ -*-===// -// -// The LLVM Compiler Infrastructure -// -// This file is distributed under the University of Illinois Open Source -// License. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// -// -// Dynamically loaded ELF object class, a subclass of ELFObjectFile. Used -// to represent a loadable ELF image. -// -//===----------------------------------------------------------------------===// - -#ifndef LLVM_RUNTIMEDYLD_DYLDELFOBJECT_H -#define LLVM_RUNTIMEDYLD_DYLDELFOBJECT_H - -#include "llvm/Object/ELF.h" - - -namespace llvm { - -using support::endianness; -using namespace llvm::object; - -template -class DyldELFObject : public ELFObjectFile { - LLVM_ELF_IMPORT_TYPES(target_endianness, is64Bits) - - typedef Elf_Shdr_Impl Elf_Shdr; - typedef Elf_Sym_Impl Elf_Sym; - typedef Elf_Rel_Impl Elf_Rel; - typedef Elf_Rel_Impl Elf_Rela; - - typedef typename ELFObjectFile:: - Elf_Ehdr Elf_Ehdr; - Elf_Ehdr *Header; - - // Update section headers according to the current location in memory - virtual void rebaseObject(std::vector *MemoryMap); - // Record memory addresses for cleanup - virtual void saveAddress(std::vector *MemoryMap, uint8_t *addr); - -protected: - virtual error_code getSymbolAddress(DataRefImpl Symb, uint64_t &Res) const; - -public: - DyldELFObject(MemoryBuffer *Object, std::vector *MemoryMap, - error_code &ec); - - // Methods for type inquiry through isa, cast, and dyn_cast - static inline bool classof(const Binary *v) { - return (isa >(v) - && classof(cast >(v))); - } - static inline bool classof( - const ELFObjectFile *v) { - return v->isDyldType(); - } - static inline bool classof(const DyldELFObject *v) { - return true; - } -}; - -template -DyldELFObject::DyldELFObject(MemoryBuffer *Object, - std::vector *MemoryMap, error_code &ec) - : ELFObjectFile(Object, ec) - , Header(0) { - this->isDyldELFObject = true; - Header = const_cast( - reinterpret_cast(this->base())); - if (Header->e_shoff == 0) - return; - - // Mark the image as a dynamic shared library - Header->e_type = ELF::ET_DYN; - - rebaseObject(MemoryMap); -} - -// Walk through the ELF headers, updating virtual addresses to reflect where -// the object is currently loaded in memory -template -void DyldELFObject::rebaseObject( - std::vector *MemoryMap) { - typedef typename ELFDataTypeTypedefHelper< - target_endianness, is64Bits>::value_type addr_type; - - uint8_t *base_p = const_cast(this->base()); - Elf_Shdr *sectionTable = - reinterpret_cast(base_p + Header->e_shoff); - uint64_t numSections = this->getNumSections(); - - // Allocate memory space for NOBITS sections (such as .bss), which only exist - // in memory, but don't occupy space in the object file. - // Update the address in the section headers to reflect this allocation. - for (uint64_t index = 0; index < numSections; index++) { - Elf_Shdr *sec = reinterpret_cast( - reinterpret_cast(sectionTable) + index * Header->e_shentsize); - - // Only update sections that are meant to be present in program memory - if (sec->sh_flags & ELF::SHF_ALLOC) { - uint8_t *addr = base_p + sec->sh_offset; - if (sec->sh_type == ELF::SHT_NOBITS) { - addr = static_cast(calloc(sec->sh_size, 1)); - saveAddress(MemoryMap, addr); - } - else { - // FIXME: Currently memory with RWX permissions is allocated. In the - // future, make sure that permissions are as necessary - if (sec->sh_flags & ELF::SHF_WRITE) { - // see FIXME above - } - if (sec->sh_flags & ELF::SHF_EXECINSTR) { - // see FIXME above - } - } - assert(sizeof(addr_type) == sizeof(intptr_t) && - "Cross-architecture ELF dy-load is not supported!"); - sec->sh_addr = static_cast(intptr_t(addr)); - } - } - - // Now allocate actual space for COMMON symbols, which also don't occupy - // space in the object file. - // We want to allocate space for all COMMON symbols at once, so the flow is: - // 1. Go over all symbols, find those that are in COMMON. For each such - // symbol, record its size and the value field in its symbol header in a - // special vector. - // 2. Allocate memory for all COMMON symbols in one fell swoop. - // 3. Using the recorded information from (1), update the address fields in - // the symbol headers of the COMMON symbols to reflect their allocated - // address. - uint64_t TotalSize = 0; - std::vector > SymbAddrInfo; - error_code ec = object_error::success; - for (symbol_iterator si = this->begin_symbols(), - se = this->end_symbols(); si != se; si.increment(ec)) { - uint64_t Size = 0; - ec = si->getSize(Size); - Elf_Sym* symb = const_cast( - this->getSymbol(si->getRawDataRefImpl())); - if (ec == object_error::success && - this->getSymbolTableIndex(symb) == ELF::SHN_COMMON && Size > 0) { - SymbAddrInfo.push_back(std::make_pair(&(symb->st_value), Size)); - TotalSize += Size; - } - } - - uint8_t* SectionPtr = (uint8_t *)calloc(TotalSize, 1); - saveAddress(MemoryMap, SectionPtr); - - typedef typename std::vector >::iterator - AddrInfoIterator; - AddrInfoIterator EndIter = SymbAddrInfo.end(); - for (AddrInfoIterator AddrIter = SymbAddrInfo.begin(); - AddrIter != EndIter; ++AddrIter) { - assert(sizeof(addr_type) == sizeof(intptr_t) && - "Cross-architecture ELF dy-load is not supported!"); - *(AddrIter->first) = static_cast(intptr_t(SectionPtr)); - SectionPtr += AddrIter->second; - } -} - -// Record memory addresses for callers -template -void DyldELFObject::saveAddress( - std::vector *MemoryMap, uint8_t* addr) { - if (MemoryMap) - MemoryMap->push_back(addr); - else - errs() << "WARNING: Memory leak - cannot record memory for ELF dyld."; -} - -template -error_code DyldELFObject::getSymbolAddress( - DataRefImpl Symb, uint64_t &Result) const { - this->validateSymbol(Symb); - const Elf_Sym *symb = this->getSymbol(Symb); - if (this->getSymbolTableIndex(symb) == ELF::SHN_COMMON) { - Result = symb->st_value; - return object_error::success; - } - else { - return ELFObjectFile::getSymbolAddress( - Symb, Result); - } -} - -} - -#endif -