//===- ELFBinaryReader.cpp ------------------------------------------------===// // // The MCLinker Project // // This file is distributed under the University of Illinois Open Source // License. See LICENSE.TXT for details. // //===----------------------------------------------------------------------===// #include "mcld/LD/ELFBinaryReader.h" #include "mcld/IRBuilder.h" #include "mcld/LinkerConfig.h" #include "mcld/MC/Input.h" #include "mcld/Support/MemoryArea.h" #include <llvm/Support/ELF.h> #include <cctype> namespace mcld { //===----------------------------------------------------------------------===// // ELFBinaryReader //===----------------------------------------------------------------------===// /// constructor ELFBinaryReader::ELFBinaryReader(IRBuilder& pBuilder, const LinkerConfig& pConfig) : m_Builder(pBuilder), m_Config(pConfig) { } /// destructor ELFBinaryReader::~ELFBinaryReader() { } bool ELFBinaryReader::isMyFormat(Input& pInput, bool& pContinue) const { pContinue = true; return m_Config.options().isBinaryInput(); } bool ELFBinaryReader::readBinary(Input& pInput) { // section: NULL m_Builder.CreateELFHeader( pInput, "", LDFileFormat::Null, llvm::ELF::SHT_NULL, 0x0); // section: .data LDSection* data_sect = m_Builder.CreateELFHeader(pInput, ".data", LDFileFormat::DATA, llvm::ELF::SHF_WRITE | llvm::ELF::SHF_ALLOC, 0x1); SectionData* data = m_Builder.CreateSectionData(*data_sect); size_t data_size = pInput.memArea()->size(); Fragment* frag = m_Builder.CreateRegion(pInput, 0x0, data_size); m_Builder.AppendFragment(*frag, *data); // section: .shstrtab m_Builder.CreateELFHeader( pInput, ".shstrtab", LDFileFormat::NamePool, llvm::ELF::SHT_STRTAB, 0x1); // section: .symtab m_Builder.CreateELFHeader(pInput, ".symtab", LDFileFormat::NamePool, llvm::ELF::SHT_SYMTAB, m_Config.targets().bitclass() / 8); // symbol: .data m_Builder.AddSymbol(pInput, ".data", ResolveInfo::Section, ResolveInfo::Define, ResolveInfo::Local, 0x0, 0x0, data_sect); // Note: in Win32, the filename is wstring. Is it correct to convert // filename to std::string? std::string mangled_name = pInput.path().filename().native(); for (std::string::iterator it = mangled_name.begin(), ie = mangled_name.end(); it != ie; ++it) { if (isalnum(*it) == 0) *it = '_'; } // symbol: _start m_Builder.AddSymbol(pInput, "_binary_" + mangled_name + "_start", ResolveInfo::NoType, ResolveInfo::Define, ResolveInfo::Global, 0x0, 0x0, data_sect); // symbol: _end m_Builder.AddSymbol(pInput, "_binary_" + mangled_name + "_end", ResolveInfo::NoType, ResolveInfo::Define, ResolveInfo::Global, 0x0, data_size, data_sect); // symbol: _size m_Builder.AddSymbol(pInput, "_binary_" + mangled_name + "_size", ResolveInfo::NoType, ResolveInfo::Define, ResolveInfo::Global, 0x0, data_size, data_sect); // section: .strtab m_Builder.CreateELFHeader( pInput, ".strtab", LDFileFormat::NamePool, llvm::ELF::SHT_STRTAB, 0x1); return true; } } // namespace mcld