1b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines/* 2b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines * Copyright 2011, The Android Open Source Project 3b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines * 4b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines * Licensed under the Apache License, Version 2.0 (the "License"); 5b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines * you may not use this file except in compliance with the License. 6b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines * You may obtain a copy of the License at 7b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines * 8b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines * http://www.apache.org/licenses/LICENSE-2.0 9b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines * 10b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines * Unless required by applicable law or agreed to in writing, software 11b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines * distributed under the License is distributed on an "AS IS" BASIS, 12b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines * See the License for the specific language governing permissions and 14b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines * limitations under the License. 15b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines */ 16b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 17b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines#ifndef ELF_SECTION_SYM_TAB_HXX 18b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines#define ELF_SECTION_SYM_TAB_HXX 19b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 20b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines#include "ELFSectionHeader.h" 21b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines#include "ELFSymbol.h" 22b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines#include "utils/rsl_assert.h" 23b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 24b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hinestemplate <unsigned Bitwidth> 25b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen HinesELFSectionSymTab<Bitwidth>::~ELFSectionSymTab() { 26b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines for (size_t i = 0; i < table.size(); ++i) { 27b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines delete table[i]; 28b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines } 29b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines} 30b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 31b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hinestemplate <unsigned Bitwidth> 32b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hinessize_t ELFSectionSymTab<Bitwidth>::getFuncCount() const { 33b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines size_t result = 0; 34b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines for (size_t i = 0; i < table.size(); ++i) { 35b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines if (table[i] && table[i]->isConcreteFunc()) { 36b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines result++; 37b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines } 38b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines } 39b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines return result; 40b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines} 41b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 42b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hinestemplate <unsigned Bitwidth> 43b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hinesinline size_t ELFSectionSymTab<Bitwidth>::getExternFuncCount() const { 44b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines size_t result = 0; 45b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines for (size_t i = 0; i < table.size(); ++i) { 46b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines if (table[i] && table[i]->isExternFunc()) { 47b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines result++; 48b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines } 49b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines } 50b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines return result; 51b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines} 52b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 53b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hinestemplate <unsigned Bitwidth> 54b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hinesinline void ELFSectionSymTab<Bitwidth>::buildNameMap() { 55b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines for (size_t i = 0; i < table.size(); ++i) { 56b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines ELFSymbolTy *symbol = table[i]; 57b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines if ( symbol ) { 58b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines name_map[symbol->getName()] = symbol; 59b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines } 60b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines } 61b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines} 62b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 63b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hinestemplate <unsigned Bitwidth> 64b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hinesinline ELFSymbol<Bitwidth> const * 65b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen HinesELFSectionSymTab<Bitwidth>::getByName(std::string const &name) const { 66b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines typename llvm::StringMap<ELFSymbolTy *>::const_iterator symbol = 67b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines name_map.find(name); 68b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines if (symbol == name_map.end()) { 69b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines return NULL; 70b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines } 71b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines return symbol->getValue(); 72b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines} 73b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 74b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hinestemplate <unsigned Bitwidth> 75b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hinesinline void 76b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen HinesELFSectionSymTab<Bitwidth>::getFuncNameList(size_t size, 77b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines char const **list) const { 78b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines for (size_t i = 0, j = 0; i < table.size() && j < size; ++i) { 79b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines if (table[i] && table[i]->isConcreteFunc()) { 80b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines list[j++] = table[i]->getName(); 81b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines } 82b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines } 83b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines} 84b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 85b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hinestemplate <unsigned Bitwidth> 86b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hinestemplate <typename Archiver> 87b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen HinesELFSectionSymTab<Bitwidth> * 88b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen HinesELFSectionSymTab<Bitwidth>::read(Archiver &AR, 89b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines ELFObjectTy *owner, 90b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines ELFSectionHeaderTy const *sh) { 91b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 92d282991c78d1fd79a222c5f114e623da255ba8a0Stephen Hines std::unique_ptr<ELFSectionSymTabTy> st(new ELFSectionSymTabTy()); 93b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 94b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines // Assert that entry size will be the same as standard. 95b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines rsl_assert(sh->getEntrySize() == TypeTraits<ELFSymbolTy>::size); 96b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 97b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines // Seek to the start of symbol table 98b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines AR.seek(sh->getOffset(), true); 99b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 100b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines // Read all symbol table entry 101b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines size_t size = sh->getSize() / sh->getEntrySize(); 102b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines for (size_t i = 0; i < size; ++i) { 103b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines st->table.push_back(ELFSymbolTy::read(AR, owner, i)); 104b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines } 105b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 106b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines if (!AR) { 107b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines // Unable to read the table. 108b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines return 0; 109b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines } 110b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 111d282991c78d1fd79a222c5f114e623da255ba8a0Stephen Hines return st.release(); 112b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines} 113b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 114b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hinestemplate <unsigned Bitwidth> 115b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hinesvoid ELFSectionSymTab<Bitwidth>::print() const { 116b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines using namespace llvm; 117b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 118b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines out() << '\n' << fillformat('=', 79) << '\n'; 119b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines out().changeColor(raw_ostream::WHITE, true); 120b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines out() << "Symbol Table" << '\n'; 121b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines out().resetColor(); 122b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 123b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines for (size_t i = 0; i < table.size(); ++i) { 124b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines table[i]->print(); 125b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines } 126b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 127b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines out() << fillformat('=', 79) << '\n'; 128b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines} 129b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines 130b53c8a59e6f21ed36a0c3d9d4ce5834d4cc3c298Stephen Hines#endif // ELF_SECTION_SYM_TAB_HXX 131