diff options
-rw-r--r-- | compiler/dwarf/dwarf_test.h | 14 | ||||
-rw-r--r-- | compiler/elf_builder.h | 121 | ||||
-rw-r--r-- | compiler/elf_writer_quick.cc | 101 | ||||
-rw-r--r-- | compiler/elf_writer_quick.h | 10 | ||||
-rw-r--r-- | oatdump/oatdump.cc | 9 | ||||
-rw-r--r-- | runtime/elf.h | 32 | ||||
-rw-r--r-- | runtime/elf_file.cc | 575 | ||||
-rw-r--r-- | runtime/elf_file.h | 10 | ||||
-rw-r--r-- | runtime/elf_file_impl.h | 21 |
9 files changed, 330 insertions, 563 deletions
diff --git a/compiler/dwarf/dwarf_test.h b/compiler/dwarf/dwarf_test.h index d31cfa5..99b8e79 100644 --- a/compiler/dwarf/dwarf_test.h +++ b/compiler/dwarf/dwarf_test.h @@ -56,8 +56,7 @@ class DwarfTest : public CommonRuntimeTest { } // Pretty-print the generated DWARF data using objdump. - template<typename Elf_Word, typename Elf_Sword, typename Elf_Addr, typename Elf_Dyn, - typename Elf_Sym, typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr> + template<typename ElfTypes> std::vector<std::string> Objdump(bool is64bit, const char* args) { // Write simple elf file with just the DWARF sections. class NoCode : public CodeOutput { @@ -66,10 +65,9 @@ class DwarfTest : public CommonRuntimeTest { } code; ScratchFile file; InstructionSet isa = is64bit ? kX86_64 : kX86; - ElfBuilder<Elf_Word, Elf_Sword, Elf_Addr, Elf_Dyn, - Elf_Sym, Elf_Ehdr, Elf_Phdr, Elf_Shdr> builder( + ElfBuilder<ElfTypes> builder( &code, file.GetFile(), isa, 0, 0, 0, 0, 0, 0, false, false); - typedef ElfRawSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr> Section; + typedef ElfRawSectionBuilder<ElfTypes> Section; Section debug_info(".debug_info", SHT_PROGBITS, 0, nullptr, 0, 1, 0); Section debug_abbrev(".debug_abbrev", SHT_PROGBITS, 0, nullptr, 0, 1, 0); Section debug_str(".debug_str", SHT_PROGBITS, 0, nullptr, 0, 1, 0); @@ -125,11 +123,9 @@ class DwarfTest : public CommonRuntimeTest { std::vector<std::string> Objdump(bool is64bit, const char* args) { if (is64bit) { - return Objdump<Elf64_Word, Elf64_Sword, Elf64_Addr, Elf64_Dyn, - Elf64_Sym, Elf64_Ehdr, Elf64_Phdr, Elf64_Shdr>(is64bit, args); + return Objdump<ElfTypes64>(is64bit, args); } else { - return Objdump<Elf32_Word, Elf32_Sword, Elf32_Addr, Elf32_Dyn, - Elf32_Sym, Elf32_Ehdr, Elf32_Phdr, Elf32_Shdr>(is64bit, args); + return Objdump<ElfTypes32>(is64bit, args); } } diff --git a/compiler/elf_builder.h b/compiler/elf_builder.h index 323c933..b67dd26 100644 --- a/compiler/elf_builder.h +++ b/compiler/elf_builder.h @@ -26,11 +26,14 @@ namespace art { -template <typename Elf_Word, typename Elf_Sword, typename Elf_Shdr> +template <typename ElfTypes> class ElfSectionBuilder : public ValueObject { public: + using Elf_Word = typename ElfTypes::Word; + using Elf_Shdr = typename ElfTypes::Shdr; + ElfSectionBuilder(const std::string& sec_name, Elf_Word type, Elf_Word flags, - const ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr> *link, Elf_Word info, + const ElfSectionBuilder<ElfTypes> *link, Elf_Word info, Elf_Word align, Elf_Word entsize) : section_index_(0), name_(sec_name), link_(link) { memset(§ion_, 0, sizeof(section_)); @@ -75,9 +78,14 @@ class ElfSectionBuilder : public ValueObject { const ElfSectionBuilder* const link_; }; -template <typename Elf_Word, typename Elf_Sword, typename Elf_Dyn, typename Elf_Shdr> -class ElfDynamicBuilder FINAL : public ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr> { +template <typename ElfTypes> +class ElfDynamicBuilder FINAL : public ElfSectionBuilder<ElfTypes> { public: + using Elf_Word = typename ElfTypes::Word; + using Elf_Sword = typename ElfTypes::Sword; + using Elf_Shdr = typename ElfTypes::Shdr; + using Elf_Dyn = typename ElfTypes::Dyn; + void AddDynamicTag(Elf_Sword tag, Elf_Word d_un) { if (tag == DT_NULL) { return; @@ -86,7 +94,7 @@ class ElfDynamicBuilder FINAL : public ElfSectionBuilder<Elf_Word, Elf_Sword, El } void AddDynamicTag(Elf_Sword tag, Elf_Word d_un, - const ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr>* section) { + const ElfSectionBuilder<ElfTypes>* section) { if (tag == DT_NULL) { return; } @@ -94,9 +102,9 @@ class ElfDynamicBuilder FINAL : public ElfSectionBuilder<Elf_Word, Elf_Sword, El } ElfDynamicBuilder(const std::string& sec_name, - ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr> *link) - : ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr>(sec_name, SHT_DYNAMIC, SHF_ALLOC | SHF_ALLOC, - link, 0, kPageSize, sizeof(Elf_Dyn)) {} + ElfSectionBuilder<ElfTypes> *link) + : ElfSectionBuilder<ElfTypes>(sec_name, SHT_DYNAMIC, SHF_ALLOC | SHF_ALLOC, + link, 0, kPageSize, sizeof(Elf_Dyn)) {} ~ElfDynamicBuilder() {} Elf_Word GetSize() const { @@ -129,21 +137,22 @@ class ElfDynamicBuilder FINAL : public ElfSectionBuilder<Elf_Word, Elf_Sword, El private: struct ElfDynamicState { - const ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr>* section_; + const ElfSectionBuilder<ElfTypes>* section_; Elf_Sword tag_; Elf_Word off_; }; std::vector<ElfDynamicState> dynamics_; }; -template <typename Elf_Word, typename Elf_Sword, typename Elf_Shdr> -class ElfRawSectionBuilder FINAL : public ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr> { +template <typename ElfTypes> +class ElfRawSectionBuilder FINAL : public ElfSectionBuilder<ElfTypes> { public: + using Elf_Word = typename ElfTypes::Word; + ElfRawSectionBuilder(const std::string& sec_name, Elf_Word type, Elf_Word flags, - const ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr>* link, Elf_Word info, + const ElfSectionBuilder<ElfTypes>* link, Elf_Word info, Elf_Word align, Elf_Word entsize) - : ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr>(sec_name, type, flags, link, info, align, - entsize) { + : ElfSectionBuilder<ElfTypes>(sec_name, type, flags, link, info, align, entsize) { } ElfRawSectionBuilder(const ElfRawSectionBuilder&) = default; @@ -161,13 +170,14 @@ class ElfRawSectionBuilder FINAL : public ElfSectionBuilder<Elf_Word, Elf_Sword, std::vector<uint8_t> buf_; }; -template <typename Elf_Word, typename Elf_Sword, typename Elf_Shdr> -class ElfOatSectionBuilder FINAL : public ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr> { +template <typename ElfTypes> +class ElfOatSectionBuilder FINAL : public ElfSectionBuilder<ElfTypes> { public: + using Elf_Word = typename ElfTypes::Word; + ElfOatSectionBuilder(const std::string& sec_name, Elf_Word size, Elf_Word offset, Elf_Word type, Elf_Word flags) - : ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr>(sec_name, type, flags, nullptr, 0, kPageSize, - 0), + : ElfSectionBuilder<ElfTypes>(sec_name, type, flags, nullptr, 0, kPageSize, 0), offset_(offset), size_(size) { } @@ -206,14 +216,17 @@ static inline unsigned elfhash(const char *_name) { return h; } -template <typename Elf_Word, typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, - typename Elf_Shdr> -class ElfSymtabBuilder FINAL : public ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr> { +template <typename ElfTypes> +class ElfSymtabBuilder FINAL : public ElfSectionBuilder<ElfTypes> { public: + using Elf_Addr = typename ElfTypes::Addr; + using Elf_Word = typename ElfTypes::Word; + using Elf_Sym = typename ElfTypes::Sym; + // Add a symbol with given name to this symtab. The symbol refers to // 'relative_addr' within the given section and has the given attributes. void AddSymbol(const std::string& name, - const ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr>* section, + const ElfSectionBuilder<ElfTypes>* section, Elf_Addr addr, bool is_relative, Elf_Word size, @@ -228,14 +241,14 @@ class ElfSymtabBuilder FINAL : public ElfSectionBuilder<Elf_Word, Elf_Sword, Elf ElfSymtabBuilder(const std::string& sec_name, Elf_Word type, const std::string& str_name, Elf_Word str_type, bool alloc) - : ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr>(sec_name, type, ((alloc) ? SHF_ALLOC : 0U), - &strtab_, 0, sizeof(Elf_Word), - sizeof(Elf_Sym)), str_name_(str_name), - str_type_(str_type), - strtab_(str_name, - str_type, - ((alloc) ? SHF_ALLOC : 0U), - nullptr, 0, 1, 1) { + : ElfSectionBuilder<ElfTypes>(sec_name, type, ((alloc) ? SHF_ALLOC : 0U), + &strtab_, 0, sizeof(Elf_Word), + sizeof(Elf_Sym)), str_name_(str_name), + str_type_(str_type), + strtab_(str_name, + str_type, + ((alloc) ? SHF_ALLOC : 0U), + nullptr, 0, 1, 1) { } ~ElfSymtabBuilder() {} @@ -365,14 +378,14 @@ class ElfSymtabBuilder FINAL : public ElfSectionBuilder<Elf_Word, Elf_Sword, Elf return symbols_.size() + 1; } - ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr>* GetStrTab() { + ElfSectionBuilder<ElfTypes>* GetStrTab() { return &strtab_; } private: struct ElfSymbolState { const std::string name_; - const ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr>* section_; + const ElfSectionBuilder<ElfTypes>* section_; Elf_Addr addr_; Elf_Word size_; bool is_relative_; @@ -387,7 +400,7 @@ class ElfSymtabBuilder FINAL : public ElfSectionBuilder<Elf_Word, Elf_Sword, Elf Elf_Word str_type_; // The symbols in the same order they will be in the symbol table. std::vector<ElfSymbolState> symbols_; - ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr> strtab_; + ElfSectionBuilder<ElfTypes> strtab_; }; template <typename Elf_Word> @@ -529,10 +542,18 @@ static inline constexpr Elf_Word NextOffset(const Elf_Shdr& cur, const Elf_Shdr& return RoundUp(prev.sh_size + prev.sh_offset, cur.sh_addralign); } -template <typename Elf_Word, typename Elf_Sword, typename Elf_Addr, typename Elf_Dyn, - typename Elf_Sym, typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr> +template <typename ElfTypes> class ElfBuilder FINAL { public: + using Elf_Addr = typename ElfTypes::Addr; + using Elf_Word = typename ElfTypes::Word; + using Elf_Sword = typename ElfTypes::Sword; + using Elf_Ehdr = typename ElfTypes::Ehdr; + using Elf_Shdr = typename ElfTypes::Shdr; + using Elf_Sym = typename ElfTypes::Sym; + using Elf_Phdr = typename ElfTypes::Phdr; + using Elf_Dyn = typename ElfTypes::Dyn; + ElfBuilder(CodeOutput* oat_writer, File* elf_file, InstructionSet isa, @@ -565,11 +586,11 @@ class ElfBuilder FINAL { } ~ElfBuilder() {} - const ElfOatSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr>& GetTextBuilder() const { + const ElfOatSectionBuilder<ElfTypes>& GetTextBuilder() const { return text_builder_; } - ElfSymtabBuilder<Elf_Word, Elf_Sword, Elf_Addr, Elf_Sym, Elf_Shdr>* GetSymtabBuilder() { + ElfSymtabBuilder<ElfTypes>* GetSymtabBuilder() { return &symtab_builder_; } @@ -1181,12 +1202,11 @@ class ElfBuilder FINAL { } // Adds the given raw section to the builder. It does not take ownership. - void RegisterRawSection(ElfRawSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr>* bld) { + void RegisterRawSection(ElfRawSectionBuilder<ElfTypes>* bld) { other_builders_.push_back(bld); } - const ElfRawSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr>* - FindRawSection(const char* name) { + const ElfRawSectionBuilder<ElfTypes>* FindRawSection(const char* name) { for (const auto* other_builder : other_builders_) { if (other_builder->GetName() == name) { return other_builder; @@ -1304,8 +1324,7 @@ class ElfBuilder FINAL { } } - void AssignSectionStr(ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr>* builder, - std::string* strtab) { + void AssignSectionStr(ElfSectionBuilder<ElfTypes>* builder, std::string* strtab) { builder->GetSection()->sh_name = strtab->size(); *strtab += builder->GetName(); *strtab += '\0'; @@ -1363,15 +1382,15 @@ class ElfBuilder FINAL { std::vector<const Elf_Shdr*> section_ptrs_; std::vector<Elf_Word> hash_; - ElfOatSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr> text_builder_; - ElfOatSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr> rodata_builder_; - ElfOatSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr> bss_builder_; - ElfSymtabBuilder<Elf_Word, Elf_Sword, Elf_Addr, Elf_Sym, Elf_Shdr> dynsym_builder_; - ElfSymtabBuilder<Elf_Word, Elf_Sword, Elf_Addr, Elf_Sym, Elf_Shdr> symtab_builder_; - ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr> hash_builder_; - ElfDynamicBuilder<Elf_Word, Elf_Sword, Elf_Dyn, Elf_Shdr> dynamic_builder_; - ElfSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr> shstrtab_builder_; - std::vector<ElfRawSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr>*> other_builders_; + ElfOatSectionBuilder<ElfTypes> text_builder_; + ElfOatSectionBuilder<ElfTypes> rodata_builder_; + ElfOatSectionBuilder<ElfTypes> bss_builder_; + ElfSymtabBuilder<ElfTypes> dynsym_builder_; + ElfSymtabBuilder<ElfTypes> symtab_builder_; + ElfSectionBuilder<ElfTypes> hash_builder_; + ElfDynamicBuilder<ElfTypes> dynamic_builder_; + ElfSectionBuilder<ElfTypes> shstrtab_builder_; + std::vector<ElfRawSectionBuilder<ElfTypes>*> other_builders_; DISALLOW_COPY_AND_ASSIGN(ElfBuilder); }; diff --git a/compiler/elf_writer_quick.cc b/compiler/elf_writer_quick.cc index 44c14a0..949fcab 100644 --- a/compiler/elf_writer_quick.cc +++ b/compiler/elf_writer_quick.cc @@ -39,16 +39,13 @@ namespace art { -template <typename Elf_Word, typename Elf_Sword, typename Elf_Addr, - typename Elf_Dyn, typename Elf_Sym, typename Elf_Ehdr, - typename Elf_Phdr, typename Elf_Shdr> -bool ElfWriterQuick<Elf_Word, Elf_Sword, Elf_Addr, Elf_Dyn, - Elf_Sym, Elf_Ehdr, Elf_Phdr, Elf_Shdr>::Create(File* elf_file, - OatWriter* oat_writer, - const std::vector<const DexFile*>& dex_files, - const std::string& android_root, - bool is_host, - const CompilerDriver& driver) { +template <typename ElfTypes> +bool ElfWriterQuick<ElfTypes>::Create(File* elf_file, + OatWriter* oat_writer, + const std::vector<const DexFile*>& dex_files, + const std::string& android_root, + bool is_host, + const CompilerDriver& driver) { ElfWriterQuick elf_writer(driver, elf_file); return elf_writer.Write(oat_writer, dex_files, android_root, is_host); } @@ -67,20 +64,14 @@ class OatWriterWrapper FINAL : public CodeOutput { OatWriter* const oat_writer_; }; -template <typename Elf_Word, typename Elf_Sword, typename Elf_Addr, - typename Elf_Dyn, typename Elf_Sym, typename Elf_Ehdr, - typename Elf_Phdr, typename Elf_Shdr> -static void WriteDebugSymbols(ElfBuilder<Elf_Word, Elf_Sword, Elf_Addr, Elf_Dyn, - Elf_Sym, Elf_Ehdr, Elf_Phdr, Elf_Shdr>* builder, - OatWriter* oat_writer); +template <typename ElfTypes> +static void WriteDebugSymbols(ElfBuilder<ElfTypes>* builder, OatWriter* oat_writer); // Encode patch locations in .oat_patches format. -template <typename Elf_Word, typename Elf_Sword, typename Elf_Addr, - typename Elf_Dyn, typename Elf_Sym, typename Elf_Ehdr, - typename Elf_Phdr, typename Elf_Shdr> -void ElfWriterQuick<Elf_Word, Elf_Sword, Elf_Addr, Elf_Dyn, Elf_Sym, Elf_Ehdr, - Elf_Phdr, Elf_Shdr>::EncodeOatPatches(const OatWriter::PatchLocationsMap& sections, - std::vector<uint8_t>* buffer) { +template <typename ElfTypes> +void ElfWriterQuick<ElfTypes>::EncodeOatPatches( + const OatWriter::PatchLocationsMap& sections, + std::vector<uint8_t>* buffer) { for (const auto& section : sections) { const std::string& name = section.first; std::vector<uintptr_t>* locations = section.second.get(); @@ -121,41 +112,36 @@ static void PatchAddresses(const std::vector<uintptr_t>* patch_locations, } } -template <typename Elf_Word, typename Elf_Sword, typename Elf_Addr, - typename Elf_Dyn, typename Elf_Sym, typename Elf_Ehdr, - typename Elf_Phdr, typename Elf_Shdr> -bool ElfWriterQuick<Elf_Word, Elf_Sword, Elf_Addr, Elf_Dyn, - Elf_Sym, Elf_Ehdr, Elf_Phdr, Elf_Shdr>::Write(OatWriter* oat_writer, - const std::vector<const DexFile*>& dex_files_unused ATTRIBUTE_UNUSED, - const std::string& android_root_unused ATTRIBUTE_UNUSED, - bool is_host_unused ATTRIBUTE_UNUSED) { +template <typename ElfTypes> +bool ElfWriterQuick<ElfTypes>::Write( + OatWriter* oat_writer, + const std::vector<const DexFile*>& dex_files_unused ATTRIBUTE_UNUSED, + const std::string& android_root_unused ATTRIBUTE_UNUSED, + bool is_host_unused ATTRIBUTE_UNUSED) { constexpr bool debug = false; const OatHeader& oat_header = oat_writer->GetOatHeader(); - Elf_Word oat_data_size = oat_header.GetExecutableOffset(); + typename ElfTypes::Word oat_data_size = oat_header.GetExecutableOffset(); uint32_t oat_exec_size = oat_writer->GetSize() - oat_data_size; uint32_t oat_bss_size = oat_writer->GetBssSize(); OatWriterWrapper wrapper(oat_writer); - std::unique_ptr<ElfBuilder<Elf_Word, Elf_Sword, Elf_Addr, Elf_Dyn, - Elf_Sym, Elf_Ehdr, Elf_Phdr, Elf_Shdr> > builder( - new ElfBuilder<Elf_Word, Elf_Sword, Elf_Addr, Elf_Dyn, - Elf_Sym, Elf_Ehdr, Elf_Phdr, Elf_Shdr>( - &wrapper, - elf_file_, - compiler_driver_->GetInstructionSet(), - 0, - oat_data_size, - oat_data_size, - oat_exec_size, - RoundUp(oat_data_size + oat_exec_size, kPageSize), - oat_bss_size, - compiler_driver_->GetCompilerOptions().GetIncludeDebugSymbols(), - debug)); + std::unique_ptr<ElfBuilder<ElfTypes>> builder(new ElfBuilder<ElfTypes>( + &wrapper, + elf_file_, + compiler_driver_->GetInstructionSet(), + 0, + oat_data_size, + oat_data_size, + oat_exec_size, + RoundUp(oat_data_size + oat_exec_size, kPageSize), + oat_bss_size, + compiler_driver_->GetCompilerOptions().GetIncludeDebugSymbols(), + debug)); InstructionSet isa = compiler_driver_->GetInstructionSet(); int alignment = GetInstructionSetPointerSize(isa); - typedef ElfRawSectionBuilder<Elf_Word, Elf_Sword, Elf_Shdr> RawSection; + typedef ElfRawSectionBuilder<ElfTypes> RawSection; RawSection eh_frame(".eh_frame", SHT_PROGBITS, SHF_ALLOC, nullptr, 0, alignment, 0); RawSection eh_frame_hdr(".eh_frame_hdr", SHT_PROGBITS, SHF_ALLOC, nullptr, 0, 4, 0); RawSection debug_info(".debug_info", SHT_PROGBITS, 0, nullptr, 0, 1, 0); @@ -210,8 +196,8 @@ bool ElfWriterQuick<Elf_Word, Elf_Sword, Elf_Addr, Elf_Dyn, } // We know where .text and .eh_frame will be located, so patch the addresses. - Elf_Addr text_addr = builder->GetTextBuilder().GetSection()->sh_addr; - // TODO: Simplify once we use Elf64 - we can use Elf_Addr instead of branching. + typename ElfTypes::Addr text_addr = builder->GetTextBuilder().GetSection()->sh_addr; + // TODO: Simplify once we use Elf64 - we can use ElfTypes::Addr instead of branching. if (Is64BitInstructionSet(compiler_driver_->GetInstructionSet())) { // relative_address = (text_addr + address) - (eh_frame_addr + patch_location); PatchAddresses<uint64_t, true>(&eh_frame_patches, @@ -229,14 +215,10 @@ bool ElfWriterQuick<Elf_Word, Elf_Sword, Elf_Addr, Elf_Dyn, return builder->Write(); } -template <typename Elf_Word, typename Elf_Sword, typename Elf_Addr, - typename Elf_Dyn, typename Elf_Sym, typename Elf_Ehdr, - typename Elf_Phdr, typename Elf_Shdr> +template <typename ElfTypes> // Do not inline to avoid Clang stack frame problems. b/18738594 NO_INLINE -static void WriteDebugSymbols(ElfBuilder<Elf_Word, Elf_Sword, Elf_Addr, Elf_Dyn, - Elf_Sym, Elf_Ehdr, Elf_Phdr, Elf_Shdr>* builder, - OatWriter* oat_writer) { +static void WriteDebugSymbols(ElfBuilder<ElfTypes>* builder, OatWriter* oat_writer) { const std::vector<OatWriter::DebugInfo>& method_info = oat_writer->GetMethodDebugInfo(); // Find all addresses (low_pc) which contain deduped methods. @@ -248,8 +230,7 @@ static void WriteDebugSymbols(ElfBuilder<Elf_Word, Elf_Sword, Elf_Addr, Elf_Dyn, } } - ElfSymtabBuilder<Elf_Word, Elf_Sword, Elf_Addr, Elf_Sym, Elf_Shdr>* symtab = - builder->GetSymtabBuilder(); + ElfSymtabBuilder<ElfTypes>* symtab = builder->GetSymtabBuilder(); for (auto it = method_info.begin(); it != method_info.end(); ++it) { std::string name = PrettyMethod(it->dex_method_index_, *it->dex_file_, true); if (deduped_addresses.find(it->low_pc_) != deduped_addresses.end()) { @@ -272,9 +253,7 @@ static void WriteDebugSymbols(ElfBuilder<Elf_Word, Elf_Sword, Elf_Addr, Elf_Dyn, } // Explicit instantiations -template class ElfWriterQuick<Elf32_Word, Elf32_Sword, Elf32_Addr, Elf32_Dyn, - Elf32_Sym, Elf32_Ehdr, Elf32_Phdr, Elf32_Shdr>; -template class ElfWriterQuick<Elf64_Word, Elf64_Sword, Elf64_Addr, Elf64_Dyn, - Elf64_Sym, Elf64_Ehdr, Elf64_Phdr, Elf64_Shdr>; +template class ElfWriterQuick<ElfTypes32>; +template class ElfWriterQuick<ElfTypes64>; } // namespace art diff --git a/compiler/elf_writer_quick.h b/compiler/elf_writer_quick.h index 811beb4..955b568 100644 --- a/compiler/elf_writer_quick.h +++ b/compiler/elf_writer_quick.h @@ -23,9 +23,7 @@ namespace art { -template <typename Elf_Word, typename Elf_Sword, typename Elf_Addr, - typename Elf_Dyn, typename Elf_Sym, typename Elf_Ehdr, - typename Elf_Phdr, typename Elf_Shdr> +template <typename ElfTypes> class ElfWriterQuick FINAL : public ElfWriter { public: // Write an ELF file. Returns true on success, false on failure. @@ -57,10 +55,8 @@ class ElfWriterQuick FINAL : public ElfWriter { }; // Explicitly instantiated in elf_writer_quick.cc -typedef ElfWriterQuick<Elf32_Word, Elf32_Sword, Elf32_Addr, Elf32_Dyn, - Elf32_Sym, Elf32_Ehdr, Elf32_Phdr, Elf32_Shdr> ElfWriterQuick32; -typedef ElfWriterQuick<Elf64_Word, Elf64_Sword, Elf64_Addr, Elf64_Dyn, - Elf64_Sym, Elf64_Ehdr, Elf64_Phdr, Elf64_Shdr> ElfWriterQuick64; +typedef ElfWriterQuick<ElfTypes32> ElfWriterQuick32; +typedef ElfWriterQuick<ElfTypes64> ElfWriterQuick64; } // namespace art diff --git a/oatdump/oatdump.cc b/oatdump/oatdump.cc index a36e5b1..d6d8808 100644 --- a/oatdump/oatdump.cc +++ b/oatdump/oatdump.cc @@ -92,8 +92,7 @@ class OatSymbolizer FINAL : public CodeOutput { elf_output_ = OS::CreateEmptyFile(output_name_.c_str()); - builder_.reset(new ElfBuilder<Elf32_Word, Elf32_Sword, Elf32_Addr, Elf32_Dyn, - Elf32_Sym, Elf32_Ehdr, Elf32_Phdr, Elf32_Shdr>( + builder_.reset(new ElfBuilder<ElfTypes32>( this, elf_output_, oat_file_->GetOatHeader().GetInstructionSet(), @@ -270,8 +269,7 @@ class OatSymbolizer FINAL : public CodeOutput { pretty_name = "[Dedup]" + pretty_name; } - ElfSymtabBuilder<Elf32_Word, Elf32_Sword, Elf32_Addr, - Elf32_Sym, Elf32_Shdr>* symtab = builder_->GetSymtabBuilder(); + ElfSymtabBuilder<ElfTypes32>* symtab = builder_->GetSymtabBuilder(); symtab->AddSymbol(pretty_name, &builder_->GetTextBuilder(), oat_method.GetCodeOffset() - oat_file_->GetOatHeader().GetExecutableOffset(), @@ -300,8 +298,7 @@ class OatSymbolizer FINAL : public CodeOutput { } const OatFile* oat_file_; - std::unique_ptr<ElfBuilder<Elf32_Word, Elf32_Sword, Elf32_Addr, Elf32_Dyn, - Elf32_Sym, Elf32_Ehdr, Elf32_Phdr, Elf32_Shdr> > builder_; + std::unique_ptr<ElfBuilder<ElfTypes32> > builder_; File* elf_output_; std::unordered_map<uint32_t, uint32_t> state_; const std::string output_name_; diff --git a/runtime/elf.h b/runtime/elf.h index 60b5248..4514bb2 100644 --- a/runtime/elf.h +++ b/runtime/elf.h @@ -1852,6 +1852,38 @@ enum { VER_NEED_CURRENT = 1 }; +struct ElfTypes32 { + typedef Elf32_Addr Addr; + typedef Elf32_Off Off; + typedef Elf32_Half Half; + typedef Elf32_Word Word; + typedef Elf32_Sword Sword; + typedef Elf32_Ehdr Ehdr; + typedef Elf32_Shdr Shdr; + typedef Elf32_Sym Sym; + typedef Elf32_Rel Rel; + typedef Elf32_Rela Rela; + typedef Elf32_Phdr Phdr; + typedef Elf32_Dyn Dyn; +}; + +struct ElfTypes64 { + typedef Elf64_Addr Addr; + typedef Elf64_Off Off; + typedef Elf64_Half Half; + typedef Elf64_Word Word; + typedef Elf64_Sword Sword; + typedef Elf64_Xword Xword; + typedef Elf64_Sxword Sxword; + typedef Elf64_Ehdr Ehdr; + typedef Elf64_Shdr Shdr; + typedef Elf64_Sym Sym; + typedef Elf64_Rel Rel; + typedef Elf64_Rela Rela; + typedef Elf64_Phdr Phdr; + typedef Elf64_Dyn Dyn; +}; + // BEGIN android-changed #endif // ART_RUNTIME_ELF_H_ // END android-changed diff --git a/runtime/elf_file.cc b/runtime/elf_file.cc index 37e391d..8969e29 100644 --- a/runtime/elf_file.cc +++ b/runtime/elf_file.cc @@ -110,12 +110,10 @@ static void UnregisterCodeEntry(JITCodeEntry* entry) { delete entry; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::ElfFileImpl(File* file, bool writable, bool program_header_only, uint8_t* requested_base) +template <typename ElfTypes> +ElfFileImpl<ElfTypes>::ElfFileImpl(File* file, bool writable, + bool program_header_only, + uint8_t* requested_base) : file_(file), writable_(writable), program_header_only_(program_header_only), @@ -138,20 +136,12 @@ ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, CHECK(file != nullptr); } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off>* - ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::Open(File* file, bool writable, bool program_header_only, - std::string* error_msg, uint8_t* requested_base) { - std::unique_ptr<ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off>> - elf_file(new ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - (file, writable, program_header_only, requested_base)); +template <typename ElfTypes> +ElfFileImpl<ElfTypes>* ElfFileImpl<ElfTypes>::Open( + File* file, bool writable, bool program_header_only, + std::string* error_msg, uint8_t* requested_base) { + std::unique_ptr<ElfFileImpl<ElfTypes>> elf_file(new ElfFileImpl<ElfTypes> + (file, writable, program_header_only, requested_base)); int prot; int flags; if (writable) { @@ -167,32 +157,20 @@ ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return elf_file.release(); } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off>* - ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::Open(File* file, int prot, int flags, std::string* error_msg) { - std::unique_ptr<ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off>> - elf_file(new ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - (file, (prot & PROT_WRITE) == PROT_WRITE, /*program_header_only*/false, - /*requested_base*/nullptr)); +template <typename ElfTypes> +ElfFileImpl<ElfTypes>* ElfFileImpl<ElfTypes>::Open( + File* file, int prot, int flags, std::string* error_msg) { + std::unique_ptr<ElfFileImpl<ElfTypes>> elf_file(new ElfFileImpl<ElfTypes> + (file, (prot & PROT_WRITE) == PROT_WRITE, /*program_header_only*/false, + /*requested_base*/nullptr)); if (!elf_file->Setup(prot, flags, error_msg)) { return nullptr; } return elf_file.release(); } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::Setup(int prot, int flags, std::string* error_msg) { +template <typename ElfTypes> +bool ElfFileImpl<ElfTypes>::Setup(int prot, int flags, std::string* error_msg) { int64_t temp_file_length = file_->GetLength(); if (temp_file_length < 0) { errno = -temp_file_length; @@ -349,12 +327,8 @@ bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return true; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::~ElfFileImpl() { +template <typename ElfTypes> +ElfFileImpl<ElfTypes>::~ElfFileImpl() { STLDeleteElements(&segments_); delete symtab_symbol_table_; delete dynsym_symbol_table_; @@ -364,13 +338,9 @@ ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, } } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::CheckAndSet(Elf32_Off offset, const char* label, - uint8_t** target, std::string* error_msg) { +template <typename ElfTypes> +bool ElfFileImpl<ElfTypes>::CheckAndSet(Elf32_Off offset, const char* label, + uint8_t** target, std::string* error_msg) { if (Begin() + offset >= End()) { *error_msg = StringPrintf("Offset %d is out of range for %s in ELF file: '%s'", offset, label, file_->GetPath().c_str()); @@ -380,12 +350,9 @@ bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return true; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::CheckSectionsLinked(const uint8_t* source, const uint8_t* target) const { +template <typename ElfTypes> +bool ElfFileImpl<ElfTypes>::CheckSectionsLinked(const uint8_t* source, + const uint8_t* target) const { // Only works in whole-program mode, as we need to iterate over the sections. // Note that we normally can't search by type, as duplicates are allowed for most section types. if (program_header_only_) { @@ -416,12 +383,8 @@ bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return target_found && source_section != nullptr && source_section->sh_link == target_index; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::CheckSectionsExist(std::string* error_msg) const { +template <typename ElfTypes> +bool ElfFileImpl<ElfTypes>::CheckSectionsExist(std::string* error_msg) const { if (!program_header_only_) { // If in full mode, need section headers. if (section_headers_start_ == nullptr) { @@ -504,12 +467,8 @@ bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return true; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::SetMap(MemMap* map, std::string* error_msg) { +template <typename ElfTypes> +bool ElfFileImpl<ElfTypes>::SetMap(MemMap* map, std::string* error_msg) { if (map == nullptr) { // MemMap::Open should have already set an error. DCHECK(!error_msg->empty()); @@ -643,64 +602,41 @@ bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return true; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Ehdr& ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetHeader() const { +template <typename ElfTypes> +typename ElfTypes::Ehdr& ElfFileImpl<ElfTypes>::GetHeader() const { CHECK(header_ != nullptr); // Header has been checked in SetMap. This is a sanity check. return *header_; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -uint8_t* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetProgramHeadersStart() const { +template <typename ElfTypes> +uint8_t* ElfFileImpl<ElfTypes>::GetProgramHeadersStart() const { CHECK(program_headers_start_ != nullptr); // Header has been set in Setup. This is a sanity // check. return program_headers_start_; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -uint8_t* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetSectionHeadersStart() const { +template <typename ElfTypes> +uint8_t* ElfFileImpl<ElfTypes>::GetSectionHeadersStart() const { CHECK(!program_header_only_); // Only used in "full" mode. CHECK(section_headers_start_ != nullptr); // Is checked in CheckSectionsExist. Sanity check. return section_headers_start_; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Phdr& ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetDynamicProgramHeader() const { +template <typename ElfTypes> +typename ElfTypes::Phdr& ElfFileImpl<ElfTypes>::GetDynamicProgramHeader() const { CHECK(dynamic_program_header_ != nullptr); // Is checked in CheckSectionsExist. Sanity check. return *dynamic_program_header_; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Dyn* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetDynamicSectionStart() const { +template <typename ElfTypes> +typename ElfTypes::Dyn* ElfFileImpl<ElfTypes>::GetDynamicSectionStart() const { CHECK(dynamic_section_start_ != nullptr); // Is checked in CheckSectionsExist. Sanity check. return dynamic_section_start_; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Sym* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetSymbolSectionStart(Elf_Word section_type) const { +template <typename ElfTypes> +typename ElfTypes::Sym* ElfFileImpl<ElfTypes>::GetSymbolSectionStart( + Elf_Word section_type) const { CHECK(IsSymbolSectionType(section_type)) << file_->GetPath() << " " << section_type; switch (section_type) { case SHT_SYMTAB: { @@ -718,12 +654,9 @@ Elf_Sym* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, } } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -const char* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetStringSectionStart(Elf_Word section_type) const { +template <typename ElfTypes> +const char* ElfFileImpl<ElfTypes>::GetStringSectionStart( + Elf_Word section_type) const { CHECK(IsSymbolSectionType(section_type)) << file_->GetPath() << " " << section_type; switch (section_type) { case SHT_SYMTAB: { @@ -739,12 +672,9 @@ const char* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, } } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -const char* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetString(Elf_Word section_type, Elf_Word i) const { +template <typename ElfTypes> +const char* ElfFileImpl<ElfTypes>::GetString(Elf_Word section_type, + Elf_Word i) const { CHECK(IsSymbolSectionType(section_type)) << file_->GetPath() << " " << section_type; if (i == 0) { return nullptr; @@ -759,39 +689,23 @@ const char* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, // WARNING: The following methods do not check for an error condition (non-existent hash section). // It is the caller's job to do this. -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Word* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetHashSectionStart() const { +template <typename ElfTypes> +typename ElfTypes::Word* ElfFileImpl<ElfTypes>::GetHashSectionStart() const { return hash_section_start_; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Word ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetHashBucketNum() const { +template <typename ElfTypes> +typename ElfTypes::Word ElfFileImpl<ElfTypes>::GetHashBucketNum() const { return GetHashSectionStart()[0]; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Word ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetHashChainNum() const { +template <typename ElfTypes> +typename ElfTypes::Word ElfFileImpl<ElfTypes>::GetHashChainNum() const { return GetHashSectionStart()[1]; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Word ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetHashBucket(size_t i, bool* ok) const { +template <typename ElfTypes> +typename ElfTypes::Word ElfFileImpl<ElfTypes>::GetHashBucket(size_t i, bool* ok) const { if (i >= GetHashBucketNum()) { *ok = false; return 0; @@ -801,12 +715,8 @@ Elf_Word ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return GetHashSectionStart()[2 + i]; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Word ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetHashChain(size_t i, bool* ok) const { +template <typename ElfTypes> +typename ElfTypes::Word ElfFileImpl<ElfTypes>::GetHashChain(size_t i, bool* ok) const { if (i >= GetHashChainNum()) { *ok = false; return 0; @@ -816,21 +726,13 @@ Elf_Word ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return GetHashSectionStart()[2 + GetHashBucketNum() + i]; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Word ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetProgramHeaderNum() const { +template <typename ElfTypes> +typename ElfTypes::Word ElfFileImpl<ElfTypes>::GetProgramHeaderNum() const { return GetHeader().e_phnum; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Phdr* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetProgramHeader(Elf_Word i) const { +template <typename ElfTypes> +typename ElfTypes::Phdr* ElfFileImpl<ElfTypes>::GetProgramHeader(Elf_Word i) const { CHECK_LT(i, GetProgramHeaderNum()) << file_->GetPath(); // Sanity check for caller. uint8_t* program_header = GetProgramHeadersStart() + (i * GetHeader().e_phentsize); if (program_header >= End()) { @@ -839,12 +741,8 @@ Elf_Phdr* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return reinterpret_cast<Elf_Phdr*>(program_header); } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Phdr* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::FindProgamHeaderByType(Elf_Word type) const { +template <typename ElfTypes> +typename ElfTypes::Phdr* ElfFileImpl<ElfTypes>::FindProgamHeaderByType(Elf_Word type) const { for (Elf_Word i = 0; i < GetProgramHeaderNum(); i++) { Elf_Phdr* program_header = GetProgramHeader(i); if (program_header->p_type == type) { @@ -854,21 +752,13 @@ Elf_Phdr* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return nullptr; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Word ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetSectionHeaderNum() const { +template <typename ElfTypes> +typename ElfTypes::Word ElfFileImpl<ElfTypes>::GetSectionHeaderNum() const { return GetHeader().e_shnum; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Shdr* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetSectionHeader(Elf_Word i) const { +template <typename ElfTypes> +typename ElfTypes::Shdr* ElfFileImpl<ElfTypes>::GetSectionHeader(Elf_Word i) const { // Can only access arbitrary sections when we have the whole file, not just program header. // Even if we Load(), it doesn't bring in all the sections. CHECK(!program_header_only_) << file_->GetPath(); @@ -882,12 +772,8 @@ Elf_Shdr* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return reinterpret_cast<Elf_Shdr*>(section_header); } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Shdr* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::FindSectionByType(Elf_Word type) const { +template <typename ElfTypes> +typename ElfTypes::Shdr* ElfFileImpl<ElfTypes>::FindSectionByType(Elf_Word type) const { // Can only access arbitrary sections when we have the whole file, not just program header. // We could change this to switch on known types if they were detected during loading. CHECK(!program_header_only_) << file_->GetPath(); @@ -914,21 +800,14 @@ static unsigned elfhash(const char *_name) { return h; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Shdr* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetSectionNameStringSection() const { +template <typename ElfTypes> +typename ElfTypes::Shdr* ElfFileImpl<ElfTypes>::GetSectionNameStringSection() const { return GetSectionHeader(GetHeader().e_shstrndx); } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -const uint8_t* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::FindDynamicSymbolAddress(const std::string& symbol_name) const { +template <typename ElfTypes> +const uint8_t* ElfFileImpl<ElfTypes>::FindDynamicSymbolAddress( + const std::string& symbol_name) const { // Check that we have a hash section. if (GetHashSectionStart() == nullptr) { return nullptr; // Failure condition. @@ -944,12 +823,9 @@ const uint8_t* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, } // WARNING: Only called from FindDynamicSymbolAddress. Elides check for hash section. -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -const Elf_Sym* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::FindDynamicSymbol(const std::string& symbol_name) const { +template <typename ElfTypes> +const typename ElfTypes::Sym* ElfFileImpl<ElfTypes>::FindDynamicSymbol( + const std::string& symbol_name) const { if (GetHashBucketNum() == 0) { // No dynamic symbols at all. return nullptr; @@ -978,34 +854,21 @@ const Elf_Sym* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return nullptr; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::IsSymbolSectionType(Elf_Word section_type) { +template <typename ElfTypes> +bool ElfFileImpl<ElfTypes>::IsSymbolSectionType(Elf_Word section_type) { return ((section_type == SHT_SYMTAB) || (section_type == SHT_DYNSYM)); } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Word ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetSymbolNum(Elf_Shdr& section_header) const { +template <typename ElfTypes> +typename ElfTypes::Word ElfFileImpl<ElfTypes>::GetSymbolNum(Elf_Shdr& section_header) const { CHECK(IsSymbolSectionType(section_header.sh_type)) << file_->GetPath() << " " << section_header.sh_type; CHECK_NE(0U, section_header.sh_entsize) << file_->GetPath(); return section_header.sh_size / section_header.sh_entsize; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Sym* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetSymbol(Elf_Word section_type, - Elf_Word i) const { +template <typename ElfTypes> +typename ElfTypes::Sym* ElfFileImpl<ElfTypes>::GetSymbol(Elf_Word section_type, Elf_Word i) const { Elf_Sym* sym_start = GetSymbolSectionStart(section_type); if (sym_start == nullptr) { return nullptr; @@ -1013,14 +876,9 @@ Elf_Sym* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return sym_start + i; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -typename ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::SymbolTable** ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetSymbolTable(Elf_Word section_type) { +template <typename ElfTypes> +typename ElfFileImpl<ElfTypes>::SymbolTable** +ElfFileImpl<ElfTypes>::GetSymbolTable(Elf_Word section_type) { CHECK(IsSymbolSectionType(section_type)) << file_->GetPath() << " " << section_type; switch (section_type) { case SHT_SYMTAB: { @@ -1036,14 +894,9 @@ typename ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, } } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Sym* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::FindSymbolByName(Elf_Word section_type, - const std::string& symbol_name, - bool build_map) { +template <typename ElfTypes> +typename ElfTypes::Sym* ElfFileImpl<ElfTypes>::FindSymbolByName( + Elf_Word section_type, const std::string& symbol_name, bool build_map) { CHECK(!program_header_only_) << file_->GetPath(); CHECK(IsSymbolSectionType(section_type)) << file_->GetPath() << " " << section_type; @@ -1122,14 +975,9 @@ Elf_Sym* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return nullptr; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Addr ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::FindSymbolAddress(Elf_Word section_type, - const std::string& symbol_name, - bool build_map) { +template <typename ElfTypes> +typename ElfTypes::Addr ElfFileImpl<ElfTypes>::FindSymbolAddress( + Elf_Word section_type, const std::string& symbol_name, bool build_map) { Elf_Sym* symbol = FindSymbolByName(section_type, symbol_name, build_map); if (symbol == nullptr) { return 0; @@ -1137,12 +985,9 @@ Elf_Addr ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return symbol->st_value; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -const char* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetString(Elf_Shdr& string_section, Elf_Word i) const { +template <typename ElfTypes> +const char* ElfFileImpl<ElfTypes>::GetString(Elf_Shdr& string_section, + Elf_Word i) const { CHECK(!program_header_only_) << file_->GetPath(); // TODO: remove this static_cast from enum when using -std=gnu++0x if (static_cast<Elf_Word>(SHT_STRTAB) != string_section.sh_type) { @@ -1162,31 +1007,19 @@ const char* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return reinterpret_cast<const char*>(string); } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Word ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetDynamicNum() const { +template <typename ElfTypes> +typename ElfTypes::Word ElfFileImpl<ElfTypes>::GetDynamicNum() const { return GetDynamicProgramHeader().p_filesz / sizeof(Elf_Dyn); } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Dyn& ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetDynamic(Elf_Word i) const { +template <typename ElfTypes> +typename ElfTypes::Dyn& ElfFileImpl<ElfTypes>::GetDynamic(Elf_Word i) const { CHECK_LT(i, GetDynamicNum()) << file_->GetPath(); return *(GetDynamicSectionStart() + i); } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Dyn* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::FindDynamicByType(Elf_Sword type) const { +template <typename ElfTypes> +typename ElfTypes::Dyn* ElfFileImpl<ElfTypes>::FindDynamicByType(Elf_Sword type) const { for (Elf_Word i = 0; i < GetDynamicNum(); i++) { Elf_Dyn* dyn = &GetDynamic(i); if (dyn->d_tag == type) { @@ -1196,12 +1029,8 @@ Elf_Dyn* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return NULL; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Word ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::FindDynamicValueByType(Elf_Sword type) const { +template <typename ElfTypes> +typename ElfTypes::Word ElfFileImpl<ElfTypes>::FindDynamicValueByType(Elf_Sword type) const { Elf_Dyn* dyn = FindDynamicByType(type); if (dyn == NULL) { return 0; @@ -1210,76 +1039,48 @@ Elf_Word ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, } } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Rel* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetRelSectionStart(Elf_Shdr& section_header) const { +template <typename ElfTypes> +typename ElfTypes::Rel* ElfFileImpl<ElfTypes>::GetRelSectionStart(Elf_Shdr& section_header) const { CHECK(SHT_REL == section_header.sh_type) << file_->GetPath() << " " << section_header.sh_type; return reinterpret_cast<Elf_Rel*>(Begin() + section_header.sh_offset); } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Word ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetRelNum(Elf_Shdr& section_header) const { +template <typename ElfTypes> +typename ElfTypes::Word ElfFileImpl<ElfTypes>::GetRelNum(Elf_Shdr& section_header) const { CHECK(SHT_REL == section_header.sh_type) << file_->GetPath() << " " << section_header.sh_type; CHECK_NE(0U, section_header.sh_entsize) << file_->GetPath(); return section_header.sh_size / section_header.sh_entsize; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Rel& ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetRel(Elf_Shdr& section_header, Elf_Word i) const { +template <typename ElfTypes> +typename ElfTypes::Rel& ElfFileImpl<ElfTypes>::GetRel(Elf_Shdr& section_header, Elf_Word i) const { CHECK(SHT_REL == section_header.sh_type) << file_->GetPath() << " " << section_header.sh_type; CHECK_LT(i, GetRelNum(section_header)) << file_->GetPath(); return *(GetRelSectionStart(section_header) + i); } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Rela* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetRelaSectionStart(Elf_Shdr& section_header) const { +template <typename ElfTypes> +typename ElfTypes::Rela* ElfFileImpl<ElfTypes>::GetRelaSectionStart(Elf_Shdr& section_header) const { CHECK(SHT_RELA == section_header.sh_type) << file_->GetPath() << " " << section_header.sh_type; return reinterpret_cast<Elf_Rela*>(Begin() + section_header.sh_offset); } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Word ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetRelaNum(Elf_Shdr& section_header) const { +template <typename ElfTypes> +typename ElfTypes::Word ElfFileImpl<ElfTypes>::GetRelaNum(Elf_Shdr& section_header) const { CHECK(SHT_RELA == section_header.sh_type) << file_->GetPath() << " " << section_header.sh_type; return section_header.sh_size / section_header.sh_entsize; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Rela& ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetRela(Elf_Shdr& section_header, Elf_Word i) const { +template <typename ElfTypes> +typename ElfTypes::Rela& ElfFileImpl<ElfTypes>::GetRela(Elf_Shdr& section_header, Elf_Word i) const { CHECK(SHT_RELA == section_header.sh_type) << file_->GetPath() << " " << section_header.sh_type; CHECK_LT(i, GetRelaNum(section_header)) << file_->GetPath(); return *(GetRelaSectionStart(section_header) + i); } // Base on bionic phdr_table_get_load_size -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -size_t ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GetLoadedSize() const { +template <typename ElfTypes> +size_t ElfFileImpl<ElfTypes>::GetLoadedSize() const { Elf_Addr min_vaddr = 0xFFFFFFFFu; Elf_Addr max_vaddr = 0x00000000u; for (Elf_Word i = 0; i < GetProgramHeaderNum(); i++) { @@ -1303,12 +1104,8 @@ size_t ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return loaded_size; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::Load(bool executable, std::string* error_msg) { +template <typename ElfTypes> +bool ElfFileImpl<ElfTypes>::Load(bool executable, std::string* error_msg) { CHECK(program_header_only_) << file_->GetPath(); if (executable) { @@ -1543,12 +1340,8 @@ bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return true; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::ValidPointer(const uint8_t* start) const { +template <typename ElfTypes> +bool ElfFileImpl<ElfTypes>::ValidPointer(const uint8_t* start) const { for (size_t i = 0; i < segments_.size(); ++i) { const MemMap* segment = segments_[i]; if (segment->Begin() <= start && start < segment->End()) { @@ -1559,12 +1352,9 @@ bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -Elf_Shdr* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::FindSectionByName(const std::string& name) const { +template <typename ElfTypes> +typename ElfTypes::Shdr* ElfFileImpl<ElfTypes>::FindSectionByName( + const std::string& name) const { CHECK(!program_header_only_); Elf_Shdr* shstrtab_sec = GetSectionNameStringSection(); if (shstrtab_sec == nullptr) { @@ -1586,12 +1376,8 @@ Elf_Shdr* ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return nullptr; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::FixupDebugSections(typename std::make_signed<Elf_Off>::type base_address_delta) { +template <typename ElfTypes> +bool ElfFileImpl<ElfTypes>::FixupDebugSections(typename std::make_signed<Elf_Off>::type base_address_delta) { const Elf_Shdr* debug_info = FindSectionByName(".debug_info"); const Elf_Shdr* debug_abbrev = FindSectionByName(".debug_abbrev"); const Elf_Shdr* debug_str = FindSectionByName(".debug_str"); @@ -1615,13 +1401,10 @@ bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return true; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::ApplyOatPatchesTo(const char* target_section_name, - typename std::make_signed<Elf_Off>::type delta) { +template <typename ElfTypes> +bool ElfFileImpl<ElfTypes>::ApplyOatPatchesTo( + const char* target_section_name, + typename std::make_signed<Elf_Off>::type delta) { auto patches_section = FindSectionByName(".oat_patches"); if (patches_section == nullptr) { LOG(ERROR) << ".oat_patches section not found."; @@ -1648,15 +1431,12 @@ bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, } // Apply .oat_patches to given section. -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::ApplyOatPatches(const uint8_t* patches, const uint8_t* patches_end, - const char* target_section_name, - typename std::make_signed<Elf_Off>::type delta, - uint8_t* to_patch, const uint8_t* to_patch_end) { +template <typename ElfTypes> +bool ElfFileImpl<ElfTypes>::ApplyOatPatches( + const uint8_t* patches, const uint8_t* patches_end, + const char* target_section_name, + typename std::make_signed<Elf_Off>::type delta, + uint8_t* to_patch, const uint8_t* to_patch_end) { // Read null-terminated section name. const char* section_name; while ((section_name = reinterpret_cast<const char*>(patches))[0] != '\0') { @@ -1681,12 +1461,8 @@ bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return false; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -void ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::GdbJITSupport() { +template <typename ElfTypes> +void ElfFileImpl<ElfTypes>::GdbJITSupport() { // We only get here if we only are mapping the program header. DCHECK(program_header_only_); @@ -1694,15 +1470,12 @@ void ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, std::string error_msg; // Make it MAP_PRIVATE so we can just give it to gdb if all the necessary // sections are there. - std::unique_ptr<ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off>> - all_ptr(Open(const_cast<File*>(file_), PROT_READ | PROT_WRITE, - MAP_PRIVATE, &error_msg)); + std::unique_ptr<ElfFileImpl<ElfTypes>> all_ptr( + Open(const_cast<File*>(file_), PROT_READ | PROT_WRITE, MAP_PRIVATE, &error_msg)); if (all_ptr.get() == nullptr) { return; } - ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off>& all = *all_ptr; + ElfFileImpl<ElfTypes>& all = *all_ptr; // We need the eh_frame for gdb but debug info might be present without it. const Elf_Shdr* eh_frame = all.FindSectionByName(".eh_frame"); @@ -1732,12 +1505,8 @@ void ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, gdb_file_mapping_.reset(all_ptr.release()); } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::Strip(std::string* error_msg) { +template <typename ElfTypes> +bool ElfFileImpl<ElfTypes>::Strip(std::string* error_msg) { // ELF files produced by MCLinker look roughly like this // // +------------+ @@ -1840,12 +1609,8 @@ bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, static const bool DEBUG_FIXUP = false; -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::Fixup(Elf_Addr base_address) { +template <typename ElfTypes> +bool ElfFileImpl<ElfTypes>::Fixup(Elf_Addr base_address) { if (!FixupDynamic(base_address)) { LOG(WARNING) << "Failed to fixup .dynamic in " << file_->GetPath(); return false; @@ -1878,12 +1643,8 @@ bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return true; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::FixupDynamic(Elf_Addr base_address) { +template <typename ElfTypes> +bool ElfFileImpl<ElfTypes>::FixupDynamic(Elf_Addr base_address) { for (Elf_Word i = 0; i < GetDynamicNum(); i++) { Elf_Dyn& elf_dyn = GetDynamic(i); Elf_Word d_tag = elf_dyn.d_tag; @@ -1902,12 +1663,8 @@ bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return true; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::FixupSectionHeaders(Elf_Addr base_address) { +template <typename ElfTypes> +bool ElfFileImpl<ElfTypes>::FixupSectionHeaders(Elf_Addr base_address) { for (Elf_Word i = 0; i < GetSectionHeaderNum(); i++) { Elf_Shdr* sh = GetSectionHeader(i); CHECK(sh != nullptr); @@ -1926,12 +1683,8 @@ bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return true; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::FixupProgramHeaders(Elf_Addr base_address) { +template <typename ElfTypes> +bool ElfFileImpl<ElfTypes>::FixupProgramHeaders(Elf_Addr base_address) { // TODO: ELFObjectFile doesn't have give to Elf_Phdr, so we do that ourselves for now. for (Elf_Word i = 0; i < GetProgramHeaderNum(); i++) { Elf_Phdr* ph = GetProgramHeader(i); @@ -1953,12 +1706,8 @@ bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return true; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::FixupSymbols(Elf_Addr base_address, bool dynamic) { +template <typename ElfTypes> +bool ElfFileImpl<ElfTypes>::FixupSymbols(Elf_Addr base_address, bool dynamic) { Elf_Word section_type = dynamic ? SHT_DYNSYM : SHT_SYMTAB; // TODO: Unfortunate ELFObjectFile has protected symbol access, so use ElfFile Elf_Shdr* symbol_section = FindSectionByType(section_type); @@ -1983,12 +1732,8 @@ bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, return true; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> -bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, Elf_Rela, Elf_Dyn, Elf_Off> - ::FixupRelocations(Elf_Addr base_address) { +template <typename ElfTypes> +bool ElfFileImpl<ElfTypes>::FixupRelocations(Elf_Addr base_address) { for (Elf_Word i = 0; i < GetSectionHeaderNum(); i++) { Elf_Shdr* sh = GetSectionHeader(i); CHECK(sh != nullptr); @@ -2020,10 +1765,8 @@ bool ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, } // Explicit instantiations -template class ElfFileImpl<Elf32_Ehdr, Elf32_Phdr, Elf32_Shdr, Elf32_Word, - Elf32_Sword, Elf32_Addr, Elf32_Sym, Elf32_Rel, Elf32_Rela, Elf32_Dyn, Elf32_Off>; -template class ElfFileImpl<Elf64_Ehdr, Elf64_Phdr, Elf64_Shdr, Elf64_Word, - Elf64_Sword, Elf64_Addr, Elf64_Sym, Elf64_Rel, Elf64_Rela, Elf64_Dyn, Elf64_Off>; +template class ElfFileImpl<ElfTypes32>; +template class ElfFileImpl<ElfTypes64>; ElfFile::ElfFile(ElfFileImpl32* elf32) : elf32_(elf32), elf64_(nullptr) { } diff --git a/runtime/elf_file.h b/runtime/elf_file.h index 286c2a6..fe6896d 100644 --- a/runtime/elf_file.h +++ b/runtime/elf_file.h @@ -26,16 +26,12 @@ #include "os.h" namespace art { -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> +template <typename ElfTypes> class ElfFileImpl; // Explicitly instantiated in elf_file.cc -typedef ElfFileImpl<Elf32_Ehdr, Elf32_Phdr, Elf32_Shdr, Elf32_Word, Elf32_Sword, - Elf32_Addr, Elf32_Sym, Elf32_Rel, Elf32_Rela, Elf32_Dyn, Elf32_Off> ElfFileImpl32; -typedef ElfFileImpl<Elf64_Ehdr, Elf64_Phdr, Elf64_Shdr, Elf64_Word, Elf64_Sword, - Elf64_Addr, Elf64_Sym, Elf64_Rel, Elf64_Rela, Elf64_Dyn, Elf64_Off> ElfFileImpl64; +typedef ElfFileImpl<ElfTypes32> ElfFileImpl32; +typedef ElfFileImpl<ElfTypes64> ElfFileImpl64; // Used for compile time and runtime for ElfFile access. Because of // the need for use at runtime, cannot directly use LLVM classes such as diff --git a/runtime/elf_file_impl.h b/runtime/elf_file_impl.h index 383dc41..047849a 100644 --- a/runtime/elf_file_impl.h +++ b/runtime/elf_file_impl.h @@ -32,11 +32,22 @@ extern "C" { struct JITCodeEntry; } -template <typename Elf_Ehdr, typename Elf_Phdr, typename Elf_Shdr, typename Elf_Word, - typename Elf_Sword, typename Elf_Addr, typename Elf_Sym, typename Elf_Rel, - typename Elf_Rela, typename Elf_Dyn, typename Elf_Off> +template <typename ElfTypes> class ElfFileImpl { public: + using Elf_Addr = typename ElfTypes::Addr; + using Elf_Off = typename ElfTypes::Off; + using Elf_Half = typename ElfTypes::Half; + using Elf_Word = typename ElfTypes::Word; + using Elf_Sword = typename ElfTypes::Sword; + using Elf_Ehdr = typename ElfTypes::Ehdr; + using Elf_Shdr = typename ElfTypes::Shdr; + using Elf_Sym = typename ElfTypes::Sym; + using Elf_Rel = typename ElfTypes::Rel; + using Elf_Rela = typename ElfTypes::Rela; + using Elf_Phdr = typename ElfTypes::Phdr; + using Elf_Dyn = typename ElfTypes::Dyn; + static ElfFileImpl* Open(File* file, bool writable, bool program_header_only, std::string* error_msg, uint8_t* requested_base = nullptr); static ElfFileImpl* Open(File* file, int mmap_prot, int mmap_flags, std::string* error_msg); @@ -209,9 +220,7 @@ class ElfFileImpl { // Support for GDB JIT uint8_t* jit_elf_image_; JITCodeEntry* jit_gdb_entry_; - std::unique_ptr<ElfFileImpl<Elf_Ehdr, Elf_Phdr, Elf_Shdr, Elf_Word, - Elf_Sword, Elf_Addr, Elf_Sym, Elf_Rel, - Elf_Rela, Elf_Dyn, Elf_Off>> gdb_file_mapping_; + std::unique_ptr<ElfFileImpl<ElfTypes>> gdb_file_mapping_; void GdbJITSupport(); // Override the 'base' p_vaddr in the first LOAD segment with this value (if non-null). |