1e2cdbc6710aa43475f17e73aba143ceb786e968cShih-wei Liao/* 2e2cdbc6710aa43475f17e73aba143ceb786e968cShih-wei Liao * Copyright 2011, The Android Open Source Project 3e2cdbc6710aa43475f17e73aba143ceb786e968cShih-wei Liao * 4e2cdbc6710aa43475f17e73aba143ceb786e968cShih-wei Liao * Licensed under the Apache License, Version 2.0 (the "License"); 5e2cdbc6710aa43475f17e73aba143ceb786e968cShih-wei Liao * you may not use this file except in compliance with the License. 6e2cdbc6710aa43475f17e73aba143ceb786e968cShih-wei Liao * You may obtain a copy of the License at 7e2cdbc6710aa43475f17e73aba143ceb786e968cShih-wei Liao * 8e2cdbc6710aa43475f17e73aba143ceb786e968cShih-wei Liao * http://www.apache.org/licenses/LICENSE-2.0 9e2cdbc6710aa43475f17e73aba143ceb786e968cShih-wei Liao * 10e2cdbc6710aa43475f17e73aba143ceb786e968cShih-wei Liao * Unless required by applicable law or agreed to in writing, software 11e2cdbc6710aa43475f17e73aba143ceb786e968cShih-wei Liao * distributed under the License is distributed on an "AS IS" BASIS, 12e2cdbc6710aa43475f17e73aba143ceb786e968cShih-wei Liao * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13e2cdbc6710aa43475f17e73aba143ceb786e968cShih-wei Liao * See the License for the specific language governing permissions and 14e2cdbc6710aa43475f17e73aba143ceb786e968cShih-wei Liao * limitations under the License. 15e2cdbc6710aa43475f17e73aba143ceb786e968cShih-wei Liao */ 16e2cdbc6710aa43475f17e73aba143ceb786e968cShih-wei Liao 17a3e9806ff102d256d38bd930d537c206adc8bb6cLogan Chien#ifndef ELF_SYMBOL_H 18a3e9806ff102d256d38bd930d537c206adc8bb6cLogan Chien#define ELF_SYMBOL_H 191e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 201e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa#include "ELFTypes.h" 21404833ada8caa7027105bd52bd36ab7822030369TDYa#include "ELF.h" 221e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 232956c0e06b1c51f521645a076802686976c4b2f6TDYa#include <llvm/ADT/OwningPtr.h> 242956c0e06b1c51f521645a076802686976c4b2f6TDYa 251e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa#include <string> 26937df4784a064c4f32b3354f76ef9c4361711173TDYa#include <algorithm> 271e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 281e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa#include <stdint.h> 29921465005aca46a100d137c9608a0aedd846e290Logan Chien#include <stdlib.h> 301e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 31d90e4881f16d40cd045bbe094f073353328d5a09Logan Chienclass ELFSymbolHelperMixin { 321e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYaprotected: 331e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa static char const *getTypeStr(uint8_t); 341e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa static char const *getBindingAttributeStr(uint8_t); 351e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa static char const *getVisibilityStr(uint8_t); 361e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa}; 371e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 38a9ab5889e842a49ff16d06594efe96b0210fe1f7Logan Chientemplate <unsigned Bitwidth> 39d90e4881f16d40cd045bbe094f073353328d5a09Logan Chienclass ELFSymbol_CRTP : private ELFSymbolHelperMixin { 401e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYapublic: 411e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa ELF_TYPE_INTRO_TO_TEMPLATE_SCOPE(Bitwidth); 421e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 431e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYaprotected: 441e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa ELFObject<Bitwidth> const *owner; 451e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 461e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa size_t index; 471e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 481e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa word_t st_name; 491e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa byte_t st_info; 501e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa byte_t st_other; 511e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa half_t st_shndx; 521e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa addr_t st_value; 539ac06bd8363c8c7e4e612eb041e921dcd81cf9d7Logan Chien symsize_t st_size; 541e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 55d91d1813cc1b99b171f16dc0f7ec4c58b7fc9cfeTDYa mutable void *my_addr; 56d91d1813cc1b99b171f16dc0f7ec4c58b7fc9cfeTDYa 571e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYaprotected: 58d90e4881f16d40cd045bbe094f073353328d5a09Logan Chien ELFSymbol_CRTP() { my_addr = 0; } 5958611fc8193e7386698178f167a2e0cbdd6a4f6fLogan Chien 60d90e4881f16d40cd045bbe094f073353328d5a09Logan Chien ~ELFSymbol_CRTP() { 619f64da291148a9c09bef5d062e9047bff64f56b9Logan Chien#if 0 62d91d1813cc1b99b171f16dc0f7ec4c58b7fc9cfeTDYa if (my_addr != 0 && 63d91d1813cc1b99b171f16dc0f7ec4c58b7fc9cfeTDYa getType() == STT_OBJECT && 64d91d1813cc1b99b171f16dc0f7ec4c58b7fc9cfeTDYa getSectionIndex() == SHN_COMMON) { 65d91d1813cc1b99b171f16dc0f7ec4c58b7fc9cfeTDYa std::free(my_addr); 66d91d1813cc1b99b171f16dc0f7ec4c58b7fc9cfeTDYa } 679f64da291148a9c09bef5d062e9047bff64f56b9Logan Chien#endif 68d91d1813cc1b99b171f16dc0f7ec4c58b7fc9cfeTDYa } 691e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 701e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYapublic: 711e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa size_t getIndex() const { 721e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa return index; 731e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa } 741e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 751e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa word_t getNameIndex() const { 761e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa return st_name; 771e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa } 781e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 791e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa char const *getName() const; 801e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 811e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa// I don't want to include elf.h in .h file, so define those macro by ourself. 821e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa#define ELF_ST_BIND(i) ((i)>>4) 831e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa#define ELF_ST_TYPE(i) ((i)&0xf) 841e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa#define ELF_ST_INFO(b,t) (((b)<<4)+((t)&0xf)) 851e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa byte_t getType() const { 861e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa return ELF_ST_TYPE(st_info); 871e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa } 881e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 891e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa byte_t getBindingAttribute() const { 901e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa return ELF_ST_BIND(st_info); 911e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa } 921e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa#undef ELF_ST_BIND 931e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa#undef ELF_ST_TYPE 941e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa#undef ELF_ST_INFO 951e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 961e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa#define ELF_ST_VISIBILITY(o) ((o)&0x3) 971e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa byte_t getVisibility() const { 981e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa return ELF_ST_VISIBILITY(st_other); 991e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa } 1001e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa#undef ELF_ST_VISIBILITY 1011e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 1021e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa half_t getSectionIndex() const { 1031e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa return st_shndx; 1041e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa } 1051e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 1061e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa addr_t getValue() const { 1071e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa return st_value; 1081e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa } 1091e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 1109ac06bd8363c8c7e4e612eb041e921dcd81cf9d7Logan Chien symsize_t getSize() const { 1111e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa return st_size; 1121e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa } 1131e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 1149ed73923af9db7283a8c76b5dfa2dda5b732a852Andrew Hsieh void *getAddress(int machine, bool autoAlloc = true) const; 115d91d1813cc1b99b171f16dc0f7ec4c58b7fc9cfeTDYa 1165c543a0761c5a7f72565351bc16ec31d6f675602TDYa void setAddress(void *addr) { 1175c543a0761c5a7f72565351bc16ec31d6f675602TDYa my_addr = addr; 1185c543a0761c5a7f72565351bc16ec31d6f675602TDYa } 1195c543a0761c5a7f72565351bc16ec31d6f675602TDYa 1201e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa bool isValid() const { 1211e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa // FIXME: Should check the correctness of the section header. 1221e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa return true; 1231e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa } 1241e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 125388f443ba0c474ffcc2e06f8d2a668c4488c3c1bLogan Chien bool isConcreteFunc() const { 126388f443ba0c474ffcc2e06f8d2a668c4488c3c1bLogan Chien return getType() == STT_FUNC; 127388f443ba0c474ffcc2e06f8d2a668c4488c3c1bLogan Chien } 128388f443ba0c474ffcc2e06f8d2a668c4488c3c1bLogan Chien 129e586f183e46f921301281352a87f67dbdc1a43b6Logan Chien bool isExternFunc() const { 130e586f183e46f921301281352a87f67dbdc1a43b6Logan Chien return getType() == STT_NOTYPE; 131e586f183e46f921301281352a87f67dbdc1a43b6Logan Chien } 132e586f183e46f921301281352a87f67dbdc1a43b6Logan Chien 1331e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa template <typename Archiver> 13458611fc8193e7386698178f167a2e0cbdd6a4f6fLogan Chien static ELFSymbolTy * 1351e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa read(Archiver &AR, ELFObject<Bitwidth> const *owner, size_t index = 0); 1361e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 1371e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa void print(bool shouldPrintHeader = false) const; 1381e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 1391e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYaprivate: 14058611fc8193e7386698178f167a2e0cbdd6a4f6fLogan Chien ELFSymbolTy *concrete() { 14158611fc8193e7386698178f167a2e0cbdd6a4f6fLogan Chien return static_cast<ELFSymbolTy *>(this); 1421e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa } 1431e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 14458611fc8193e7386698178f167a2e0cbdd6a4f6fLogan Chien ELFSymbolTy const *concrete() const { 14558611fc8193e7386698178f167a2e0cbdd6a4f6fLogan Chien return static_cast<ELFSymbolTy const *>(this); 1461e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa } 1471e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa}; 1481e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 1491e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYatemplate <> 150d90e4881f16d40cd045bbe094f073353328d5a09Logan Chienclass ELFSymbol<32> : public ELFSymbol_CRTP<32> { 151d90e4881f16d40cd045bbe094f073353328d5a09Logan Chien friend class ELFSymbol_CRTP<32>; 1521e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 1531e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYaprivate: 154d90e4881f16d40cd045bbe094f073353328d5a09Logan Chien ELFSymbol() { 1551e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa } 1561e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 1571e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa template <typename Archiver> 1581e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa bool serialize(Archiver &AR) { 159d90e4881f16d40cd045bbe094f073353328d5a09Logan Chien AR.prologue(TypeTraits<ELFSymbol>::size); 1601e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 1611e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa AR & st_name; 1621e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa AR & st_value; 1631e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa AR & st_size; 1641e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa AR & st_info; 1651e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa AR & st_other; 1661e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa AR & st_shndx; 1671e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 168d90e4881f16d40cd045bbe094f073353328d5a09Logan Chien AR.epilogue(TypeTraits<ELFSymbol>::size); 1691e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa return AR; 1701e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa } 1711e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa}; 1721e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 1731e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYatemplate <> 174d90e4881f16d40cd045bbe094f073353328d5a09Logan Chienclass ELFSymbol<64> : public ELFSymbol_CRTP<64> { 175d90e4881f16d40cd045bbe094f073353328d5a09Logan Chien friend class ELFSymbol_CRTP<64>; 1761e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 1771e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYaprivate: 178d90e4881f16d40cd045bbe094f073353328d5a09Logan Chien ELFSymbol() { 1791e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa } 1801e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 1811e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa template <typename Archiver> 1821e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa bool serialize(Archiver &AR) { 183d90e4881f16d40cd045bbe094f073353328d5a09Logan Chien AR.prologue(TypeTraits<ELFSymbol>::size); 1841e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 1851e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa AR & st_name; 1861e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa AR & st_info; 1871e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa AR & st_other; 1881e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa AR & st_shndx; 1891e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa AR & st_value; 1901e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa AR & st_size; 1911e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 192d90e4881f16d40cd045bbe094f073353328d5a09Logan Chien AR.epilogue(TypeTraits<ELFSymbol>::size); 1931e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa return AR; 1941e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa } 1951e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa}; 1961e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 1979f3703c8165b74517567e0d3a7a4f71ae8337c72Logan Chien#include "impl/ELFSymbol.hxx" 1981e278e29f1ce0a00a4626cb3c839ad37e46abcdfTDYa 199a3e9806ff102d256d38bd930d537c206adc8bb6cLogan Chien#endif // ELF_SYMBOL_H 200