1 //===-- ELFDumper.cpp - ELF-specific dumper ---------------------*- C++ -*-===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 /// 10 /// \file 11 /// \brief This file implements the ELF-specific dumper for llvm-readobj. 12 /// 13 //===----------------------------------------------------------------------===// 14 15 #include "llvm-readobj.h" 16 #include "ARMAttributeParser.h" 17 #include "ARMEHABIPrinter.h" 18 #include "Error.h" 19 #include "ObjDumper.h" 20 #include "StreamWriter.h" 21 #include "llvm/ADT/Optional.h" 22 #include "llvm/ADT/SmallString.h" 23 #include "llvm/ADT/StringExtras.h" 24 #include "llvm/Object/ELFObjectFile.h" 25 #include "llvm/Support/ARMBuildAttributes.h" 26 #include "llvm/Support/Compiler.h" 27 #include "llvm/Support/Format.h" 28 #include "llvm/Support/MathExtras.h" 29 #include "llvm/Support/raw_ostream.h" 30 31 using namespace llvm; 32 using namespace llvm::object; 33 using namespace ELF; 34 35 #define LLVM_READOBJ_ENUM_CASE(ns, enum) \ 36 case ns::enum: return #enum; 37 38 namespace { 39 40 template<typename ELFT> 41 class ELFDumper : public ObjDumper { 42 public: 43 ELFDumper(const ELFFile<ELFT> *Obj, StreamWriter &Writer) 44 : ObjDumper(Writer), Obj(Obj) {} 45 46 void printFileHeaders() override; 47 void printSections() override; 48 void printRelocations() override; 49 void printSymbols() override; 50 void printDynamicSymbols() override; 51 void printUnwindInfo() override; 52 53 void printDynamicTable() override; 54 void printNeededLibraries() override; 55 void printProgramHeaders() override; 56 57 void printAttributes() override; 58 void printMipsPLTGOT() override; 59 60 private: 61 typedef ELFFile<ELFT> ELFO; 62 typedef typename ELFO::Elf_Shdr Elf_Shdr; 63 typedef typename ELFO::Elf_Sym Elf_Sym; 64 65 void printSymbol(typename ELFO::Elf_Sym_Iter Symbol); 66 67 void printRelocations(const Elf_Shdr *Sec); 68 void printRelocation(const Elf_Shdr *Sec, typename ELFO::Elf_Rela Rel); 69 70 const ELFO *Obj; 71 }; 72 73 template <class T> T errorOrDefault(ErrorOr<T> Val, T Default = T()) { 74 if (!Val) { 75 error(Val.getError()); 76 return Default; 77 } 78 79 return *Val; 80 } 81 } // namespace 82 83 namespace llvm { 84 85 template <class ELFT> 86 static std::error_code createELFDumper(const ELFFile<ELFT> *Obj, 87 StreamWriter &Writer, 88 std::unique_ptr<ObjDumper> &Result) { 89 Result.reset(new ELFDumper<ELFT>(Obj, Writer)); 90 return readobj_error::success; 91 } 92 93 std::error_code createELFDumper(const object::ObjectFile *Obj, 94 StreamWriter &Writer, 95 std::unique_ptr<ObjDumper> &Result) { 96 // Little-endian 32-bit 97 if (const ELF32LEObjectFile *ELFObj = dyn_cast<ELF32LEObjectFile>(Obj)) 98 return createELFDumper(ELFObj->getELFFile(), Writer, Result); 99 100 // Big-endian 32-bit 101 if (const ELF32BEObjectFile *ELFObj = dyn_cast<ELF32BEObjectFile>(Obj)) 102 return createELFDumper(ELFObj->getELFFile(), Writer, Result); 103 104 // Little-endian 64-bit 105 if (const ELF64LEObjectFile *ELFObj = dyn_cast<ELF64LEObjectFile>(Obj)) 106 return createELFDumper(ELFObj->getELFFile(), Writer, Result); 107 108 // Big-endian 64-bit 109 if (const ELF64BEObjectFile *ELFObj = dyn_cast<ELF64BEObjectFile>(Obj)) 110 return createELFDumper(ELFObj->getELFFile(), Writer, Result); 111 112 return readobj_error::unsupported_obj_file_format; 113 } 114 115 } // namespace llvm 116 117 template <typename ELFO> 118 static std::string getFullSymbolName(const ELFO &Obj, 119 typename ELFO::Elf_Sym_Iter Symbol) { 120 StringRef SymbolName = errorOrDefault(Obj.getSymbolName(Symbol)); 121 if (!Symbol.isDynamic()) 122 return SymbolName; 123 124 std::string FullSymbolName(SymbolName); 125 126 bool IsDefault; 127 ErrorOr<StringRef> Version = 128 Obj.getSymbolVersion(nullptr, &*Symbol, IsDefault); 129 if (Version) { 130 FullSymbolName += (IsDefault ? "@@" : "@"); 131 FullSymbolName += *Version; 132 } else 133 error(Version.getError()); 134 return FullSymbolName; 135 } 136 137 template <typename ELFO> 138 static void 139 getSectionNameIndex(const ELFO &Obj, typename ELFO::Elf_Sym_Iter Symbol, 140 StringRef &SectionName, unsigned &SectionIndex) { 141 SectionIndex = Symbol->st_shndx; 142 if (SectionIndex == SHN_UNDEF) { 143 SectionName = "Undefined"; 144 } else if (SectionIndex >= SHN_LOPROC && SectionIndex <= SHN_HIPROC) { 145 SectionName = "Processor Specific"; 146 } else if (SectionIndex >= SHN_LOOS && SectionIndex <= SHN_HIOS) { 147 SectionName = "Operating System Specific"; 148 } else if (SectionIndex > SHN_HIOS && SectionIndex < SHN_ABS) { 149 SectionName = "Reserved"; 150 } else if (SectionIndex == SHN_ABS) { 151 SectionName = "Absolute"; 152 } else if (SectionIndex == SHN_COMMON) { 153 SectionName = "Common"; 154 } else { 155 if (SectionIndex == SHN_XINDEX) 156 SectionIndex = Obj.getSymbolTableIndex(&*Symbol); 157 assert(SectionIndex != SHN_XINDEX && 158 "getSymbolTableIndex should handle this"); 159 const typename ELFO::Elf_Shdr *Sec = Obj.getSection(SectionIndex); 160 SectionName = errorOrDefault(Obj.getSectionName(Sec)); 161 } 162 } 163 164 template <class ELFT> 165 static const typename ELFFile<ELFT>::Elf_Shdr * 166 findSectionByAddress(const ELFFile<ELFT> *Obj, uint64_t Addr) { 167 for (const auto &Shdr : Obj->sections()) 168 if (Shdr.sh_addr == Addr) 169 return &Shdr; 170 return nullptr; 171 } 172 173 static const EnumEntry<unsigned> ElfClass[] = { 174 { "None", ELF::ELFCLASSNONE }, 175 { "32-bit", ELF::ELFCLASS32 }, 176 { "64-bit", ELF::ELFCLASS64 }, 177 }; 178 179 static const EnumEntry<unsigned> ElfDataEncoding[] = { 180 { "None", ELF::ELFDATANONE }, 181 { "LittleEndian", ELF::ELFDATA2LSB }, 182 { "BigEndian", ELF::ELFDATA2MSB }, 183 }; 184 185 static const EnumEntry<unsigned> ElfObjectFileType[] = { 186 { "None", ELF::ET_NONE }, 187 { "Relocatable", ELF::ET_REL }, 188 { "Executable", ELF::ET_EXEC }, 189 { "SharedObject", ELF::ET_DYN }, 190 { "Core", ELF::ET_CORE }, 191 }; 192 193 static const EnumEntry<unsigned> ElfOSABI[] = { 194 { "SystemV", ELF::ELFOSABI_NONE }, 195 { "HPUX", ELF::ELFOSABI_HPUX }, 196 { "NetBSD", ELF::ELFOSABI_NETBSD }, 197 { "GNU/Linux", ELF::ELFOSABI_LINUX }, 198 { "GNU/Hurd", ELF::ELFOSABI_HURD }, 199 { "Solaris", ELF::ELFOSABI_SOLARIS }, 200 { "AIX", ELF::ELFOSABI_AIX }, 201 { "IRIX", ELF::ELFOSABI_IRIX }, 202 { "FreeBSD", ELF::ELFOSABI_FREEBSD }, 203 { "TRU64", ELF::ELFOSABI_TRU64 }, 204 { "Modesto", ELF::ELFOSABI_MODESTO }, 205 { "OpenBSD", ELF::ELFOSABI_OPENBSD }, 206 { "OpenVMS", ELF::ELFOSABI_OPENVMS }, 207 { "NSK", ELF::ELFOSABI_NSK }, 208 { "AROS", ELF::ELFOSABI_AROS }, 209 { "FenixOS", ELF::ELFOSABI_FENIXOS }, 210 { "CloudABI", ELF::ELFOSABI_CLOUDABI }, 211 { "C6000_ELFABI", ELF::ELFOSABI_C6000_ELFABI }, 212 { "C6000_LINUX" , ELF::ELFOSABI_C6000_LINUX }, 213 { "ARM", ELF::ELFOSABI_ARM }, 214 { "Standalone" , ELF::ELFOSABI_STANDALONE } 215 }; 216 217 static const EnumEntry<unsigned> ElfMachineType[] = { 218 LLVM_READOBJ_ENUM_ENT(ELF, EM_NONE ), 219 LLVM_READOBJ_ENUM_ENT(ELF, EM_M32 ), 220 LLVM_READOBJ_ENUM_ENT(ELF, EM_SPARC ), 221 LLVM_READOBJ_ENUM_ENT(ELF, EM_386 ), 222 LLVM_READOBJ_ENUM_ENT(ELF, EM_68K ), 223 LLVM_READOBJ_ENUM_ENT(ELF, EM_88K ), 224 LLVM_READOBJ_ENUM_ENT(ELF, EM_486 ), 225 LLVM_READOBJ_ENUM_ENT(ELF, EM_860 ), 226 LLVM_READOBJ_ENUM_ENT(ELF, EM_MIPS ), 227 LLVM_READOBJ_ENUM_ENT(ELF, EM_S370 ), 228 LLVM_READOBJ_ENUM_ENT(ELF, EM_MIPS_RS3_LE ), 229 LLVM_READOBJ_ENUM_ENT(ELF, EM_PARISC ), 230 LLVM_READOBJ_ENUM_ENT(ELF, EM_VPP500 ), 231 LLVM_READOBJ_ENUM_ENT(ELF, EM_SPARC32PLUS ), 232 LLVM_READOBJ_ENUM_ENT(ELF, EM_960 ), 233 LLVM_READOBJ_ENUM_ENT(ELF, EM_PPC ), 234 LLVM_READOBJ_ENUM_ENT(ELF, EM_PPC64 ), 235 LLVM_READOBJ_ENUM_ENT(ELF, EM_S390 ), 236 LLVM_READOBJ_ENUM_ENT(ELF, EM_SPU ), 237 LLVM_READOBJ_ENUM_ENT(ELF, EM_V800 ), 238 LLVM_READOBJ_ENUM_ENT(ELF, EM_FR20 ), 239 LLVM_READOBJ_ENUM_ENT(ELF, EM_RH32 ), 240 LLVM_READOBJ_ENUM_ENT(ELF, EM_RCE ), 241 LLVM_READOBJ_ENUM_ENT(ELF, EM_ARM ), 242 LLVM_READOBJ_ENUM_ENT(ELF, EM_ALPHA ), 243 LLVM_READOBJ_ENUM_ENT(ELF, EM_SH ), 244 LLVM_READOBJ_ENUM_ENT(ELF, EM_SPARCV9 ), 245 LLVM_READOBJ_ENUM_ENT(ELF, EM_TRICORE ), 246 LLVM_READOBJ_ENUM_ENT(ELF, EM_ARC ), 247 LLVM_READOBJ_ENUM_ENT(ELF, EM_H8_300 ), 248 LLVM_READOBJ_ENUM_ENT(ELF, EM_H8_300H ), 249 LLVM_READOBJ_ENUM_ENT(ELF, EM_H8S ), 250 LLVM_READOBJ_ENUM_ENT(ELF, EM_H8_500 ), 251 LLVM_READOBJ_ENUM_ENT(ELF, EM_IA_64 ), 252 LLVM_READOBJ_ENUM_ENT(ELF, EM_MIPS_X ), 253 LLVM_READOBJ_ENUM_ENT(ELF, EM_COLDFIRE ), 254 LLVM_READOBJ_ENUM_ENT(ELF, EM_68HC12 ), 255 LLVM_READOBJ_ENUM_ENT(ELF, EM_MMA ), 256 LLVM_READOBJ_ENUM_ENT(ELF, EM_PCP ), 257 LLVM_READOBJ_ENUM_ENT(ELF, EM_NCPU ), 258 LLVM_READOBJ_ENUM_ENT(ELF, EM_NDR1 ), 259 LLVM_READOBJ_ENUM_ENT(ELF, EM_STARCORE ), 260 LLVM_READOBJ_ENUM_ENT(ELF, EM_ME16 ), 261 LLVM_READOBJ_ENUM_ENT(ELF, EM_ST100 ), 262 LLVM_READOBJ_ENUM_ENT(ELF, EM_TINYJ ), 263 LLVM_READOBJ_ENUM_ENT(ELF, EM_X86_64 ), 264 LLVM_READOBJ_ENUM_ENT(ELF, EM_PDSP ), 265 LLVM_READOBJ_ENUM_ENT(ELF, EM_PDP10 ), 266 LLVM_READOBJ_ENUM_ENT(ELF, EM_PDP11 ), 267 LLVM_READOBJ_ENUM_ENT(ELF, EM_FX66 ), 268 LLVM_READOBJ_ENUM_ENT(ELF, EM_ST9PLUS ), 269 LLVM_READOBJ_ENUM_ENT(ELF, EM_ST7 ), 270 LLVM_READOBJ_ENUM_ENT(ELF, EM_68HC16 ), 271 LLVM_READOBJ_ENUM_ENT(ELF, EM_68HC11 ), 272 LLVM_READOBJ_ENUM_ENT(ELF, EM_68HC08 ), 273 LLVM_READOBJ_ENUM_ENT(ELF, EM_68HC05 ), 274 LLVM_READOBJ_ENUM_ENT(ELF, EM_SVX ), 275 LLVM_READOBJ_ENUM_ENT(ELF, EM_ST19 ), 276 LLVM_READOBJ_ENUM_ENT(ELF, EM_VAX ), 277 LLVM_READOBJ_ENUM_ENT(ELF, EM_CRIS ), 278 LLVM_READOBJ_ENUM_ENT(ELF, EM_JAVELIN ), 279 LLVM_READOBJ_ENUM_ENT(ELF, EM_FIREPATH ), 280 LLVM_READOBJ_ENUM_ENT(ELF, EM_ZSP ), 281 LLVM_READOBJ_ENUM_ENT(ELF, EM_MMIX ), 282 LLVM_READOBJ_ENUM_ENT(ELF, EM_HUANY ), 283 LLVM_READOBJ_ENUM_ENT(ELF, EM_PRISM ), 284 LLVM_READOBJ_ENUM_ENT(ELF, EM_AVR ), 285 LLVM_READOBJ_ENUM_ENT(ELF, EM_FR30 ), 286 LLVM_READOBJ_ENUM_ENT(ELF, EM_D10V ), 287 LLVM_READOBJ_ENUM_ENT(ELF, EM_D30V ), 288 LLVM_READOBJ_ENUM_ENT(ELF, EM_V850 ), 289 LLVM_READOBJ_ENUM_ENT(ELF, EM_M32R ), 290 LLVM_READOBJ_ENUM_ENT(ELF, EM_MN10300 ), 291 LLVM_READOBJ_ENUM_ENT(ELF, EM_MN10200 ), 292 LLVM_READOBJ_ENUM_ENT(ELF, EM_PJ ), 293 LLVM_READOBJ_ENUM_ENT(ELF, EM_OPENRISC ), 294 LLVM_READOBJ_ENUM_ENT(ELF, EM_ARC_COMPACT ), 295 LLVM_READOBJ_ENUM_ENT(ELF, EM_XTENSA ), 296 LLVM_READOBJ_ENUM_ENT(ELF, EM_VIDEOCORE ), 297 LLVM_READOBJ_ENUM_ENT(ELF, EM_TMM_GPP ), 298 LLVM_READOBJ_ENUM_ENT(ELF, EM_NS32K ), 299 LLVM_READOBJ_ENUM_ENT(ELF, EM_TPC ), 300 LLVM_READOBJ_ENUM_ENT(ELF, EM_SNP1K ), 301 LLVM_READOBJ_ENUM_ENT(ELF, EM_ST200 ), 302 LLVM_READOBJ_ENUM_ENT(ELF, EM_IP2K ), 303 LLVM_READOBJ_ENUM_ENT(ELF, EM_MAX ), 304 LLVM_READOBJ_ENUM_ENT(ELF, EM_CR ), 305 LLVM_READOBJ_ENUM_ENT(ELF, EM_F2MC16 ), 306 LLVM_READOBJ_ENUM_ENT(ELF, EM_MSP430 ), 307 LLVM_READOBJ_ENUM_ENT(ELF, EM_BLACKFIN ), 308 LLVM_READOBJ_ENUM_ENT(ELF, EM_SE_C33 ), 309 LLVM_READOBJ_ENUM_ENT(ELF, EM_SEP ), 310 LLVM_READOBJ_ENUM_ENT(ELF, EM_ARCA ), 311 LLVM_READOBJ_ENUM_ENT(ELF, EM_UNICORE ), 312 LLVM_READOBJ_ENUM_ENT(ELF, EM_EXCESS ), 313 LLVM_READOBJ_ENUM_ENT(ELF, EM_DXP ), 314 LLVM_READOBJ_ENUM_ENT(ELF, EM_ALTERA_NIOS2 ), 315 LLVM_READOBJ_ENUM_ENT(ELF, EM_CRX ), 316 LLVM_READOBJ_ENUM_ENT(ELF, EM_XGATE ), 317 LLVM_READOBJ_ENUM_ENT(ELF, EM_C166 ), 318 LLVM_READOBJ_ENUM_ENT(ELF, EM_M16C ), 319 LLVM_READOBJ_ENUM_ENT(ELF, EM_DSPIC30F ), 320 LLVM_READOBJ_ENUM_ENT(ELF, EM_CE ), 321 LLVM_READOBJ_ENUM_ENT(ELF, EM_M32C ), 322 LLVM_READOBJ_ENUM_ENT(ELF, EM_TSK3000 ), 323 LLVM_READOBJ_ENUM_ENT(ELF, EM_RS08 ), 324 LLVM_READOBJ_ENUM_ENT(ELF, EM_SHARC ), 325 LLVM_READOBJ_ENUM_ENT(ELF, EM_ECOG2 ), 326 LLVM_READOBJ_ENUM_ENT(ELF, EM_SCORE7 ), 327 LLVM_READOBJ_ENUM_ENT(ELF, EM_DSP24 ), 328 LLVM_READOBJ_ENUM_ENT(ELF, EM_VIDEOCORE3 ), 329 LLVM_READOBJ_ENUM_ENT(ELF, EM_LATTICEMICO32), 330 LLVM_READOBJ_ENUM_ENT(ELF, EM_SE_C17 ), 331 LLVM_READOBJ_ENUM_ENT(ELF, EM_TI_C6000 ), 332 LLVM_READOBJ_ENUM_ENT(ELF, EM_TI_C2000 ), 333 LLVM_READOBJ_ENUM_ENT(ELF, EM_TI_C5500 ), 334 LLVM_READOBJ_ENUM_ENT(ELF, EM_MMDSP_PLUS ), 335 LLVM_READOBJ_ENUM_ENT(ELF, EM_CYPRESS_M8C ), 336 LLVM_READOBJ_ENUM_ENT(ELF, EM_R32C ), 337 LLVM_READOBJ_ENUM_ENT(ELF, EM_TRIMEDIA ), 338 LLVM_READOBJ_ENUM_ENT(ELF, EM_HEXAGON ), 339 LLVM_READOBJ_ENUM_ENT(ELF, EM_8051 ), 340 LLVM_READOBJ_ENUM_ENT(ELF, EM_STXP7X ), 341 LLVM_READOBJ_ENUM_ENT(ELF, EM_NDS32 ), 342 LLVM_READOBJ_ENUM_ENT(ELF, EM_ECOG1 ), 343 LLVM_READOBJ_ENUM_ENT(ELF, EM_ECOG1X ), 344 LLVM_READOBJ_ENUM_ENT(ELF, EM_MAXQ30 ), 345 LLVM_READOBJ_ENUM_ENT(ELF, EM_XIMO16 ), 346 LLVM_READOBJ_ENUM_ENT(ELF, EM_MANIK ), 347 LLVM_READOBJ_ENUM_ENT(ELF, EM_CRAYNV2 ), 348 LLVM_READOBJ_ENUM_ENT(ELF, EM_RX ), 349 LLVM_READOBJ_ENUM_ENT(ELF, EM_METAG ), 350 LLVM_READOBJ_ENUM_ENT(ELF, EM_MCST_ELBRUS ), 351 LLVM_READOBJ_ENUM_ENT(ELF, EM_ECOG16 ), 352 LLVM_READOBJ_ENUM_ENT(ELF, EM_CR16 ), 353 LLVM_READOBJ_ENUM_ENT(ELF, EM_ETPU ), 354 LLVM_READOBJ_ENUM_ENT(ELF, EM_SLE9X ), 355 LLVM_READOBJ_ENUM_ENT(ELF, EM_L10M ), 356 LLVM_READOBJ_ENUM_ENT(ELF, EM_K10M ), 357 LLVM_READOBJ_ENUM_ENT(ELF, EM_AARCH64 ), 358 LLVM_READOBJ_ENUM_ENT(ELF, EM_AVR32 ), 359 LLVM_READOBJ_ENUM_ENT(ELF, EM_STM8 ), 360 LLVM_READOBJ_ENUM_ENT(ELF, EM_TILE64 ), 361 LLVM_READOBJ_ENUM_ENT(ELF, EM_TILEPRO ), 362 LLVM_READOBJ_ENUM_ENT(ELF, EM_CUDA ), 363 LLVM_READOBJ_ENUM_ENT(ELF, EM_TILEGX ), 364 LLVM_READOBJ_ENUM_ENT(ELF, EM_CLOUDSHIELD ), 365 LLVM_READOBJ_ENUM_ENT(ELF, EM_COREA_1ST ), 366 LLVM_READOBJ_ENUM_ENT(ELF, EM_COREA_2ND ), 367 LLVM_READOBJ_ENUM_ENT(ELF, EM_ARC_COMPACT2 ), 368 LLVM_READOBJ_ENUM_ENT(ELF, EM_OPEN8 ), 369 LLVM_READOBJ_ENUM_ENT(ELF, EM_RL78 ), 370 LLVM_READOBJ_ENUM_ENT(ELF, EM_VIDEOCORE5 ), 371 LLVM_READOBJ_ENUM_ENT(ELF, EM_78KOR ), 372 LLVM_READOBJ_ENUM_ENT(ELF, EM_56800EX ) 373 }; 374 375 static const EnumEntry<unsigned> ElfSymbolBindings[] = { 376 { "Local", ELF::STB_LOCAL }, 377 { "Global", ELF::STB_GLOBAL }, 378 { "Weak", ELF::STB_WEAK }, 379 { "Unique", ELF::STB_GNU_UNIQUE } 380 }; 381 382 static const EnumEntry<unsigned> ElfSymbolTypes[] = { 383 { "None", ELF::STT_NOTYPE }, 384 { "Object", ELF::STT_OBJECT }, 385 { "Function", ELF::STT_FUNC }, 386 { "Section", ELF::STT_SECTION }, 387 { "File", ELF::STT_FILE }, 388 { "Common", ELF::STT_COMMON }, 389 { "TLS", ELF::STT_TLS }, 390 { "GNU_IFunc", ELF::STT_GNU_IFUNC } 391 }; 392 393 static const char *getElfSectionType(unsigned Arch, unsigned Type) { 394 switch (Arch) { 395 case ELF::EM_ARM: 396 switch (Type) { 397 LLVM_READOBJ_ENUM_CASE(ELF, SHT_ARM_EXIDX); 398 LLVM_READOBJ_ENUM_CASE(ELF, SHT_ARM_PREEMPTMAP); 399 LLVM_READOBJ_ENUM_CASE(ELF, SHT_ARM_ATTRIBUTES); 400 LLVM_READOBJ_ENUM_CASE(ELF, SHT_ARM_DEBUGOVERLAY); 401 LLVM_READOBJ_ENUM_CASE(ELF, SHT_ARM_OVERLAYSECTION); 402 } 403 case ELF::EM_HEXAGON: 404 switch (Type) { LLVM_READOBJ_ENUM_CASE(ELF, SHT_HEX_ORDERED); } 405 case ELF::EM_X86_64: 406 switch (Type) { LLVM_READOBJ_ENUM_CASE(ELF, SHT_X86_64_UNWIND); } 407 case ELF::EM_MIPS: 408 case ELF::EM_MIPS_RS3_LE: 409 switch (Type) { 410 LLVM_READOBJ_ENUM_CASE(ELF, SHT_MIPS_REGINFO); 411 LLVM_READOBJ_ENUM_CASE(ELF, SHT_MIPS_OPTIONS); 412 LLVM_READOBJ_ENUM_CASE(ELF, SHT_MIPS_ABIFLAGS); 413 } 414 } 415 416 switch (Type) { 417 LLVM_READOBJ_ENUM_CASE(ELF, SHT_NULL ); 418 LLVM_READOBJ_ENUM_CASE(ELF, SHT_PROGBITS ); 419 LLVM_READOBJ_ENUM_CASE(ELF, SHT_SYMTAB ); 420 LLVM_READOBJ_ENUM_CASE(ELF, SHT_STRTAB ); 421 LLVM_READOBJ_ENUM_CASE(ELF, SHT_RELA ); 422 LLVM_READOBJ_ENUM_CASE(ELF, SHT_HASH ); 423 LLVM_READOBJ_ENUM_CASE(ELF, SHT_DYNAMIC ); 424 LLVM_READOBJ_ENUM_CASE(ELF, SHT_NOTE ); 425 LLVM_READOBJ_ENUM_CASE(ELF, SHT_NOBITS ); 426 LLVM_READOBJ_ENUM_CASE(ELF, SHT_REL ); 427 LLVM_READOBJ_ENUM_CASE(ELF, SHT_SHLIB ); 428 LLVM_READOBJ_ENUM_CASE(ELF, SHT_DYNSYM ); 429 LLVM_READOBJ_ENUM_CASE(ELF, SHT_INIT_ARRAY ); 430 LLVM_READOBJ_ENUM_CASE(ELF, SHT_FINI_ARRAY ); 431 LLVM_READOBJ_ENUM_CASE(ELF, SHT_PREINIT_ARRAY ); 432 LLVM_READOBJ_ENUM_CASE(ELF, SHT_GROUP ); 433 LLVM_READOBJ_ENUM_CASE(ELF, SHT_SYMTAB_SHNDX ); 434 LLVM_READOBJ_ENUM_CASE(ELF, SHT_GNU_ATTRIBUTES ); 435 LLVM_READOBJ_ENUM_CASE(ELF, SHT_GNU_HASH ); 436 LLVM_READOBJ_ENUM_CASE(ELF, SHT_GNU_verdef ); 437 LLVM_READOBJ_ENUM_CASE(ELF, SHT_GNU_verneed ); 438 LLVM_READOBJ_ENUM_CASE(ELF, SHT_GNU_versym ); 439 default: return ""; 440 } 441 } 442 443 static const EnumEntry<unsigned> ElfSectionFlags[] = { 444 LLVM_READOBJ_ENUM_ENT(ELF, SHF_WRITE ), 445 LLVM_READOBJ_ENUM_ENT(ELF, SHF_ALLOC ), 446 LLVM_READOBJ_ENUM_ENT(ELF, SHF_EXCLUDE ), 447 LLVM_READOBJ_ENUM_ENT(ELF, SHF_EXECINSTR ), 448 LLVM_READOBJ_ENUM_ENT(ELF, SHF_MERGE ), 449 LLVM_READOBJ_ENUM_ENT(ELF, SHF_STRINGS ), 450 LLVM_READOBJ_ENUM_ENT(ELF, SHF_INFO_LINK ), 451 LLVM_READOBJ_ENUM_ENT(ELF, SHF_LINK_ORDER ), 452 LLVM_READOBJ_ENUM_ENT(ELF, SHF_OS_NONCONFORMING), 453 LLVM_READOBJ_ENUM_ENT(ELF, SHF_GROUP ), 454 LLVM_READOBJ_ENUM_ENT(ELF, SHF_TLS ), 455 LLVM_READOBJ_ENUM_ENT(ELF, XCORE_SHF_CP_SECTION), 456 LLVM_READOBJ_ENUM_ENT(ELF, XCORE_SHF_DP_SECTION), 457 LLVM_READOBJ_ENUM_ENT(ELF, SHF_MIPS_NOSTRIP ) 458 }; 459 460 static const char *getElfSegmentType(unsigned Arch, unsigned Type) { 461 // Check potentially overlapped processor-specific 462 // program header type. 463 switch (Arch) { 464 case ELF::EM_ARM: 465 switch (Type) { 466 LLVM_READOBJ_ENUM_CASE(ELF, PT_ARM_EXIDX); 467 } 468 case ELF::EM_MIPS: 469 case ELF::EM_MIPS_RS3_LE: 470 switch (Type) { 471 LLVM_READOBJ_ENUM_CASE(ELF, PT_MIPS_REGINFO); 472 LLVM_READOBJ_ENUM_CASE(ELF, PT_MIPS_RTPROC); 473 LLVM_READOBJ_ENUM_CASE(ELF, PT_MIPS_OPTIONS); 474 } 475 } 476 477 switch (Type) { 478 LLVM_READOBJ_ENUM_CASE(ELF, PT_NULL ); 479 LLVM_READOBJ_ENUM_CASE(ELF, PT_LOAD ); 480 LLVM_READOBJ_ENUM_CASE(ELF, PT_DYNAMIC); 481 LLVM_READOBJ_ENUM_CASE(ELF, PT_INTERP ); 482 LLVM_READOBJ_ENUM_CASE(ELF, PT_NOTE ); 483 LLVM_READOBJ_ENUM_CASE(ELF, PT_SHLIB ); 484 LLVM_READOBJ_ENUM_CASE(ELF, PT_PHDR ); 485 LLVM_READOBJ_ENUM_CASE(ELF, PT_TLS ); 486 487 LLVM_READOBJ_ENUM_CASE(ELF, PT_GNU_EH_FRAME); 488 LLVM_READOBJ_ENUM_CASE(ELF, PT_SUNW_UNWIND); 489 490 LLVM_READOBJ_ENUM_CASE(ELF, PT_GNU_STACK); 491 LLVM_READOBJ_ENUM_CASE(ELF, PT_GNU_RELRO); 492 default: return ""; 493 } 494 } 495 496 static const EnumEntry<unsigned> ElfSegmentFlags[] = { 497 LLVM_READOBJ_ENUM_ENT(ELF, PF_X), 498 LLVM_READOBJ_ENUM_ENT(ELF, PF_W), 499 LLVM_READOBJ_ENUM_ENT(ELF, PF_R) 500 }; 501 502 static const EnumEntry<unsigned> ElfHeaderMipsFlags[] = { 503 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_NOREORDER), 504 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_PIC), 505 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_CPIC), 506 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_ABI2), 507 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_32BITMODE), 508 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_NAN2008), 509 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_ABI_O32), 510 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_MICROMIPS), 511 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_ARCH_ASE_M16), 512 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_ARCH_1), 513 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_ARCH_2), 514 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_ARCH_3), 515 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_ARCH_4), 516 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_ARCH_5), 517 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_ARCH_32), 518 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_ARCH_64), 519 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_ARCH_32R2), 520 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_ARCH_64R2), 521 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_ARCH_32R6), 522 LLVM_READOBJ_ENUM_ENT(ELF, EF_MIPS_ARCH_64R6) 523 }; 524 525 template<class ELFT> 526 void ELFDumper<ELFT>::printFileHeaders() { 527 const typename ELFO::Elf_Ehdr *Header = Obj->getHeader(); 528 529 { 530 DictScope D(W, "ElfHeader"); 531 { 532 DictScope D(W, "Ident"); 533 W.printBinary("Magic", makeArrayRef(Header->e_ident).slice(ELF::EI_MAG0, 534 4)); 535 W.printEnum ("Class", Header->e_ident[ELF::EI_CLASS], 536 makeArrayRef(ElfClass)); 537 W.printEnum ("DataEncoding", Header->e_ident[ELF::EI_DATA], 538 makeArrayRef(ElfDataEncoding)); 539 W.printNumber("FileVersion", Header->e_ident[ELF::EI_VERSION]); 540 W.printEnum ("OS/ABI", Header->e_ident[ELF::EI_OSABI], 541 makeArrayRef(ElfOSABI)); 542 W.printNumber("ABIVersion", Header->e_ident[ELF::EI_ABIVERSION]); 543 W.printBinary("Unused", makeArrayRef(Header->e_ident).slice(ELF::EI_PAD)); 544 } 545 546 W.printEnum ("Type", Header->e_type, makeArrayRef(ElfObjectFileType)); 547 W.printEnum ("Machine", Header->e_machine, makeArrayRef(ElfMachineType)); 548 W.printNumber("Version", Header->e_version); 549 W.printHex ("Entry", Header->e_entry); 550 W.printHex ("ProgramHeaderOffset", Header->e_phoff); 551 W.printHex ("SectionHeaderOffset", Header->e_shoff); 552 if (Header->e_machine == EM_MIPS) 553 W.printFlags("Flags", Header->e_flags, makeArrayRef(ElfHeaderMipsFlags), 554 unsigned(ELF::EF_MIPS_ARCH)); 555 else 556 W.printFlags("Flags", Header->e_flags); 557 W.printNumber("HeaderSize", Header->e_ehsize); 558 W.printNumber("ProgramHeaderEntrySize", Header->e_phentsize); 559 W.printNumber("ProgramHeaderCount", Header->e_phnum); 560 W.printNumber("SectionHeaderEntrySize", Header->e_shentsize); 561 W.printNumber("SectionHeaderCount", Header->e_shnum); 562 W.printNumber("StringTableSectionIndex", Header->e_shstrndx); 563 } 564 } 565 566 template<class ELFT> 567 void ELFDumper<ELFT>::printSections() { 568 ListScope SectionsD(W, "Sections"); 569 570 int SectionIndex = -1; 571 for (typename ELFO::Elf_Shdr_Iter SecI = Obj->begin_sections(), 572 SecE = Obj->end_sections(); 573 SecI != SecE; ++SecI) { 574 ++SectionIndex; 575 576 const Elf_Shdr *Section = &*SecI; 577 StringRef Name = errorOrDefault(Obj->getSectionName(Section)); 578 579 DictScope SectionD(W, "Section"); 580 W.printNumber("Index", SectionIndex); 581 W.printNumber("Name", Name, Section->sh_name); 582 W.printHex("Type", 583 getElfSectionType(Obj->getHeader()->e_machine, Section->sh_type), 584 Section->sh_type); 585 W.printFlags ("Flags", Section->sh_flags, makeArrayRef(ElfSectionFlags)); 586 W.printHex ("Address", Section->sh_addr); 587 W.printHex ("Offset", Section->sh_offset); 588 W.printNumber("Size", Section->sh_size); 589 W.printNumber("Link", Section->sh_link); 590 W.printNumber("Info", Section->sh_info); 591 W.printNumber("AddressAlignment", Section->sh_addralign); 592 W.printNumber("EntrySize", Section->sh_entsize); 593 594 if (opts::SectionRelocations) { 595 ListScope D(W, "Relocations"); 596 printRelocations(Section); 597 } 598 599 if (opts::SectionSymbols) { 600 ListScope D(W, "Symbols"); 601 for (typename ELFO::Elf_Sym_Iter SymI = Obj->begin_symbols(), 602 SymE = Obj->end_symbols(); 603 SymI != SymE; ++SymI) { 604 if (Obj->getSection(&*SymI) == Section) 605 printSymbol(SymI); 606 } 607 } 608 609 if (opts::SectionData && Section->sh_type != ELF::SHT_NOBITS) { 610 ArrayRef<uint8_t> Data = errorOrDefault(Obj->getSectionContents(Section)); 611 W.printBinaryBlock("SectionData", 612 StringRef((const char *)Data.data(), Data.size())); 613 } 614 } 615 } 616 617 template<class ELFT> 618 void ELFDumper<ELFT>::printRelocations() { 619 ListScope D(W, "Relocations"); 620 621 int SectionNumber = -1; 622 for (typename ELFO::Elf_Shdr_Iter SecI = Obj->begin_sections(), 623 SecE = Obj->end_sections(); 624 SecI != SecE; ++SecI) { 625 ++SectionNumber; 626 627 if (SecI->sh_type != ELF::SHT_REL && SecI->sh_type != ELF::SHT_RELA) 628 continue; 629 630 StringRef Name = errorOrDefault(Obj->getSectionName(&*SecI)); 631 632 W.startLine() << "Section (" << SectionNumber << ") " << Name << " {\n"; 633 W.indent(); 634 635 printRelocations(&*SecI); 636 637 W.unindent(); 638 W.startLine() << "}\n"; 639 } 640 } 641 642 template <class ELFT> 643 void ELFDumper<ELFT>::printRelocations(const Elf_Shdr *Sec) { 644 switch (Sec->sh_type) { 645 case ELF::SHT_REL: 646 for (typename ELFO::Elf_Rel_Iter RI = Obj->begin_rel(Sec), 647 RE = Obj->end_rel(Sec); 648 RI != RE; ++RI) { 649 typename ELFO::Elf_Rela Rela; 650 Rela.r_offset = RI->r_offset; 651 Rela.r_info = RI->r_info; 652 Rela.r_addend = 0; 653 printRelocation(Sec, Rela); 654 } 655 break; 656 case ELF::SHT_RELA: 657 for (typename ELFO::Elf_Rela_Iter RI = Obj->begin_rela(Sec), 658 RE = Obj->end_rela(Sec); 659 RI != RE; ++RI) { 660 printRelocation(Sec, *RI); 661 } 662 break; 663 } 664 } 665 666 template <class ELFT> 667 void ELFDumper<ELFT>::printRelocation(const Elf_Shdr *Sec, 668 typename ELFO::Elf_Rela Rel) { 669 SmallString<32> RelocName; 670 Obj->getRelocationTypeName(Rel.getType(Obj->isMips64EL()), RelocName); 671 StringRef SymbolName; 672 std::pair<const Elf_Shdr *, const Elf_Sym *> Sym = 673 Obj->getRelocationSymbol(Sec, &Rel); 674 if (Sym.first) 675 SymbolName = errorOrDefault(Obj->getSymbolName(Sym.first, Sym.second)); 676 677 if (opts::ExpandRelocs) { 678 DictScope Group(W, "Relocation"); 679 W.printHex("Offset", Rel.r_offset); 680 W.printNumber("Type", RelocName, (int)Rel.getType(Obj->isMips64EL())); 681 W.printNumber("Symbol", SymbolName.size() > 0 ? SymbolName : "-", 682 Rel.getSymbol(Obj->isMips64EL())); 683 W.printHex("Addend", Rel.r_addend); 684 } else { 685 raw_ostream& OS = W.startLine(); 686 OS << W.hex(Rel.r_offset) 687 << " " << RelocName 688 << " " << (SymbolName.size() > 0 ? SymbolName : "-") 689 << " " << W.hex(Rel.r_addend) 690 << "\n"; 691 } 692 } 693 694 template<class ELFT> 695 void ELFDumper<ELFT>::printSymbols() { 696 ListScope Group(W, "Symbols"); 697 for (typename ELFO::Elf_Sym_Iter SymI = Obj->begin_symbols(), 698 SymE = Obj->end_symbols(); 699 SymI != SymE; ++SymI) { 700 printSymbol(SymI); 701 } 702 } 703 704 template<class ELFT> 705 void ELFDumper<ELFT>::printDynamicSymbols() { 706 ListScope Group(W, "DynamicSymbols"); 707 708 for (typename ELFO::Elf_Sym_Iter SymI = Obj->begin_dynamic_symbols(), 709 SymE = Obj->end_dynamic_symbols(); 710 SymI != SymE; ++SymI) { 711 printSymbol(SymI); 712 } 713 } 714 715 template <class ELFT> 716 void ELFDumper<ELFT>::printSymbol(typename ELFO::Elf_Sym_Iter Symbol) { 717 unsigned SectionIndex = 0; 718 StringRef SectionName; 719 getSectionNameIndex(*Obj, Symbol, SectionName, SectionIndex); 720 std::string FullSymbolName = getFullSymbolName(*Obj, Symbol); 721 722 DictScope D(W, "Symbol"); 723 W.printNumber("Name", FullSymbolName, Symbol->st_name); 724 W.printHex ("Value", Symbol->st_value); 725 W.printNumber("Size", Symbol->st_size); 726 W.printEnum ("Binding", Symbol->getBinding(), 727 makeArrayRef(ElfSymbolBindings)); 728 W.printEnum ("Type", Symbol->getType(), makeArrayRef(ElfSymbolTypes)); 729 W.printNumber("Other", Symbol->st_other); 730 W.printHex("Section", SectionName, SectionIndex); 731 } 732 733 #define LLVM_READOBJ_TYPE_CASE(name) \ 734 case DT_##name: return #name 735 736 static const char *getTypeString(uint64_t Type) { 737 switch (Type) { 738 LLVM_READOBJ_TYPE_CASE(BIND_NOW); 739 LLVM_READOBJ_TYPE_CASE(DEBUG); 740 LLVM_READOBJ_TYPE_CASE(FINI); 741 LLVM_READOBJ_TYPE_CASE(FINI_ARRAY); 742 LLVM_READOBJ_TYPE_CASE(FINI_ARRAYSZ); 743 LLVM_READOBJ_TYPE_CASE(FLAGS); 744 LLVM_READOBJ_TYPE_CASE(HASH); 745 LLVM_READOBJ_TYPE_CASE(INIT); 746 LLVM_READOBJ_TYPE_CASE(INIT_ARRAY); 747 LLVM_READOBJ_TYPE_CASE(INIT_ARRAYSZ); 748 LLVM_READOBJ_TYPE_CASE(PREINIT_ARRAY); 749 LLVM_READOBJ_TYPE_CASE(PREINIT_ARRAYSZ); 750 LLVM_READOBJ_TYPE_CASE(JMPREL); 751 LLVM_READOBJ_TYPE_CASE(NEEDED); 752 LLVM_READOBJ_TYPE_CASE(NULL); 753 LLVM_READOBJ_TYPE_CASE(PLTGOT); 754 LLVM_READOBJ_TYPE_CASE(PLTREL); 755 LLVM_READOBJ_TYPE_CASE(PLTRELSZ); 756 LLVM_READOBJ_TYPE_CASE(REL); 757 LLVM_READOBJ_TYPE_CASE(RELA); 758 LLVM_READOBJ_TYPE_CASE(RELENT); 759 LLVM_READOBJ_TYPE_CASE(RELSZ); 760 LLVM_READOBJ_TYPE_CASE(RELAENT); 761 LLVM_READOBJ_TYPE_CASE(RELASZ); 762 LLVM_READOBJ_TYPE_CASE(RPATH); 763 LLVM_READOBJ_TYPE_CASE(RUNPATH); 764 LLVM_READOBJ_TYPE_CASE(SONAME); 765 LLVM_READOBJ_TYPE_CASE(STRSZ); 766 LLVM_READOBJ_TYPE_CASE(STRTAB); 767 LLVM_READOBJ_TYPE_CASE(SYMBOLIC); 768 LLVM_READOBJ_TYPE_CASE(SYMENT); 769 LLVM_READOBJ_TYPE_CASE(SYMTAB); 770 LLVM_READOBJ_TYPE_CASE(TEXTREL); 771 LLVM_READOBJ_TYPE_CASE(VERNEED); 772 LLVM_READOBJ_TYPE_CASE(VERNEEDNUM); 773 LLVM_READOBJ_TYPE_CASE(VERSYM); 774 LLVM_READOBJ_TYPE_CASE(RELCOUNT); 775 LLVM_READOBJ_TYPE_CASE(GNU_HASH); 776 LLVM_READOBJ_TYPE_CASE(MIPS_RLD_VERSION); 777 LLVM_READOBJ_TYPE_CASE(MIPS_FLAGS); 778 LLVM_READOBJ_TYPE_CASE(MIPS_BASE_ADDRESS); 779 LLVM_READOBJ_TYPE_CASE(MIPS_LOCAL_GOTNO); 780 LLVM_READOBJ_TYPE_CASE(MIPS_SYMTABNO); 781 LLVM_READOBJ_TYPE_CASE(MIPS_UNREFEXTNO); 782 LLVM_READOBJ_TYPE_CASE(MIPS_GOTSYM); 783 LLVM_READOBJ_TYPE_CASE(MIPS_RLD_MAP); 784 LLVM_READOBJ_TYPE_CASE(MIPS_PLTGOT); 785 LLVM_READOBJ_TYPE_CASE(MIPS_OPTIONS); 786 default: return "unknown"; 787 } 788 } 789 790 #undef LLVM_READOBJ_TYPE_CASE 791 792 #define LLVM_READOBJ_DT_FLAG_ENT(prefix, enum) \ 793 { #enum, prefix##_##enum } 794 795 static const EnumEntry<unsigned> ElfDynamicDTFlags[] = { 796 LLVM_READOBJ_DT_FLAG_ENT(DF, ORIGIN), 797 LLVM_READOBJ_DT_FLAG_ENT(DF, SYMBOLIC), 798 LLVM_READOBJ_DT_FLAG_ENT(DF, TEXTREL), 799 LLVM_READOBJ_DT_FLAG_ENT(DF, BIND_NOW), 800 LLVM_READOBJ_DT_FLAG_ENT(DF, STATIC_TLS) 801 }; 802 803 static const EnumEntry<unsigned> ElfDynamicDTMipsFlags[] = { 804 LLVM_READOBJ_DT_FLAG_ENT(RHF, NONE), 805 LLVM_READOBJ_DT_FLAG_ENT(RHF, QUICKSTART), 806 LLVM_READOBJ_DT_FLAG_ENT(RHF, NOTPOT), 807 LLVM_READOBJ_DT_FLAG_ENT(RHS, NO_LIBRARY_REPLACEMENT), 808 LLVM_READOBJ_DT_FLAG_ENT(RHF, NO_MOVE), 809 LLVM_READOBJ_DT_FLAG_ENT(RHF, SGI_ONLY), 810 LLVM_READOBJ_DT_FLAG_ENT(RHF, GUARANTEE_INIT), 811 LLVM_READOBJ_DT_FLAG_ENT(RHF, DELTA_C_PLUS_PLUS), 812 LLVM_READOBJ_DT_FLAG_ENT(RHF, GUARANTEE_START_INIT), 813 LLVM_READOBJ_DT_FLAG_ENT(RHF, PIXIE), 814 LLVM_READOBJ_DT_FLAG_ENT(RHF, DEFAULT_DELAY_LOAD), 815 LLVM_READOBJ_DT_FLAG_ENT(RHF, REQUICKSTART), 816 LLVM_READOBJ_DT_FLAG_ENT(RHF, REQUICKSTARTED), 817 LLVM_READOBJ_DT_FLAG_ENT(RHF, CORD), 818 LLVM_READOBJ_DT_FLAG_ENT(RHF, NO_UNRES_UNDEF), 819 LLVM_READOBJ_DT_FLAG_ENT(RHF, RLD_ORDER_SAFE) 820 }; 821 822 #undef LLVM_READOBJ_DT_FLAG_ENT 823 824 template <typename T, typename TFlag> 825 void printFlags(T Value, ArrayRef<EnumEntry<TFlag>> Flags, raw_ostream &OS) { 826 typedef EnumEntry<TFlag> FlagEntry; 827 typedef SmallVector<FlagEntry, 10> FlagVector; 828 FlagVector SetFlags; 829 830 for (const auto &Flag : Flags) { 831 if (Flag.Value == 0) 832 continue; 833 834 if ((Value & Flag.Value) == Flag.Value) 835 SetFlags.push_back(Flag); 836 } 837 838 for (const auto &Flag : SetFlags) { 839 OS << Flag.Name << " "; 840 } 841 } 842 843 template <class ELFT> 844 static void printValue(const ELFFile<ELFT> *O, uint64_t Type, uint64_t Value, 845 bool Is64, raw_ostream &OS) { 846 switch (Type) { 847 case DT_PLTREL: 848 if (Value == DT_REL) { 849 OS << "REL"; 850 break; 851 } else if (Value == DT_RELA) { 852 OS << "RELA"; 853 break; 854 } 855 // Fallthrough. 856 case DT_PLTGOT: 857 case DT_HASH: 858 case DT_STRTAB: 859 case DT_SYMTAB: 860 case DT_RELA: 861 case DT_INIT: 862 case DT_FINI: 863 case DT_REL: 864 case DT_JMPREL: 865 case DT_INIT_ARRAY: 866 case DT_FINI_ARRAY: 867 case DT_PREINIT_ARRAY: 868 case DT_DEBUG: 869 case DT_VERNEED: 870 case DT_VERSYM: 871 case DT_GNU_HASH: 872 case DT_NULL: 873 case DT_MIPS_BASE_ADDRESS: 874 case DT_MIPS_GOTSYM: 875 case DT_MIPS_RLD_MAP: 876 case DT_MIPS_PLTGOT: 877 case DT_MIPS_OPTIONS: 878 OS << format("0x%" PRIX64, Value); 879 break; 880 case DT_RELCOUNT: 881 case DT_VERNEEDNUM: 882 case DT_MIPS_RLD_VERSION: 883 case DT_MIPS_LOCAL_GOTNO: 884 case DT_MIPS_SYMTABNO: 885 case DT_MIPS_UNREFEXTNO: 886 OS << Value; 887 break; 888 case DT_PLTRELSZ: 889 case DT_RELASZ: 890 case DT_RELAENT: 891 case DT_STRSZ: 892 case DT_SYMENT: 893 case DT_RELSZ: 894 case DT_RELENT: 895 case DT_INIT_ARRAYSZ: 896 case DT_FINI_ARRAYSZ: 897 case DT_PREINIT_ARRAYSZ: 898 OS << Value << " (bytes)"; 899 break; 900 case DT_NEEDED: 901 OS << "SharedLibrary (" << O->getDynamicString(Value) << ")"; 902 break; 903 case DT_SONAME: 904 OS << "LibrarySoname (" << O->getDynamicString(Value) << ")"; 905 break; 906 case DT_RPATH: 907 case DT_RUNPATH: 908 OS << O->getDynamicString(Value); 909 break; 910 case DT_MIPS_FLAGS: 911 printFlags(Value, makeArrayRef(ElfDynamicDTMipsFlags), OS); 912 break; 913 case DT_FLAGS: 914 printFlags(Value, makeArrayRef(ElfDynamicDTFlags), OS); 915 break; 916 } 917 } 918 919 template<class ELFT> 920 void ELFDumper<ELFT>::printUnwindInfo() { 921 W.startLine() << "UnwindInfo not implemented.\n"; 922 } 923 924 namespace { 925 template <> 926 void ELFDumper<ELFType<support::little, 2, false> >::printUnwindInfo() { 927 const unsigned Machine = Obj->getHeader()->e_machine; 928 if (Machine == EM_ARM) { 929 ARM::EHABI::PrinterContext<ELFType<support::little, 2, false> > Ctx(W, Obj); 930 return Ctx.PrintUnwindInformation(); 931 } 932 W.startLine() << "UnwindInfo not implemented.\n"; 933 } 934 } 935 936 template<class ELFT> 937 void ELFDumper<ELFT>::printDynamicTable() { 938 auto DynTable = Obj->dynamic_table(true); 939 940 ptrdiff_t Total = std::distance(DynTable.begin(), DynTable.end()); 941 if (Total == 0) 942 return; 943 944 raw_ostream &OS = W.getOStream(); 945 W.startLine() << "DynamicSection [ (" << Total << " entries)\n"; 946 947 bool Is64 = ELFT::Is64Bits; 948 949 W.startLine() 950 << " Tag" << (Is64 ? " " : " ") << "Type" 951 << " " << "Name/Value\n"; 952 for (const auto &Entry : DynTable) { 953 W.startLine() 954 << " " 955 << format(Is64 ? "0x%016" PRIX64 : "0x%08" PRIX64, Entry.getTag()) 956 << " " << format("%-21s", getTypeString(Entry.getTag())); 957 printValue(Obj, Entry.getTag(), Entry.getVal(), Is64, OS); 958 OS << "\n"; 959 } 960 961 W.startLine() << "]\n"; 962 } 963 964 template<class ELFT> 965 void ELFDumper<ELFT>::printNeededLibraries() { 966 ListScope D(W, "NeededLibraries"); 967 968 typedef std::vector<StringRef> LibsTy; 969 LibsTy Libs; 970 971 for (const auto &Entry : Obj->dynamic_table()) 972 if (Entry.d_tag == ELF::DT_NEEDED) 973 Libs.push_back(Obj->getDynamicString(Entry.d_un.d_val)); 974 975 std::stable_sort(Libs.begin(), Libs.end()); 976 977 for (LibsTy::const_iterator I = Libs.begin(), E = Libs.end(); I != E; ++I) { 978 outs() << " " << *I << "\n"; 979 } 980 } 981 982 template<class ELFT> 983 void ELFDumper<ELFT>::printProgramHeaders() { 984 ListScope L(W, "ProgramHeaders"); 985 986 for (typename ELFO::Elf_Phdr_Iter PI = Obj->begin_program_headers(), 987 PE = Obj->end_program_headers(); 988 PI != PE; ++PI) { 989 DictScope P(W, "ProgramHeader"); 990 W.printHex ("Type", 991 getElfSegmentType(Obj->getHeader()->e_machine, PI->p_type), 992 PI->p_type); 993 W.printHex ("Offset", PI->p_offset); 994 W.printHex ("VirtualAddress", PI->p_vaddr); 995 W.printHex ("PhysicalAddress", PI->p_paddr); 996 W.printNumber("FileSize", PI->p_filesz); 997 W.printNumber("MemSize", PI->p_memsz); 998 W.printFlags ("Flags", PI->p_flags, makeArrayRef(ElfSegmentFlags)); 999 W.printNumber("Alignment", PI->p_align); 1000 } 1001 } 1002 1003 template <class ELFT> 1004 void ELFDumper<ELFT>::printAttributes() { 1005 W.startLine() << "Attributes not implemented.\n"; 1006 } 1007 1008 namespace { 1009 template <> 1010 void ELFDumper<ELFType<support::little, 2, false> >::printAttributes() { 1011 if (Obj->getHeader()->e_machine != EM_ARM) { 1012 W.startLine() << "Attributes not implemented.\n"; 1013 return; 1014 } 1015 1016 DictScope BA(W, "BuildAttributes"); 1017 for (ELFO::Elf_Shdr_Iter SI = Obj->begin_sections(), SE = Obj->end_sections(); 1018 SI != SE; ++SI) { 1019 if (SI->sh_type != ELF::SHT_ARM_ATTRIBUTES) 1020 continue; 1021 1022 ErrorOr<ArrayRef<uint8_t> > Contents = Obj->getSectionContents(&(*SI)); 1023 if (!Contents) 1024 continue; 1025 1026 if ((*Contents)[0] != ARMBuildAttrs::Format_Version) { 1027 errs() << "unrecognised FormatVersion: 0x" << utohexstr((*Contents)[0]) 1028 << '\n'; 1029 continue; 1030 } 1031 1032 W.printHex("FormatVersion", (*Contents)[0]); 1033 if (Contents->size() == 1) 1034 continue; 1035 1036 ARMAttributeParser(W).Parse(*Contents); 1037 } 1038 } 1039 } 1040 1041 namespace { 1042 template <class ELFT> class MipsGOTParser { 1043 public: 1044 typedef object::ELFFile<ELFT> ObjectFile; 1045 typedef typename ObjectFile::Elf_Shdr Elf_Shdr; 1046 1047 MipsGOTParser(const ObjectFile *Obj, StreamWriter &W) : Obj(Obj), W(W) {} 1048 1049 void parseGOT(const Elf_Shdr &GOTShdr); 1050 1051 private: 1052 typedef typename ObjectFile::Elf_Sym_Iter Elf_Sym_Iter; 1053 typedef typename ObjectFile::Elf_Addr GOTEntry; 1054 typedef typename ObjectFile::template ELFEntityIterator<const GOTEntry> 1055 GOTIter; 1056 1057 const ObjectFile *Obj; 1058 StreamWriter &W; 1059 1060 std::size_t getGOTTotal(ArrayRef<uint8_t> GOT) const; 1061 GOTIter makeGOTIter(ArrayRef<uint8_t> GOT, std::size_t EntryNum); 1062 1063 bool getGOTTags(uint64_t &LocalGotNum, uint64_t &GotSym); 1064 void printGotEntry(uint64_t GotAddr, GOTIter BeginIt, GOTIter It); 1065 void printGlobalGotEntry(uint64_t GotAddr, GOTIter BeginIt, GOTIter It, 1066 Elf_Sym_Iter Sym); 1067 }; 1068 } 1069 1070 template <class ELFT> 1071 void MipsGOTParser<ELFT>::parseGOT(const Elf_Shdr &GOTShdr) { 1072 // See "Global Offset Table" in Chapter 5 in the following document 1073 // for detailed GOT description. 1074 // ftp://www.linux-mips.org/pub/linux/mips/doc/ABI/mipsabi.pdf 1075 1076 ErrorOr<ArrayRef<uint8_t>> GOT = Obj->getSectionContents(&GOTShdr); 1077 if (!GOT) { 1078 W.startLine() << "The .got section is empty.\n"; 1079 return; 1080 } 1081 1082 uint64_t DtLocalGotNum; 1083 uint64_t DtGotSym; 1084 if (!getGOTTags(DtLocalGotNum, DtGotSym)) 1085 return; 1086 1087 if (DtLocalGotNum > getGOTTotal(*GOT)) { 1088 W.startLine() << "MIPS_LOCAL_GOTNO exceeds a number of GOT entries.\n"; 1089 return; 1090 } 1091 1092 Elf_Sym_Iter DynSymBegin = Obj->begin_dynamic_symbols(); 1093 Elf_Sym_Iter DynSymEnd = Obj->end_dynamic_symbols(); 1094 std::size_t DynSymTotal = std::size_t(std::distance(DynSymBegin, DynSymEnd)); 1095 1096 if (DtGotSym > DynSymTotal) { 1097 W.startLine() << "MIPS_GOTSYM exceeds a number of dynamic symbols.\n"; 1098 return; 1099 } 1100 1101 std::size_t GlobalGotNum = DynSymTotal - DtGotSym; 1102 1103 if (DtLocalGotNum + GlobalGotNum > getGOTTotal(*GOT)) { 1104 W.startLine() << "Number of global GOT entries exceeds the size of GOT.\n"; 1105 return; 1106 } 1107 1108 GOTIter GotBegin = makeGOTIter(*GOT, 0); 1109 GOTIter GotLocalEnd = makeGOTIter(*GOT, DtLocalGotNum); 1110 GOTIter It = GotBegin; 1111 1112 DictScope GS(W, "Primary GOT"); 1113 1114 W.printHex("Canonical gp value", GOTShdr.sh_addr + 0x7ff0); 1115 { 1116 ListScope RS(W, "Reserved entries"); 1117 1118 { 1119 DictScope D(W, "Entry"); 1120 printGotEntry(GOTShdr.sh_addr, GotBegin, It++); 1121 W.printString("Purpose", StringRef("Lazy resolver")); 1122 } 1123 1124 if (It != GotLocalEnd && (*It >> (sizeof(GOTEntry) * 8 - 1)) != 0) { 1125 DictScope D(W, "Entry"); 1126 printGotEntry(GOTShdr.sh_addr, GotBegin, It++); 1127 W.printString("Purpose", StringRef("Module pointer (GNU extension)")); 1128 } 1129 } 1130 { 1131 ListScope LS(W, "Local entries"); 1132 for (; It != GotLocalEnd; ++It) { 1133 DictScope D(W, "Entry"); 1134 printGotEntry(GOTShdr.sh_addr, GotBegin, It); 1135 } 1136 } 1137 { 1138 ListScope GS(W, "Global entries"); 1139 1140 GOTIter GotGlobalEnd = makeGOTIter(*GOT, DtLocalGotNum + GlobalGotNum); 1141 Elf_Sym_Iter GotDynSym = DynSymBegin + DtGotSym; 1142 for (; It != GotGlobalEnd; ++It) { 1143 DictScope D(W, "Entry"); 1144 printGlobalGotEntry(GOTShdr.sh_addr, GotBegin, It, GotDynSym++); 1145 } 1146 } 1147 1148 std::size_t SpecGotNum = getGOTTotal(*GOT) - DtLocalGotNum - GlobalGotNum; 1149 W.printNumber("Number of TLS and multi-GOT entries", uint64_t(SpecGotNum)); 1150 } 1151 1152 template <class ELFT> 1153 std::size_t MipsGOTParser<ELFT>::getGOTTotal(ArrayRef<uint8_t> GOT) const { 1154 return GOT.size() / sizeof(GOTEntry); 1155 } 1156 1157 template <class ELFT> 1158 typename MipsGOTParser<ELFT>::GOTIter 1159 MipsGOTParser<ELFT>::makeGOTIter(ArrayRef<uint8_t> GOT, std::size_t EntryNum) { 1160 const char *Data = reinterpret_cast<const char *>(GOT.data()); 1161 return GOTIter(sizeof(GOTEntry), Data + EntryNum * sizeof(GOTEntry)); 1162 } 1163 1164 template <class ELFT> 1165 bool MipsGOTParser<ELFT>::getGOTTags(uint64_t &LocalGotNum, uint64_t &GotSym) { 1166 bool FoundLocalGotNum = false; 1167 bool FoundGotSym = false; 1168 for (const auto &Entry : Obj->dynamic_table()) { 1169 switch (Entry.getTag()) { 1170 case ELF::DT_MIPS_LOCAL_GOTNO: 1171 LocalGotNum = Entry.getVal(); 1172 FoundLocalGotNum = true; 1173 break; 1174 case ELF::DT_MIPS_GOTSYM: 1175 GotSym = Entry.getVal(); 1176 FoundGotSym = true; 1177 break; 1178 } 1179 } 1180 1181 if (!FoundLocalGotNum) { 1182 W.startLine() << "Cannot find MIPS_LOCAL_GOTNO dynamic table tag.\n"; 1183 return false; 1184 } 1185 1186 if (!FoundGotSym) { 1187 W.startLine() << "Cannot find MIPS_GOTSYM dynamic table tag.\n"; 1188 return false; 1189 } 1190 1191 return true; 1192 } 1193 1194 template <class ELFT> 1195 void MipsGOTParser<ELFT>::printGotEntry(uint64_t GotAddr, GOTIter BeginIt, 1196 GOTIter It) { 1197 int64_t Offset = std::distance(BeginIt, It) * sizeof(GOTEntry); 1198 W.printHex("Address", GotAddr + Offset); 1199 W.printNumber("Access", Offset - 0x7ff0); 1200 W.printHex("Initial", *It); 1201 } 1202 1203 template <class ELFT> 1204 void MipsGOTParser<ELFT>::printGlobalGotEntry(uint64_t GotAddr, GOTIter BeginIt, 1205 GOTIter It, Elf_Sym_Iter Sym) { 1206 printGotEntry(GotAddr, BeginIt, It); 1207 1208 W.printHex("Value", Sym->st_value); 1209 W.printEnum("Type", Sym->getType(), makeArrayRef(ElfSymbolTypes)); 1210 1211 unsigned SectionIndex = 0; 1212 StringRef SectionName; 1213 getSectionNameIndex(*Obj, Sym, SectionName, SectionIndex); 1214 W.printHex("Section", SectionName, SectionIndex); 1215 1216 std::string FullSymbolName = getFullSymbolName(*Obj, Sym); 1217 W.printNumber("Name", FullSymbolName, Sym->st_name); 1218 } 1219 1220 template <class ELFT> void ELFDumper<ELFT>::printMipsPLTGOT() { 1221 if (Obj->getHeader()->e_machine != EM_MIPS) { 1222 W.startLine() << "MIPS PLT GOT is available for MIPS targets only.\n"; 1223 return; 1224 } 1225 1226 llvm::Optional<uint64_t> DtPltGot; 1227 for (const auto &Entry : Obj->dynamic_table()) { 1228 if (Entry.getTag() == ELF::DT_PLTGOT) { 1229 DtPltGot = Entry.getVal(); 1230 break; 1231 } 1232 } 1233 1234 if (!DtPltGot) { 1235 W.startLine() << "Cannot find PLTGOT dynamic table tag.\n"; 1236 return; 1237 } 1238 1239 const Elf_Shdr *GotShdr = findSectionByAddress(Obj, *DtPltGot); 1240 if (!GotShdr) { 1241 W.startLine() << "There is no .got section in the file.\n"; 1242 return; 1243 } 1244 1245 MipsGOTParser<ELFT>(Obj, W).parseGOT(*GotShdr); 1246 } 1247