1 //===-- ObjectFileELF.cpp ------------------------------------- -*- 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 #include "ObjectFileELF.h" 11 12 #include <cassert> 13 #include <algorithm> 14 15 #include "lldb/Core/ArchSpec.h" 16 #include "lldb/Core/DataBuffer.h" 17 #include "lldb/Core/Error.h" 18 #include "lldb/Core/FileSpecList.h" 19 #include "lldb/Core/Module.h" 20 #include "lldb/Core/PluginManager.h" 21 #include "lldb/Core/Section.h" 22 #include "lldb/Core/Stream.h" 23 #include "lldb/Symbol/SymbolContext.h" 24 #include "lldb/Host/Host.h" 25 26 #include "llvm/ADT/PointerUnion.h" 27 28 #define CASE_AND_STREAM(s, def, width) \ 29 case def: s->Printf("%-*s", width, #def); break; 30 31 using namespace lldb; 32 using namespace lldb_private; 33 using namespace elf; 34 using namespace llvm::ELF; 35 36 namespace { 37 //===----------------------------------------------------------------------===// 38 /// @class ELFRelocation 39 /// @brief Generic wrapper for ELFRel and ELFRela. 40 /// 41 /// This helper class allows us to parse both ELFRel and ELFRela relocation 42 /// entries in a generic manner. 43 class ELFRelocation 44 { 45 public: 46 47 /// Constructs an ELFRelocation entry with a personality as given by @p 48 /// type. 49 /// 50 /// @param type Either DT_REL or DT_RELA. Any other value is invalid. 51 ELFRelocation(unsigned type); 52 53 ~ELFRelocation(); 54 55 bool 56 Parse(const lldb_private::DataExtractor &data, lldb::offset_t *offset); 57 58 static unsigned 59 RelocType32(const ELFRelocation &rel); 60 61 static unsigned 62 RelocType64(const ELFRelocation &rel); 63 64 static unsigned 65 RelocSymbol32(const ELFRelocation &rel); 66 67 static unsigned 68 RelocSymbol64(const ELFRelocation &rel); 69 70 private: 71 typedef llvm::PointerUnion<ELFRel*, ELFRela*> RelocUnion; 72 73 RelocUnion reloc; 74 }; 75 76 ELFRelocation::ELFRelocation(unsigned type) 77 { 78 if (type == DT_REL) 79 reloc = new ELFRel(); 80 else if (type == DT_RELA) 81 reloc = new ELFRela(); 82 else { 83 assert(false && "unexpected relocation type"); 84 reloc = static_cast<ELFRel*>(NULL); 85 } 86 } 87 88 ELFRelocation::~ELFRelocation() 89 { 90 if (reloc.is<ELFRel*>()) 91 delete reloc.get<ELFRel*>(); 92 else 93 delete reloc.get<ELFRela*>(); 94 } 95 96 bool 97 ELFRelocation::Parse(const lldb_private::DataExtractor &data, lldb::offset_t *offset) 98 { 99 if (reloc.is<ELFRel*>()) 100 return reloc.get<ELFRel*>()->Parse(data, offset); 101 else 102 return reloc.get<ELFRela*>()->Parse(data, offset); 103 } 104 105 unsigned 106 ELFRelocation::RelocType32(const ELFRelocation &rel) 107 { 108 if (rel.reloc.is<ELFRel*>()) 109 return ELFRel::RelocType32(*rel.reloc.get<ELFRel*>()); 110 else 111 return ELFRela::RelocType32(*rel.reloc.get<ELFRela*>()); 112 } 113 114 unsigned 115 ELFRelocation::RelocType64(const ELFRelocation &rel) 116 { 117 if (rel.reloc.is<ELFRel*>()) 118 return ELFRel::RelocType64(*rel.reloc.get<ELFRel*>()); 119 else 120 return ELFRela::RelocType64(*rel.reloc.get<ELFRela*>()); 121 } 122 123 unsigned 124 ELFRelocation::RelocSymbol32(const ELFRelocation &rel) 125 { 126 if (rel.reloc.is<ELFRel*>()) 127 return ELFRel::RelocSymbol32(*rel.reloc.get<ELFRel*>()); 128 else 129 return ELFRela::RelocSymbol32(*rel.reloc.get<ELFRela*>()); 130 } 131 132 unsigned 133 ELFRelocation::RelocSymbol64(const ELFRelocation &rel) 134 { 135 if (rel.reloc.is<ELFRel*>()) 136 return ELFRel::RelocSymbol64(*rel.reloc.get<ELFRel*>()); 137 else 138 return ELFRela::RelocSymbol64(*rel.reloc.get<ELFRela*>()); 139 } 140 141 } // end anonymous namespace 142 143 //------------------------------------------------------------------ 144 // Static methods. 145 //------------------------------------------------------------------ 146 void 147 ObjectFileELF::Initialize() 148 { 149 PluginManager::RegisterPlugin(GetPluginNameStatic(), 150 GetPluginDescriptionStatic(), 151 CreateInstance, 152 CreateMemoryInstance); 153 } 154 155 void 156 ObjectFileELF::Terminate() 157 { 158 PluginManager::UnregisterPlugin(CreateInstance); 159 } 160 161 const char * 162 ObjectFileELF::GetPluginNameStatic() 163 { 164 return "object-file.elf"; 165 } 166 167 const char * 168 ObjectFileELF::GetPluginDescriptionStatic() 169 { 170 return "ELF object file reader."; 171 } 172 173 ObjectFile * 174 ObjectFileELF::CreateInstance (const lldb::ModuleSP &module_sp, 175 DataBufferSP &data_sp, 176 lldb::offset_t data_offset, 177 const lldb_private::FileSpec* file, 178 lldb::offset_t file_offset, 179 lldb::offset_t length) 180 { 181 if (!data_sp) 182 { 183 data_sp = file->MemoryMapFileContents(file_offset, length); 184 data_offset = 0; 185 } 186 187 if (data_sp && data_sp->GetByteSize() > (llvm::ELF::EI_NIDENT + data_offset)) 188 { 189 const uint8_t *magic = data_sp->GetBytes() + data_offset; 190 if (ELFHeader::MagicBytesMatch(magic)) 191 { 192 // Update the data to contain the entire file if it doesn't already 193 if (data_sp->GetByteSize() < length) { 194 data_sp = file->MemoryMapFileContents(file_offset, length); 195 data_offset = 0; 196 magic = data_sp->GetBytes(); 197 } 198 unsigned address_size = ELFHeader::AddressSizeInBytes(magic); 199 if (address_size == 4 || address_size == 8) 200 { 201 STD_UNIQUE_PTR(ObjectFileELF) objfile_ap(new ObjectFileELF(module_sp, data_sp, data_offset, file, file_offset, length)); 202 ArchSpec spec; 203 if (objfile_ap->GetArchitecture(spec) && 204 objfile_ap->SetModulesArchitecture(spec)) 205 return objfile_ap.release(); 206 } 207 } 208 } 209 return NULL; 210 } 211 212 213 ObjectFile* 214 ObjectFileELF::CreateMemoryInstance (const lldb::ModuleSP &module_sp, 215 DataBufferSP& data_sp, 216 const lldb::ProcessSP &process_sp, 217 lldb::addr_t header_addr) 218 { 219 return NULL; 220 } 221 222 223 //------------------------------------------------------------------ 224 // PluginInterface protocol 225 //------------------------------------------------------------------ 226 const char * 227 ObjectFileELF::GetPluginName() 228 { 229 return "ObjectFileELF"; 230 } 231 232 const char * 233 ObjectFileELF::GetShortPluginName() 234 { 235 return GetPluginNameStatic(); 236 } 237 238 uint32_t 239 ObjectFileELF::GetPluginVersion() 240 { 241 return m_plugin_version; 242 } 243 //------------------------------------------------------------------ 244 // ObjectFile protocol 245 //------------------------------------------------------------------ 246 247 ObjectFileELF::ObjectFileELF (const lldb::ModuleSP &module_sp, 248 DataBufferSP& data_sp, 249 lldb::offset_t data_offset, 250 const FileSpec* file, 251 lldb::offset_t file_offset, 252 lldb::offset_t length) : 253 ObjectFile(module_sp, file, file_offset, length, data_sp, data_offset), 254 m_header(), 255 m_program_headers(), 256 m_section_headers(), 257 m_filespec_ap(), 258 m_shstr_data() 259 { 260 if (file) 261 m_file = *file; 262 ::memset(&m_header, 0, sizeof(m_header)); 263 } 264 265 ObjectFileELF::~ObjectFileELF() 266 { 267 } 268 269 bool 270 ObjectFileELF::IsExecutable() const 271 { 272 return m_header.e_entry != 0; 273 } 274 275 ByteOrder 276 ObjectFileELF::GetByteOrder() const 277 { 278 if (m_header.e_ident[EI_DATA] == ELFDATA2MSB) 279 return eByteOrderBig; 280 if (m_header.e_ident[EI_DATA] == ELFDATA2LSB) 281 return eByteOrderLittle; 282 return eByteOrderInvalid; 283 } 284 285 uint32_t 286 ObjectFileELF::GetAddressByteSize() const 287 { 288 return m_data.GetAddressByteSize(); 289 } 290 291 size_t 292 ObjectFileELF::SectionIndex(const SectionHeaderCollIter &I) 293 { 294 return std::distance(m_section_headers.begin(), I) + 1u; 295 } 296 297 size_t 298 ObjectFileELF::SectionIndex(const SectionHeaderCollConstIter &I) const 299 { 300 return std::distance(m_section_headers.begin(), I) + 1u; 301 } 302 303 bool 304 ObjectFileELF::ParseHeader() 305 { 306 lldb::offset_t offset = GetFileOffset(); 307 return m_header.Parse(m_data, &offset); 308 } 309 310 bool 311 ObjectFileELF::GetUUID(lldb_private::UUID* uuid) 312 { 313 // FIXME: Return MD5 sum here. See comment in ObjectFile.h. 314 return false; 315 } 316 317 uint32_t 318 ObjectFileELF::GetDependentModules(FileSpecList &files) 319 { 320 size_t num_modules = ParseDependentModules(); 321 uint32_t num_specs = 0; 322 323 for (unsigned i = 0; i < num_modules; ++i) 324 { 325 if (files.AppendIfUnique(m_filespec_ap->GetFileSpecAtIndex(i))) 326 num_specs++; 327 } 328 329 return num_specs; 330 } 331 332 user_id_t 333 ObjectFileELF::GetSectionIndexByType(unsigned type) 334 { 335 if (!ParseSectionHeaders()) 336 return 0; 337 338 for (SectionHeaderCollIter sh_pos = m_section_headers.begin(); 339 sh_pos != m_section_headers.end(); ++sh_pos) 340 { 341 if (sh_pos->sh_type == type) 342 return SectionIndex(sh_pos); 343 } 344 345 return 0; 346 } 347 348 Address 349 ObjectFileELF::GetImageInfoAddress() 350 { 351 if (!ParseDynamicSymbols()) 352 return Address(); 353 354 SectionList *section_list = GetSectionList(); 355 if (!section_list) 356 return Address(); 357 358 user_id_t dynsym_id = GetSectionIndexByType(SHT_DYNAMIC); 359 if (!dynsym_id) 360 return Address(); 361 362 const ELFSectionHeader *dynsym_hdr = GetSectionHeaderByIndex(dynsym_id); 363 if (!dynsym_hdr) 364 return Address(); 365 366 SectionSP dynsym_section_sp (section_list->FindSectionByID(dynsym_id)); 367 if (dynsym_section_sp) 368 { 369 for (size_t i = 0; i < m_dynamic_symbols.size(); ++i) 370 { 371 ELFDynamic &symbol = m_dynamic_symbols[i]; 372 373 if (symbol.d_tag == DT_DEBUG) 374 { 375 // Compute the offset as the number of previous entries plus the 376 // size of d_tag. 377 addr_t offset = i * dynsym_hdr->sh_entsize + GetAddressByteSize(); 378 return Address(dynsym_section_sp, offset); 379 } 380 } 381 } 382 383 return Address(); 384 } 385 386 lldb_private::Address 387 ObjectFileELF::GetEntryPointAddress () 388 { 389 SectionList *sections; 390 addr_t offset; 391 392 if (m_entry_point_address.IsValid()) 393 return m_entry_point_address; 394 395 if (!ParseHeader() || !IsExecutable()) 396 return m_entry_point_address; 397 398 sections = GetSectionList(); 399 offset = m_header.e_entry; 400 401 if (!sections) 402 { 403 m_entry_point_address.SetOffset(offset); 404 return m_entry_point_address; 405 } 406 407 m_entry_point_address.ResolveAddressUsingFileSections(offset, sections); 408 409 return m_entry_point_address; 410 } 411 412 //---------------------------------------------------------------------- 413 // ParseDependentModules 414 //---------------------------------------------------------------------- 415 size_t 416 ObjectFileELF::ParseDependentModules() 417 { 418 if (m_filespec_ap.get()) 419 return m_filespec_ap->GetSize(); 420 421 m_filespec_ap.reset(new FileSpecList()); 422 423 if (!(ParseSectionHeaders() && GetSectionHeaderStringTable())) 424 return 0; 425 426 // Locate the dynamic table. 427 user_id_t dynsym_id = 0; 428 user_id_t dynstr_id = 0; 429 for (SectionHeaderCollIter sh_pos = m_section_headers.begin(); 430 sh_pos != m_section_headers.end(); ++sh_pos) 431 { 432 if (sh_pos->sh_type == SHT_DYNAMIC) 433 { 434 dynsym_id = SectionIndex(sh_pos); 435 dynstr_id = sh_pos->sh_link + 1; // Section ID's are 1 based. 436 break; 437 } 438 } 439 440 if (!(dynsym_id && dynstr_id)) 441 return 0; 442 443 SectionList *section_list = GetSectionList(); 444 if (!section_list) 445 return 0; 446 447 // Resolve and load the dynamic table entries and corresponding string 448 // table. 449 Section *dynsym = section_list->FindSectionByID(dynsym_id).get(); 450 Section *dynstr = section_list->FindSectionByID(dynstr_id).get(); 451 if (!(dynsym && dynstr)) 452 return 0; 453 454 DataExtractor dynsym_data; 455 DataExtractor dynstr_data; 456 if (ReadSectionData(dynsym, dynsym_data) && 457 ReadSectionData(dynstr, dynstr_data)) 458 { 459 ELFDynamic symbol; 460 const lldb::offset_t section_size = dynsym_data.GetByteSize(); 461 lldb::offset_t offset = 0; 462 463 // The only type of entries we are concerned with are tagged DT_NEEDED, 464 // yielding the name of a required library. 465 while (offset < section_size) 466 { 467 if (!symbol.Parse(dynsym_data, &offset)) 468 break; 469 470 if (symbol.d_tag != DT_NEEDED) 471 continue; 472 473 uint32_t str_index = static_cast<uint32_t>(symbol.d_val); 474 const char *lib_name = dynstr_data.PeekCStr(str_index); 475 m_filespec_ap->Append(FileSpec(lib_name, true)); 476 } 477 } 478 479 return m_filespec_ap->GetSize(); 480 } 481 482 //---------------------------------------------------------------------- 483 // ParseProgramHeaders 484 //---------------------------------------------------------------------- 485 size_t 486 ObjectFileELF::ParseProgramHeaders() 487 { 488 // We have already parsed the program headers 489 if (!m_program_headers.empty()) 490 return m_program_headers.size(); 491 492 // If there are no program headers to read we are done. 493 if (m_header.e_phnum == 0) 494 return 0; 495 496 m_program_headers.resize(m_header.e_phnum); 497 if (m_program_headers.size() != m_header.e_phnum) 498 return 0; 499 500 const size_t ph_size = m_header.e_phnum * m_header.e_phentsize; 501 const elf_off ph_offset = m_header.e_phoff; 502 DataExtractor data; 503 if (GetData (ph_offset, ph_size, data) != ph_size) 504 return 0; 505 506 uint32_t idx; 507 lldb::offset_t offset; 508 for (idx = 0, offset = 0; idx < m_header.e_phnum; ++idx) 509 { 510 if (m_program_headers[idx].Parse(data, &offset) == false) 511 break; 512 } 513 514 if (idx < m_program_headers.size()) 515 m_program_headers.resize(idx); 516 517 return m_program_headers.size(); 518 } 519 520 //---------------------------------------------------------------------- 521 // ParseSectionHeaders 522 //---------------------------------------------------------------------- 523 size_t 524 ObjectFileELF::ParseSectionHeaders() 525 { 526 // We have already parsed the section headers 527 if (!m_section_headers.empty()) 528 return m_section_headers.size(); 529 530 // If there are no section headers we are done. 531 if (m_header.e_shnum == 0) 532 return 0; 533 534 m_section_headers.resize(m_header.e_shnum); 535 if (m_section_headers.size() != m_header.e_shnum) 536 return 0; 537 538 const size_t sh_size = m_header.e_shnum * m_header.e_shentsize; 539 const elf_off sh_offset = m_header.e_shoff; 540 DataExtractor data; 541 if (GetData (sh_offset, sh_size, data) != sh_size) 542 return 0; 543 544 uint32_t idx; 545 lldb::offset_t offset; 546 for (idx = 0, offset = 0; idx < m_header.e_shnum; ++idx) 547 { 548 if (m_section_headers[idx].Parse(data, &offset) == false) 549 break; 550 } 551 if (idx < m_section_headers.size()) 552 m_section_headers.resize(idx); 553 554 return m_section_headers.size(); 555 } 556 557 size_t 558 ObjectFileELF::GetSectionHeaderStringTable() 559 { 560 if (m_shstr_data.GetByteSize() == 0) 561 { 562 const unsigned strtab_idx = m_header.e_shstrndx; 563 564 if (strtab_idx && strtab_idx < m_section_headers.size()) 565 { 566 const ELFSectionHeader &sheader = m_section_headers[strtab_idx]; 567 const size_t byte_size = sheader.sh_size; 568 const Elf64_Off offset = sheader.sh_offset; 569 m_shstr_data.SetData (m_data, offset, byte_size); 570 571 if (m_shstr_data.GetByteSize() != byte_size) 572 return 0; 573 } 574 } 575 return m_shstr_data.GetByteSize(); 576 } 577 578 lldb::user_id_t 579 ObjectFileELF::GetSectionIndexByName(const char *name) 580 { 581 if (!(ParseSectionHeaders() && GetSectionHeaderStringTable())) 582 return 0; 583 584 // Search the collection of section headers for one with a matching name. 585 for (SectionHeaderCollIter I = m_section_headers.begin(); 586 I != m_section_headers.end(); ++I) 587 { 588 const char *sectionName = m_shstr_data.PeekCStr(I->sh_name); 589 590 if (!sectionName) 591 return 0; 592 593 if (strcmp(name, sectionName) != 0) 594 continue; 595 596 return SectionIndex(I); 597 } 598 599 return 0; 600 } 601 602 const elf::ELFSectionHeader * 603 ObjectFileELF::GetSectionHeaderByIndex(lldb::user_id_t id) 604 { 605 if (!ParseSectionHeaders() || !id) 606 return NULL; 607 608 if (--id < m_section_headers.size()) 609 return &m_section_headers[id]; 610 611 return NULL; 612 } 613 614 SectionList * 615 ObjectFileELF::GetSectionList() 616 { 617 if (m_sections_ap.get()) 618 return m_sections_ap.get(); 619 620 if (ParseSectionHeaders() && GetSectionHeaderStringTable()) 621 { 622 m_sections_ap.reset(new SectionList()); 623 624 for (SectionHeaderCollIter I = m_section_headers.begin(); 625 I != m_section_headers.end(); ++I) 626 { 627 const ELFSectionHeader &header = *I; 628 629 ConstString name(m_shstr_data.PeekCStr(header.sh_name)); 630 const uint64_t file_size = header.sh_type == SHT_NOBITS ? 0 : header.sh_size; 631 const uint64_t vm_size = header.sh_flags & SHF_ALLOC ? header.sh_size : 0; 632 633 static ConstString g_sect_name_text (".text"); 634 static ConstString g_sect_name_data (".data"); 635 static ConstString g_sect_name_bss (".bss"); 636 static ConstString g_sect_name_tdata (".tdata"); 637 static ConstString g_sect_name_tbss (".tbss"); 638 static ConstString g_sect_name_dwarf_debug_abbrev (".debug_abbrev"); 639 static ConstString g_sect_name_dwarf_debug_aranges (".debug_aranges"); 640 static ConstString g_sect_name_dwarf_debug_frame (".debug_frame"); 641 static ConstString g_sect_name_dwarf_debug_info (".debug_info"); 642 static ConstString g_sect_name_dwarf_debug_line (".debug_line"); 643 static ConstString g_sect_name_dwarf_debug_loc (".debug_loc"); 644 static ConstString g_sect_name_dwarf_debug_macinfo (".debug_macinfo"); 645 static ConstString g_sect_name_dwarf_debug_pubnames (".debug_pubnames"); 646 static ConstString g_sect_name_dwarf_debug_pubtypes (".debug_pubtypes"); 647 static ConstString g_sect_name_dwarf_debug_ranges (".debug_ranges"); 648 static ConstString g_sect_name_dwarf_debug_str (".debug_str"); 649 static ConstString g_sect_name_eh_frame (".eh_frame"); 650 651 SectionType sect_type = eSectionTypeOther; 652 653 bool is_thread_specific = false; 654 655 if (name == g_sect_name_text) sect_type = eSectionTypeCode; 656 else if (name == g_sect_name_data) sect_type = eSectionTypeData; 657 else if (name == g_sect_name_bss) sect_type = eSectionTypeZeroFill; 658 else if (name == g_sect_name_tdata) 659 { 660 sect_type = eSectionTypeData; 661 is_thread_specific = true; 662 } 663 else if (name == g_sect_name_tbss) 664 { 665 sect_type = eSectionTypeZeroFill; 666 is_thread_specific = true; 667 } 668 else if (name == g_sect_name_dwarf_debug_abbrev) sect_type = eSectionTypeDWARFDebugAbbrev; 669 else if (name == g_sect_name_dwarf_debug_aranges) sect_type = eSectionTypeDWARFDebugAranges; 670 else if (name == g_sect_name_dwarf_debug_frame) sect_type = eSectionTypeDWARFDebugFrame; 671 else if (name == g_sect_name_dwarf_debug_info) sect_type = eSectionTypeDWARFDebugInfo; 672 else if (name == g_sect_name_dwarf_debug_line) sect_type = eSectionTypeDWARFDebugLine; 673 else if (name == g_sect_name_dwarf_debug_loc) sect_type = eSectionTypeDWARFDebugLoc; 674 else if (name == g_sect_name_dwarf_debug_macinfo) sect_type = eSectionTypeDWARFDebugMacInfo; 675 else if (name == g_sect_name_dwarf_debug_pubnames) sect_type = eSectionTypeDWARFDebugPubNames; 676 else if (name == g_sect_name_dwarf_debug_pubtypes) sect_type = eSectionTypeDWARFDebugPubTypes; 677 else if (name == g_sect_name_dwarf_debug_ranges) sect_type = eSectionTypeDWARFDebugRanges; 678 else if (name == g_sect_name_dwarf_debug_str) sect_type = eSectionTypeDWARFDebugStr; 679 else if (name == g_sect_name_eh_frame) sect_type = eSectionTypeEHFrame; 680 681 682 SectionSP section_sp(new Section( 683 GetModule(), // Module to which this section belongs. 684 SectionIndex(I), // Section ID. 685 name, // Section name. 686 sect_type, // Section type. 687 header.sh_addr, // VM address. 688 vm_size, // VM size in bytes of this section. 689 header.sh_offset, // Offset of this section in the file. 690 file_size, // Size of the section as found in the file. 691 header.sh_flags)); // Flags for this section. 692 693 if (is_thread_specific) 694 section_sp->SetIsThreadSpecific (is_thread_specific); 695 m_sections_ap->AddSection(section_sp); 696 } 697 698 m_sections_ap->Finalize(); // Now that we're done adding sections, finalize to build fast-lookup caches 699 } 700 701 return m_sections_ap.get(); 702 } 703 704 static unsigned 705 ParseSymbols(Symtab *symtab, 706 user_id_t start_id, 707 SectionList *section_list, 708 const ELFSectionHeader *symtab_shdr, 709 const DataExtractor &symtab_data, 710 const DataExtractor &strtab_data) 711 { 712 ELFSymbol symbol; 713 lldb::offset_t offset = 0; 714 const size_t num_symbols = symtab_data.GetByteSize() / symtab_shdr->sh_entsize; 715 716 static ConstString text_section_name(".text"); 717 static ConstString init_section_name(".init"); 718 static ConstString fini_section_name(".fini"); 719 static ConstString ctors_section_name(".ctors"); 720 static ConstString dtors_section_name(".dtors"); 721 722 static ConstString data_section_name(".data"); 723 static ConstString rodata_section_name(".rodata"); 724 static ConstString rodata1_section_name(".rodata1"); 725 static ConstString data2_section_name(".data1"); 726 static ConstString bss_section_name(".bss"); 727 728 //StreamFile strm(stdout, false); 729 unsigned i; 730 for (i = 0; i < num_symbols; ++i) 731 { 732 if (symbol.Parse(symtab_data, &offset) == false) 733 break; 734 735 const char *symbol_name = strtab_data.PeekCStr(symbol.st_name); 736 737 // No need to add symbols that have no names 738 if (symbol_name == NULL || symbol_name[0] == '\0') 739 continue; 740 741 //symbol.Dump (&strm, i, &strtab_data, section_list); 742 743 SectionSP symbol_section_sp; 744 SymbolType symbol_type = eSymbolTypeInvalid; 745 Elf64_Half symbol_idx = symbol.st_shndx; 746 747 switch (symbol_idx) 748 { 749 case SHN_ABS: 750 symbol_type = eSymbolTypeAbsolute; 751 break; 752 case SHN_UNDEF: 753 symbol_type = eSymbolTypeUndefined; 754 break; 755 default: 756 symbol_section_sp = section_list->GetSectionAtIndex(symbol_idx); 757 break; 758 } 759 760 // If a symbol is undefined do not process it further even if it has a STT type 761 if (symbol_type != eSymbolTypeUndefined) 762 { 763 switch (symbol.getType()) 764 { 765 default: 766 case STT_NOTYPE: 767 // The symbol's type is not specified. 768 break; 769 770 case STT_OBJECT: 771 // The symbol is associated with a data object, such as a variable, 772 // an array, etc. 773 symbol_type = eSymbolTypeData; 774 break; 775 776 case STT_FUNC: 777 // The symbol is associated with a function or other executable code. 778 symbol_type = eSymbolTypeCode; 779 break; 780 781 case STT_SECTION: 782 // The symbol is associated with a section. Symbol table entries of 783 // this type exist primarily for relocation and normally have 784 // STB_LOCAL binding. 785 break; 786 787 case STT_FILE: 788 // Conventionally, the symbol's name gives the name of the source 789 // file associated with the object file. A file symbol has STB_LOCAL 790 // binding, its section index is SHN_ABS, and it precedes the other 791 // STB_LOCAL symbols for the file, if it is present. 792 symbol_type = eSymbolTypeSourceFile; 793 break; 794 795 case STT_GNU_IFUNC: 796 // The symbol is associated with an indirect function. The actual 797 // function will be resolved if it is referenced. 798 symbol_type = eSymbolTypeResolver; 799 break; 800 } 801 } 802 803 if (symbol_type == eSymbolTypeInvalid) 804 { 805 if (symbol_section_sp) 806 { 807 const ConstString §_name = symbol_section_sp->GetName(); 808 if (sect_name == text_section_name || 809 sect_name == init_section_name || 810 sect_name == fini_section_name || 811 sect_name == ctors_section_name || 812 sect_name == dtors_section_name) 813 { 814 symbol_type = eSymbolTypeCode; 815 } 816 else if (sect_name == data_section_name || 817 sect_name == data2_section_name || 818 sect_name == rodata_section_name || 819 sect_name == rodata1_section_name || 820 sect_name == bss_section_name) 821 { 822 symbol_type = eSymbolTypeData; 823 } 824 } 825 } 826 827 uint64_t symbol_value = symbol.st_value; 828 if (symbol_section_sp) 829 symbol_value -= symbol_section_sp->GetFileAddress(); 830 bool is_global = symbol.getBinding() == STB_GLOBAL; 831 uint32_t flags = symbol.st_other << 8 | symbol.st_info; 832 bool is_mangled = symbol_name ? (symbol_name[0] == '_' && symbol_name[1] == 'Z') : false; 833 Symbol dc_symbol( 834 i + start_id, // ID is the original symbol table index. 835 symbol_name, // Symbol name. 836 is_mangled, // Is the symbol name mangled? 837 symbol_type, // Type of this symbol 838 is_global, // Is this globally visible? 839 false, // Is this symbol debug info? 840 false, // Is this symbol a trampoline? 841 false, // Is this symbol artificial? 842 symbol_section_sp, // Section in which this symbol is defined or null. 843 symbol_value, // Offset in section or symbol value. 844 symbol.st_size, // Size in bytes of this symbol. 845 true, // Size is valid 846 flags); // Symbol flags. 847 symtab->AddSymbol(dc_symbol); 848 } 849 850 return i; 851 } 852 853 unsigned 854 ObjectFileELF::ParseSymbolTable(Symtab *symbol_table, user_id_t start_id, 855 const ELFSectionHeader *symtab_hdr, 856 user_id_t symtab_id) 857 { 858 assert(symtab_hdr->sh_type == SHT_SYMTAB || 859 symtab_hdr->sh_type == SHT_DYNSYM); 860 861 // Parse in the section list if needed. 862 SectionList *section_list = GetSectionList(); 863 if (!section_list) 864 return 0; 865 866 // Section ID's are ones based. 867 user_id_t strtab_id = symtab_hdr->sh_link + 1; 868 869 Section *symtab = section_list->FindSectionByID(symtab_id).get(); 870 Section *strtab = section_list->FindSectionByID(strtab_id).get(); 871 unsigned num_symbols = 0; 872 if (symtab && strtab) 873 { 874 DataExtractor symtab_data; 875 DataExtractor strtab_data; 876 if (ReadSectionData(symtab, symtab_data) && 877 ReadSectionData(strtab, strtab_data)) 878 { 879 num_symbols = ParseSymbols(symbol_table, start_id, 880 section_list, symtab_hdr, 881 symtab_data, strtab_data); 882 } 883 } 884 885 return num_symbols; 886 } 887 888 size_t 889 ObjectFileELF::ParseDynamicSymbols() 890 { 891 if (m_dynamic_symbols.size()) 892 return m_dynamic_symbols.size(); 893 894 user_id_t dyn_id = GetSectionIndexByType(SHT_DYNAMIC); 895 if (!dyn_id) 896 return 0; 897 898 SectionList *section_list = GetSectionList(); 899 if (!section_list) 900 return 0; 901 902 Section *dynsym = section_list->FindSectionByID(dyn_id).get(); 903 if (!dynsym) 904 return 0; 905 906 ELFDynamic symbol; 907 DataExtractor dynsym_data; 908 if (ReadSectionData(dynsym, dynsym_data)) 909 { 910 const lldb::offset_t section_size = dynsym_data.GetByteSize(); 911 lldb::offset_t cursor = 0; 912 913 while (cursor < section_size) 914 { 915 if (!symbol.Parse(dynsym_data, &cursor)) 916 break; 917 918 m_dynamic_symbols.push_back(symbol); 919 } 920 } 921 922 return m_dynamic_symbols.size(); 923 } 924 925 const ELFDynamic * 926 ObjectFileELF::FindDynamicSymbol(unsigned tag) 927 { 928 if (!ParseDynamicSymbols()) 929 return NULL; 930 931 SectionList *section_list = GetSectionList(); 932 if (!section_list) 933 return 0; 934 935 DynamicSymbolCollIter I = m_dynamic_symbols.begin(); 936 DynamicSymbolCollIter E = m_dynamic_symbols.end(); 937 for ( ; I != E; ++I) 938 { 939 ELFDynamic *symbol = &*I; 940 941 if (symbol->d_tag == tag) 942 return symbol; 943 } 944 945 return NULL; 946 } 947 948 Section * 949 ObjectFileELF::PLTSection() 950 { 951 const ELFDynamic *symbol = FindDynamicSymbol(DT_JMPREL); 952 SectionList *section_list = GetSectionList(); 953 954 if (symbol && section_list) 955 { 956 addr_t addr = symbol->d_ptr; 957 return section_list->FindSectionContainingFileAddress(addr).get(); 958 } 959 960 return NULL; 961 } 962 963 unsigned 964 ObjectFileELF::PLTRelocationType() 965 { 966 const ELFDynamic *symbol = FindDynamicSymbol(DT_PLTREL); 967 968 if (symbol) 969 return symbol->d_val; 970 971 return 0; 972 } 973 974 static unsigned 975 ParsePLTRelocations(Symtab *symbol_table, 976 user_id_t start_id, 977 unsigned rel_type, 978 const ELFHeader *hdr, 979 const ELFSectionHeader *rel_hdr, 980 const ELFSectionHeader *plt_hdr, 981 const ELFSectionHeader *sym_hdr, 982 const lldb::SectionSP &plt_section_sp, 983 DataExtractor &rel_data, 984 DataExtractor &symtab_data, 985 DataExtractor &strtab_data) 986 { 987 ELFRelocation rel(rel_type); 988 ELFSymbol symbol; 989 lldb::offset_t offset = 0; 990 const elf_xword plt_entsize = plt_hdr->sh_entsize; 991 const elf_xword num_relocations = rel_hdr->sh_size / rel_hdr->sh_entsize; 992 993 typedef unsigned (*reloc_info_fn)(const ELFRelocation &rel); 994 reloc_info_fn reloc_type; 995 reloc_info_fn reloc_symbol; 996 997 if (hdr->Is32Bit()) 998 { 999 reloc_type = ELFRelocation::RelocType32; 1000 reloc_symbol = ELFRelocation::RelocSymbol32; 1001 } 1002 else 1003 { 1004 reloc_type = ELFRelocation::RelocType64; 1005 reloc_symbol = ELFRelocation::RelocSymbol64; 1006 } 1007 1008 unsigned slot_type = hdr->GetRelocationJumpSlotType(); 1009 unsigned i; 1010 for (i = 0; i < num_relocations; ++i) 1011 { 1012 if (rel.Parse(rel_data, &offset) == false) 1013 break; 1014 1015 if (reloc_type(rel) != slot_type) 1016 continue; 1017 1018 lldb::offset_t symbol_offset = reloc_symbol(rel) * sym_hdr->sh_entsize; 1019 uint64_t plt_index = (i + 1) * plt_entsize; 1020 1021 if (!symbol.Parse(symtab_data, &symbol_offset)) 1022 break; 1023 1024 const char *symbol_name = strtab_data.PeekCStr(symbol.st_name); 1025 bool is_mangled = symbol_name ? (symbol_name[0] == '_' && symbol_name[1] == 'Z') : false; 1026 1027 Symbol jump_symbol( 1028 i + start_id, // Symbol table index 1029 symbol_name, // symbol name. 1030 is_mangled, // is the symbol name mangled? 1031 eSymbolTypeTrampoline, // Type of this symbol 1032 false, // Is this globally visible? 1033 false, // Is this symbol debug info? 1034 true, // Is this symbol a trampoline? 1035 true, // Is this symbol artificial? 1036 plt_section_sp, // Section in which this symbol is defined or null. 1037 plt_index, // Offset in section or symbol value. 1038 plt_entsize, // Size in bytes of this symbol. 1039 true, // Size is valid 1040 0); // Symbol flags. 1041 1042 symbol_table->AddSymbol(jump_symbol); 1043 } 1044 1045 return i; 1046 } 1047 1048 unsigned 1049 ObjectFileELF::ParseTrampolineSymbols(Symtab *symbol_table, 1050 user_id_t start_id, 1051 const ELFSectionHeader *rel_hdr, 1052 user_id_t rel_id) 1053 { 1054 assert(rel_hdr->sh_type == SHT_RELA || rel_hdr->sh_type == SHT_REL); 1055 1056 // The link field points to the asscoiated symbol table. The info field 1057 // points to the section holding the plt. 1058 user_id_t symtab_id = rel_hdr->sh_link; 1059 user_id_t plt_id = rel_hdr->sh_info; 1060 1061 if (!symtab_id || !plt_id) 1062 return 0; 1063 1064 // Section ID's are ones based; 1065 symtab_id++; 1066 plt_id++; 1067 1068 const ELFSectionHeader *plt_hdr = GetSectionHeaderByIndex(plt_id); 1069 if (!plt_hdr) 1070 return 0; 1071 1072 const ELFSectionHeader *sym_hdr = GetSectionHeaderByIndex(symtab_id); 1073 if (!sym_hdr) 1074 return 0; 1075 1076 SectionList *section_list = GetSectionList(); 1077 if (!section_list) 1078 return 0; 1079 1080 Section *rel_section = section_list->FindSectionByID(rel_id).get(); 1081 if (!rel_section) 1082 return 0; 1083 1084 SectionSP plt_section_sp (section_list->FindSectionByID(plt_id)); 1085 if (!plt_section_sp) 1086 return 0; 1087 1088 Section *symtab = section_list->FindSectionByID(symtab_id).get(); 1089 if (!symtab) 1090 return 0; 1091 1092 Section *strtab = section_list->FindSectionByID(sym_hdr->sh_link + 1).get(); 1093 if (!strtab) 1094 return 0; 1095 1096 DataExtractor rel_data; 1097 if (!ReadSectionData(rel_section, rel_data)) 1098 return 0; 1099 1100 DataExtractor symtab_data; 1101 if (!ReadSectionData(symtab, symtab_data)) 1102 return 0; 1103 1104 DataExtractor strtab_data; 1105 if (!ReadSectionData(strtab, strtab_data)) 1106 return 0; 1107 1108 unsigned rel_type = PLTRelocationType(); 1109 if (!rel_type) 1110 return 0; 1111 1112 return ParsePLTRelocations (symbol_table, 1113 start_id, 1114 rel_type, 1115 &m_header, 1116 rel_hdr, 1117 plt_hdr, 1118 sym_hdr, 1119 plt_section_sp, 1120 rel_data, 1121 symtab_data, 1122 strtab_data); 1123 } 1124 1125 Symtab * 1126 ObjectFileELF::GetSymtab() 1127 { 1128 if (m_symtab_ap.get()) 1129 return m_symtab_ap.get(); 1130 1131 Symtab *symbol_table = new Symtab(this); 1132 m_symtab_ap.reset(symbol_table); 1133 1134 Mutex::Locker locker(symbol_table->GetMutex()); 1135 1136 if (!(ParseSectionHeaders() && GetSectionHeaderStringTable())) 1137 return symbol_table; 1138 1139 // Locate and parse all linker symbol tables. 1140 uint64_t symbol_id = 0; 1141 for (SectionHeaderCollIter I = m_section_headers.begin(); 1142 I != m_section_headers.end(); ++I) 1143 { 1144 if (I->sh_type == SHT_SYMTAB || I->sh_type == SHT_DYNSYM) 1145 { 1146 const ELFSectionHeader &symtab_header = *I; 1147 user_id_t section_id = SectionIndex(I); 1148 symbol_id += ParseSymbolTable(symbol_table, symbol_id, 1149 &symtab_header, section_id); 1150 } 1151 } 1152 1153 // Synthesize trampoline symbols to help navigate the PLT. 1154 Section *reloc_section = PLTSection(); 1155 if (reloc_section) 1156 { 1157 user_id_t reloc_id = reloc_section->GetID(); 1158 const ELFSectionHeader *reloc_header = GetSectionHeaderByIndex(reloc_id); 1159 assert(reloc_header); 1160 1161 ParseTrampolineSymbols(symbol_table, symbol_id, reloc_header, reloc_id); 1162 } 1163 1164 return symbol_table; 1165 } 1166 1167 //===----------------------------------------------------------------------===// 1168 // Dump 1169 // 1170 // Dump the specifics of the runtime file container (such as any headers 1171 // segments, sections, etc). 1172 //---------------------------------------------------------------------- 1173 void 1174 ObjectFileELF::Dump(Stream *s) 1175 { 1176 DumpELFHeader(s, m_header); 1177 s->EOL(); 1178 DumpELFProgramHeaders(s); 1179 s->EOL(); 1180 DumpELFSectionHeaders(s); 1181 s->EOL(); 1182 SectionList *section_list = GetSectionList(); 1183 if (section_list) 1184 section_list->Dump(s, NULL, true, UINT32_MAX); 1185 Symtab *symtab = GetSymtab(); 1186 if (symtab) 1187 symtab->Dump(s, NULL, eSortOrderNone); 1188 s->EOL(); 1189 DumpDependentModules(s); 1190 s->EOL(); 1191 } 1192 1193 //---------------------------------------------------------------------- 1194 // DumpELFHeader 1195 // 1196 // Dump the ELF header to the specified output stream 1197 //---------------------------------------------------------------------- 1198 void 1199 ObjectFileELF::DumpELFHeader(Stream *s, const ELFHeader &header) 1200 { 1201 s->PutCString("ELF Header\n"); 1202 s->Printf("e_ident[EI_MAG0 ] = 0x%2.2x\n", header.e_ident[EI_MAG0]); 1203 s->Printf("e_ident[EI_MAG1 ] = 0x%2.2x '%c'\n", 1204 header.e_ident[EI_MAG1], header.e_ident[EI_MAG1]); 1205 s->Printf("e_ident[EI_MAG2 ] = 0x%2.2x '%c'\n", 1206 header.e_ident[EI_MAG2], header.e_ident[EI_MAG2]); 1207 s->Printf("e_ident[EI_MAG3 ] = 0x%2.2x '%c'\n", 1208 header.e_ident[EI_MAG3], header.e_ident[EI_MAG3]); 1209 1210 s->Printf("e_ident[EI_CLASS ] = 0x%2.2x\n", header.e_ident[EI_CLASS]); 1211 s->Printf("e_ident[EI_DATA ] = 0x%2.2x ", header.e_ident[EI_DATA]); 1212 DumpELFHeader_e_ident_EI_DATA(s, header.e_ident[EI_DATA]); 1213 s->Printf ("\ne_ident[EI_VERSION] = 0x%2.2x\n", header.e_ident[EI_VERSION]); 1214 s->Printf ("e_ident[EI_PAD ] = 0x%2.2x\n", header.e_ident[EI_PAD]); 1215 1216 s->Printf("e_type = 0x%4.4x ", header.e_type); 1217 DumpELFHeader_e_type(s, header.e_type); 1218 s->Printf("\ne_machine = 0x%4.4x\n", header.e_machine); 1219 s->Printf("e_version = 0x%8.8x\n", header.e_version); 1220 s->Printf("e_entry = 0x%8.8" PRIx64 "\n", header.e_entry); 1221 s->Printf("e_phoff = 0x%8.8" PRIx64 "\n", header.e_phoff); 1222 s->Printf("e_shoff = 0x%8.8" PRIx64 "\n", header.e_shoff); 1223 s->Printf("e_flags = 0x%8.8x\n", header.e_flags); 1224 s->Printf("e_ehsize = 0x%4.4x\n", header.e_ehsize); 1225 s->Printf("e_phentsize = 0x%4.4x\n", header.e_phentsize); 1226 s->Printf("e_phnum = 0x%4.4x\n", header.e_phnum); 1227 s->Printf("e_shentsize = 0x%4.4x\n", header.e_shentsize); 1228 s->Printf("e_shnum = 0x%4.4x\n", header.e_shnum); 1229 s->Printf("e_shstrndx = 0x%4.4x\n", header.e_shstrndx); 1230 } 1231 1232 //---------------------------------------------------------------------- 1233 // DumpELFHeader_e_type 1234 // 1235 // Dump an token value for the ELF header member e_type 1236 //---------------------------------------------------------------------- 1237 void 1238 ObjectFileELF::DumpELFHeader_e_type(Stream *s, elf_half e_type) 1239 { 1240 switch (e_type) 1241 { 1242 case ET_NONE: *s << "ET_NONE"; break; 1243 case ET_REL: *s << "ET_REL"; break; 1244 case ET_EXEC: *s << "ET_EXEC"; break; 1245 case ET_DYN: *s << "ET_DYN"; break; 1246 case ET_CORE: *s << "ET_CORE"; break; 1247 default: 1248 break; 1249 } 1250 } 1251 1252 //---------------------------------------------------------------------- 1253 // DumpELFHeader_e_ident_EI_DATA 1254 // 1255 // Dump an token value for the ELF header member e_ident[EI_DATA] 1256 //---------------------------------------------------------------------- 1257 void 1258 ObjectFileELF::DumpELFHeader_e_ident_EI_DATA(Stream *s, unsigned char ei_data) 1259 { 1260 switch (ei_data) 1261 { 1262 case ELFDATANONE: *s << "ELFDATANONE"; break; 1263 case ELFDATA2LSB: *s << "ELFDATA2LSB - Little Endian"; break; 1264 case ELFDATA2MSB: *s << "ELFDATA2MSB - Big Endian"; break; 1265 default: 1266 break; 1267 } 1268 } 1269 1270 1271 //---------------------------------------------------------------------- 1272 // DumpELFProgramHeader 1273 // 1274 // Dump a single ELF program header to the specified output stream 1275 //---------------------------------------------------------------------- 1276 void 1277 ObjectFileELF::DumpELFProgramHeader(Stream *s, const ELFProgramHeader &ph) 1278 { 1279 DumpELFProgramHeader_p_type(s, ph.p_type); 1280 s->Printf(" %8.8" PRIx64 " %8.8" PRIx64 " %8.8" PRIx64, ph.p_offset, ph.p_vaddr, ph.p_paddr); 1281 s->Printf(" %8.8" PRIx64 " %8.8" PRIx64 " %8.8x (", ph.p_filesz, ph.p_memsz, ph.p_flags); 1282 1283 DumpELFProgramHeader_p_flags(s, ph.p_flags); 1284 s->Printf(") %8.8" PRIx64, ph.p_align); 1285 } 1286 1287 //---------------------------------------------------------------------- 1288 // DumpELFProgramHeader_p_type 1289 // 1290 // Dump an token value for the ELF program header member p_type which 1291 // describes the type of the program header 1292 // ---------------------------------------------------------------------- 1293 void 1294 ObjectFileELF::DumpELFProgramHeader_p_type(Stream *s, elf_word p_type) 1295 { 1296 const int kStrWidth = 10; 1297 switch (p_type) 1298 { 1299 CASE_AND_STREAM(s, PT_NULL , kStrWidth); 1300 CASE_AND_STREAM(s, PT_LOAD , kStrWidth); 1301 CASE_AND_STREAM(s, PT_DYNAMIC , kStrWidth); 1302 CASE_AND_STREAM(s, PT_INTERP , kStrWidth); 1303 CASE_AND_STREAM(s, PT_NOTE , kStrWidth); 1304 CASE_AND_STREAM(s, PT_SHLIB , kStrWidth); 1305 CASE_AND_STREAM(s, PT_PHDR , kStrWidth); 1306 default: 1307 s->Printf("0x%8.8x%*s", p_type, kStrWidth - 10, ""); 1308 break; 1309 } 1310 } 1311 1312 1313 //---------------------------------------------------------------------- 1314 // DumpELFProgramHeader_p_flags 1315 // 1316 // Dump an token value for the ELF program header member p_flags 1317 //---------------------------------------------------------------------- 1318 void 1319 ObjectFileELF::DumpELFProgramHeader_p_flags(Stream *s, elf_word p_flags) 1320 { 1321 *s << ((p_flags & PF_X) ? "PF_X" : " ") 1322 << (((p_flags & PF_X) && (p_flags & PF_W)) ? '+' : ' ') 1323 << ((p_flags & PF_W) ? "PF_W" : " ") 1324 << (((p_flags & PF_W) && (p_flags & PF_R)) ? '+' : ' ') 1325 << ((p_flags & PF_R) ? "PF_R" : " "); 1326 } 1327 1328 //---------------------------------------------------------------------- 1329 // DumpELFProgramHeaders 1330 // 1331 // Dump all of the ELF program header to the specified output stream 1332 //---------------------------------------------------------------------- 1333 void 1334 ObjectFileELF::DumpELFProgramHeaders(Stream *s) 1335 { 1336 if (ParseProgramHeaders()) 1337 { 1338 s->PutCString("Program Headers\n"); 1339 s->PutCString("IDX p_type p_offset p_vaddr p_paddr " 1340 "p_filesz p_memsz p_flags p_align\n"); 1341 s->PutCString("==== ---------- -------- -------- -------- " 1342 "-------- -------- ------------------------- --------\n"); 1343 1344 uint32_t idx = 0; 1345 for (ProgramHeaderCollConstIter I = m_program_headers.begin(); 1346 I != m_program_headers.end(); ++I, ++idx) 1347 { 1348 s->Printf("[%2u] ", idx); 1349 ObjectFileELF::DumpELFProgramHeader(s, *I); 1350 s->EOL(); 1351 } 1352 } 1353 } 1354 1355 //---------------------------------------------------------------------- 1356 // DumpELFSectionHeader 1357 // 1358 // Dump a single ELF section header to the specified output stream 1359 //---------------------------------------------------------------------- 1360 void 1361 ObjectFileELF::DumpELFSectionHeader(Stream *s, const ELFSectionHeader &sh) 1362 { 1363 s->Printf("%8.8x ", sh.sh_name); 1364 DumpELFSectionHeader_sh_type(s, sh.sh_type); 1365 s->Printf(" %8.8" PRIx64 " (", sh.sh_flags); 1366 DumpELFSectionHeader_sh_flags(s, sh.sh_flags); 1367 s->Printf(") %8.8" PRIx64 " %8.8" PRIx64 " %8.8" PRIx64, sh.sh_addr, sh.sh_offset, sh.sh_size); 1368 s->Printf(" %8.8x %8.8x", sh.sh_link, sh.sh_info); 1369 s->Printf(" %8.8" PRIx64 " %8.8" PRIx64, sh.sh_addralign, sh.sh_entsize); 1370 } 1371 1372 //---------------------------------------------------------------------- 1373 // DumpELFSectionHeader_sh_type 1374 // 1375 // Dump an token value for the ELF section header member sh_type which 1376 // describes the type of the section 1377 //---------------------------------------------------------------------- 1378 void 1379 ObjectFileELF::DumpELFSectionHeader_sh_type(Stream *s, elf_word sh_type) 1380 { 1381 const int kStrWidth = 12; 1382 switch (sh_type) 1383 { 1384 CASE_AND_STREAM(s, SHT_NULL , kStrWidth); 1385 CASE_AND_STREAM(s, SHT_PROGBITS , kStrWidth); 1386 CASE_AND_STREAM(s, SHT_SYMTAB , kStrWidth); 1387 CASE_AND_STREAM(s, SHT_STRTAB , kStrWidth); 1388 CASE_AND_STREAM(s, SHT_RELA , kStrWidth); 1389 CASE_AND_STREAM(s, SHT_HASH , kStrWidth); 1390 CASE_AND_STREAM(s, SHT_DYNAMIC , kStrWidth); 1391 CASE_AND_STREAM(s, SHT_NOTE , kStrWidth); 1392 CASE_AND_STREAM(s, SHT_NOBITS , kStrWidth); 1393 CASE_AND_STREAM(s, SHT_REL , kStrWidth); 1394 CASE_AND_STREAM(s, SHT_SHLIB , kStrWidth); 1395 CASE_AND_STREAM(s, SHT_DYNSYM , kStrWidth); 1396 CASE_AND_STREAM(s, SHT_LOPROC , kStrWidth); 1397 CASE_AND_STREAM(s, SHT_HIPROC , kStrWidth); 1398 CASE_AND_STREAM(s, SHT_LOUSER , kStrWidth); 1399 CASE_AND_STREAM(s, SHT_HIUSER , kStrWidth); 1400 default: 1401 s->Printf("0x%8.8x%*s", sh_type, kStrWidth - 10, ""); 1402 break; 1403 } 1404 } 1405 1406 //---------------------------------------------------------------------- 1407 // DumpELFSectionHeader_sh_flags 1408 // 1409 // Dump an token value for the ELF section header member sh_flags 1410 //---------------------------------------------------------------------- 1411 void 1412 ObjectFileELF::DumpELFSectionHeader_sh_flags(Stream *s, elf_xword sh_flags) 1413 { 1414 *s << ((sh_flags & SHF_WRITE) ? "WRITE" : " ") 1415 << (((sh_flags & SHF_WRITE) && (sh_flags & SHF_ALLOC)) ? '+' : ' ') 1416 << ((sh_flags & SHF_ALLOC) ? "ALLOC" : " ") 1417 << (((sh_flags & SHF_ALLOC) && (sh_flags & SHF_EXECINSTR)) ? '+' : ' ') 1418 << ((sh_flags & SHF_EXECINSTR) ? "EXECINSTR" : " "); 1419 } 1420 1421 //---------------------------------------------------------------------- 1422 // DumpELFSectionHeaders 1423 // 1424 // Dump all of the ELF section header to the specified output stream 1425 //---------------------------------------------------------------------- 1426 void 1427 ObjectFileELF::DumpELFSectionHeaders(Stream *s) 1428 { 1429 if (!(ParseSectionHeaders() && GetSectionHeaderStringTable())) 1430 return; 1431 1432 s->PutCString("Section Headers\n"); 1433 s->PutCString("IDX name type flags " 1434 "addr offset size link info addralgn " 1435 "entsize Name\n"); 1436 s->PutCString("==== -------- ------------ -------------------------------- " 1437 "-------- -------- -------- -------- -------- -------- " 1438 "-------- ====================\n"); 1439 1440 uint32_t idx = 0; 1441 for (SectionHeaderCollConstIter I = m_section_headers.begin(); 1442 I != m_section_headers.end(); ++I, ++idx) 1443 { 1444 s->Printf("[%2u] ", idx); 1445 ObjectFileELF::DumpELFSectionHeader(s, *I); 1446 const char* section_name = m_shstr_data.PeekCStr(I->sh_name); 1447 if (section_name) 1448 *s << ' ' << section_name << "\n"; 1449 } 1450 } 1451 1452 void 1453 ObjectFileELF::DumpDependentModules(lldb_private::Stream *s) 1454 { 1455 size_t num_modules = ParseDependentModules(); 1456 1457 if (num_modules > 0) 1458 { 1459 s->PutCString("Dependent Modules:\n"); 1460 for (unsigned i = 0; i < num_modules; ++i) 1461 { 1462 const FileSpec &spec = m_filespec_ap->GetFileSpecAtIndex(i); 1463 s->Printf(" %s\n", spec.GetFilename().GetCString()); 1464 } 1465 } 1466 } 1467 1468 bool 1469 ObjectFileELF::GetArchitecture (ArchSpec &arch) 1470 { 1471 if (!ParseHeader()) 1472 return false; 1473 1474 arch.SetArchitecture (eArchTypeELF, m_header.e_machine, LLDB_INVALID_CPUTYPE); 1475 arch.GetTriple().setOSName (Host::GetOSString().GetCString()); 1476 arch.GetTriple().setVendorName(Host::GetVendorString().GetCString()); 1477 return true; 1478 } 1479 1480 ObjectFile::Type 1481 ObjectFileELF::CalculateType() 1482 { 1483 switch (m_header.e_type) 1484 { 1485 case llvm::ELF::ET_NONE: 1486 // 0 - No file type 1487 return eTypeUnknown; 1488 1489 case llvm::ELF::ET_REL: 1490 // 1 - Relocatable file 1491 return eTypeObjectFile; 1492 1493 case llvm::ELF::ET_EXEC: 1494 // 2 - Executable file 1495 return eTypeExecutable; 1496 1497 case llvm::ELF::ET_DYN: 1498 // 3 - Shared object file 1499 return eTypeSharedLibrary; 1500 1501 case ET_CORE: 1502 // 4 - Core file 1503 return eTypeCoreFile; 1504 1505 default: 1506 break; 1507 } 1508 return eTypeUnknown; 1509 } 1510 1511 ObjectFile::Strata 1512 ObjectFileELF::CalculateStrata() 1513 { 1514 switch (m_header.e_type) 1515 { 1516 case llvm::ELF::ET_NONE: 1517 // 0 - No file type 1518 return eStrataUnknown; 1519 1520 case llvm::ELF::ET_REL: 1521 // 1 - Relocatable file 1522 return eStrataUnknown; 1523 1524 case llvm::ELF::ET_EXEC: 1525 // 2 - Executable file 1526 // TODO: is there any way to detect that an executable is a kernel 1527 // related executable by inspecting the program headers, section 1528 // headers, symbols, or any other flag bits??? 1529 return eStrataUser; 1530 1531 case llvm::ELF::ET_DYN: 1532 // 3 - Shared object file 1533 // TODO: is there any way to detect that an shared library is a kernel 1534 // related executable by inspecting the program headers, section 1535 // headers, symbols, or any other flag bits??? 1536 return eStrataUnknown; 1537 1538 case ET_CORE: 1539 // 4 - Core file 1540 // TODO: is there any way to detect that an core file is a kernel 1541 // related executable by inspecting the program headers, section 1542 // headers, symbols, or any other flag bits??? 1543 return eStrataUnknown; 1544 1545 default: 1546 break; 1547 } 1548 return eStrataUnknown; 1549 } 1550 1551