diff --git a/lldb/include/lldb/Symbol/ObjectFile.h b/lldb/include/lldb/Symbol/ObjectFile.h index d89314d44bf671..8592323322e383 100644 --- a/lldb/include/lldb/Symbol/ObjectFile.h +++ b/lldb/include/lldb/Symbol/ObjectFile.h @@ -656,9 +656,8 @@ class ObjectFile : public std::enable_shared_from_this, // When an object file is in memory, subclasses should try and lock the // process weak pointer. If the process weak pointer produces a valid // ProcessSP, then subclasses can call this function to read memory. - static lldb::WritableDataBufferSP - ReadMemory(const lldb::ProcessSP &process_sp, lldb::addr_t addr, - size_t byte_size); + static lldb::DataBufferSP ReadMemory(const lldb::ProcessSP &process_sp, + lldb::addr_t addr, size_t byte_size); // This function returns raw file contents. Do not use it if you want // transparent decompression of section contents. diff --git a/lldb/source/Plugins/ObjectFile/ELF/ObjectFileELF.cpp b/lldb/source/Plugins/ObjectFile/ELF/ObjectFileELF.cpp index 414ac6112d5797..890db5c2748146 100644 --- a/lldb/source/Plugins/ObjectFile/ELF/ObjectFileELF.cpp +++ b/lldb/source/Plugins/ObjectFile/ELF/ObjectFileELF.cpp @@ -419,35 +419,19 @@ ObjectFile *ObjectFileELF::CreateInstance(const lldb::ModuleSP &module_sp, ObjectFile *ObjectFileELF::CreateMemoryInstance( const lldb::ModuleSP &module_sp, WritableDataBufferSP data_sp, const lldb::ProcessSP &process_sp, lldb::addr_t header_addr) { - if (!data_sp || data_sp->GetByteSize() < (llvm::ELF::EI_NIDENT)) - return nullptr; - const uint8_t *magic = data_sp->GetBytes(); - if (!ELFHeader::MagicBytesMatch(magic)) - return nullptr; - // Read the ELF header first so we can figure out how many bytes we need - // to read to get as least the ELF header + program headers. - DataExtractor data; - data.SetData(data_sp); - elf::ELFHeader hdr; - lldb::offset_t offset = 0; - if (!hdr.Parse(data, &offset)) - return nullptr; - - // Make sure the address size is set correctly in the ELF header. - if (!hdr.Is32Bit() && !hdr.Is64Bit()) - return nullptr; - // Figure out where the program headers end and read enough bytes to get the - // program headers in their entirety. - lldb::offset_t end_phdrs = hdr.e_phoff + (hdr.e_phentsize * hdr.e_phnum); - if (end_phdrs > data_sp->GetByteSize()) - data_sp = ReadMemory(process_sp, header_addr, end_phdrs); - - std::unique_ptr objfile_up( - new ObjectFileELF(module_sp, data_sp, process_sp, header_addr)); - ArchSpec spec = objfile_up->GetArchitecture(); - if (spec && objfile_up->SetModulesArchitecture(spec)) - return objfile_up.release(); - + if (data_sp && data_sp->GetByteSize() > (llvm::ELF::EI_NIDENT)) { + const uint8_t *magic = data_sp->GetBytes(); + if (ELFHeader::MagicBytesMatch(magic)) { + unsigned address_size = ELFHeader::AddressSizeInBytes(magic); + if (address_size == 4 || address_size == 8) { + std::unique_ptr objfile_up( + new ObjectFileELF(module_sp, data_sp, process_sp, header_addr)); + ArchSpec spec = objfile_up->GetArchitecture(); + if (spec && objfile_up->SetModulesArchitecture(spec)) + return objfile_up.release(); + } + } + } return nullptr; } @@ -889,37 +873,42 @@ Address ObjectFileELF::GetImageInfoAddress(Target *target) { if (!section_list) return Address(); - for (size_t i = 0; i < m_dynamic_symbols.size(); ++i) { - const ELFDynamic &symbol = m_dynamic_symbols[i].symbol; + // Find the SHT_DYNAMIC (.dynamic) section. + SectionSP dynsym_section_sp( + section_list->FindSectionByType(eSectionTypeELFDynamicLinkInfo, true)); + if (!dynsym_section_sp) + return Address(); + assert(dynsym_section_sp->GetObjectFile() == this); - if (symbol.d_tag != DT_DEBUG && symbol.d_tag != DT_MIPS_RLD_MAP && - symbol.d_tag != DT_MIPS_RLD_MAP_REL) - continue; + user_id_t dynsym_id = dynsym_section_sp->GetID(); + const ELFSectionHeaderInfo *dynsym_hdr = GetSectionHeaderByIndex(dynsym_id); + if (!dynsym_hdr) + return Address(); - // Compute the offset as the number of previous entries plus the size of - // d_tag. - const addr_t offset = (i * 2 + 1) * GetAddressByteSize(); - const addr_t d_file_addr = m_dynamic_base_addr + offset; - Address d_addr; - if (d_addr.ResolveAddressUsingFileSections(d_file_addr, GetSectionList())) - return Address(); - if (symbol.d_tag == DT_DEBUG) - return d_addr; + for (size_t i = 0; i < m_dynamic_symbols.size(); ++i) { + ELFDynamic &symbol = m_dynamic_symbols[i]; + if (symbol.d_tag == DT_DEBUG) { + // Compute the offset as the number of previous entries plus the size of + // d_tag. + addr_t offset = i * dynsym_hdr->sh_entsize + GetAddressByteSize(); + return Address(dynsym_section_sp, offset); + } // MIPS executables uses DT_MIPS_RLD_MAP_REL to support PIE. DT_MIPS_RLD_MAP // exists in non-PIE. - if ((symbol.d_tag == DT_MIPS_RLD_MAP || - symbol.d_tag == DT_MIPS_RLD_MAP_REL) && - target) { - const addr_t d_load_addr = d_addr.GetLoadAddress(target); - if (d_load_addr == LLDB_INVALID_ADDRESS) + else if ((symbol.d_tag == DT_MIPS_RLD_MAP || + symbol.d_tag == DT_MIPS_RLD_MAP_REL) && + target) { + addr_t offset = i * dynsym_hdr->sh_entsize + GetAddressByteSize(); + addr_t dyn_base = dynsym_section_sp->GetLoadBaseAddress(target); + if (dyn_base == LLDB_INVALID_ADDRESS) return Address(); Status error; if (symbol.d_tag == DT_MIPS_RLD_MAP) { // DT_MIPS_RLD_MAP tag stores an absolute address of the debug pointer. Address addr; - if (target->ReadPointerFromMemory(d_load_addr, error, addr, true)) + if (target->ReadPointerFromMemory(dyn_base + offset, error, addr, true)) return addr; } if (symbol.d_tag == DT_MIPS_RLD_MAP_REL) { @@ -927,17 +916,18 @@ Address ObjectFileELF::GetImageInfoAddress(Target *target) { // relative to the address of the tag. uint64_t rel_offset; rel_offset = target->ReadUnsignedIntegerFromMemory( - d_load_addr, GetAddressByteSize(), UINT64_MAX, error, true); + dyn_base + offset, GetAddressByteSize(), UINT64_MAX, error, true); if (error.Success() && rel_offset != UINT64_MAX) { Address addr; addr_t debug_ptr_address = - d_load_addr - GetAddressByteSize() + rel_offset; + dyn_base + (offset - GetAddressByteSize()) + rel_offset; addr.SetOffset(debug_ptr_address); return addr; } } } } + return Address(); } @@ -980,23 +970,62 @@ Address ObjectFileELF::GetBaseAddress() { return LLDB_INVALID_ADDRESS; } +// ParseDependentModules size_t ObjectFileELF::ParseDependentModules() { if (m_filespec_up) return m_filespec_up->GetSize(); m_filespec_up = std::make_unique(); - if (ParseDynamicSymbols()) { - for (const auto &entry : m_dynamic_symbols) { - if (entry.symbol.d_tag != DT_NEEDED) + if (!ParseSectionHeaders()) + return 0; + + SectionList *section_list = GetSectionList(); + if (!section_list) + return 0; + + // Find the SHT_DYNAMIC section. + Section *dynsym = + section_list->FindSectionByType(eSectionTypeELFDynamicLinkInfo, true) + .get(); + if (!dynsym) + return 0; + assert(dynsym->GetObjectFile() == this); + + const ELFSectionHeaderInfo *header = GetSectionHeaderByIndex(dynsym->GetID()); + if (!header) + return 0; + // sh_link: section header index of string table used by entries in the + // section. + Section *dynstr = section_list->FindSectionByID(header->sh_link).get(); + if (!dynstr) + return 0; + + DataExtractor dynsym_data; + DataExtractor dynstr_data; + if (ReadSectionData(dynsym, dynsym_data) && + ReadSectionData(dynstr, dynstr_data)) { + ELFDynamic symbol; + const lldb::offset_t section_size = dynsym_data.GetByteSize(); + lldb::offset_t offset = 0; + + // The only type of entries we are concerned with are tagged DT_NEEDED, + // yielding the name of a required library. + while (offset < section_size) { + if (!symbol.Parse(dynsym_data, &offset)) + break; + + if (symbol.d_tag != DT_NEEDED) continue; - if (!entry.name.empty()) { - FileSpec file_spec(entry.name); - FileSystem::Instance().Resolve(file_spec); - m_filespec_up->Append(file_spec); - } + + uint32_t str_index = static_cast(symbol.d_val); + const char *lib_name = dynstr_data.PeekCStr(str_index); + FileSpec file_spec(lib_name); + FileSystem::Instance().Resolve(file_spec); + m_filespec_up->Append(file_spec); } } + return m_filespec_up->GetSize(); } @@ -2443,47 +2472,48 @@ size_t ObjectFileELF::ParseDynamicSymbols() { if (m_dynamic_symbols.size()) return m_dynamic_symbols.size(); - std::optional dynamic_data = GetDynamicData(); - if (!dynamic_data) + SectionList *section_list = GetSectionList(); + if (!section_list) return 0; - ELFDynamicWithName e; - lldb::offset_t cursor = 0; - while (e.symbol.Parse(*dynamic_data, &cursor)) { - m_dynamic_symbols.push_back(e); - if (e.symbol.d_tag == DT_NULL) - break; - } - if (std::optional dynstr_data = GetDynstrData()) { - for (ELFDynamicWithName &entry : m_dynamic_symbols) { - switch (entry.symbol.d_tag) { - case DT_NEEDED: - case DT_SONAME: - case DT_RPATH: - case DT_RUNPATH: - case DT_AUXILIARY: - case DT_FILTER: { - lldb::offset_t cursor = entry.symbol.d_val; - const char *name = dynstr_data->GetCStr(&cursor); - if (name) - entry.name = std::string(name); - break; - } - default: + // Find the SHT_DYNAMIC section. + Section *dynsym = + section_list->FindSectionByType(eSectionTypeELFDynamicLinkInfo, true) + .get(); + if (!dynsym) + return 0; + assert(dynsym->GetObjectFile() == this); + + ELFDynamic symbol; + DataExtractor dynsym_data; + if (ReadSectionData(dynsym, dynsym_data)) { + const lldb::offset_t section_size = dynsym_data.GetByteSize(); + lldb::offset_t cursor = 0; + + while (cursor < section_size) { + if (!symbol.Parse(dynsym_data, &cursor)) break; - } + + m_dynamic_symbols.push_back(symbol); } } + return m_dynamic_symbols.size(); } const ELFDynamic *ObjectFileELF::FindDynamicSymbol(unsigned tag) { if (!ParseDynamicSymbols()) return nullptr; - for (const auto &entry : m_dynamic_symbols) { - if (entry.symbol.d_tag == tag) - return &entry.symbol; + + DynamicSymbolCollIter I = m_dynamic_symbols.begin(); + DynamicSymbolCollIter E = m_dynamic_symbols.end(); + for (; I != E; ++I) { + ELFDynamic *symbol = &*I; + + if (symbol->d_tag == tag) + return symbol; } + return nullptr; } @@ -3200,10 +3230,7 @@ void ObjectFileELF::Dump(Stream *s) { ArchSpec header_arch = GetArchitecture(); *s << ", file = '" << m_file - << "', arch = " << header_arch.GetArchitectureName(); - if (m_memory_addr != LLDB_INVALID_ADDRESS) - s->Printf(", addr = %#16.16" PRIx64, m_memory_addr); - s->EOL(); + << "', arch = " << header_arch.GetArchitectureName() << "\n"; DumpELFHeader(s, m_header); s->EOL(); @@ -3221,8 +3248,6 @@ void ObjectFileELF::Dump(Stream *s) { s->EOL(); DumpDependentModules(s); s->EOL(); - DumpELFDynamic(s); - s->EOL(); } // DumpELFHeader @@ -3467,111 +3492,6 @@ void ObjectFileELF::DumpDependentModules(lldb_private::Stream *s) { } } -std::string static getDynamicTagAsString(uint16_t Arch, uint64_t Type) { -#define DYNAMIC_STRINGIFY_ENUM(tag, value) \ - case value: \ - return #tag; - -#define DYNAMIC_TAG(n, v) - switch (Arch) { - case llvm::ELF::EM_AARCH64: - switch (Type) { -#define AARCH64_DYNAMIC_TAG(name, value) DYNAMIC_STRINGIFY_ENUM(name, value) -#include "llvm/BinaryFormat/DynamicTags.def" -#undef AARCH64_DYNAMIC_TAG - } - break; - - case llvm::ELF::EM_HEXAGON: - switch (Type) { -#define HEXAGON_DYNAMIC_TAG(name, value) DYNAMIC_STRINGIFY_ENUM(name, value) -#include "llvm/BinaryFormat/DynamicTags.def" -#undef HEXAGON_DYNAMIC_TAG - } - break; - - case llvm::ELF::EM_MIPS: - switch (Type) { -#define MIPS_DYNAMIC_TAG(name, value) DYNAMIC_STRINGIFY_ENUM(name, value) -#include "llvm/BinaryFormat/DynamicTags.def" -#undef MIPS_DYNAMIC_TAG - } - break; - - case llvm::ELF::EM_PPC: - switch (Type) { -#define PPC_DYNAMIC_TAG(name, value) DYNAMIC_STRINGIFY_ENUM(name, value) -#include "llvm/BinaryFormat/DynamicTags.def" -#undef PPC_DYNAMIC_TAG - } - break; - - case llvm::ELF::EM_PPC64: - switch (Type) { -#define PPC64_DYNAMIC_TAG(name, value) DYNAMIC_STRINGIFY_ENUM(name, value) -#include "llvm/BinaryFormat/DynamicTags.def" -#undef PPC64_DYNAMIC_TAG - } - break; - - case llvm::ELF::EM_RISCV: - switch (Type) { -#define RISCV_DYNAMIC_TAG(name, value) DYNAMIC_STRINGIFY_ENUM(name, value) -#include "llvm/BinaryFormat/DynamicTags.def" -#undef RISCV_DYNAMIC_TAG - } - break; - } -#undef DYNAMIC_TAG - switch (Type) { -// Now handle all dynamic tags except the architecture specific ones -#define AARCH64_DYNAMIC_TAG(name, value) -#define MIPS_DYNAMIC_TAG(name, value) -#define HEXAGON_DYNAMIC_TAG(name, value) -#define PPC_DYNAMIC_TAG(name, value) -#define PPC64_DYNAMIC_TAG(name, value) -#define RISCV_DYNAMIC_TAG(name, value) -// Also ignore marker tags such as DT_HIOS (maps to DT_VERNEEDNUM), etc. -#define DYNAMIC_TAG_MARKER(name, value) -#define DYNAMIC_TAG(name, value) \ - case value: \ - return #name; -#include "llvm/BinaryFormat/DynamicTags.def" -#undef DYNAMIC_TAG -#undef AARCH64_DYNAMIC_TAG -#undef MIPS_DYNAMIC_TAG -#undef HEXAGON_DYNAMIC_TAG -#undef PPC_DYNAMIC_TAG -#undef PPC64_DYNAMIC_TAG -#undef RISCV_DYNAMIC_TAG -#undef DYNAMIC_TAG_MARKER -#undef DYNAMIC_STRINGIFY_ENUM - default: - return "0x" + llvm::utohexstr(Type, true); - } -} - -void ObjectFileELF::DumpELFDynamic(lldb_private::Stream *s) { - ParseDynamicSymbols(); - if (m_dynamic_symbols.empty()) - return; - - s->PutCString(".dynamic:\n"); - s->PutCString("IDX d_tag d_val/d_ptr\n"); - s->PutCString("==== ---------------- ------------------\n"); - uint32_t idx = 0; - for (const auto &entry : m_dynamic_symbols) { - s->Printf("[%2u] ", idx++); - s->Printf( - "%-16s 0x%16.16" PRIx64, - getDynamicTagAsString(m_header.e_machine, entry.symbol.d_tag).c_str(), - entry.symbol.d_ptr); - if (!entry.name.empty()) - s->Printf(" \"%s\"", entry.name.c_str()); - s->EOL(); - } -} - ArchSpec ObjectFileELF::GetArchitecture() { if (!ParseHeader()) return ArchSpec(); @@ -3744,24 +3664,7 @@ llvm::ArrayRef ObjectFileELF::ProgramHeaders() { } DataExtractor ObjectFileELF::GetSegmentData(const ELFProgramHeader &H) { - // Try and read the program header from our cached m_data which can come from - // the file on disk being mmap'ed or from the initial part of the ELF file we - // read from memory and cached. - DataExtractor data = DataExtractor(m_data, H.p_offset, H.p_filesz); - if (data.GetByteSize() == H.p_filesz) - return data; - if (IsInMemory()) { - // We have a ELF file in process memory, read the program header data from - // the process. - if (ProcessSP process_sp = m_process_wp.lock()) { - const lldb::offset_t base_file_addr = GetBaseAddress().GetFileAddress(); - const addr_t load_bias = m_memory_addr - base_file_addr; - const addr_t data_addr = H.p_vaddr + load_bias; - if (DataBufferSP data_sp = ReadMemory(process_sp, data_addr, H.p_memsz)) - return DataExtractor(data_sp, GetByteOrder(), GetAddressByteSize()); - } - } - return DataExtractor(); + return DataExtractor(m_data, H.p_offset, H.p_filesz); } bool ObjectFileELF::AnySegmentHasPhysicalAddress() { @@ -3801,88 +3704,3 @@ ObjectFileELF::MapFileDataWritable(const FileSpec &file, uint64_t Size, return FileSystem::Instance().CreateWritableDataBuffer(file.GetPath(), Size, Offset); } - -std::optional ObjectFileELF::GetDynstrData() { - if (SectionList *section_list = GetSectionList()) { - // Find the SHT_DYNAMIC section. - if (Section *dynamic = - section_list - ->FindSectionByType(eSectionTypeELFDynamicLinkInfo, true) - .get()) { - assert(dynamic->GetObjectFile() == this); - if (const ELFSectionHeaderInfo *header = - GetSectionHeaderByIndex(dynamic->GetID())) { - // sh_link: section header index of string table used by entries in - // the section. - if (Section *dynstr = - section_list->FindSectionByID(header->sh_link).get()) { - DataExtractor data; - if (ReadSectionData(dynstr, data)) - return data; - } - } - } - } - - // Every ELF file which represents an executable or shared library has - // mandatory .dynamic entries. Two of these values are DT_STRTAB and DT_STRSZ - // and represent the dynamic symbol tables's string table. These are needed - // by the dynamic loader and we can read them from a process' address space. - // - // When loading and ELF file from memory, only the program headers end up - // being mapped into memory, and we can find these values in the PT_DYNAMIC - // segment. - const ELFDynamic *strtab = FindDynamicSymbol(DT_STRTAB); - const ELFDynamic *strsz = FindDynamicSymbol(DT_STRSZ); - if (strtab == nullptr || strsz == nullptr) - return std::nullopt; - - if (ProcessSP process_sp = m_process_wp.lock()) { - if (DataBufferSP data_sp = - ReadMemory(process_sp, strtab->d_ptr, strsz->d_val)) - return DataExtractor(data_sp, GetByteOrder(), GetAddressByteSize()); - } else { - // We have an ELF file with no section headers or we didn't find the - // .dynamic section. Try and find the .dynstr section. - Address addr; - if (addr.ResolveAddressUsingFileSections(strtab->d_ptr, GetSectionList())) { - DataExtractor data; - addr.GetSection()->GetSectionData(data); - return DataExtractor(data, - strtab->d_ptr - addr.GetSection()->GetFileAddress(), - strsz->d_val); - } - } - return std::nullopt; -} - -std::optional ObjectFileELF::GetDynamicData() { - DataExtractor data; - // The PT_DYNAMIC program header describes where the .dynamic section is and - // doesn't require parsing section headers. The PT_DYNAMIC is required by - // executables and shared libraries so it will always be available. - for (const ELFProgramHeader &H : ProgramHeaders()) { - if (H.p_type == llvm::ELF::PT_DYNAMIC) { - data = GetSegmentData(H); - if (data.GetByteSize() > 0) { - m_dynamic_base_addr = H.p_vaddr; - return data; - } - } - } - // Fall back to using section headers. - if (SectionList *section_list = GetSectionList()) { - // Find the SHT_DYNAMIC section. - if (Section *dynamic = - section_list - ->FindSectionByType(eSectionTypeELFDynamicLinkInfo, true) - .get()) { - assert(dynamic->GetObjectFile() == this); - if (ReadSectionData(dynamic, data)) { - m_dynamic_base_addr = dynamic->GetFileAddress(); - return data; - } - } - } - return std::nullopt; -} diff --git a/lldb/source/Plugins/ObjectFile/ELF/ObjectFileELF.h b/lldb/source/Plugins/ObjectFile/ELF/ObjectFileELF.h index aba3a5bfcbf5b6..844e981b1d890a 100644 --- a/lldb/source/Plugins/ObjectFile/ELF/ObjectFileELF.h +++ b/lldb/source/Plugins/ObjectFile/ELF/ObjectFileELF.h @@ -183,11 +183,7 @@ class ObjectFileELF : public lldb_private::ObjectFile { typedef SectionHeaderColl::iterator SectionHeaderCollIter; typedef SectionHeaderColl::const_iterator SectionHeaderCollConstIter; - struct ELFDynamicWithName { - elf::ELFDynamic symbol; - std::string name; - }; - typedef std::vector DynamicSymbolColl; + typedef std::vector DynamicSymbolColl; typedef DynamicSymbolColl::iterator DynamicSymbolCollIter; typedef DynamicSymbolColl::const_iterator DynamicSymbolCollConstIter; @@ -217,10 +213,6 @@ class ObjectFileELF : public lldb_private::ObjectFile { /// Collection of section headers. SectionHeaderColl m_section_headers; - /// The file address of the .dynamic section. This can be found in the p_vaddr - /// of the PT_DYNAMIC program header. - lldb::addr_t m_dynamic_base_addr = LLDB_INVALID_ADDRESS; - /// Collection of symbols from the dynamic table. DynamicSymbolColl m_dynamic_symbols; @@ -392,9 +384,6 @@ class ObjectFileELF : public lldb_private::ObjectFile { /// ELF dependent module dump routine. void DumpDependentModules(lldb_private::Stream *s); - /// ELF dump the .dynamic section - void DumpELFDynamic(lldb_private::Stream *s); - const elf::ELFDynamic *FindDynamicSymbol(unsigned tag); unsigned PLTRelocationType(); @@ -413,28 +402,6 @@ class ObjectFileELF : public lldb_private::ObjectFile { /// .gnu_debugdata section or \c nullptr if an error occured or if there's no /// section with that name. std::shared_ptr GetGnuDebugDataObjectFile(); - - /// Get the bytes that represent the .dynamic section. - /// - /// This function will fetch the data for the .dynamic section in an ELF file. - /// The PT_DYNAMIC program header will be used to extract the data and this - /// function will fall back to using the section headers if PT_DYNAMIC isn't - /// found. - /// - /// \return The bytes that represent the string table data or \c std::nullopt - /// if an error occured. - std::optional GetDynamicData(); - - /// Get the bytes that represent the dynamic string table data. - /// - /// This function will fetch the data for the string table in an ELF file. If - /// the ELF file is loaded from a file on disk, it will use the section - /// headers to extract the data and fall back to using the DT_STRTAB and - /// DT_STRSZ .dynamic entries. - /// - /// \return The bytes that represent the string table data or \c std::nullopt - /// if an error occured. - std::optional GetDynstrData(); }; #endif // LLDB_SOURCE_PLUGINS_OBJECTFILE_ELF_OBJECTFILEELF_H diff --git a/lldb/source/Symbol/ObjectFile.cpp b/lldb/source/Symbol/ObjectFile.cpp index 35317d209de1f9..2608a9c5fb79a2 100644 --- a/lldb/source/Symbol/ObjectFile.cpp +++ b/lldb/source/Symbol/ObjectFile.cpp @@ -454,10 +454,9 @@ AddressClass ObjectFile::GetAddressClass(addr_t file_addr) { return AddressClass::eUnknown; } -WritableDataBufferSP ObjectFile::ReadMemory(const ProcessSP &process_sp, - lldb::addr_t addr, - size_t byte_size) { - WritableDataBufferSP data_sp; +DataBufferSP ObjectFile::ReadMemory(const ProcessSP &process_sp, + lldb::addr_t addr, size_t byte_size) { + DataBufferSP data_sp; if (process_sp) { std::unique_ptr data_up(new DataBufferHeap(byte_size, 0)); Status error; diff --git a/lldb/test/Shell/ObjectFile/ELF/Inputs/memory-elf.cpp b/lldb/test/Shell/ObjectFile/ELF/Inputs/memory-elf.cpp deleted file mode 100644 index 9cae6c99c9f761..00000000000000 --- a/lldb/test/Shell/ObjectFile/ELF/Inputs/memory-elf.cpp +++ /dev/null @@ -1,5 +0,0 @@ -#include -int main() { - printf("Hello World\n"); // Use something from libc.so - return 0; -} diff --git a/lldb/test/Shell/ObjectFile/ELF/elf-dynamic-no-shdrs.yaml b/lldb/test/Shell/ObjectFile/ELF/elf-dynamic-no-shdrs.yaml deleted file mode 100644 index bc34e16e0b6ad2..00000000000000 --- a/lldb/test/Shell/ObjectFile/ELF/elf-dynamic-no-shdrs.yaml +++ /dev/null @@ -1,90 +0,0 @@ -## This test verifies that loading an ELF file that has no section headers can -## find the contents on the .dynamic section and the strings associated with -## the .dynamic seciton. -## - Loading the .dynamic section from the PT_DYNAMIC -## This test will make a simple executable that links against libc.so and we -## verify that we can find the DT_NEEDED entry with the shared library found -## in the .dynamic dump from "image dump objfile" - -# RUN: yaml2obj %s -o %t - -# RUN: %lldb -b \ -# RUN: -o "target create -d '%t'" \ -# RUN: -o "image dump objfile" \ -# RUN: | FileCheck %s --dump-input=always -# CHECK: (lldb) image dump objfile -# CHECK: Dumping headers for 1 module(s). -# CHECK: ObjectFileELF, file = -# CHECK: ELF Header -# Make sure there are no section headers -# CHECK: e_shnum = 0x00000000 - -# Make sure we find the program headers and see a PT_DYNAMIC entry. -# CHECK: Program Headers -# CHECK: IDX p_type p_offset p_vaddr p_paddr p_filesz p_memsz p_flags p_align -# CHECK: ==== --------------- -------- -------- -------- -------- -------- ------------------------- -------- -# CHECK: [ 0] PT_LOAD 000000b0 00000000 00000000 00000170 00000170 00000000 ( ) 00000001 -# CHECK: [ 1] PT_DYNAMIC 000001b0 00000100 00000100 00000070 00000070 00000000 ( ) 00000008 - -# CHECK: Dependent Modules: -# CHECK: ccc -# CHECK: aaa -# CHECK: bbb - -# Make sure we see some sections created from the program headers -# MAIN: SectID -# MAIN: PT_LOAD[0] - -# CHECK: .dynamic: -# CHECK: IDX d_tag d_val/d_ptr -# CHECK: ==== ---------------- ------------------ -# CHECK: [ 0] STRTAB 0x0000000000000000 -# CHECK: [ 1] NEEDED 0x0000000000000009 "ccc" -# CHECK: [ 2] NEEDED 0x0000000000000001 "aaa" -# CHECK: [ 3] NEEDED 0x0000000000000005 "bbb" -# CHECK: [ 4] STRSZ 0x0000000000000100 -# CHECK: [ 5] DEBUG 0x00000000deadbeef -# CHECK: [ 6] NULL 0x0000000000000000 - ---- !ELF -FileHeader: - Class: ELFCLASS64 - Data: ELFDATA2LSB - Type: ET_EXEC - Machine: EM_X86_64 -Sections: - - Type: SectionHeaderTable - NoHeaders: true - - Name: .dynstr - Type: SHT_STRTAB - Flags: [ SHF_ALLOC ] - Content: '00616161006262620063636300' ## 0,a,a,a,0,b,b,b,0,c,c,c,0 - Size: 0x100 - - Name: .dynamic - Type: SHT_DYNAMIC - Address: 0x100 - Entries: - - Tag: DT_STRTAB - Value: 0x0000000000000000 - - Tag: DT_NEEDED - Value: 9 - - Tag: DT_NEEDED - Value: 1 - - Tag: DT_NEEDED - Value: 5 - - Tag: DT_STRSZ - Value: 0x100 - - Tag: DT_DEBUG - Value: 0xdeadbeef - - Tag: DT_NULL - Value: 0x0 -ProgramHeaders: - - Type: PT_LOAD - VAddr: 0x0 - FirstSec: .dynstr - LastSec: .dynamic - - Type: PT_DYNAMIC - FirstSec: .dynamic - LastSec: .dynamic - VAddr: 0x100 - Align: 0x8 diff --git a/lldb/test/Shell/ObjectFile/ELF/elf-memory.test b/lldb/test/Shell/ObjectFile/ELF/elf-memory.test deleted file mode 100644 index 0b1c01486a4b43..00000000000000 --- a/lldb/test/Shell/ObjectFile/ELF/elf-memory.test +++ /dev/null @@ -1,55 +0,0 @@ -// REQUIRES: system-linux, native - -// This test verifies that loading an ELF file from memory works and the new -// features that were added when loading from memory work like: -// - Loading the .dynamic section from the PT_DYNAMIC since ELF files loaded -// from memory don't have the section headers available. -// This test will make a simple executable that: -// - links against libc -// - runs and stops at a breakpoint -// - create a memory ELF file -// - verify that "image dump objfile" will dump the dynamic section of the -// memory elf file and find the .dynamic string table. - -// RUN: %clang_host %p/Inputs/memory-elf.cpp -g -O0 -o %t - -// RUN: %lldb %t -b \ -// RUN: -o "b main" \ -// RUN: -o "run" \ -// RUN: -o "script real_module = lldb.target.module[0]" \ -// RUN: -o "script base_addr = real_module.GetObjectFileHeaderAddress().GetLoadAddress(lldb.target)" \ -// RUN: -o "script mem_module = lldb.SBModule(lldb.process, base_addr)" \ -// RUN: -o "script target2 = lldb.debugger.CreateTarget('')" \ -// RUN: -o "script target2.AddModule(mem_module)" \ -// RUN: -o "target select 1" \ -// RUN: -o "image dump objfile" \ -// RUN: | FileCheck %s --check-prefix=MAIN --dump-input=always -// MAIN: (lldb) image dump objfile -// MAIN: Dumping headers for 1 module(s). -// MAIN: ObjectFileELF, file = '', arch = {{.*, addr = 0x[0-9a-f]+}} -// MAIN: ELF Header - -// Make sure we find the program headers and see a PT_DYNAMIC entry. -// MAIN: Program Headers -// MAIN: ] PT_DYNAMIC - -// Make sure we see some sections created from the program headers -// MAIN: SectID -// MAIN: PT_LOAD[0] - -// Ensure we find some dependent modules as won't find these if we aren't able -// to load the .dynamic section from the PT_DYNAMIC program header. -// MAIN: Dependent Modules: - -// Check for the .dynamic dump and ensure we find all dynamic entries that are -// required to be there and needed to get the .dynstr section and the symbol -// table, and the DT_DEBUG entry to find the list of shared libraries. -// MAIN: .dynamic: -// Make sure we found the .dynstr section by checking for valid strings after NEEDED -// MAIN-DAG: NEEDED {{0x[0-9a-f]+ ".*libc.*"}} -// MAIN-DAG: STRTAB {{0x[0-9a-f]+}} -// MAIN-DAG: SYMTAB {{0x[0-9a-f]+}} -// MAIN-DAG: STRSZ {{0x[0-9a-f]+}} -// MAIN-DAG: SYMENT {{0x[0-9a-f]+}} -// MAIN-DAG: DEBUG {{0x[0-9a-f]+}} -// MAIN: NULL {{0x[0-9a-f]+}}