1 /* 2 * Copyright (c) 2021-2022 Huawei Device Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16 #ifndef HIPERF_ELF_PARSER_TEST_H 17 #define HIPERF_ELF_PARSER_TEST_H 18 19 #if !is_ohos 20 // this is not good enough 21 #include <../musl/include/elf.h> 22 #else 23 #include <elf.h> 24 #endif 25 #include <gmock/gmock.h> 26 #include <gtest/gtest.h> 27 #include <hilog/log.h> 28 29 #include "elf_parser.h" 30 31 namespace OHOS { 32 namespace Developtools { 33 namespace HiPerf { 34 namespace UnitTest { 35 class EhdrFromReadelf { 36 public: 37 static std::unique_ptr<EhdrFromReadelf> MakeUnique(FILE *fp); 38 bool Init(FILE *fp); 39 40 unsigned char ehdrIdent_[EI_NIDENT]; 41 uint16_t ehdrSize_; 42 uint16_t phdrEntSize_; 43 uint16_t phdrNumEnts_; 44 uint16_t shdrEntSize_; 45 uint16_t shdrNumEnts_; 46 uint16_t shdrStrTabIdx_; 47 uint32_t ehdrFlags_; 48 uint64_t prgEntryVaddr_; 49 uint64_t phdrOffset_; 50 uint64_t shdrOffset_; 51 52 private: 53 explicit EhdrFromReadelf() = default; 54 bool GetMagic(FILE * const fp); 55 bool GetEntryAddr(FILE * const fp); 56 bool GetPrgOffset(FILE * const fp); 57 bool GetSecOffset(FILE * const fp); 58 bool GetFlag(FILE * const fp); 59 bool GetEhdrSize(FILE * const fp); 60 bool GetPhdrSize(FILE * const fp); 61 bool GetNumPhdrs(FILE * const fp); 62 bool GetShdrSize(FILE * const fp); 63 bool GetNumShdrs(FILE * const fp); 64 bool GetShdrStrTabIdx(FILE * const fp); 65 }; 66 67 class PhdrFromReadelf { 68 public: 69 static std::unique_ptr<PhdrFromReadelf> MakeUnique(const std::string &line); 70 bool Init(const std::string &line); 71 72 uint64_t offset_ {0}; 73 uint64_t vaddr_ {0}; 74 uint64_t paddr_ {0}; 75 uint64_t fileSize_ {0}; 76 uint64_t memSize_ {0}; 77 uint64_t secAlign_ {0}; 78 79 private: 80 explicit PhdrFromReadelf() = default; 81 int64_t GetOffset(const std::string &line); 82 int64_t GetVaddr(const std::string &line); 83 int64_t GetPaddr(const std::string &line); 84 int64_t GetFileSize(const std::string &line); 85 int64_t GetMemSize(const std::string &line); 86 int64_t GetAlign(const std::string &line); 87 }; 88 89 class ShdrFromReadelf { 90 public: 91 static std::unique_ptr<ShdrFromReadelf> MakeUnique(const std::string &line); 92 bool Init(const std::string &line); 93 GetSecName()94 inline const std::string GetSecName() 95 { 96 return secName_; 97 } 98 99 uint32_t link_ {0}; 100 uint32_t info_ {0}; 101 uint64_t secVaddr_ {0}; 102 uint64_t fileOffset_ {0}; 103 uint64_t secSize_ {0}; 104 uint64_t secAddrAlign_ {0}; 105 uint64_t secEntrySize_ {0}; 106 uint32_t secIndex_ {0}; 107 std::string secName_ {}; 108 109 private: 110 explicit ShdrFromReadelf() = default; 111 int64_t GetSecIndex(const std::string &line); 112 const std::string GetName(const std::string &line); 113 int64_t GetAddress(const std::string &line); 114 int64_t GetFileOffset(const std::string &line); 115 int64_t GetSecSize(const std::string &line); 116 int64_t GetEntrySize(const std::string &line); 117 int64_t GetLink(const std::string &line); 118 int64_t GetInfo(const std::string &line); 119 int64_t GetAlign(const std::string &line); 120 }; 121 122 class ElfSymbolFromReadelf { 123 public: 124 static std::unique_ptr<ElfSymbolFromReadelf> MakeUnique(const std::string &line); 125 bool Init(const std::string &line); 126 127 uint32_t num_ {0}; 128 uint64_t value_ {0}; 129 uint64_t size_ {0}; 130 std::string name_ {}; 131 132 private: 133 explicit ElfSymbolFromReadelf() = default; 134 int64_t GetNum(const std::string &line); 135 int64_t GetValue(const std::string &line); 136 int64_t GetSize(const std::string &line); 137 const std::string GetName(const std::string &line); 138 }; 139 140 class ElfFileFromReadelf { 141 public: 142 enum class ElfFileType { 143 ELF32, 144 ELF64, 145 }; 146 ~ElfFileFromReadelf(); 147 static std::unique_ptr<ElfFileFromReadelf> MakeUnique(ElfFileType fileType); 148 bool Init(); 149 150 std::unique_ptr<EhdrFromReadelf> ehdr_ {nullptr}; 151 std::vector<std::unique_ptr<ShdrFromReadelf>> shdrs_; 152 std::vector<std::unique_ptr<PhdrFromReadelf>> phdrs_; 153 std::vector<std::unique_ptr<ElfSymbolFromReadelf>> syms_; 154 std::vector<std::unique_ptr<ElfSymbolFromReadelf>> dynSyms_; 155 156 private: 157 explicit ElfFileFromReadelf(ElfFileType fileType); 158 bool ParseElfHeader(); 159 bool ParsePrgHeaders64(); 160 bool ParsePrgHeaders32(); 161 bool ParseSecHeaders64(); 162 bool ParseSecHeaders32(); 163 bool ParseSymTable(); 164 bool IsOpened(); 165 bool ParseSymsInSymTab(); 166 bool ParseSymsInDynSym(); 167 const std::string GetNextPhdrLine(); 168 const std::string GetNextShdrLine(); 169 const std::string GetNextSymLine(); 170 171 FILE *ehdrFP_ {nullptr}; 172 FILE *shdrsFP_ {nullptr}; 173 FILE *phdrsFP_ {nullptr}; 174 FILE *symTabFP_ {nullptr}; 175 }; 176 } // namespace UnitTest 177 } // namespace HiPerf 178 } // namespace Developtools 179 } // namespace OHOS 180 #endif // HIPERF_ELF_PARSER_TEST_H 181