[Lldb-commits] [lldb] r280751 - *** This commit represents a complete reformatting of the LLDB source code
Kate Stone via lldb-commits
lldb-commits at lists.llvm.org
Tue Sep 6 13:58:36 PDT 2016
Modified: lldb/trunk/source/Symbol/CompactUnwindInfo.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/CompactUnwindInfo.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/CompactUnwindInfo.cpp (original)
+++ lldb/trunk/source/Symbol/CompactUnwindInfo.cpp Tue Sep 6 15:57:50 2016
@@ -7,7 +7,6 @@
//
//===----------------------------------------------------------------------===//
-
// C Includes
// C++ Includes
#include <algorithm>
@@ -30,125 +29,114 @@
using namespace lldb;
using namespace lldb_private;
-
namespace lldb_private {
- // Constants from <mach-o/compact_unwind_encoding.h>
+// Constants from <mach-o/compact_unwind_encoding.h>
- FLAGS_ANONYMOUS_ENUM()
- {
- UNWIND_IS_NOT_FUNCTION_START = 0x80000000,
- UNWIND_HAS_LSDA = 0x40000000,
- UNWIND_PERSONALITY_MASK = 0x30000000,
- };
-
- FLAGS_ANONYMOUS_ENUM()
- {
- UNWIND_X86_MODE_MASK = 0x0F000000,
- UNWIND_X86_MODE_EBP_FRAME = 0x01000000,
- UNWIND_X86_MODE_STACK_IMMD = 0x02000000,
- UNWIND_X86_MODE_STACK_IND = 0x03000000,
- UNWIND_X86_MODE_DWARF = 0x04000000,
-
- UNWIND_X86_EBP_FRAME_REGISTERS = 0x00007FFF,
- UNWIND_X86_EBP_FRAME_OFFSET = 0x00FF0000,
-
- UNWIND_X86_FRAMELESS_STACK_SIZE = 0x00FF0000,
- UNWIND_X86_FRAMELESS_STACK_ADJUST = 0x0000E000,
- UNWIND_X86_FRAMELESS_STACK_REG_COUNT = 0x00001C00,
- UNWIND_X86_FRAMELESS_STACK_REG_PERMUTATION = 0x000003FF,
-
- UNWIND_X86_DWARF_SECTION_OFFSET = 0x00FFFFFF,
- };
-
- enum
- {
- UNWIND_X86_REG_NONE = 0,
- UNWIND_X86_REG_EBX = 1,
- UNWIND_X86_REG_ECX = 2,
- UNWIND_X86_REG_EDX = 3,
- UNWIND_X86_REG_EDI = 4,
- UNWIND_X86_REG_ESI = 5,
- UNWIND_X86_REG_EBP = 6,
- };
-
- FLAGS_ANONYMOUS_ENUM()
- {
- UNWIND_X86_64_MODE_MASK = 0x0F000000,
- UNWIND_X86_64_MODE_RBP_FRAME = 0x01000000,
- UNWIND_X86_64_MODE_STACK_IMMD = 0x02000000,
- UNWIND_X86_64_MODE_STACK_IND = 0x03000000,
- UNWIND_X86_64_MODE_DWARF = 0x04000000,
-
- UNWIND_X86_64_RBP_FRAME_REGISTERS = 0x00007FFF,
- UNWIND_X86_64_RBP_FRAME_OFFSET = 0x00FF0000,
-
- UNWIND_X86_64_FRAMELESS_STACK_SIZE = 0x00FF0000,
- UNWIND_X86_64_FRAMELESS_STACK_ADJUST = 0x0000E000,
- UNWIND_X86_64_FRAMELESS_STACK_REG_COUNT = 0x00001C00,
- UNWIND_X86_64_FRAMELESS_STACK_REG_PERMUTATION = 0x000003FF,
-
- UNWIND_X86_64_DWARF_SECTION_OFFSET = 0x00FFFFFF,
- };
-
- enum
- {
- UNWIND_X86_64_REG_NONE = 0,
- UNWIND_X86_64_REG_RBX = 1,
- UNWIND_X86_64_REG_R12 = 2,
- UNWIND_X86_64_REG_R13 = 3,
- UNWIND_X86_64_REG_R14 = 4,
- UNWIND_X86_64_REG_R15 = 5,
- UNWIND_X86_64_REG_RBP = 6,
- };
-
- FLAGS_ANONYMOUS_ENUM()
- {
- UNWIND_ARM64_MODE_MASK = 0x0F000000,
- UNWIND_ARM64_MODE_FRAMELESS = 0x02000000,
- UNWIND_ARM64_MODE_DWARF = 0x03000000,
- UNWIND_ARM64_MODE_FRAME = 0x04000000,
-
- UNWIND_ARM64_FRAME_X19_X20_PAIR = 0x00000001,
- UNWIND_ARM64_FRAME_X21_X22_PAIR = 0x00000002,
- UNWIND_ARM64_FRAME_X23_X24_PAIR = 0x00000004,
- UNWIND_ARM64_FRAME_X25_X26_PAIR = 0x00000008,
- UNWIND_ARM64_FRAME_X27_X28_PAIR = 0x00000010,
- UNWIND_ARM64_FRAME_D8_D9_PAIR = 0x00000100,
- UNWIND_ARM64_FRAME_D10_D11_PAIR = 0x00000200,
- UNWIND_ARM64_FRAME_D12_D13_PAIR = 0x00000400,
- UNWIND_ARM64_FRAME_D14_D15_PAIR = 0x00000800,
-
- UNWIND_ARM64_FRAMELESS_STACK_SIZE_MASK = 0x00FFF000,
- UNWIND_ARM64_DWARF_SECTION_OFFSET = 0x00FFFFFF,
- };
-
- FLAGS_ANONYMOUS_ENUM()
- {
- UNWIND_ARM_MODE_MASK = 0x0F000000,
- UNWIND_ARM_MODE_FRAME = 0x01000000,
- UNWIND_ARM_MODE_FRAME_D = 0x02000000,
- UNWIND_ARM_MODE_DWARF = 0x04000000,
-
- UNWIND_ARM_FRAME_STACK_ADJUST_MASK = 0x00C00000,
-
- UNWIND_ARM_FRAME_FIRST_PUSH_R4 = 0x00000001,
- UNWIND_ARM_FRAME_FIRST_PUSH_R5 = 0x00000002,
- UNWIND_ARM_FRAME_FIRST_PUSH_R6 = 0x00000004,
-
- UNWIND_ARM_FRAME_SECOND_PUSH_R8 = 0x00000008,
- UNWIND_ARM_FRAME_SECOND_PUSH_R9 = 0x00000010,
- UNWIND_ARM_FRAME_SECOND_PUSH_R10 = 0x00000020,
- UNWIND_ARM_FRAME_SECOND_PUSH_R11 = 0x00000040,
- UNWIND_ARM_FRAME_SECOND_PUSH_R12 = 0x00000080,
+FLAGS_ANONYMOUS_ENUM(){
+ UNWIND_IS_NOT_FUNCTION_START = 0x80000000, UNWIND_HAS_LSDA = 0x40000000,
+ UNWIND_PERSONALITY_MASK = 0x30000000,
+};
- UNWIND_ARM_FRAME_D_REG_COUNT_MASK = 0x00000700,
+FLAGS_ANONYMOUS_ENUM(){
+ UNWIND_X86_MODE_MASK = 0x0F000000,
+ UNWIND_X86_MODE_EBP_FRAME = 0x01000000,
+ UNWIND_X86_MODE_STACK_IMMD = 0x02000000,
+ UNWIND_X86_MODE_STACK_IND = 0x03000000,
+ UNWIND_X86_MODE_DWARF = 0x04000000,
+
+ UNWIND_X86_EBP_FRAME_REGISTERS = 0x00007FFF,
+ UNWIND_X86_EBP_FRAME_OFFSET = 0x00FF0000,
+
+ UNWIND_X86_FRAMELESS_STACK_SIZE = 0x00FF0000,
+ UNWIND_X86_FRAMELESS_STACK_ADJUST = 0x0000E000,
+ UNWIND_X86_FRAMELESS_STACK_REG_COUNT = 0x00001C00,
+ UNWIND_X86_FRAMELESS_STACK_REG_PERMUTATION = 0x000003FF,
- UNWIND_ARM_DWARF_SECTION_OFFSET = 0x00FFFFFF,
- };
+ UNWIND_X86_DWARF_SECTION_OFFSET = 0x00FFFFFF,
+};
-}
+enum {
+ UNWIND_X86_REG_NONE = 0,
+ UNWIND_X86_REG_EBX = 1,
+ UNWIND_X86_REG_ECX = 2,
+ UNWIND_X86_REG_EDX = 3,
+ UNWIND_X86_REG_EDI = 4,
+ UNWIND_X86_REG_ESI = 5,
+ UNWIND_X86_REG_EBP = 6,
+};
+
+FLAGS_ANONYMOUS_ENUM(){
+ UNWIND_X86_64_MODE_MASK = 0x0F000000,
+ UNWIND_X86_64_MODE_RBP_FRAME = 0x01000000,
+ UNWIND_X86_64_MODE_STACK_IMMD = 0x02000000,
+ UNWIND_X86_64_MODE_STACK_IND = 0x03000000,
+ UNWIND_X86_64_MODE_DWARF = 0x04000000,
+
+ UNWIND_X86_64_RBP_FRAME_REGISTERS = 0x00007FFF,
+ UNWIND_X86_64_RBP_FRAME_OFFSET = 0x00FF0000,
+
+ UNWIND_X86_64_FRAMELESS_STACK_SIZE = 0x00FF0000,
+ UNWIND_X86_64_FRAMELESS_STACK_ADJUST = 0x0000E000,
+ UNWIND_X86_64_FRAMELESS_STACK_REG_COUNT = 0x00001C00,
+ UNWIND_X86_64_FRAMELESS_STACK_REG_PERMUTATION = 0x000003FF,
+
+ UNWIND_X86_64_DWARF_SECTION_OFFSET = 0x00FFFFFF,
+};
+
+enum {
+ UNWIND_X86_64_REG_NONE = 0,
+ UNWIND_X86_64_REG_RBX = 1,
+ UNWIND_X86_64_REG_R12 = 2,
+ UNWIND_X86_64_REG_R13 = 3,
+ UNWIND_X86_64_REG_R14 = 4,
+ UNWIND_X86_64_REG_R15 = 5,
+ UNWIND_X86_64_REG_RBP = 6,
+};
+
+FLAGS_ANONYMOUS_ENUM(){
+ UNWIND_ARM64_MODE_MASK = 0x0F000000,
+ UNWIND_ARM64_MODE_FRAMELESS = 0x02000000,
+ UNWIND_ARM64_MODE_DWARF = 0x03000000,
+ UNWIND_ARM64_MODE_FRAME = 0x04000000,
+
+ UNWIND_ARM64_FRAME_X19_X20_PAIR = 0x00000001,
+ UNWIND_ARM64_FRAME_X21_X22_PAIR = 0x00000002,
+ UNWIND_ARM64_FRAME_X23_X24_PAIR = 0x00000004,
+ UNWIND_ARM64_FRAME_X25_X26_PAIR = 0x00000008,
+ UNWIND_ARM64_FRAME_X27_X28_PAIR = 0x00000010,
+ UNWIND_ARM64_FRAME_D8_D9_PAIR = 0x00000100,
+ UNWIND_ARM64_FRAME_D10_D11_PAIR = 0x00000200,
+ UNWIND_ARM64_FRAME_D12_D13_PAIR = 0x00000400,
+ UNWIND_ARM64_FRAME_D14_D15_PAIR = 0x00000800,
+
+ UNWIND_ARM64_FRAMELESS_STACK_SIZE_MASK = 0x00FFF000,
+ UNWIND_ARM64_DWARF_SECTION_OFFSET = 0x00FFFFFF,
+};
+FLAGS_ANONYMOUS_ENUM(){
+ UNWIND_ARM_MODE_MASK = 0x0F000000,
+ UNWIND_ARM_MODE_FRAME = 0x01000000,
+ UNWIND_ARM_MODE_FRAME_D = 0x02000000,
+ UNWIND_ARM_MODE_DWARF = 0x04000000,
+
+ UNWIND_ARM_FRAME_STACK_ADJUST_MASK = 0x00C00000,
+
+ UNWIND_ARM_FRAME_FIRST_PUSH_R4 = 0x00000001,
+ UNWIND_ARM_FRAME_FIRST_PUSH_R5 = 0x00000002,
+ UNWIND_ARM_FRAME_FIRST_PUSH_R6 = 0x00000004,
+
+ UNWIND_ARM_FRAME_SECOND_PUSH_R8 = 0x00000008,
+ UNWIND_ARM_FRAME_SECOND_PUSH_R9 = 0x00000010,
+ UNWIND_ARM_FRAME_SECOND_PUSH_R10 = 0x00000020,
+ UNWIND_ARM_FRAME_SECOND_PUSH_R11 = 0x00000040,
+ UNWIND_ARM_FRAME_SECOND_PUSH_R12 = 0x00000080,
+
+ UNWIND_ARM_FRAME_D_REG_COUNT_MASK = 0x00000700,
+
+ UNWIND_ARM_DWARF_SECTION_OFFSET = 0x00FFFFFF,
+};
+}
#ifndef UNWIND_SECOND_LEVEL_REGULAR
#define UNWIND_SECOND_LEVEL_REGULAR 2
@@ -159,1515 +147,1481 @@ namespace lldb_private {
#endif
#ifndef UNWIND_INFO_COMPRESSED_ENTRY_FUNC_OFFSET
-#define UNWIND_INFO_COMPRESSED_ENTRY_FUNC_OFFSET(entry) (entry & 0x00FFFFFF)
+#define UNWIND_INFO_COMPRESSED_ENTRY_FUNC_OFFSET(entry) (entry & 0x00FFFFFF)
#endif
#ifndef UNWIND_INFO_COMPRESSED_ENTRY_ENCODING_INDEX
-#define UNWIND_INFO_COMPRESSED_ENTRY_ENCODING_INDEX(entry) ((entry >> 24) & 0xFF)
+#define UNWIND_INFO_COMPRESSED_ENTRY_ENCODING_INDEX(entry) \
+ ((entry >> 24) & 0xFF)
#endif
-#define EXTRACT_BITS(value, mask) \
- ( (value >> llvm::countTrailingZeros(static_cast<uint32_t>(mask), llvm::ZB_Width)) & \
- (((1 << llvm::countPopulation(static_cast<uint32_t>(mask))))-1) )
-
-
+#define EXTRACT_BITS(value, mask) \
+ ((value >> \
+ llvm::countTrailingZeros(static_cast<uint32_t>(mask), llvm::ZB_Width)) & \
+ (((1 << llvm::countPopulation(static_cast<uint32_t>(mask)))) - 1))
//----------------------
// constructor
//----------------------
CompactUnwindInfo::CompactUnwindInfo(ObjectFile &objfile, SectionSP §ion_sp)
- : m_objfile(objfile),
- m_section_sp(section_sp),
- m_section_contents_if_encrypted(),
- m_mutex(),
- m_indexes(),
- m_indexes_computed(eLazyBoolCalculate),
- m_unwindinfo_data(),
- m_unwindinfo_data_computed(false),
- m_unwind_header()
-{
-}
+ : m_objfile(objfile), m_section_sp(section_sp),
+ m_section_contents_if_encrypted(), m_mutex(), m_indexes(),
+ m_indexes_computed(eLazyBoolCalculate), m_unwindinfo_data(),
+ m_unwindinfo_data_computed(false), m_unwind_header() {}
//----------------------
// destructor
//----------------------
-CompactUnwindInfo::~CompactUnwindInfo()
-{
-}
-
-bool
-CompactUnwindInfo::GetUnwindPlan (Target &target, Address addr, UnwindPlan& unwind_plan)
-{
- if (!IsValid (target.GetProcessSP()))
- {
- return false;
- }
- FunctionInfo function_info;
- if (GetCompactUnwindInfoForFunction (target, addr, function_info))
- {
- // shortcut return for functions that have no compact unwind
- if (function_info.encoding == 0)
- return false;
-
- ArchSpec arch;
- if (m_objfile.GetArchitecture (arch))
- {
-
- Log *log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_UNWIND));
- if (log && log->GetVerbose())
- {
- StreamString strm;
- addr.Dump (&strm, NULL, Address::DumpStyle::DumpStyleResolvedDescriptionNoFunctionArguments, Address::DumpStyle::DumpStyleFileAddress, arch.GetAddressByteSize());
- log->Printf ("Got compact unwind encoding 0x%x for function %s", function_info.encoding, strm.GetData());
- }
-
- if (function_info.valid_range_offset_start != 0 && function_info.valid_range_offset_end != 0)
- {
- SectionList *sl = m_objfile.GetSectionList ();
- if (sl)
- {
- addr_t func_range_start_file_addr =
- function_info.valid_range_offset_start + m_objfile.GetHeaderAddress().GetFileAddress();
- AddressRange func_range (func_range_start_file_addr,
- function_info.valid_range_offset_end - function_info.valid_range_offset_start,
- sl);
- unwind_plan.SetPlanValidAddressRange (func_range);
- }
- }
+CompactUnwindInfo::~CompactUnwindInfo() {}
- if (arch.GetTriple().getArch() == llvm::Triple::x86_64)
- {
- return CreateUnwindPlan_x86_64 (target, function_info, unwind_plan, addr);
- }
- if (arch.GetTriple().getArch() == llvm::Triple::aarch64)
- {
- return CreateUnwindPlan_arm64 (target, function_info, unwind_plan, addr);
- }
- if (arch.GetTriple().getArch() == llvm::Triple::x86)
- {
- return CreateUnwindPlan_i386 (target, function_info, unwind_plan, addr);
- }
- if (arch.GetTriple().getArch() == llvm::Triple::arm || arch.GetTriple().getArch() == llvm::Triple::thumb)
- {
- return CreateUnwindPlan_armv7 (target, function_info, unwind_plan, addr);
- }
- }
- }
+bool CompactUnwindInfo::GetUnwindPlan(Target &target, Address addr,
+ UnwindPlan &unwind_plan) {
+ if (!IsValid(target.GetProcessSP())) {
return false;
+ }
+ FunctionInfo function_info;
+ if (GetCompactUnwindInfoForFunction(target, addr, function_info)) {
+ // shortcut return for functions that have no compact unwind
+ if (function_info.encoding == 0)
+ return false;
+
+ ArchSpec arch;
+ if (m_objfile.GetArchitecture(arch)) {
+
+ Log *log(GetLogIfAllCategoriesSet(LIBLLDB_LOG_UNWIND));
+ if (log && log->GetVerbose()) {
+ StreamString strm;
+ addr.Dump(
+ &strm, NULL,
+ Address::DumpStyle::DumpStyleResolvedDescriptionNoFunctionArguments,
+ Address::DumpStyle::DumpStyleFileAddress,
+ arch.GetAddressByteSize());
+ log->Printf("Got compact unwind encoding 0x%x for function %s",
+ function_info.encoding, strm.GetData());
+ }
+
+ if (function_info.valid_range_offset_start != 0 &&
+ function_info.valid_range_offset_end != 0) {
+ SectionList *sl = m_objfile.GetSectionList();
+ if (sl) {
+ addr_t func_range_start_file_addr =
+ function_info.valid_range_offset_start +
+ m_objfile.GetHeaderAddress().GetFileAddress();
+ AddressRange func_range(func_range_start_file_addr,
+ function_info.valid_range_offset_end -
+ function_info.valid_range_offset_start,
+ sl);
+ unwind_plan.SetPlanValidAddressRange(func_range);
+ }
+ }
+
+ if (arch.GetTriple().getArch() == llvm::Triple::x86_64) {
+ return CreateUnwindPlan_x86_64(target, function_info, unwind_plan,
+ addr);
+ }
+ if (arch.GetTriple().getArch() == llvm::Triple::aarch64) {
+ return CreateUnwindPlan_arm64(target, function_info, unwind_plan, addr);
+ }
+ if (arch.GetTriple().getArch() == llvm::Triple::x86) {
+ return CreateUnwindPlan_i386(target, function_info, unwind_plan, addr);
+ }
+ if (arch.GetTriple().getArch() == llvm::Triple::arm ||
+ arch.GetTriple().getArch() == llvm::Triple::thumb) {
+ return CreateUnwindPlan_armv7(target, function_info, unwind_plan, addr);
+ }
+ }
+ }
+ return false;
}
-bool
-CompactUnwindInfo::IsValid (const ProcessSP &process_sp)
-{
- if (m_section_sp.get() == nullptr)
- return false;
+bool CompactUnwindInfo::IsValid(const ProcessSP &process_sp) {
+ if (m_section_sp.get() == nullptr)
+ return false;
- if (m_indexes_computed == eLazyBoolYes && m_unwindinfo_data_computed)
- return true;
+ if (m_indexes_computed == eLazyBoolYes && m_unwindinfo_data_computed)
+ return true;
- ScanIndex (process_sp);
+ ScanIndex(process_sp);
- return m_indexes_computed == eLazyBoolYes && m_unwindinfo_data_computed;
+ return m_indexes_computed == eLazyBoolYes && m_unwindinfo_data_computed;
}
-void
-CompactUnwindInfo::ScanIndex (const ProcessSP &process_sp)
-{
- std::lock_guard<std::mutex> guard(m_mutex);
- if (m_indexes_computed == eLazyBoolYes && m_unwindinfo_data_computed)
- return;
-
- // We can't read the index for some reason.
- if (m_indexes_computed == eLazyBoolNo)
- {
+void CompactUnwindInfo::ScanIndex(const ProcessSP &process_sp) {
+ std::lock_guard<std::mutex> guard(m_mutex);
+ if (m_indexes_computed == eLazyBoolYes && m_unwindinfo_data_computed)
+ return;
+
+ // We can't read the index for some reason.
+ if (m_indexes_computed == eLazyBoolNo) {
+ return;
+ }
+
+ Log *log(GetLogIfAllCategoriesSet(LIBLLDB_LOG_UNWIND));
+ if (log)
+ m_objfile.GetModule()->LogMessage(
+ log, "Reading compact unwind first-level indexes");
+
+ if (m_unwindinfo_data_computed == false) {
+ if (m_section_sp->IsEncrypted()) {
+ // Can't get section contents of a protected/encrypted section until we
+ // have a live
+ // process and can read them out of memory.
+ if (process_sp.get() == nullptr)
return;
- }
+ m_section_contents_if_encrypted.reset(
+ new DataBufferHeap(m_section_sp->GetByteSize(), 0));
+ Error error;
+ if (process_sp->ReadMemory(
+ m_section_sp->GetLoadBaseAddress(&process_sp->GetTarget()),
+ m_section_contents_if_encrypted->GetBytes(),
+ m_section_sp->GetByteSize(),
+ error) == m_section_sp->GetByteSize() &&
+ error.Success()) {
+ m_unwindinfo_data.SetAddressByteSize(
+ process_sp->GetTarget().GetArchitecture().GetAddressByteSize());
+ m_unwindinfo_data.SetByteOrder(
+ process_sp->GetTarget().GetArchitecture().GetByteOrder());
+ m_unwindinfo_data.SetData(m_section_contents_if_encrypted, 0);
+ }
+ } else {
+ m_objfile.ReadSectionData(m_section_sp.get(), m_unwindinfo_data);
+ }
+ if (m_unwindinfo_data.GetByteSize() != m_section_sp->GetByteSize())
+ return;
+ m_unwindinfo_data_computed = true;
+ }
- Log *log (GetLogIfAllCategoriesSet (LIBLLDB_LOG_UNWIND));
- if (log)
- m_objfile.GetModule()->LogMessage(log, "Reading compact unwind first-level indexes");
-
- if (m_unwindinfo_data_computed == false)
- {
- if (m_section_sp->IsEncrypted())
- {
- // Can't get section contents of a protected/encrypted section until we have a live
- // process and can read them out of memory.
- if (process_sp.get() == nullptr)
- return;
- m_section_contents_if_encrypted.reset (new DataBufferHeap (m_section_sp->GetByteSize(), 0));
- Error error;
- if (process_sp->ReadMemory (
- m_section_sp->GetLoadBaseAddress (&process_sp->GetTarget()),
- m_section_contents_if_encrypted->GetBytes(),
- m_section_sp->GetByteSize(), error) == m_section_sp->GetByteSize() && error.Success())
- {
- m_unwindinfo_data.SetAddressByteSize (process_sp->GetTarget().GetArchitecture().GetAddressByteSize());
- m_unwindinfo_data.SetByteOrder (process_sp->GetTarget().GetArchitecture().GetByteOrder());
- m_unwindinfo_data.SetData (m_section_contents_if_encrypted, 0);
- }
- }
- else
- {
- m_objfile.ReadSectionData (m_section_sp.get(), m_unwindinfo_data);
- }
- if (m_unwindinfo_data.GetByteSize() != m_section_sp->GetByteSize())
- return;
- m_unwindinfo_data_computed = true;
- }
-
- if (m_unwindinfo_data.GetByteSize() > 0)
- {
- offset_t offset = 0;
-
- // struct unwind_info_section_header
- // {
- // uint32_t version; // UNWIND_SECTION_VERSION
- // uint32_t commonEncodingsArraySectionOffset;
- // uint32_t commonEncodingsArrayCount;
- // uint32_t personalityArraySectionOffset;
- // uint32_t personalityArrayCount;
- // uint32_t indexSectionOffset;
- // uint32_t indexCount;
-
- m_unwind_header.version = m_unwindinfo_data.GetU32(&offset);
- m_unwind_header.common_encodings_array_offset = m_unwindinfo_data.GetU32(&offset);
- m_unwind_header.common_encodings_array_count = m_unwindinfo_data.GetU32(&offset);
- m_unwind_header.personality_array_offset = m_unwindinfo_data.GetU32(&offset);
- m_unwind_header.personality_array_count = m_unwindinfo_data.GetU32(&offset);
- uint32_t indexSectionOffset = m_unwindinfo_data.GetU32(&offset);
-
- uint32_t indexCount = m_unwindinfo_data.GetU32(&offset);
-
- if (m_unwind_header.common_encodings_array_offset > m_unwindinfo_data.GetByteSize()
- || m_unwind_header.personality_array_offset > m_unwindinfo_data.GetByteSize()
- || indexSectionOffset > m_unwindinfo_data.GetByteSize()
- || offset > m_unwindinfo_data.GetByteSize())
- {
- Host::SystemLog (Host::eSystemLogError,
- "error: Invalid offset encountered in compact unwind info, skipping\n");
- // don't trust anything from this compact_unwind section if it looks
- // blatantly invalid data in the header.
- m_indexes_computed = eLazyBoolNo;
- return;
- }
-
- // Parse the basic information from the indexes
- // We wait to scan the second level page info until it's needed
+ if (m_unwindinfo_data.GetByteSize() > 0) {
+ offset_t offset = 0;
- // struct unwind_info_section_header_index_entry
- // {
- // uint32_t functionOffset;
- // uint32_t secondLevelPagesSectionOffset;
- // uint32_t lsdaIndexArraySectionOffset;
- // };
-
- bool clear_address_zeroth_bit = false;
- ArchSpec arch;
- if (m_objfile.GetArchitecture (arch))
- {
- if (arch.GetTriple().getArch() == llvm::Triple::arm || arch.GetTriple().getArch() == llvm::Triple::thumb)
- clear_address_zeroth_bit = true;
- }
+ // struct unwind_info_section_header
+ // {
+ // uint32_t version; // UNWIND_SECTION_VERSION
+ // uint32_t commonEncodingsArraySectionOffset;
+ // uint32_t commonEncodingsArrayCount;
+ // uint32_t personalityArraySectionOffset;
+ // uint32_t personalityArrayCount;
+ // uint32_t indexSectionOffset;
+ // uint32_t indexCount;
+
+ m_unwind_header.version = m_unwindinfo_data.GetU32(&offset);
+ m_unwind_header.common_encodings_array_offset =
+ m_unwindinfo_data.GetU32(&offset);
+ m_unwind_header.common_encodings_array_count =
+ m_unwindinfo_data.GetU32(&offset);
+ m_unwind_header.personality_array_offset =
+ m_unwindinfo_data.GetU32(&offset);
+ m_unwind_header.personality_array_count = m_unwindinfo_data.GetU32(&offset);
+ uint32_t indexSectionOffset = m_unwindinfo_data.GetU32(&offset);
+
+ uint32_t indexCount = m_unwindinfo_data.GetU32(&offset);
+
+ if (m_unwind_header.common_encodings_array_offset >
+ m_unwindinfo_data.GetByteSize() ||
+ m_unwind_header.personality_array_offset >
+ m_unwindinfo_data.GetByteSize() ||
+ indexSectionOffset > m_unwindinfo_data.GetByteSize() ||
+ offset > m_unwindinfo_data.GetByteSize()) {
+ Host::SystemLog(Host::eSystemLogError, "error: Invalid offset "
+ "encountered in compact unwind "
+ "info, skipping\n");
+ // don't trust anything from this compact_unwind section if it looks
+ // blatantly invalid data in the header.
+ m_indexes_computed = eLazyBoolNo;
+ return;
+ }
- offset = indexSectionOffset;
- for (uint32_t idx = 0; idx < indexCount; idx++)
- {
- uint32_t function_offset = m_unwindinfo_data.GetU32(&offset); // functionOffset
- uint32_t second_level_offset = m_unwindinfo_data.GetU32(&offset); // secondLevelPagesSectionOffset
- uint32_t lsda_offset = m_unwindinfo_data.GetU32(&offset); // lsdaIndexArraySectionOffset
-
- if (second_level_offset > m_section_sp->GetByteSize() || lsda_offset > m_section_sp->GetByteSize())
- {
- m_indexes_computed = eLazyBoolNo;
- }
+ // Parse the basic information from the indexes
+ // We wait to scan the second level page info until it's needed
- if (clear_address_zeroth_bit)
- function_offset &= ~1ull;
+ // struct unwind_info_section_header_index_entry
+ // {
+ // uint32_t functionOffset;
+ // uint32_t secondLevelPagesSectionOffset;
+ // uint32_t lsdaIndexArraySectionOffset;
+ // };
+
+ bool clear_address_zeroth_bit = false;
+ ArchSpec arch;
+ if (m_objfile.GetArchitecture(arch)) {
+ if (arch.GetTriple().getArch() == llvm::Triple::arm ||
+ arch.GetTriple().getArch() == llvm::Triple::thumb)
+ clear_address_zeroth_bit = true;
+ }
+
+ offset = indexSectionOffset;
+ for (uint32_t idx = 0; idx < indexCount; idx++) {
+ uint32_t function_offset =
+ m_unwindinfo_data.GetU32(&offset); // functionOffset
+ uint32_t second_level_offset =
+ m_unwindinfo_data.GetU32(&offset); // secondLevelPagesSectionOffset
+ uint32_t lsda_offset =
+ m_unwindinfo_data.GetU32(&offset); // lsdaIndexArraySectionOffset
- UnwindIndex this_index;
- this_index.function_offset = function_offset;
- this_index.second_level = second_level_offset;
- this_index.lsda_array_start = lsda_offset;
-
- if (m_indexes.size() > 0)
- {
- m_indexes[m_indexes.size() - 1].lsda_array_end = lsda_offset;
- }
+ if (second_level_offset > m_section_sp->GetByteSize() ||
+ lsda_offset > m_section_sp->GetByteSize()) {
+ m_indexes_computed = eLazyBoolNo;
+ }
- if (second_level_offset == 0)
- {
- this_index.sentinal_entry = true;
- }
+ if (clear_address_zeroth_bit)
+ function_offset &= ~1ull;
- m_indexes.push_back (this_index);
- }
- m_indexes_computed = eLazyBoolYes;
- }
- else
- {
- m_indexes_computed = eLazyBoolNo;
- }
+ UnwindIndex this_index;
+ this_index.function_offset = function_offset;
+ this_index.second_level = second_level_offset;
+ this_index.lsda_array_start = lsda_offset;
+
+ if (m_indexes.size() > 0) {
+ m_indexes[m_indexes.size() - 1].lsda_array_end = lsda_offset;
+ }
+
+ if (second_level_offset == 0) {
+ this_index.sentinal_entry = true;
+ }
+
+ m_indexes.push_back(this_index);
+ }
+ m_indexes_computed = eLazyBoolYes;
+ } else {
+ m_indexes_computed = eLazyBoolNo;
+ }
}
-uint32_t
-CompactUnwindInfo::GetLSDAForFunctionOffset (uint32_t lsda_offset, uint32_t lsda_count, uint32_t function_offset)
-{
- // struct unwind_info_section_header_lsda_index_entry
- // {
- // uint32_t functionOffset;
- // uint32_t lsdaOffset;
- // };
-
- offset_t first_entry = lsda_offset;
- uint32_t low = 0;
- uint32_t high = lsda_count;
- while (low < high)
- {
- uint32_t mid = (low + high) / 2;
- offset_t offset = first_entry + (mid * 8);
- uint32_t mid_func_offset = m_unwindinfo_data.GetU32(&offset); // functionOffset
- uint32_t mid_lsda_offset = m_unwindinfo_data.GetU32(&offset); // lsdaOffset
- if (mid_func_offset == function_offset)
- {
- return mid_lsda_offset;
- }
- if (mid_func_offset < function_offset)
- {
- low = mid + 1;
- }
- else
- {
- high = mid;
- }
+uint32_t CompactUnwindInfo::GetLSDAForFunctionOffset(uint32_t lsda_offset,
+ uint32_t lsda_count,
+ uint32_t function_offset) {
+ // struct unwind_info_section_header_lsda_index_entry
+ // {
+ // uint32_t functionOffset;
+ // uint32_t lsdaOffset;
+ // };
+
+ offset_t first_entry = lsda_offset;
+ uint32_t low = 0;
+ uint32_t high = lsda_count;
+ while (low < high) {
+ uint32_t mid = (low + high) / 2;
+ offset_t offset = first_entry + (mid * 8);
+ uint32_t mid_func_offset =
+ m_unwindinfo_data.GetU32(&offset); // functionOffset
+ uint32_t mid_lsda_offset = m_unwindinfo_data.GetU32(&offset); // lsdaOffset
+ if (mid_func_offset == function_offset) {
+ return mid_lsda_offset;
+ }
+ if (mid_func_offset < function_offset) {
+ low = mid + 1;
+ } else {
+ high = mid;
}
- return 0;
+ }
+ return 0;
}
-lldb::offset_t
-CompactUnwindInfo::BinarySearchRegularSecondPage (uint32_t entry_page_offset, uint32_t entry_count, uint32_t function_offset, uint32_t *entry_func_start_offset, uint32_t *entry_func_end_offset)
-{
- // typedef uint32_t compact_unwind_encoding_t;
- // struct unwind_info_regular_second_level_entry
- // {
- // uint32_t functionOffset;
- // compact_unwind_encoding_t encoding;
-
- offset_t first_entry = entry_page_offset;
-
- uint32_t low = 0;
- uint32_t high = entry_count;
- uint32_t last = high - 1;
- while (low < high)
- {
- uint32_t mid = (low + high) / 2;
- offset_t offset = first_entry + (mid * 8);
- uint32_t mid_func_offset = m_unwindinfo_data.GetU32(&offset); // functionOffset
- uint32_t next_func_offset = 0;
- if (mid < last)
- {
- offset = first_entry + ((mid + 1) * 8);
- next_func_offset = m_unwindinfo_data.GetU32(&offset); // functionOffset
- }
- if (mid_func_offset <= function_offset)
- {
- if (mid == last || (next_func_offset > function_offset))
- {
- if (entry_func_start_offset)
- *entry_func_start_offset = mid_func_offset;
- if (mid != last && entry_func_end_offset)
- *entry_func_end_offset = next_func_offset;
- return first_entry + (mid * 8);
- }
- else
- {
- low = mid + 1;
- }
- }
- else
- {
- high = mid;
- }
+lldb::offset_t CompactUnwindInfo::BinarySearchRegularSecondPage(
+ uint32_t entry_page_offset, uint32_t entry_count, uint32_t function_offset,
+ uint32_t *entry_func_start_offset, uint32_t *entry_func_end_offset) {
+ // typedef uint32_t compact_unwind_encoding_t;
+ // struct unwind_info_regular_second_level_entry
+ // {
+ // uint32_t functionOffset;
+ // compact_unwind_encoding_t encoding;
+
+ offset_t first_entry = entry_page_offset;
+
+ uint32_t low = 0;
+ uint32_t high = entry_count;
+ uint32_t last = high - 1;
+ while (low < high) {
+ uint32_t mid = (low + high) / 2;
+ offset_t offset = first_entry + (mid * 8);
+ uint32_t mid_func_offset =
+ m_unwindinfo_data.GetU32(&offset); // functionOffset
+ uint32_t next_func_offset = 0;
+ if (mid < last) {
+ offset = first_entry + ((mid + 1) * 8);
+ next_func_offset = m_unwindinfo_data.GetU32(&offset); // functionOffset
+ }
+ if (mid_func_offset <= function_offset) {
+ if (mid == last || (next_func_offset > function_offset)) {
+ if (entry_func_start_offset)
+ *entry_func_start_offset = mid_func_offset;
+ if (mid != last && entry_func_end_offset)
+ *entry_func_end_offset = next_func_offset;
+ return first_entry + (mid * 8);
+ } else {
+ low = mid + 1;
+ }
+ } else {
+ high = mid;
}
- return LLDB_INVALID_OFFSET;
+ }
+ return LLDB_INVALID_OFFSET;
}
-uint32_t
-CompactUnwindInfo::BinarySearchCompressedSecondPage (uint32_t entry_page_offset, uint32_t entry_count, uint32_t function_offset_to_find, uint32_t function_offset_base, uint32_t *entry_func_start_offset, uint32_t *entry_func_end_offset)
-{
- offset_t first_entry = entry_page_offset;
-
- uint32_t low = 0;
- uint32_t high = entry_count;
- uint32_t last = high - 1;
- while (low < high)
- {
- uint32_t mid = (low + high) / 2;
- offset_t offset = first_entry + (mid * 4);
- uint32_t entry = m_unwindinfo_data.GetU32(&offset); // entry
- uint32_t mid_func_offset = UNWIND_INFO_COMPRESSED_ENTRY_FUNC_OFFSET (entry);
- mid_func_offset += function_offset_base;
- uint32_t next_func_offset = 0;
- if (mid < last)
- {
- offset = first_entry + ((mid + 1) * 4);
- uint32_t next_entry = m_unwindinfo_data.GetU32(&offset); // entry
- next_func_offset = UNWIND_INFO_COMPRESSED_ENTRY_FUNC_OFFSET (next_entry);
- next_func_offset += function_offset_base;
- }
- if (mid_func_offset <= function_offset_to_find)
- {
- if (mid == last || (next_func_offset > function_offset_to_find))
- {
- if (entry_func_start_offset)
- *entry_func_start_offset = mid_func_offset;
- if (mid != last && entry_func_end_offset)
- *entry_func_end_offset = next_func_offset;
- return UNWIND_INFO_COMPRESSED_ENTRY_ENCODING_INDEX (entry);
- }
- else
- {
- low = mid + 1;
- }
- }
- else
- {
- high = mid;
- }
+uint32_t CompactUnwindInfo::BinarySearchCompressedSecondPage(
+ uint32_t entry_page_offset, uint32_t entry_count,
+ uint32_t function_offset_to_find, uint32_t function_offset_base,
+ uint32_t *entry_func_start_offset, uint32_t *entry_func_end_offset) {
+ offset_t first_entry = entry_page_offset;
+
+ uint32_t low = 0;
+ uint32_t high = entry_count;
+ uint32_t last = high - 1;
+ while (low < high) {
+ uint32_t mid = (low + high) / 2;
+ offset_t offset = first_entry + (mid * 4);
+ uint32_t entry = m_unwindinfo_data.GetU32(&offset); // entry
+ uint32_t mid_func_offset = UNWIND_INFO_COMPRESSED_ENTRY_FUNC_OFFSET(entry);
+ mid_func_offset += function_offset_base;
+ uint32_t next_func_offset = 0;
+ if (mid < last) {
+ offset = first_entry + ((mid + 1) * 4);
+ uint32_t next_entry = m_unwindinfo_data.GetU32(&offset); // entry
+ next_func_offset = UNWIND_INFO_COMPRESSED_ENTRY_FUNC_OFFSET(next_entry);
+ next_func_offset += function_offset_base;
+ }
+ if (mid_func_offset <= function_offset_to_find) {
+ if (mid == last || (next_func_offset > function_offset_to_find)) {
+ if (entry_func_start_offset)
+ *entry_func_start_offset = mid_func_offset;
+ if (mid != last && entry_func_end_offset)
+ *entry_func_end_offset = next_func_offset;
+ return UNWIND_INFO_COMPRESSED_ENTRY_ENCODING_INDEX(entry);
+ } else {
+ low = mid + 1;
+ }
+ } else {
+ high = mid;
}
+ }
- return UINT32_MAX;
+ return UINT32_MAX;
}
-bool
-CompactUnwindInfo::GetCompactUnwindInfoForFunction (Target &target, Address address, FunctionInfo &unwind_info)
-{
- unwind_info.encoding = 0;
- unwind_info.lsda_address.Clear();
- unwind_info.personality_ptr_address.Clear();
+bool CompactUnwindInfo::GetCompactUnwindInfoForFunction(
+ Target &target, Address address, FunctionInfo &unwind_info) {
+ unwind_info.encoding = 0;
+ unwind_info.lsda_address.Clear();
+ unwind_info.personality_ptr_address.Clear();
- if (!IsValid (target.GetProcessSP()))
- return false;
+ if (!IsValid(target.GetProcessSP()))
+ return false;
- addr_t text_section_file_address = LLDB_INVALID_ADDRESS;
- SectionList *sl = m_objfile.GetSectionList ();
- if (sl)
- {
- SectionSP text_sect = sl->FindSectionByType (eSectionTypeCode, true);
- if (text_sect.get())
- {
- text_section_file_address = text_sect->GetFileAddress();
- }
+ addr_t text_section_file_address = LLDB_INVALID_ADDRESS;
+ SectionList *sl = m_objfile.GetSectionList();
+ if (sl) {
+ SectionSP text_sect = sl->FindSectionByType(eSectionTypeCode, true);
+ if (text_sect.get()) {
+ text_section_file_address = text_sect->GetFileAddress();
}
- if (text_section_file_address == LLDB_INVALID_ADDRESS)
- return false;
+ }
+ if (text_section_file_address == LLDB_INVALID_ADDRESS)
+ return false;
- addr_t function_offset = address.GetFileAddress() - m_objfile.GetHeaderAddress().GetFileAddress();
+ addr_t function_offset =
+ address.GetFileAddress() - m_objfile.GetHeaderAddress().GetFileAddress();
- UnwindIndex key;
- key.function_offset = function_offset;
+ UnwindIndex key;
+ key.function_offset = function_offset;
- std::vector<UnwindIndex>::const_iterator it;
- it = std::lower_bound (m_indexes.begin(), m_indexes.end(), key);
- if (it == m_indexes.end())
- {
- return false;
- }
+ std::vector<UnwindIndex>::const_iterator it;
+ it = std::lower_bound(m_indexes.begin(), m_indexes.end(), key);
+ if (it == m_indexes.end()) {
+ return false;
+ }
- if (it->function_offset != key.function_offset)
- {
- if (it != m_indexes.begin())
- --it;
- }
+ if (it->function_offset != key.function_offset) {
+ if (it != m_indexes.begin())
+ --it;
+ }
- if (it->sentinal_entry == true)
- {
- return false;
- }
+ if (it->sentinal_entry == true) {
+ return false;
+ }
- auto next_it = it + 1;
- if (next_it != m_indexes.end())
- {
- // initialize the function offset end range to be the start of the
- // next index offset. If we find an entry which is at the end of
- // the index table, this will establish the range end.
- unwind_info.valid_range_offset_end = next_it->function_offset;
- }
-
- offset_t second_page_offset = it->second_level;
- offset_t lsda_array_start = it->lsda_array_start;
- offset_t lsda_array_count = (it->lsda_array_end - it->lsda_array_start) / 8;
-
- offset_t offset = second_page_offset;
- uint32_t kind = m_unwindinfo_data.GetU32(&offset); // UNWIND_SECOND_LEVEL_REGULAR or UNWIND_SECOND_LEVEL_COMPRESSED
-
- if (kind == UNWIND_SECOND_LEVEL_REGULAR)
- {
- // struct unwind_info_regular_second_level_page_header
- // {
- // uint32_t kind; // UNWIND_SECOND_LEVEL_REGULAR
- // uint16_t entryPageOffset;
- // uint16_t entryCount;
-
- // typedef uint32_t compact_unwind_encoding_t;
- // struct unwind_info_regular_second_level_entry
- // {
- // uint32_t functionOffset;
- // compact_unwind_encoding_t encoding;
-
- uint16_t entry_page_offset = m_unwindinfo_data.GetU16(&offset); // entryPageOffset
- uint16_t entry_count = m_unwindinfo_data.GetU16(&offset); // entryCount
-
- offset_t entry_offset = BinarySearchRegularSecondPage (second_page_offset + entry_page_offset, entry_count, function_offset, &unwind_info.valid_range_offset_start, &unwind_info.valid_range_offset_end);
- if (entry_offset == LLDB_INVALID_OFFSET)
- {
- return false;
- }
- entry_offset += 4; // skip over functionOffset
- unwind_info.encoding = m_unwindinfo_data.GetU32(&entry_offset); // encoding
- if (unwind_info.encoding & UNWIND_HAS_LSDA)
- {
- SectionList *sl = m_objfile.GetSectionList ();
- if (sl)
- {
- uint32_t lsda_offset = GetLSDAForFunctionOffset (lsda_array_start, lsda_array_count, function_offset);
- addr_t objfile_header_file_address = m_objfile.GetHeaderAddress().GetFileAddress();
- unwind_info.lsda_address.ResolveAddressUsingFileSections (objfile_header_file_address + lsda_offset, sl);
- }
- }
- if (unwind_info.encoding & UNWIND_PERSONALITY_MASK)
- {
- uint32_t personality_index = EXTRACT_BITS (unwind_info.encoding, UNWIND_PERSONALITY_MASK);
-
- if (personality_index > 0)
- {
- personality_index--;
- if (personality_index < m_unwind_header.personality_array_count)
- {
- offset_t offset = m_unwind_header.personality_array_offset;
- offset += 4 * personality_index;
- SectionList *sl = m_objfile.GetSectionList ();
- if (sl)
- {
- uint32_t personality_offset = m_unwindinfo_data.GetU32(&offset);
- addr_t objfile_header_file_address = m_objfile.GetHeaderAddress().GetFileAddress();
- unwind_info.personality_ptr_address.ResolveAddressUsingFileSections (objfile_header_file_address + personality_offset, sl);
- }
- }
- }
- }
- return true;
- }
- else if (kind == UNWIND_SECOND_LEVEL_COMPRESSED)
- {
- // struct unwind_info_compressed_second_level_page_header
- // {
- // uint32_t kind; // UNWIND_SECOND_LEVEL_COMPRESSED
- // uint16_t entryPageOffset; // offset from this 2nd lvl page idx to array of entries
- // // (an entry has a function offset and index into the encodings)
- // // NB function offset from the entry in the compressed page
- // // must be added to the index's functionOffset value.
- // uint16_t entryCount;
- // uint16_t encodingsPageOffset; // offset from this 2nd lvl page idx to array of encodings
- // uint16_t encodingsCount;
-
- uint16_t entry_page_offset = m_unwindinfo_data.GetU16(&offset); // entryPageOffset
- uint16_t entry_count = m_unwindinfo_data.GetU16(&offset); // entryCount
- uint16_t encodings_page_offset = m_unwindinfo_data.GetU16(&offset); // encodingsPageOffset
- uint16_t encodings_count = m_unwindinfo_data.GetU16(&offset); // encodingsCount
-
- uint32_t encoding_index = BinarySearchCompressedSecondPage (second_page_offset + entry_page_offset, entry_count, function_offset, it->function_offset, &unwind_info.valid_range_offset_start, &unwind_info.valid_range_offset_end);
- if (encoding_index == UINT32_MAX || encoding_index >= encodings_count + m_unwind_header.common_encodings_array_count)
- {
- return false;
- }
- uint32_t encoding = 0;
- if (encoding_index < m_unwind_header.common_encodings_array_count)
- {
- offset = m_unwind_header.common_encodings_array_offset + (encoding_index * sizeof (uint32_t));
- encoding = m_unwindinfo_data.GetU32(&offset); // encoding entry from the commonEncodingsArray
- }
- else
- {
- uint32_t page_specific_entry_index = encoding_index - m_unwind_header.common_encodings_array_count;
- offset = second_page_offset + encodings_page_offset + (page_specific_entry_index * sizeof (uint32_t));
- encoding = m_unwindinfo_data.GetU32(&offset); // encoding entry from the page-specific encoding array
- }
- if (encoding == 0)
- return false;
+ auto next_it = it + 1;
+ if (next_it != m_indexes.end()) {
+ // initialize the function offset end range to be the start of the
+ // next index offset. If we find an entry which is at the end of
+ // the index table, this will establish the range end.
+ unwind_info.valid_range_offset_end = next_it->function_offset;
+ }
+
+ offset_t second_page_offset = it->second_level;
+ offset_t lsda_array_start = it->lsda_array_start;
+ offset_t lsda_array_count = (it->lsda_array_end - it->lsda_array_start) / 8;
+
+ offset_t offset = second_page_offset;
+ uint32_t kind = m_unwindinfo_data.GetU32(
+ &offset); // UNWIND_SECOND_LEVEL_REGULAR or UNWIND_SECOND_LEVEL_COMPRESSED
- unwind_info.encoding = encoding;
- if (unwind_info.encoding & UNWIND_HAS_LSDA)
- {
- SectionList *sl = m_objfile.GetSectionList ();
- if (sl)
- {
- uint32_t lsda_offset = GetLSDAForFunctionOffset (lsda_array_start, lsda_array_count, function_offset);
- addr_t objfile_header_file_address = m_objfile.GetHeaderAddress().GetFileAddress();
- unwind_info.lsda_address.ResolveAddressUsingFileSections (objfile_header_file_address + lsda_offset, sl);
- }
+ if (kind == UNWIND_SECOND_LEVEL_REGULAR) {
+ // struct unwind_info_regular_second_level_page_header
+ // {
+ // uint32_t kind; // UNWIND_SECOND_LEVEL_REGULAR
+ // uint16_t entryPageOffset;
+ // uint16_t entryCount;
+
+ // typedef uint32_t compact_unwind_encoding_t;
+ // struct unwind_info_regular_second_level_entry
+ // {
+ // uint32_t functionOffset;
+ // compact_unwind_encoding_t encoding;
+
+ uint16_t entry_page_offset =
+ m_unwindinfo_data.GetU16(&offset); // entryPageOffset
+ uint16_t entry_count = m_unwindinfo_data.GetU16(&offset); // entryCount
+
+ offset_t entry_offset = BinarySearchRegularSecondPage(
+ second_page_offset + entry_page_offset, entry_count, function_offset,
+ &unwind_info.valid_range_offset_start,
+ &unwind_info.valid_range_offset_end);
+ if (entry_offset == LLDB_INVALID_OFFSET) {
+ return false;
+ }
+ entry_offset += 4; // skip over functionOffset
+ unwind_info.encoding = m_unwindinfo_data.GetU32(&entry_offset); // encoding
+ if (unwind_info.encoding & UNWIND_HAS_LSDA) {
+ SectionList *sl = m_objfile.GetSectionList();
+ if (sl) {
+ uint32_t lsda_offset = GetLSDAForFunctionOffset(
+ lsda_array_start, lsda_array_count, function_offset);
+ addr_t objfile_header_file_address =
+ m_objfile.GetHeaderAddress().GetFileAddress();
+ unwind_info.lsda_address.ResolveAddressUsingFileSections(
+ objfile_header_file_address + lsda_offset, sl);
+ }
+ }
+ if (unwind_info.encoding & UNWIND_PERSONALITY_MASK) {
+ uint32_t personality_index =
+ EXTRACT_BITS(unwind_info.encoding, UNWIND_PERSONALITY_MASK);
+
+ if (personality_index > 0) {
+ personality_index--;
+ if (personality_index < m_unwind_header.personality_array_count) {
+ offset_t offset = m_unwind_header.personality_array_offset;
+ offset += 4 * personality_index;
+ SectionList *sl = m_objfile.GetSectionList();
+ if (sl) {
+ uint32_t personality_offset = m_unwindinfo_data.GetU32(&offset);
+ addr_t objfile_header_file_address =
+ m_objfile.GetHeaderAddress().GetFileAddress();
+ unwind_info.personality_ptr_address.ResolveAddressUsingFileSections(
+ objfile_header_file_address + personality_offset, sl);
+ }
}
- if (unwind_info.encoding & UNWIND_PERSONALITY_MASK)
- {
- uint32_t personality_index = EXTRACT_BITS (unwind_info.encoding, UNWIND_PERSONALITY_MASK);
-
- if (personality_index > 0)
- {
- personality_index--;
- if (personality_index < m_unwind_header.personality_array_count)
- {
- offset_t offset = m_unwind_header.personality_array_offset;
- offset += 4 * personality_index;
- SectionList *sl = m_objfile.GetSectionList ();
- if (sl)
- {
- uint32_t personality_offset = m_unwindinfo_data.GetU32(&offset);
- addr_t objfile_header_file_address = m_objfile.GetHeaderAddress().GetFileAddress();
- unwind_info.personality_ptr_address.ResolveAddressUsingFileSections (objfile_header_file_address + personality_offset, sl);
- }
- }
- }
+ }
+ }
+ return true;
+ } else if (kind == UNWIND_SECOND_LEVEL_COMPRESSED) {
+ // struct unwind_info_compressed_second_level_page_header
+ // {
+ // uint32_t kind; // UNWIND_SECOND_LEVEL_COMPRESSED
+ // uint16_t entryPageOffset; // offset from this 2nd lvl page
+ // idx to array of entries
+ // // (an entry has a function
+ // offset and index into the
+ // encodings)
+ // // NB function offset from the
+ // entry in the compressed page
+ // // must be added to the index's
+ // functionOffset value.
+ // uint16_t entryCount;
+ // uint16_t encodingsPageOffset; // offset from this 2nd lvl page
+ // idx to array of encodings
+ // uint16_t encodingsCount;
+
+ uint16_t entry_page_offset =
+ m_unwindinfo_data.GetU16(&offset); // entryPageOffset
+ uint16_t entry_count = m_unwindinfo_data.GetU16(&offset); // entryCount
+ uint16_t encodings_page_offset =
+ m_unwindinfo_data.GetU16(&offset); // encodingsPageOffset
+ uint16_t encodings_count =
+ m_unwindinfo_data.GetU16(&offset); // encodingsCount
+
+ uint32_t encoding_index = BinarySearchCompressedSecondPage(
+ second_page_offset + entry_page_offset, entry_count, function_offset,
+ it->function_offset, &unwind_info.valid_range_offset_start,
+ &unwind_info.valid_range_offset_end);
+ if (encoding_index == UINT32_MAX ||
+ encoding_index >=
+ encodings_count + m_unwind_header.common_encodings_array_count) {
+ return false;
+ }
+ uint32_t encoding = 0;
+ if (encoding_index < m_unwind_header.common_encodings_array_count) {
+ offset = m_unwind_header.common_encodings_array_offset +
+ (encoding_index * sizeof(uint32_t));
+ encoding = m_unwindinfo_data.GetU32(
+ &offset); // encoding entry from the commonEncodingsArray
+ } else {
+ uint32_t page_specific_entry_index =
+ encoding_index - m_unwind_header.common_encodings_array_count;
+ offset = second_page_offset + encodings_page_offset +
+ (page_specific_entry_index * sizeof(uint32_t));
+ encoding = m_unwindinfo_data.GetU32(
+ &offset); // encoding entry from the page-specific encoding array
+ }
+ if (encoding == 0)
+ return false;
+
+ unwind_info.encoding = encoding;
+ if (unwind_info.encoding & UNWIND_HAS_LSDA) {
+ SectionList *sl = m_objfile.GetSectionList();
+ if (sl) {
+ uint32_t lsda_offset = GetLSDAForFunctionOffset(
+ lsda_array_start, lsda_array_count, function_offset);
+ addr_t objfile_header_file_address =
+ m_objfile.GetHeaderAddress().GetFileAddress();
+ unwind_info.lsda_address.ResolveAddressUsingFileSections(
+ objfile_header_file_address + lsda_offset, sl);
+ }
+ }
+ if (unwind_info.encoding & UNWIND_PERSONALITY_MASK) {
+ uint32_t personality_index =
+ EXTRACT_BITS(unwind_info.encoding, UNWIND_PERSONALITY_MASK);
+
+ if (personality_index > 0) {
+ personality_index--;
+ if (personality_index < m_unwind_header.personality_array_count) {
+ offset_t offset = m_unwind_header.personality_array_offset;
+ offset += 4 * personality_index;
+ SectionList *sl = m_objfile.GetSectionList();
+ if (sl) {
+ uint32_t personality_offset = m_unwindinfo_data.GetU32(&offset);
+ addr_t objfile_header_file_address =
+ m_objfile.GetHeaderAddress().GetFileAddress();
+ unwind_info.personality_ptr_address.ResolveAddressUsingFileSections(
+ objfile_header_file_address + personality_offset, sl);
+ }
}
- return true;
+ }
}
- return false;
+ return true;
+ }
+ return false;
}
enum x86_64_eh_regnum {
- rax = 0,
- rdx = 1,
- rcx = 2,
- rbx = 3,
- rsi = 4,
- rdi = 5,
- rbp = 6,
- rsp = 7,
- r8 = 8,
- r9 = 9,
- r10 = 10,
- r11 = 11,
- r12 = 12,
- r13 = 13,
- r14 = 14,
- r15 = 15,
- rip = 16 // this is officially the Return Address register number, but close enough
+ rax = 0,
+ rdx = 1,
+ rcx = 2,
+ rbx = 3,
+ rsi = 4,
+ rdi = 5,
+ rbp = 6,
+ rsp = 7,
+ r8 = 8,
+ r9 = 9,
+ r10 = 10,
+ r11 = 11,
+ r12 = 12,
+ r13 = 13,
+ r14 = 14,
+ r15 = 15,
+ rip = 16 // this is officially the Return Address register number, but close
+ // enough
};
// Convert the compact_unwind_info.h register numbering scheme
// to eRegisterKindEHFrame (eh_frame) register numbering scheme.
-uint32_t
-translate_to_eh_frame_regnum_x86_64 (uint32_t unwind_regno)
-{
- switch (unwind_regno)
- {
- case UNWIND_X86_64_REG_RBX:
- return x86_64_eh_regnum::rbx;
- case UNWIND_X86_64_REG_R12:
- return x86_64_eh_regnum::r12;
- case UNWIND_X86_64_REG_R13:
- return x86_64_eh_regnum::r13;
- case UNWIND_X86_64_REG_R14:
- return x86_64_eh_regnum::r14;
- case UNWIND_X86_64_REG_R15:
- return x86_64_eh_regnum::r15;
- case UNWIND_X86_64_REG_RBP:
- return x86_64_eh_regnum::rbp;
- default:
- return LLDB_INVALID_REGNUM;
- }
+uint32_t translate_to_eh_frame_regnum_x86_64(uint32_t unwind_regno) {
+ switch (unwind_regno) {
+ case UNWIND_X86_64_REG_RBX:
+ return x86_64_eh_regnum::rbx;
+ case UNWIND_X86_64_REG_R12:
+ return x86_64_eh_regnum::r12;
+ case UNWIND_X86_64_REG_R13:
+ return x86_64_eh_regnum::r13;
+ case UNWIND_X86_64_REG_R14:
+ return x86_64_eh_regnum::r14;
+ case UNWIND_X86_64_REG_R15:
+ return x86_64_eh_regnum::r15;
+ case UNWIND_X86_64_REG_RBP:
+ return x86_64_eh_regnum::rbp;
+ default:
+ return LLDB_INVALID_REGNUM;
+ }
}
-bool
-CompactUnwindInfo::CreateUnwindPlan_x86_64 (Target &target, FunctionInfo &function_info, UnwindPlan &unwind_plan, Address pc_or_function_start)
-{
- unwind_plan.SetSourceName ("compact unwind info");
- unwind_plan.SetSourcedFromCompiler (eLazyBoolYes);
- unwind_plan.SetUnwindPlanValidAtAllInstructions (eLazyBoolNo);
- unwind_plan.SetRegisterKind (eRegisterKindEHFrame);
-
- unwind_plan.SetLSDAAddress (function_info.lsda_address);
- unwind_plan.SetPersonalityFunctionPtr (function_info.personality_ptr_address);
-
- UnwindPlan::RowSP row (new UnwindPlan::Row);
-
- const int wordsize = 8;
- int mode = function_info.encoding & UNWIND_X86_64_MODE_MASK;
- switch (mode)
- {
- case UNWIND_X86_64_MODE_RBP_FRAME:
- {
- row->GetCFAValue().SetIsRegisterPlusOffset (
- translate_to_eh_frame_regnum_x86_64 (UNWIND_X86_64_REG_RBP),
- 2 * wordsize);
- row->SetOffset (0);
- row->SetRegisterLocationToAtCFAPlusOffset (x86_64_eh_regnum::rbp, wordsize * -2, true);
- row->SetRegisterLocationToAtCFAPlusOffset (x86_64_eh_regnum::rip, wordsize * -1, true);
- row->SetRegisterLocationToIsCFAPlusOffset (x86_64_eh_regnum::rsp, 0, true);
-
- uint32_t saved_registers_offset = EXTRACT_BITS (function_info.encoding, UNWIND_X86_64_RBP_FRAME_OFFSET);
-
- uint32_t saved_registers_locations = EXTRACT_BITS (function_info.encoding, UNWIND_X86_64_RBP_FRAME_REGISTERS);
-
- saved_registers_offset += 2;
-
- for (int i = 0; i < 5; i++)
- {
- uint32_t regnum = saved_registers_locations & 0x7;
- switch (regnum)
- {
- case UNWIND_X86_64_REG_NONE:
- break;
- case UNWIND_X86_64_REG_RBX:
- case UNWIND_X86_64_REG_R12:
- case UNWIND_X86_64_REG_R13:
- case UNWIND_X86_64_REG_R14:
- case UNWIND_X86_64_REG_R15:
- row->SetRegisterLocationToAtCFAPlusOffset (translate_to_eh_frame_regnum_x86_64 (regnum), wordsize * -saved_registers_offset, true);
- break;
- }
- saved_registers_offset--;
- saved_registers_locations >>= 3;
- }
- unwind_plan.AppendRow (row);
- return true;
- }
+bool CompactUnwindInfo::CreateUnwindPlan_x86_64(Target &target,
+ FunctionInfo &function_info,
+ UnwindPlan &unwind_plan,
+ Address pc_or_function_start) {
+ unwind_plan.SetSourceName("compact unwind info");
+ unwind_plan.SetSourcedFromCompiler(eLazyBoolYes);
+ unwind_plan.SetUnwindPlanValidAtAllInstructions(eLazyBoolNo);
+ unwind_plan.SetRegisterKind(eRegisterKindEHFrame);
+
+ unwind_plan.SetLSDAAddress(function_info.lsda_address);
+ unwind_plan.SetPersonalityFunctionPtr(function_info.personality_ptr_address);
+
+ UnwindPlan::RowSP row(new UnwindPlan::Row);
+
+ const int wordsize = 8;
+ int mode = function_info.encoding & UNWIND_X86_64_MODE_MASK;
+ switch (mode) {
+ case UNWIND_X86_64_MODE_RBP_FRAME: {
+ row->GetCFAValue().SetIsRegisterPlusOffset(
+ translate_to_eh_frame_regnum_x86_64(UNWIND_X86_64_REG_RBP),
+ 2 * wordsize);
+ row->SetOffset(0);
+ row->SetRegisterLocationToAtCFAPlusOffset(x86_64_eh_regnum::rbp,
+ wordsize * -2, true);
+ row->SetRegisterLocationToAtCFAPlusOffset(x86_64_eh_regnum::rip,
+ wordsize * -1, true);
+ row->SetRegisterLocationToIsCFAPlusOffset(x86_64_eh_regnum::rsp, 0, true);
+
+ uint32_t saved_registers_offset =
+ EXTRACT_BITS(function_info.encoding, UNWIND_X86_64_RBP_FRAME_OFFSET);
+
+ uint32_t saved_registers_locations =
+ EXTRACT_BITS(function_info.encoding, UNWIND_X86_64_RBP_FRAME_REGISTERS);
+
+ saved_registers_offset += 2;
+
+ for (int i = 0; i < 5; i++) {
+ uint32_t regnum = saved_registers_locations & 0x7;
+ switch (regnum) {
+ case UNWIND_X86_64_REG_NONE:
break;
-
- case UNWIND_X86_64_MODE_STACK_IND:
- {
- // The clang in Xcode 6 is emitting incorrect compact unwind encodings for this
- // style of unwind. It was fixed in llvm r217020.
- // The clang in Xcode 7 has this fixed.
- return false;
- }
+ case UNWIND_X86_64_REG_RBX:
+ case UNWIND_X86_64_REG_R12:
+ case UNWIND_X86_64_REG_R13:
+ case UNWIND_X86_64_REG_R14:
+ case UNWIND_X86_64_REG_R15:
+ row->SetRegisterLocationToAtCFAPlusOffset(
+ translate_to_eh_frame_regnum_x86_64(regnum),
+ wordsize * -saved_registers_offset, true);
break;
+ }
+ saved_registers_offset--;
+ saved_registers_locations >>= 3;
+ }
+ unwind_plan.AppendRow(row);
+ return true;
+ } break;
- case UNWIND_X86_64_MODE_STACK_IMMD:
- {
- uint32_t stack_size = EXTRACT_BITS (function_info.encoding, UNWIND_X86_64_FRAMELESS_STACK_SIZE);
- uint32_t register_count = EXTRACT_BITS (function_info.encoding, UNWIND_X86_64_FRAMELESS_STACK_REG_COUNT);
- uint32_t permutation = EXTRACT_BITS (function_info.encoding, UNWIND_X86_64_FRAMELESS_STACK_REG_PERMUTATION);
-
- if (mode == UNWIND_X86_64_MODE_STACK_IND && function_info.valid_range_offset_start != 0)
- {
- uint32_t stack_adjust = EXTRACT_BITS (function_info.encoding, UNWIND_X86_64_FRAMELESS_STACK_ADJUST);
-
- // offset into the function instructions; 0 == beginning of first instruction
- uint32_t offset_to_subl_insn = EXTRACT_BITS (function_info.encoding, UNWIND_X86_64_FRAMELESS_STACK_SIZE);
-
- SectionList *sl = m_objfile.GetSectionList ();
- if (sl)
- {
- ProcessSP process_sp = target.GetProcessSP();
- if (process_sp)
- {
- Address subl_payload_addr (function_info.valid_range_offset_start, sl);
- subl_payload_addr.Slide (offset_to_subl_insn);
- Error error;
- uint64_t large_stack_size = process_sp->ReadUnsignedIntegerFromMemory (subl_payload_addr.GetLoadAddress (&target),
- 4, 0, error);
- if (large_stack_size != 0 && error.Success ())
- {
- // Got the large stack frame size correctly - use it
- stack_size = large_stack_size + (stack_adjust * wordsize);
- }
- else
- {
- return false;
- }
- }
- else
- {
- return false;
- }
- }
- else
- {
- return false;
- }
- }
-
- int32_t offset = mode == UNWIND_X86_64_MODE_STACK_IND ? stack_size : stack_size * wordsize;
- row->GetCFAValue().SetIsRegisterPlusOffset (x86_64_eh_regnum::rsp, offset);
-
- row->SetOffset (0);
- row->SetRegisterLocationToAtCFAPlusOffset (x86_64_eh_regnum::rip, wordsize * -1, true);
- row->SetRegisterLocationToIsCFAPlusOffset (x86_64_eh_regnum::rsp, 0, true);
-
- if (register_count > 0)
- {
-
- // We need to include (up to) 6 registers in 10 bits.
- // That would be 18 bits if we just used 3 bits per reg to indicate
- // the order they're saved on the stack.
- //
- // This is done with Lehmer code permutation, e.g. see
- // http://stackoverflow.com/questions/1506078/fast-permutation-number-permutation-mapping-algorithms
- int permunreg[6] = {0, 0, 0, 0, 0, 0};
-
- // This decodes the variable-base number in the 10 bits
- // and gives us the Lehmer code sequence which can then
- // be decoded.
-
- switch (register_count)
- {
- case 6:
- permunreg[0] = permutation/120; // 120 == 5!
- permutation -= (permunreg[0]*120);
- permunreg[1] = permutation/24; // 24 == 4!
- permutation -= (permunreg[1]*24);
- permunreg[2] = permutation/6; // 6 == 3!
- permutation -= (permunreg[2]*6);
- permunreg[3] = permutation/2; // 2 == 2!
- permutation -= (permunreg[3]*2);
- permunreg[4] = permutation; // 1 == 1!
- permunreg[5] = 0;
- break;
- case 5:
- permunreg[0] = permutation/120;
- permutation -= (permunreg[0]*120);
- permunreg[1] = permutation/24;
- permutation -= (permunreg[1]*24);
- permunreg[2] = permutation/6;
- permutation -= (permunreg[2]*6);
- permunreg[3] = permutation/2;
- permutation -= (permunreg[3]*2);
- permunreg[4] = permutation;
- break;
- case 4:
- permunreg[0] = permutation/60;
- permutation -= (permunreg[0]*60);
- permunreg[1] = permutation/12;
- permutation -= (permunreg[1]*12);
- permunreg[2] = permutation/3;
- permutation -= (permunreg[2]*3);
- permunreg[3] = permutation;
- break;
- case 3:
- permunreg[0] = permutation/20;
- permutation -= (permunreg[0]*20);
- permunreg[1] = permutation/4;
- permutation -= (permunreg[1]*4);
- permunreg[2] = permutation;
- break;
- case 2:
- permunreg[0] = permutation/5;
- permutation -= (permunreg[0]*5);
- permunreg[1] = permutation;
- break;
- case 1:
- permunreg[0] = permutation;
- break;
- }
-
- // Decode the Lehmer code for this permutation of
- // the registers v. http://en.wikipedia.org/wiki/Lehmer_code
-
- int registers[6] = { UNWIND_X86_64_REG_NONE, UNWIND_X86_64_REG_NONE, UNWIND_X86_64_REG_NONE, UNWIND_X86_64_REG_NONE, UNWIND_X86_64_REG_NONE, UNWIND_X86_64_REG_NONE };
- bool used[7] = { false, false, false, false, false, false, false };
- for (uint32_t i = 0; i < register_count; i++)
- {
- int renum = 0;
- for (int j = 1; j < 7; j++)
- {
- if (used[j] == false)
- {
- if (renum == permunreg[i])
- {
- registers[i] = j;
- used[j] = true;
- break;
- }
- renum++;
- }
- }
- }
-
- uint32_t saved_registers_offset = 1;
- saved_registers_offset++;
-
- for (int i = (sizeof (registers) / sizeof (int)) - 1; i >= 0; i--)
- {
- switch (registers[i])
- {
- case UNWIND_X86_64_REG_NONE:
- break;
- case UNWIND_X86_64_REG_RBX:
- case UNWIND_X86_64_REG_R12:
- case UNWIND_X86_64_REG_R13:
- case UNWIND_X86_64_REG_R14:
- case UNWIND_X86_64_REG_R15:
- case UNWIND_X86_64_REG_RBP:
- row->SetRegisterLocationToAtCFAPlusOffset (translate_to_eh_frame_regnum_x86_64 (registers[i]), wordsize * -saved_registers_offset, true);
- saved_registers_offset++;
- break;
- }
- }
- }
- unwind_plan.AppendRow (row);
- return true;
- }
- break;
+ case UNWIND_X86_64_MODE_STACK_IND: {
+ // The clang in Xcode 6 is emitting incorrect compact unwind encodings for
+ // this
+ // style of unwind. It was fixed in llvm r217020.
+ // The clang in Xcode 7 has this fixed.
+ return false;
+ } break;
- case UNWIND_X86_64_MODE_DWARF:
- {
+ case UNWIND_X86_64_MODE_STACK_IMMD: {
+ uint32_t stack_size = EXTRACT_BITS(function_info.encoding,
+ UNWIND_X86_64_FRAMELESS_STACK_SIZE);
+ uint32_t register_count = EXTRACT_BITS(
+ function_info.encoding, UNWIND_X86_64_FRAMELESS_STACK_REG_COUNT);
+ uint32_t permutation = EXTRACT_BITS(
+ function_info.encoding, UNWIND_X86_64_FRAMELESS_STACK_REG_PERMUTATION);
+
+ if (mode == UNWIND_X86_64_MODE_STACK_IND &&
+ function_info.valid_range_offset_start != 0) {
+ uint32_t stack_adjust = EXTRACT_BITS(
+ function_info.encoding, UNWIND_X86_64_FRAMELESS_STACK_ADJUST);
+
+ // offset into the function instructions; 0 == beginning of first
+ // instruction
+ uint32_t offset_to_subl_insn = EXTRACT_BITS(
+ function_info.encoding, UNWIND_X86_64_FRAMELESS_STACK_SIZE);
+
+ SectionList *sl = m_objfile.GetSectionList();
+ if (sl) {
+ ProcessSP process_sp = target.GetProcessSP();
+ if (process_sp) {
+ Address subl_payload_addr(function_info.valid_range_offset_start, sl);
+ subl_payload_addr.Slide(offset_to_subl_insn);
+ Error error;
+ uint64_t large_stack_size = process_sp->ReadUnsignedIntegerFromMemory(
+ subl_payload_addr.GetLoadAddress(&target), 4, 0, error);
+ if (large_stack_size != 0 && error.Success()) {
+ // Got the large stack frame size correctly - use it
+ stack_size = large_stack_size + (stack_adjust * wordsize);
+ } else {
return false;
+ }
+ } else {
+ return false;
}
+ } else {
+ return false;
+ }
+ }
+
+ int32_t offset = mode == UNWIND_X86_64_MODE_STACK_IND
+ ? stack_size
+ : stack_size * wordsize;
+ row->GetCFAValue().SetIsRegisterPlusOffset(x86_64_eh_regnum::rsp, offset);
+
+ row->SetOffset(0);
+ row->SetRegisterLocationToAtCFAPlusOffset(x86_64_eh_regnum::rip,
+ wordsize * -1, true);
+ row->SetRegisterLocationToIsCFAPlusOffset(x86_64_eh_regnum::rsp, 0, true);
+
+ if (register_count > 0) {
+
+ // We need to include (up to) 6 registers in 10 bits.
+ // That would be 18 bits if we just used 3 bits per reg to indicate
+ // the order they're saved on the stack.
+ //
+ // This is done with Lehmer code permutation, e.g. see
+ // http://stackoverflow.com/questions/1506078/fast-permutation-number-permutation-mapping-algorithms
+ int permunreg[6] = {0, 0, 0, 0, 0, 0};
+
+ // This decodes the variable-base number in the 10 bits
+ // and gives us the Lehmer code sequence which can then
+ // be decoded.
+
+ switch (register_count) {
+ case 6:
+ permunreg[0] = permutation / 120; // 120 == 5!
+ permutation -= (permunreg[0] * 120);
+ permunreg[1] = permutation / 24; // 24 == 4!
+ permutation -= (permunreg[1] * 24);
+ permunreg[2] = permutation / 6; // 6 == 3!
+ permutation -= (permunreg[2] * 6);
+ permunreg[3] = permutation / 2; // 2 == 2!
+ permutation -= (permunreg[3] * 2);
+ permunreg[4] = permutation; // 1 == 1!
+ permunreg[5] = 0;
+ break;
+ case 5:
+ permunreg[0] = permutation / 120;
+ permutation -= (permunreg[0] * 120);
+ permunreg[1] = permutation / 24;
+ permutation -= (permunreg[1] * 24);
+ permunreg[2] = permutation / 6;
+ permutation -= (permunreg[2] * 6);
+ permunreg[3] = permutation / 2;
+ permutation -= (permunreg[3] * 2);
+ permunreg[4] = permutation;
+ break;
+ case 4:
+ permunreg[0] = permutation / 60;
+ permutation -= (permunreg[0] * 60);
+ permunreg[1] = permutation / 12;
+ permutation -= (permunreg[1] * 12);
+ permunreg[2] = permutation / 3;
+ permutation -= (permunreg[2] * 3);
+ permunreg[3] = permutation;
+ break;
+ case 3:
+ permunreg[0] = permutation / 20;
+ permutation -= (permunreg[0] * 20);
+ permunreg[1] = permutation / 4;
+ permutation -= (permunreg[1] * 4);
+ permunreg[2] = permutation;
break;
+ case 2:
+ permunreg[0] = permutation / 5;
+ permutation -= (permunreg[0] * 5);
+ permunreg[1] = permutation;
+ break;
+ case 1:
+ permunreg[0] = permutation;
+ break;
+ }
- case 0:
- {
- return false;
+ // Decode the Lehmer code for this permutation of
+ // the registers v. http://en.wikipedia.org/wiki/Lehmer_code
+
+ int registers[6] = {UNWIND_X86_64_REG_NONE, UNWIND_X86_64_REG_NONE,
+ UNWIND_X86_64_REG_NONE, UNWIND_X86_64_REG_NONE,
+ UNWIND_X86_64_REG_NONE, UNWIND_X86_64_REG_NONE};
+ bool used[7] = {false, false, false, false, false, false, false};
+ for (uint32_t i = 0; i < register_count; i++) {
+ int renum = 0;
+ for (int j = 1; j < 7; j++) {
+ if (used[j] == false) {
+ if (renum == permunreg[i]) {
+ registers[i] = j;
+ used[j] = true;
+ break;
+ }
+ renum++;
+ }
+ }
+ }
+
+ uint32_t saved_registers_offset = 1;
+ saved_registers_offset++;
+
+ for (int i = (sizeof(registers) / sizeof(int)) - 1; i >= 0; i--) {
+ switch (registers[i]) {
+ case UNWIND_X86_64_REG_NONE:
+ break;
+ case UNWIND_X86_64_REG_RBX:
+ case UNWIND_X86_64_REG_R12:
+ case UNWIND_X86_64_REG_R13:
+ case UNWIND_X86_64_REG_R14:
+ case UNWIND_X86_64_REG_R15:
+ case UNWIND_X86_64_REG_RBP:
+ row->SetRegisterLocationToAtCFAPlusOffset(
+ translate_to_eh_frame_regnum_x86_64(registers[i]),
+ wordsize * -saved_registers_offset, true);
+ saved_registers_offset++;
+ break;
}
- break;
+ }
}
+ unwind_plan.AppendRow(row);
+ return true;
+ } break;
+
+ case UNWIND_X86_64_MODE_DWARF: {
+ return false;
+ } break;
+
+ case 0: {
return false;
+ } break;
+ }
+ return false;
}
enum i386_eh_regnum {
- eax = 0,
- ecx = 1,
- edx = 2,
- ebx = 3,
- ebp = 4,
- esp = 5,
- esi = 6,
- edi = 7,
- eip = 8 // this is officially the Return Address register number, but close enough
+ eax = 0,
+ ecx = 1,
+ edx = 2,
+ ebx = 3,
+ ebp = 4,
+ esp = 5,
+ esi = 6,
+ edi = 7,
+ eip = 8 // this is officially the Return Address register number, but close
+ // enough
};
// Convert the compact_unwind_info.h register numbering scheme
// to eRegisterKindEHFrame (eh_frame) register numbering scheme.
-uint32_t
-translate_to_eh_frame_regnum_i386 (uint32_t unwind_regno)
-{
- switch (unwind_regno)
- {
- case UNWIND_X86_REG_EBX:
- return i386_eh_regnum::ebx;
- case UNWIND_X86_REG_ECX:
- return i386_eh_regnum::ecx;
- case UNWIND_X86_REG_EDX:
- return i386_eh_regnum::edx;
- case UNWIND_X86_REG_EDI:
- return i386_eh_regnum::edi;
- case UNWIND_X86_REG_ESI:
- return i386_eh_regnum::esi;
- case UNWIND_X86_REG_EBP:
- return i386_eh_regnum::ebp;
- default:
- return LLDB_INVALID_REGNUM;
- }
+uint32_t translate_to_eh_frame_regnum_i386(uint32_t unwind_regno) {
+ switch (unwind_regno) {
+ case UNWIND_X86_REG_EBX:
+ return i386_eh_regnum::ebx;
+ case UNWIND_X86_REG_ECX:
+ return i386_eh_regnum::ecx;
+ case UNWIND_X86_REG_EDX:
+ return i386_eh_regnum::edx;
+ case UNWIND_X86_REG_EDI:
+ return i386_eh_regnum::edi;
+ case UNWIND_X86_REG_ESI:
+ return i386_eh_regnum::esi;
+ case UNWIND_X86_REG_EBP:
+ return i386_eh_regnum::ebp;
+ default:
+ return LLDB_INVALID_REGNUM;
+ }
}
-
-bool
-CompactUnwindInfo::CreateUnwindPlan_i386 (Target &target, FunctionInfo &function_info, UnwindPlan &unwind_plan, Address pc_or_function_start)
-{
- unwind_plan.SetSourceName ("compact unwind info");
- unwind_plan.SetSourcedFromCompiler (eLazyBoolYes);
- unwind_plan.SetUnwindPlanValidAtAllInstructions (eLazyBoolNo);
- unwind_plan.SetRegisterKind (eRegisterKindEHFrame);
-
- unwind_plan.SetLSDAAddress (function_info.lsda_address);
- unwind_plan.SetPersonalityFunctionPtr (function_info.personality_ptr_address);
-
- UnwindPlan::RowSP row (new UnwindPlan::Row);
-
- const int wordsize = 4;
- int mode = function_info.encoding & UNWIND_X86_MODE_MASK;
- switch (mode)
- {
- case UNWIND_X86_MODE_EBP_FRAME:
- {
- row->GetCFAValue().SetIsRegisterPlusOffset (
- translate_to_eh_frame_regnum_i386 (UNWIND_X86_REG_EBP), 2 * wordsize);
- row->SetOffset (0);
- row->SetRegisterLocationToAtCFAPlusOffset (i386_eh_regnum::ebp, wordsize * -2, true);
- row->SetRegisterLocationToAtCFAPlusOffset (i386_eh_regnum::eip, wordsize * -1, true);
- row->SetRegisterLocationToIsCFAPlusOffset (i386_eh_regnum::esp, 0, true);
-
- uint32_t saved_registers_offset = EXTRACT_BITS (function_info.encoding, UNWIND_X86_EBP_FRAME_OFFSET);
-
- uint32_t saved_registers_locations = EXTRACT_BITS (function_info.encoding, UNWIND_X86_EBP_FRAME_REGISTERS);
-
- saved_registers_offset += 2;
-
- for (int i = 0; i < 5; i++)
- {
- uint32_t regnum = saved_registers_locations & 0x7;
- switch (regnum)
- {
- case UNWIND_X86_REG_NONE:
- break;
- case UNWIND_X86_REG_EBX:
- case UNWIND_X86_REG_ECX:
- case UNWIND_X86_REG_EDX:
- case UNWIND_X86_REG_EDI:
- case UNWIND_X86_REG_ESI:
- row->SetRegisterLocationToAtCFAPlusOffset (translate_to_eh_frame_regnum_i386 (regnum), wordsize * -saved_registers_offset, true);
- break;
- }
- saved_registers_offset--;
- saved_registers_locations >>= 3;
- }
- unwind_plan.AppendRow (row);
- return true;
- }
+bool CompactUnwindInfo::CreateUnwindPlan_i386(Target &target,
+ FunctionInfo &function_info,
+ UnwindPlan &unwind_plan,
+ Address pc_or_function_start) {
+ unwind_plan.SetSourceName("compact unwind info");
+ unwind_plan.SetSourcedFromCompiler(eLazyBoolYes);
+ unwind_plan.SetUnwindPlanValidAtAllInstructions(eLazyBoolNo);
+ unwind_plan.SetRegisterKind(eRegisterKindEHFrame);
+
+ unwind_plan.SetLSDAAddress(function_info.lsda_address);
+ unwind_plan.SetPersonalityFunctionPtr(function_info.personality_ptr_address);
+
+ UnwindPlan::RowSP row(new UnwindPlan::Row);
+
+ const int wordsize = 4;
+ int mode = function_info.encoding & UNWIND_X86_MODE_MASK;
+ switch (mode) {
+ case UNWIND_X86_MODE_EBP_FRAME: {
+ row->GetCFAValue().SetIsRegisterPlusOffset(
+ translate_to_eh_frame_regnum_i386(UNWIND_X86_REG_EBP), 2 * wordsize);
+ row->SetOffset(0);
+ row->SetRegisterLocationToAtCFAPlusOffset(i386_eh_regnum::ebp,
+ wordsize * -2, true);
+ row->SetRegisterLocationToAtCFAPlusOffset(i386_eh_regnum::eip,
+ wordsize * -1, true);
+ row->SetRegisterLocationToIsCFAPlusOffset(i386_eh_regnum::esp, 0, true);
+
+ uint32_t saved_registers_offset =
+ EXTRACT_BITS(function_info.encoding, UNWIND_X86_EBP_FRAME_OFFSET);
+
+ uint32_t saved_registers_locations =
+ EXTRACT_BITS(function_info.encoding, UNWIND_X86_EBP_FRAME_REGISTERS);
+
+ saved_registers_offset += 2;
+
+ for (int i = 0; i < 5; i++) {
+ uint32_t regnum = saved_registers_locations & 0x7;
+ switch (regnum) {
+ case UNWIND_X86_REG_NONE:
break;
-
- case UNWIND_X86_MODE_STACK_IND:
- case UNWIND_X86_MODE_STACK_IMMD:
- {
- uint32_t stack_size = EXTRACT_BITS (function_info.encoding, UNWIND_X86_FRAMELESS_STACK_SIZE);
- uint32_t register_count = EXTRACT_BITS (function_info.encoding, UNWIND_X86_FRAMELESS_STACK_REG_COUNT);
- uint32_t permutation = EXTRACT_BITS (function_info.encoding, UNWIND_X86_FRAMELESS_STACK_REG_PERMUTATION);
-
- if (mode == UNWIND_X86_MODE_STACK_IND && function_info.valid_range_offset_start != 0)
- {
- uint32_t stack_adjust = EXTRACT_BITS (function_info.encoding, UNWIND_X86_FRAMELESS_STACK_ADJUST);
-
- // offset into the function instructions; 0 == beginning of first instruction
- uint32_t offset_to_subl_insn = EXTRACT_BITS (function_info.encoding, UNWIND_X86_FRAMELESS_STACK_SIZE);
-
- SectionList *sl = m_objfile.GetSectionList ();
- if (sl)
- {
- ProcessSP process_sp = target.GetProcessSP();
- if (process_sp)
- {
- Address subl_payload_addr (function_info.valid_range_offset_start, sl);
- subl_payload_addr.Slide (offset_to_subl_insn);
- Error error;
- uint64_t large_stack_size = process_sp->ReadUnsignedIntegerFromMemory (subl_payload_addr.GetLoadAddress (&target),
- 4, 0, error);
- if (large_stack_size != 0 && error.Success ())
- {
- // Got the large stack frame size correctly - use it
- stack_size = large_stack_size + (stack_adjust * wordsize);
- }
- else
- {
- return false;
- }
- }
- else
- {
- return false;
- }
- }
- else
- {
- return false;
- }
- }
-
- int32_t offset = mode == UNWIND_X86_MODE_STACK_IND ? stack_size : stack_size * wordsize;
- row->GetCFAValue().SetIsRegisterPlusOffset (i386_eh_regnum::esp, offset);
- row->SetOffset (0);
- row->SetRegisterLocationToAtCFAPlusOffset (i386_eh_regnum::eip, wordsize * -1, true);
- row->SetRegisterLocationToIsCFAPlusOffset (i386_eh_regnum::esp, 0, true);
-
- if (register_count > 0)
- {
-
- // We need to include (up to) 6 registers in 10 bits.
- // That would be 18 bits if we just used 3 bits per reg to indicate
- // the order they're saved on the stack.
- //
- // This is done with Lehmer code permutation, e.g. see
- // http://stackoverflow.com/questions/1506078/fast-permutation-number-permutation-mapping-algorithms
- int permunreg[6] = {0, 0, 0, 0, 0, 0};
-
- // This decodes the variable-base number in the 10 bits
- // and gives us the Lehmer code sequence which can then
- // be decoded.
-
- switch (register_count)
- {
- case 6:
- permunreg[0] = permutation/120; // 120 == 5!
- permutation -= (permunreg[0]*120);
- permunreg[1] = permutation/24; // 24 == 4!
- permutation -= (permunreg[1]*24);
- permunreg[2] = permutation/6; // 6 == 3!
- permutation -= (permunreg[2]*6);
- permunreg[3] = permutation/2; // 2 == 2!
- permutation -= (permunreg[3]*2);
- permunreg[4] = permutation; // 1 == 1!
- permunreg[5] = 0;
- break;
- case 5:
- permunreg[0] = permutation/120;
- permutation -= (permunreg[0]*120);
- permunreg[1] = permutation/24;
- permutation -= (permunreg[1]*24);
- permunreg[2] = permutation/6;
- permutation -= (permunreg[2]*6);
- permunreg[3] = permutation/2;
- permutation -= (permunreg[3]*2);
- permunreg[4] = permutation;
- break;
- case 4:
- permunreg[0] = permutation/60;
- permutation -= (permunreg[0]*60);
- permunreg[1] = permutation/12;
- permutation -= (permunreg[1]*12);
- permunreg[2] = permutation/3;
- permutation -= (permunreg[2]*3);
- permunreg[3] = permutation;
- break;
- case 3:
- permunreg[0] = permutation/20;
- permutation -= (permunreg[0]*20);
- permunreg[1] = permutation/4;
- permutation -= (permunreg[1]*4);
- permunreg[2] = permutation;
- break;
- case 2:
- permunreg[0] = permutation/5;
- permutation -= (permunreg[0]*5);
- permunreg[1] = permutation;
- break;
- case 1:
- permunreg[0] = permutation;
- break;
- }
-
- // Decode the Lehmer code for this permutation of
- // the registers v. http://en.wikipedia.org/wiki/Lehmer_code
-
- int registers[6] = { UNWIND_X86_REG_NONE, UNWIND_X86_REG_NONE, UNWIND_X86_REG_NONE, UNWIND_X86_REG_NONE, UNWIND_X86_REG_NONE, UNWIND_X86_REG_NONE };
- bool used[7] = { false, false, false, false, false, false, false };
- for (uint32_t i = 0; i < register_count; i++)
- {
- int renum = 0;
- for (int j = 1; j < 7; j++)
- {
- if (used[j] == false)
- {
- if (renum == permunreg[i])
- {
- registers[i] = j;
- used[j] = true;
- break;
- }
- renum++;
- }
- }
- }
-
- uint32_t saved_registers_offset = 1;
- saved_registers_offset++;
-
- for (int i = (sizeof (registers) / sizeof (int)) - 1; i >= 0; i--)
- {
- switch (registers[i])
- {
- case UNWIND_X86_REG_NONE:
- break;
- case UNWIND_X86_REG_EBX:
- case UNWIND_X86_REG_ECX:
- case UNWIND_X86_REG_EDX:
- case UNWIND_X86_REG_EDI:
- case UNWIND_X86_REG_ESI:
- case UNWIND_X86_REG_EBP:
- row->SetRegisterLocationToAtCFAPlusOffset (translate_to_eh_frame_regnum_i386 (registers[i]), wordsize * -saved_registers_offset, true);
- saved_registers_offset++;
- break;
- }
- }
- }
-
- unwind_plan.AppendRow (row);
- return true;
- }
+ case UNWIND_X86_REG_EBX:
+ case UNWIND_X86_REG_ECX:
+ case UNWIND_X86_REG_EDX:
+ case UNWIND_X86_REG_EDI:
+ case UNWIND_X86_REG_ESI:
+ row->SetRegisterLocationToAtCFAPlusOffset(
+ translate_to_eh_frame_regnum_i386(regnum),
+ wordsize * -saved_registers_offset, true);
break;
+ }
+ saved_registers_offset--;
+ saved_registers_locations >>= 3;
+ }
+ unwind_plan.AppendRow(row);
+ return true;
+ } break;
- case UNWIND_X86_MODE_DWARF:
- {
+ case UNWIND_X86_MODE_STACK_IND:
+ case UNWIND_X86_MODE_STACK_IMMD: {
+ uint32_t stack_size =
+ EXTRACT_BITS(function_info.encoding, UNWIND_X86_FRAMELESS_STACK_SIZE);
+ uint32_t register_count = EXTRACT_BITS(
+ function_info.encoding, UNWIND_X86_FRAMELESS_STACK_REG_COUNT);
+ uint32_t permutation = EXTRACT_BITS(
+ function_info.encoding, UNWIND_X86_FRAMELESS_STACK_REG_PERMUTATION);
+
+ if (mode == UNWIND_X86_MODE_STACK_IND &&
+ function_info.valid_range_offset_start != 0) {
+ uint32_t stack_adjust = EXTRACT_BITS(function_info.encoding,
+ UNWIND_X86_FRAMELESS_STACK_ADJUST);
+
+ // offset into the function instructions; 0 == beginning of first
+ // instruction
+ uint32_t offset_to_subl_insn =
+ EXTRACT_BITS(function_info.encoding, UNWIND_X86_FRAMELESS_STACK_SIZE);
+
+ SectionList *sl = m_objfile.GetSectionList();
+ if (sl) {
+ ProcessSP process_sp = target.GetProcessSP();
+ if (process_sp) {
+ Address subl_payload_addr(function_info.valid_range_offset_start, sl);
+ subl_payload_addr.Slide(offset_to_subl_insn);
+ Error error;
+ uint64_t large_stack_size = process_sp->ReadUnsignedIntegerFromMemory(
+ subl_payload_addr.GetLoadAddress(&target), 4, 0, error);
+ if (large_stack_size != 0 && error.Success()) {
+ // Got the large stack frame size correctly - use it
+ stack_size = large_stack_size + (stack_adjust * wordsize);
+ } else {
return false;
+ }
+ } else {
+ return false;
}
+ } else {
+ return false;
+ }
+ }
+
+ int32_t offset =
+ mode == UNWIND_X86_MODE_STACK_IND ? stack_size : stack_size * wordsize;
+ row->GetCFAValue().SetIsRegisterPlusOffset(i386_eh_regnum::esp, offset);
+ row->SetOffset(0);
+ row->SetRegisterLocationToAtCFAPlusOffset(i386_eh_regnum::eip,
+ wordsize * -1, true);
+ row->SetRegisterLocationToIsCFAPlusOffset(i386_eh_regnum::esp, 0, true);
+
+ if (register_count > 0) {
+
+ // We need to include (up to) 6 registers in 10 bits.
+ // That would be 18 bits if we just used 3 bits per reg to indicate
+ // the order they're saved on the stack.
+ //
+ // This is done with Lehmer code permutation, e.g. see
+ // http://stackoverflow.com/questions/1506078/fast-permutation-number-permutation-mapping-algorithms
+ int permunreg[6] = {0, 0, 0, 0, 0, 0};
+
+ // This decodes the variable-base number in the 10 bits
+ // and gives us the Lehmer code sequence which can then
+ // be decoded.
+
+ switch (register_count) {
+ case 6:
+ permunreg[0] = permutation / 120; // 120 == 5!
+ permutation -= (permunreg[0] * 120);
+ permunreg[1] = permutation / 24; // 24 == 4!
+ permutation -= (permunreg[1] * 24);
+ permunreg[2] = permutation / 6; // 6 == 3!
+ permutation -= (permunreg[2] * 6);
+ permunreg[3] = permutation / 2; // 2 == 2!
+ permutation -= (permunreg[3] * 2);
+ permunreg[4] = permutation; // 1 == 1!
+ permunreg[5] = 0;
+ break;
+ case 5:
+ permunreg[0] = permutation / 120;
+ permutation -= (permunreg[0] * 120);
+ permunreg[1] = permutation / 24;
+ permutation -= (permunreg[1] * 24);
+ permunreg[2] = permutation / 6;
+ permutation -= (permunreg[2] * 6);
+ permunreg[3] = permutation / 2;
+ permutation -= (permunreg[3] * 2);
+ permunreg[4] = permutation;
+ break;
+ case 4:
+ permunreg[0] = permutation / 60;
+ permutation -= (permunreg[0] * 60);
+ permunreg[1] = permutation / 12;
+ permutation -= (permunreg[1] * 12);
+ permunreg[2] = permutation / 3;
+ permutation -= (permunreg[2] * 3);
+ permunreg[3] = permutation;
+ break;
+ case 3:
+ permunreg[0] = permutation / 20;
+ permutation -= (permunreg[0] * 20);
+ permunreg[1] = permutation / 4;
+ permutation -= (permunreg[1] * 4);
+ permunreg[2] = permutation;
break;
+ case 2:
+ permunreg[0] = permutation / 5;
+ permutation -= (permunreg[0] * 5);
+ permunreg[1] = permutation;
+ break;
+ case 1:
+ permunreg[0] = permutation;
+ break;
+ }
+
+ // Decode the Lehmer code for this permutation of
+ // the registers v. http://en.wikipedia.org/wiki/Lehmer_code
+
+ int registers[6] = {UNWIND_X86_REG_NONE, UNWIND_X86_REG_NONE,
+ UNWIND_X86_REG_NONE, UNWIND_X86_REG_NONE,
+ UNWIND_X86_REG_NONE, UNWIND_X86_REG_NONE};
+ bool used[7] = {false, false, false, false, false, false, false};
+ for (uint32_t i = 0; i < register_count; i++) {
+ int renum = 0;
+ for (int j = 1; j < 7; j++) {
+ if (used[j] == false) {
+ if (renum == permunreg[i]) {
+ registers[i] = j;
+ used[j] = true;
+ break;
+ }
+ renum++;
+ }
+ }
+ }
+
+ uint32_t saved_registers_offset = 1;
+ saved_registers_offset++;
+
+ for (int i = (sizeof(registers) / sizeof(int)) - 1; i >= 0; i--) {
+ switch (registers[i]) {
+ case UNWIND_X86_REG_NONE:
+ break;
+ case UNWIND_X86_REG_EBX:
+ case UNWIND_X86_REG_ECX:
+ case UNWIND_X86_REG_EDX:
+ case UNWIND_X86_REG_EDI:
+ case UNWIND_X86_REG_ESI:
+ case UNWIND_X86_REG_EBP:
+ row->SetRegisterLocationToAtCFAPlusOffset(
+ translate_to_eh_frame_regnum_i386(registers[i]),
+ wordsize * -saved_registers_offset, true);
+ saved_registers_offset++;
+ break;
+ }
+ }
}
- return false;
-}
+ unwind_plan.AppendRow(row);
+ return true;
+ } break;
+ case UNWIND_X86_MODE_DWARF: {
+ return false;
+ } break;
+ }
+ return false;
+}
-// DWARF register numbers from "DWARF for the ARM 64-bit Architecture (AArch64)" doc by ARM
+// DWARF register numbers from "DWARF for the ARM 64-bit Architecture (AArch64)"
+// doc by ARM
enum arm64_eh_regnum {
- x19 = 19,
- x20 = 20,
- x21 = 21,
- x22 = 22,
- x23 = 23,
- x24 = 24,
- x25 = 25,
- x26 = 26,
- x27 = 27,
- x28 = 28,
-
- fp = 29,
- ra = 30,
- sp = 31,
- pc = 32,
-
- // Compact unwind encodes d8-d15 but we don't have eh_frame / dwarf reg #'s for the 64-bit
- // fp regs. Normally in DWARF it's context sensitive - so it knows it is fetching a
- // 32- or 64-bit quantity from reg v8 to indicate s0 or d0 - but the unwinder is operating
- // at a lower level and we'd try to fetch 128 bits if we were told that v8 were stored on
- // the stack...
- v8 = 72,
- v9 = 73,
- v10 = 74,
- v11 = 75,
- v12 = 76,
- v13 = 77,
- v14 = 78,
- v15 = 79,
+ x19 = 19,
+ x20 = 20,
+ x21 = 21,
+ x22 = 22,
+ x23 = 23,
+ x24 = 24,
+ x25 = 25,
+ x26 = 26,
+ x27 = 27,
+ x28 = 28,
+
+ fp = 29,
+ ra = 30,
+ sp = 31,
+ pc = 32,
+
+ // Compact unwind encodes d8-d15 but we don't have eh_frame / dwarf reg #'s
+ // for the 64-bit
+ // fp regs. Normally in DWARF it's context sensitive - so it knows it is
+ // fetching a
+ // 32- or 64-bit quantity from reg v8 to indicate s0 or d0 - but the unwinder
+ // is operating
+ // at a lower level and we'd try to fetch 128 bits if we were told that v8
+ // were stored on
+ // the stack...
+ v8 = 72,
+ v9 = 73,
+ v10 = 74,
+ v11 = 75,
+ v12 = 76,
+ v13 = 77,
+ v14 = 78,
+ v15 = 79,
};
enum arm_eh_regnum {
- arm_r0 = 0,
- arm_r1 = 1,
- arm_r2 = 2,
- arm_r3 = 3,
- arm_r4 = 4,
- arm_r5 = 5,
- arm_r6 = 6,
- arm_r7 = 7,
- arm_r8 = 8,
- arm_r9 = 9,
- arm_r10 = 10,
- arm_r11 = 11,
- arm_r12 = 12,
-
- arm_sp = 13,
- arm_lr = 14,
- arm_pc = 15,
-
- arm_d0 = 256,
- arm_d1 = 257,
- arm_d2 = 258,
- arm_d3 = 259,
- arm_d4 = 260,
- arm_d5 = 261,
- arm_d6 = 262,
- arm_d7 = 263,
- arm_d8 = 264,
- arm_d9 = 265,
- arm_d10 = 266,
- arm_d11 = 267,
- arm_d12 = 268,
- arm_d13 = 269,
- arm_d14 = 270,
+ arm_r0 = 0,
+ arm_r1 = 1,
+ arm_r2 = 2,
+ arm_r3 = 3,
+ arm_r4 = 4,
+ arm_r5 = 5,
+ arm_r6 = 6,
+ arm_r7 = 7,
+ arm_r8 = 8,
+ arm_r9 = 9,
+ arm_r10 = 10,
+ arm_r11 = 11,
+ arm_r12 = 12,
+
+ arm_sp = 13,
+ arm_lr = 14,
+ arm_pc = 15,
+
+ arm_d0 = 256,
+ arm_d1 = 257,
+ arm_d2 = 258,
+ arm_d3 = 259,
+ arm_d4 = 260,
+ arm_d5 = 261,
+ arm_d6 = 262,
+ arm_d7 = 263,
+ arm_d8 = 264,
+ arm_d9 = 265,
+ arm_d10 = 266,
+ arm_d11 = 267,
+ arm_d12 = 268,
+ arm_d13 = 269,
+ arm_d14 = 270,
};
+bool CompactUnwindInfo::CreateUnwindPlan_arm64(Target &target,
+ FunctionInfo &function_info,
+ UnwindPlan &unwind_plan,
+ Address pc_or_function_start) {
+ unwind_plan.SetSourceName("compact unwind info");
+ unwind_plan.SetSourcedFromCompiler(eLazyBoolYes);
+ unwind_plan.SetUnwindPlanValidAtAllInstructions(eLazyBoolNo);
+ unwind_plan.SetRegisterKind(eRegisterKindEHFrame);
+
+ unwind_plan.SetLSDAAddress(function_info.lsda_address);
+ unwind_plan.SetPersonalityFunctionPtr(function_info.personality_ptr_address);
+ UnwindPlan::RowSP row(new UnwindPlan::Row);
-bool
-CompactUnwindInfo::CreateUnwindPlan_arm64 (Target &target, FunctionInfo &function_info, UnwindPlan &unwind_plan, Address pc_or_function_start)
-{
- unwind_plan.SetSourceName ("compact unwind info");
- unwind_plan.SetSourcedFromCompiler (eLazyBoolYes);
- unwind_plan.SetUnwindPlanValidAtAllInstructions (eLazyBoolNo);
- unwind_plan.SetRegisterKind (eRegisterKindEHFrame);
-
- unwind_plan.SetLSDAAddress (function_info.lsda_address);
- unwind_plan.SetPersonalityFunctionPtr (function_info.personality_ptr_address);
-
- UnwindPlan::RowSP row (new UnwindPlan::Row);
+ const int wordsize = 8;
+ int mode = function_info.encoding & UNWIND_ARM64_MODE_MASK;
- const int wordsize = 8;
- int mode = function_info.encoding & UNWIND_ARM64_MODE_MASK;
-
- if (mode == UNWIND_ARM64_MODE_DWARF)
- return false;
-
- if (mode == UNWIND_ARM64_MODE_FRAMELESS)
- {
- row->SetOffset (0);
-
- uint32_t stack_size = (EXTRACT_BITS (function_info.encoding, UNWIND_ARM64_FRAMELESS_STACK_SIZE_MASK)) * 16;
-
- // Our previous Call Frame Address is the stack pointer plus the stack size
- row->GetCFAValue().SetIsRegisterPlusOffset (arm64_eh_regnum::sp, stack_size);
+ if (mode == UNWIND_ARM64_MODE_DWARF)
+ return false;
- // Our previous PC is in the LR
- row->SetRegisterLocationToRegister(arm64_eh_regnum::pc, arm64_eh_regnum::ra, true);
+ if (mode == UNWIND_ARM64_MODE_FRAMELESS) {
+ row->SetOffset(0);
- unwind_plan.AppendRow (row);
- return true;
- }
+ uint32_t stack_size =
+ (EXTRACT_BITS(function_info.encoding,
+ UNWIND_ARM64_FRAMELESS_STACK_SIZE_MASK)) *
+ 16;
+
+ // Our previous Call Frame Address is the stack pointer plus the stack size
+ row->GetCFAValue().SetIsRegisterPlusOffset(arm64_eh_regnum::sp, stack_size);
+
+ // Our previous PC is in the LR
+ row->SetRegisterLocationToRegister(arm64_eh_regnum::pc, arm64_eh_regnum::ra,
+ true);
- // Should not be possible
- if (mode != UNWIND_ARM64_MODE_FRAME)
- return false;
+ unwind_plan.AppendRow(row);
+ return true;
+ }
+ // Should not be possible
+ if (mode != UNWIND_ARM64_MODE_FRAME)
+ return false;
- // mode == UNWIND_ARM64_MODE_FRAME
+ // mode == UNWIND_ARM64_MODE_FRAME
- row->GetCFAValue().SetIsRegisterPlusOffset (arm64_eh_regnum::fp , 2 * wordsize);
- row->SetOffset (0);
- row->SetRegisterLocationToAtCFAPlusOffset (arm64_eh_regnum::fp, wordsize * -2, true);
- row->SetRegisterLocationToAtCFAPlusOffset (arm64_eh_regnum::pc, wordsize * -1, true);
- row->SetRegisterLocationToIsCFAPlusOffset (arm64_eh_regnum::sp, 0, true);
-
- int reg_pairs_saved_count = 1;
-
- uint32_t saved_register_bits = function_info.encoding & 0xfff;
-
- if (saved_register_bits & UNWIND_ARM64_FRAME_X19_X20_PAIR)
- {
- int cfa_offset = reg_pairs_saved_count * -2 * wordsize;
- cfa_offset -= wordsize;
- row->SetRegisterLocationToAtCFAPlusOffset (arm64_eh_regnum::x19, cfa_offset, true);
- cfa_offset -= wordsize;
- row->SetRegisterLocationToAtCFAPlusOffset (arm64_eh_regnum::x20, cfa_offset, true);
- reg_pairs_saved_count++;
- }
-
- if (saved_register_bits & UNWIND_ARM64_FRAME_X21_X22_PAIR)
- {
- int cfa_offset = reg_pairs_saved_count * -2 * wordsize;
- cfa_offset -= wordsize;
- row->SetRegisterLocationToAtCFAPlusOffset (arm64_eh_regnum::x21, cfa_offset, true);
- cfa_offset -= wordsize;
- row->SetRegisterLocationToAtCFAPlusOffset (arm64_eh_regnum::x22, cfa_offset, true);
- reg_pairs_saved_count++;
- }
-
- if (saved_register_bits & UNWIND_ARM64_FRAME_X23_X24_PAIR)
- {
- int cfa_offset = reg_pairs_saved_count * -2 * wordsize;
- cfa_offset -= wordsize;
- row->SetRegisterLocationToAtCFAPlusOffset (arm64_eh_regnum::x23, cfa_offset, true);
- cfa_offset -= wordsize;
- row->SetRegisterLocationToAtCFAPlusOffset (arm64_eh_regnum::x24, cfa_offset, true);
- reg_pairs_saved_count++;
- }
-
- if (saved_register_bits & UNWIND_ARM64_FRAME_X25_X26_PAIR)
- {
- int cfa_offset = reg_pairs_saved_count * -2 * wordsize;
- cfa_offset -= wordsize;
- row->SetRegisterLocationToAtCFAPlusOffset (arm64_eh_regnum::x25, cfa_offset, true);
- cfa_offset -= wordsize;
- row->SetRegisterLocationToAtCFAPlusOffset (arm64_eh_regnum::x26, cfa_offset, true);
- reg_pairs_saved_count++;
- }
-
- if (saved_register_bits & UNWIND_ARM64_FRAME_X27_X28_PAIR)
- {
- int cfa_offset = reg_pairs_saved_count * -2 * wordsize;
- cfa_offset -= wordsize;
- row->SetRegisterLocationToAtCFAPlusOffset (arm64_eh_regnum::x27, cfa_offset, true);
- cfa_offset -= wordsize;
- row->SetRegisterLocationToAtCFAPlusOffset (arm64_eh_regnum::x28, cfa_offset, true);
- reg_pairs_saved_count++;
- }
-
- // If we use the v8-v15 regnums here, the unwinder will try to grab 128 bits off the stack;
- // not sure if we have a good way to represent the 64-bitness of these saves.
-
- if (saved_register_bits & UNWIND_ARM64_FRAME_D8_D9_PAIR)
- {
- reg_pairs_saved_count++;
- }
- if (saved_register_bits & UNWIND_ARM64_FRAME_D10_D11_PAIR)
- {
- reg_pairs_saved_count++;
- }
- if (saved_register_bits & UNWIND_ARM64_FRAME_D12_D13_PAIR)
- {
- reg_pairs_saved_count++;
- }
- if (saved_register_bits & UNWIND_ARM64_FRAME_D14_D15_PAIR)
- {
- reg_pairs_saved_count++;
- }
+ row->GetCFAValue().SetIsRegisterPlusOffset(arm64_eh_regnum::fp, 2 * wordsize);
+ row->SetOffset(0);
+ row->SetRegisterLocationToAtCFAPlusOffset(arm64_eh_regnum::fp, wordsize * -2,
+ true);
+ row->SetRegisterLocationToAtCFAPlusOffset(arm64_eh_regnum::pc, wordsize * -1,
+ true);
+ row->SetRegisterLocationToIsCFAPlusOffset(arm64_eh_regnum::sp, 0, true);
+
+ int reg_pairs_saved_count = 1;
+
+ uint32_t saved_register_bits = function_info.encoding & 0xfff;
+
+ if (saved_register_bits & UNWIND_ARM64_FRAME_X19_X20_PAIR) {
+ int cfa_offset = reg_pairs_saved_count * -2 * wordsize;
+ cfa_offset -= wordsize;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm64_eh_regnum::x19, cfa_offset,
+ true);
+ cfa_offset -= wordsize;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm64_eh_regnum::x20, cfa_offset,
+ true);
+ reg_pairs_saved_count++;
+ }
+
+ if (saved_register_bits & UNWIND_ARM64_FRAME_X21_X22_PAIR) {
+ int cfa_offset = reg_pairs_saved_count * -2 * wordsize;
+ cfa_offset -= wordsize;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm64_eh_regnum::x21, cfa_offset,
+ true);
+ cfa_offset -= wordsize;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm64_eh_regnum::x22, cfa_offset,
+ true);
+ reg_pairs_saved_count++;
+ }
+
+ if (saved_register_bits & UNWIND_ARM64_FRAME_X23_X24_PAIR) {
+ int cfa_offset = reg_pairs_saved_count * -2 * wordsize;
+ cfa_offset -= wordsize;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm64_eh_regnum::x23, cfa_offset,
+ true);
+ cfa_offset -= wordsize;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm64_eh_regnum::x24, cfa_offset,
+ true);
+ reg_pairs_saved_count++;
+ }
+
+ if (saved_register_bits & UNWIND_ARM64_FRAME_X25_X26_PAIR) {
+ int cfa_offset = reg_pairs_saved_count * -2 * wordsize;
+ cfa_offset -= wordsize;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm64_eh_regnum::x25, cfa_offset,
+ true);
+ cfa_offset -= wordsize;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm64_eh_regnum::x26, cfa_offset,
+ true);
+ reg_pairs_saved_count++;
+ }
+
+ if (saved_register_bits & UNWIND_ARM64_FRAME_X27_X28_PAIR) {
+ int cfa_offset = reg_pairs_saved_count * -2 * wordsize;
+ cfa_offset -= wordsize;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm64_eh_regnum::x27, cfa_offset,
+ true);
+ cfa_offset -= wordsize;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm64_eh_regnum::x28, cfa_offset,
+ true);
+ reg_pairs_saved_count++;
+ }
+
+ // If we use the v8-v15 regnums here, the unwinder will try to grab 128 bits
+ // off the stack;
+ // not sure if we have a good way to represent the 64-bitness of these saves.
+
+ if (saved_register_bits & UNWIND_ARM64_FRAME_D8_D9_PAIR) {
+ reg_pairs_saved_count++;
+ }
+ if (saved_register_bits & UNWIND_ARM64_FRAME_D10_D11_PAIR) {
+ reg_pairs_saved_count++;
+ }
+ if (saved_register_bits & UNWIND_ARM64_FRAME_D12_D13_PAIR) {
+ reg_pairs_saved_count++;
+ }
+ if (saved_register_bits & UNWIND_ARM64_FRAME_D14_D15_PAIR) {
+ reg_pairs_saved_count++;
+ }
- unwind_plan.AppendRow (row);
- return true;
+ unwind_plan.AppendRow(row);
+ return true;
}
-bool
-CompactUnwindInfo::CreateUnwindPlan_armv7 (Target &target, FunctionInfo &function_info, UnwindPlan &unwind_plan, Address pc_or_function_start)
-{
- unwind_plan.SetSourceName ("compact unwind info");
- unwind_plan.SetSourcedFromCompiler (eLazyBoolYes);
- unwind_plan.SetUnwindPlanValidAtAllInstructions (eLazyBoolNo);
- unwind_plan.SetRegisterKind (eRegisterKindEHFrame);
-
- unwind_plan.SetLSDAAddress (function_info.lsda_address);
- unwind_plan.SetPersonalityFunctionPtr (function_info.personality_ptr_address);
-
- UnwindPlan::RowSP row (new UnwindPlan::Row);
+bool CompactUnwindInfo::CreateUnwindPlan_armv7(Target &target,
+ FunctionInfo &function_info,
+ UnwindPlan &unwind_plan,
+ Address pc_or_function_start) {
+ unwind_plan.SetSourceName("compact unwind info");
+ unwind_plan.SetSourcedFromCompiler(eLazyBoolYes);
+ unwind_plan.SetUnwindPlanValidAtAllInstructions(eLazyBoolNo);
+ unwind_plan.SetRegisterKind(eRegisterKindEHFrame);
+
+ unwind_plan.SetLSDAAddress(function_info.lsda_address);
+ unwind_plan.SetPersonalityFunctionPtr(function_info.personality_ptr_address);
- const int wordsize = 4;
- int mode = function_info.encoding & UNWIND_ARM_MODE_MASK;
+ UnwindPlan::RowSP row(new UnwindPlan::Row);
- if (mode == UNWIND_ARM_MODE_DWARF)
- return false;
+ const int wordsize = 4;
+ int mode = function_info.encoding & UNWIND_ARM_MODE_MASK;
- uint32_t stack_adjust = (EXTRACT_BITS (function_info.encoding, UNWIND_ARM_FRAME_STACK_ADJUST_MASK)) * wordsize;
-
- row->GetCFAValue().SetIsRegisterPlusOffset (arm_r7 , (2 * wordsize) + stack_adjust);
- row->SetOffset (0);
- row->SetRegisterLocationToAtCFAPlusOffset (arm_r7, (wordsize * -2) - stack_adjust, true);
- row->SetRegisterLocationToAtCFAPlusOffset (arm_pc, (wordsize * -1) - stack_adjust, true);
- row->SetRegisterLocationToIsCFAPlusOffset (arm_sp, 0, true);
-
- int cfa_offset = -stack_adjust - (2 * wordsize);
-
- uint32_t saved_register_bits = function_info.encoding & 0xff;
-
- if (saved_register_bits & UNWIND_ARM_FRAME_FIRST_PUSH_R6)
- {
- cfa_offset -= wordsize;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_r6, cfa_offset, true);
- }
-
- if (saved_register_bits & UNWIND_ARM_FRAME_FIRST_PUSH_R5)
- {
- cfa_offset -= wordsize;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_r5, cfa_offset, true);
- }
-
- if (saved_register_bits & UNWIND_ARM_FRAME_FIRST_PUSH_R4)
- {
- cfa_offset -= wordsize;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_r4, cfa_offset, true);
- }
-
- if (saved_register_bits & UNWIND_ARM_FRAME_SECOND_PUSH_R12)
- {
- cfa_offset -= wordsize;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_r12, cfa_offset, true);
- }
-
- if (saved_register_bits & UNWIND_ARM_FRAME_SECOND_PUSH_R11)
- {
- cfa_offset -= wordsize;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_r11, cfa_offset, true);
- }
-
- if (saved_register_bits & UNWIND_ARM_FRAME_SECOND_PUSH_R10)
- {
- cfa_offset -= wordsize;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_r10, cfa_offset, true);
- }
-
- if (saved_register_bits & UNWIND_ARM_FRAME_SECOND_PUSH_R9)
- {
- cfa_offset -= wordsize;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_r9, cfa_offset, true);
- }
-
- if (saved_register_bits & UNWIND_ARM_FRAME_SECOND_PUSH_R8)
- {
- cfa_offset -= wordsize;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_r8, cfa_offset, true);
- }
-
-
- if (mode == UNWIND_ARM_MODE_FRAME_D)
- {
- uint32_t d_reg_bits = EXTRACT_BITS (function_info.encoding, UNWIND_ARM_FRAME_D_REG_COUNT_MASK);
- switch (d_reg_bits)
- {
- case 0:
- // vpush {d8}
- cfa_offset -= 8;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_d8, cfa_offset, true);
- break;
- case 1:
- // vpush {d10}
- // vpush {d8}
- cfa_offset -= 8;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_d10, cfa_offset, true);
- cfa_offset -= 8;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_d8, cfa_offset, true);
- break;
- case 2:
- // vpush {d12}
- // vpush {d10}
- // vpush {d8}
- cfa_offset -= 8;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_d12, cfa_offset, true);
- cfa_offset -= 8;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_d10, cfa_offset, true);
- cfa_offset -= 8;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_d8, cfa_offset, true);
- break;
- case 3:
- // vpush {d14}
- // vpush {d12}
- // vpush {d10}
- // vpush {d8}
- cfa_offset -= 8;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_d14, cfa_offset, true);
- cfa_offset -= 8;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_d12, cfa_offset, true);
- cfa_offset -= 8;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_d10, cfa_offset, true);
- cfa_offset -= 8;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_d8, cfa_offset, true);
- break;
- case 4:
- // vpush {d14}
- // vpush {d12}
- // sp = (sp - 24) & (-16);
- // vst {d8, d9, d10}
- cfa_offset -= 8;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_d14, cfa_offset, true);
- cfa_offset -= 8;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_d12, cfa_offset, true);
-
- // FIXME we don't have a way to represent reg saves at an specific alignment short of
- // coming up with some DWARF location description.
-
- break;
- case 5:
- // vpush {d14}
- // sp = (sp - 40) & (-16);
- // vst {d8, d9, d10, d11}
- // vst {d12}
-
- cfa_offset -= 8;
- row->SetRegisterLocationToAtCFAPlusOffset (arm_d14, cfa_offset, true);
-
- // FIXME we don't have a way to represent reg saves at an specific alignment short of
- // coming up with some DWARF location description.
-
- break;
- case 6:
- // sp = (sp - 56) & (-16);
- // vst {d8, d9, d10, d11}
- // vst {d12, d13, d14}
-
- // FIXME we don't have a way to represent reg saves at an specific alignment short of
- // coming up with some DWARF location description.
-
- break;
- case 7:
- // sp = (sp - 64) & (-16);
- // vst {d8, d9, d10, d11}
- // vst {d12, d13, d14, d15}
+ if (mode == UNWIND_ARM_MODE_DWARF)
+ return false;
- // FIXME we don't have a way to represent reg saves at an specific alignment short of
- // coming up with some DWARF location description.
+ uint32_t stack_adjust = (EXTRACT_BITS(function_info.encoding,
+ UNWIND_ARM_FRAME_STACK_ADJUST_MASK)) *
+ wordsize;
+
+ row->GetCFAValue().SetIsRegisterPlusOffset(arm_r7,
+ (2 * wordsize) + stack_adjust);
+ row->SetOffset(0);
+ row->SetRegisterLocationToAtCFAPlusOffset(
+ arm_r7, (wordsize * -2) - stack_adjust, true);
+ row->SetRegisterLocationToAtCFAPlusOffset(
+ arm_pc, (wordsize * -1) - stack_adjust, true);
+ row->SetRegisterLocationToIsCFAPlusOffset(arm_sp, 0, true);
+
+ int cfa_offset = -stack_adjust - (2 * wordsize);
+
+ uint32_t saved_register_bits = function_info.encoding & 0xff;
+
+ if (saved_register_bits & UNWIND_ARM_FRAME_FIRST_PUSH_R6) {
+ cfa_offset -= wordsize;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_r6, cfa_offset, true);
+ }
+
+ if (saved_register_bits & UNWIND_ARM_FRAME_FIRST_PUSH_R5) {
+ cfa_offset -= wordsize;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_r5, cfa_offset, true);
+ }
+
+ if (saved_register_bits & UNWIND_ARM_FRAME_FIRST_PUSH_R4) {
+ cfa_offset -= wordsize;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_r4, cfa_offset, true);
+ }
+
+ if (saved_register_bits & UNWIND_ARM_FRAME_SECOND_PUSH_R12) {
+ cfa_offset -= wordsize;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_r12, cfa_offset, true);
+ }
+
+ if (saved_register_bits & UNWIND_ARM_FRAME_SECOND_PUSH_R11) {
+ cfa_offset -= wordsize;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_r11, cfa_offset, true);
+ }
+
+ if (saved_register_bits & UNWIND_ARM_FRAME_SECOND_PUSH_R10) {
+ cfa_offset -= wordsize;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_r10, cfa_offset, true);
+ }
+
+ if (saved_register_bits & UNWIND_ARM_FRAME_SECOND_PUSH_R9) {
+ cfa_offset -= wordsize;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_r9, cfa_offset, true);
+ }
+
+ if (saved_register_bits & UNWIND_ARM_FRAME_SECOND_PUSH_R8) {
+ cfa_offset -= wordsize;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_r8, cfa_offset, true);
+ }
+
+ if (mode == UNWIND_ARM_MODE_FRAME_D) {
+ uint32_t d_reg_bits =
+ EXTRACT_BITS(function_info.encoding, UNWIND_ARM_FRAME_D_REG_COUNT_MASK);
+ switch (d_reg_bits) {
+ case 0:
+ // vpush {d8}
+ cfa_offset -= 8;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_d8, cfa_offset, true);
+ break;
+ case 1:
+ // vpush {d10}
+ // vpush {d8}
+ cfa_offset -= 8;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_d10, cfa_offset, true);
+ cfa_offset -= 8;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_d8, cfa_offset, true);
+ break;
+ case 2:
+ // vpush {d12}
+ // vpush {d10}
+ // vpush {d8}
+ cfa_offset -= 8;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_d12, cfa_offset, true);
+ cfa_offset -= 8;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_d10, cfa_offset, true);
+ cfa_offset -= 8;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_d8, cfa_offset, true);
+ break;
+ case 3:
+ // vpush {d14}
+ // vpush {d12}
+ // vpush {d10}
+ // vpush {d8}
+ cfa_offset -= 8;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_d14, cfa_offset, true);
+ cfa_offset -= 8;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_d12, cfa_offset, true);
+ cfa_offset -= 8;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_d10, cfa_offset, true);
+ cfa_offset -= 8;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_d8, cfa_offset, true);
+ break;
+ case 4:
+ // vpush {d14}
+ // vpush {d12}
+ // sp = (sp - 24) & (-16);
+ // vst {d8, d9, d10}
+ cfa_offset -= 8;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_d14, cfa_offset, true);
+ cfa_offset -= 8;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_d12, cfa_offset, true);
+
+ // FIXME we don't have a way to represent reg saves at an specific
+ // alignment short of
+ // coming up with some DWARF location description.
+
+ break;
+ case 5:
+ // vpush {d14}
+ // sp = (sp - 40) & (-16);
+ // vst {d8, d9, d10, d11}
+ // vst {d12}
+
+ cfa_offset -= 8;
+ row->SetRegisterLocationToAtCFAPlusOffset(arm_d14, cfa_offset, true);
+
+ // FIXME we don't have a way to represent reg saves at an specific
+ // alignment short of
+ // coming up with some DWARF location description.
+
+ break;
+ case 6:
+ // sp = (sp - 56) & (-16);
+ // vst {d8, d9, d10, d11}
+ // vst {d12, d13, d14}
+
+ // FIXME we don't have a way to represent reg saves at an specific
+ // alignment short of
+ // coming up with some DWARF location description.
+
+ break;
+ case 7:
+ // sp = (sp - 64) & (-16);
+ // vst {d8, d9, d10, d11}
+ // vst {d12, d13, d14, d15}
+
+ // FIXME we don't have a way to represent reg saves at an specific
+ // alignment short of
+ // coming up with some DWARF location description.
- break;
- }
+ break;
}
+ }
- unwind_plan.AppendRow (row);
- return true;
+ unwind_plan.AppendRow(row);
+ return true;
}
-
-
Modified: lldb/trunk/source/Symbol/CompileUnit.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/CompileUnit.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/CompileUnit.cpp (original)
+++ lldb/trunk/source/Symbol/CompileUnit.cpp Tue Sep 6 15:57:50 2016
@@ -17,84 +17,54 @@
using namespace lldb;
using namespace lldb_private;
-CompileUnit::CompileUnit(const lldb::ModuleSP &module_sp, void *user_data, const char *pathname,
- const lldb::user_id_t cu_sym_id, lldb::LanguageType language,
+CompileUnit::CompileUnit(const lldb::ModuleSP &module_sp, void *user_data,
+ const char *pathname, const lldb::user_id_t cu_sym_id,
+ lldb::LanguageType language,
lldb_private::LazyBool is_optimized)
- : ModuleChild(module_sp),
- FileSpec(pathname, false),
- UserID(cu_sym_id),
- m_user_data(user_data),
- m_language(language),
- m_flags(0),
- m_functions(),
- m_support_files(),
- m_line_table_ap(),
- m_variables(),
- m_is_optimized(is_optimized)
-{
- if (language != eLanguageTypeUnknown)
- m_flags.Set(flagsParsedLanguage);
- assert(module_sp);
+ : ModuleChild(module_sp), FileSpec(pathname, false), UserID(cu_sym_id),
+ m_user_data(user_data), m_language(language), m_flags(0), m_functions(),
+ m_support_files(), m_line_table_ap(), m_variables(),
+ m_is_optimized(is_optimized) {
+ if (language != eLanguageTypeUnknown)
+ m_flags.Set(flagsParsedLanguage);
+ assert(module_sp);
}
-CompileUnit::CompileUnit(const lldb::ModuleSP &module_sp, void *user_data, const FileSpec &fspec,
- const lldb::user_id_t cu_sym_id, lldb::LanguageType language,
+CompileUnit::CompileUnit(const lldb::ModuleSP &module_sp, void *user_data,
+ const FileSpec &fspec, const lldb::user_id_t cu_sym_id,
+ lldb::LanguageType language,
lldb_private::LazyBool is_optimized)
- : ModuleChild(module_sp),
- FileSpec(fspec),
- UserID(cu_sym_id),
- m_user_data(user_data),
- m_language(language),
- m_flags(0),
- m_functions(),
- m_support_files(),
- m_line_table_ap(),
- m_variables(),
- m_is_optimized(is_optimized)
-{
- if (language != eLanguageTypeUnknown)
- m_flags.Set(flagsParsedLanguage);
- assert(module_sp);
-}
-
-CompileUnit::~CompileUnit ()
-{
-}
-
-void
-CompileUnit::CalculateSymbolContext(SymbolContext* sc)
-{
- sc->comp_unit = this;
- GetModule()->CalculateSymbolContext(sc);
-}
-
-ModuleSP
-CompileUnit::CalculateSymbolContextModule ()
-{
- return GetModule();
-}
-
-CompileUnit *
-CompileUnit::CalculateSymbolContextCompileUnit ()
-{
- return this;
-}
-
-void
-CompileUnit::DumpSymbolContext(Stream *s)
-{
- GetModule()->DumpSymbolContext(s);
- s->Printf(", CompileUnit{0x%8.8" PRIx64 "}", GetID());
+ : ModuleChild(module_sp), FileSpec(fspec), UserID(cu_sym_id),
+ m_user_data(user_data), m_language(language), m_flags(0), m_functions(),
+ m_support_files(), m_line_table_ap(), m_variables(),
+ m_is_optimized(is_optimized) {
+ if (language != eLanguageTypeUnknown)
+ m_flags.Set(flagsParsedLanguage);
+ assert(module_sp);
}
+CompileUnit::~CompileUnit() {}
-void
-CompileUnit::GetDescription(Stream *s, lldb::DescriptionLevel level) const
-{
- const char* language = Language::GetNameForLanguageType(m_language);
- *s << "id = " << (const UserID&)*this << ", file = \"" << (const FileSpec&)*this << "\", language = \"" << language << '"';
+void CompileUnit::CalculateSymbolContext(SymbolContext *sc) {
+ sc->comp_unit = this;
+ GetModule()->CalculateSymbolContext(sc);
}
+ModuleSP CompileUnit::CalculateSymbolContextModule() { return GetModule(); }
+
+CompileUnit *CompileUnit::CalculateSymbolContextCompileUnit() { return this; }
+
+void CompileUnit::DumpSymbolContext(Stream *s) {
+ GetModule()->DumpSymbolContext(s);
+ s->Printf(", CompileUnit{0x%8.8" PRIx64 "}", GetID());
+}
+
+void CompileUnit::GetDescription(Stream *s,
+ lldb::DescriptionLevel level) const {
+ const char *language = Language::GetNameForLanguageType(m_language);
+ *s << "id = " << (const UserID &)*this << ", file = \""
+ << (const FileSpec &)*this << "\", language = \"" << language << '"';
+}
//----------------------------------------------------------------------
// Dump the current contents of this object. No functions that cause on
@@ -102,58 +72,49 @@ CompileUnit::GetDescription(Stream *s, l
// is a good function to call to get an idea of the current contents of
// the CompileUnit object.
//----------------------------------------------------------------------
-void
-CompileUnit::Dump(Stream *s, bool show_context) const
-{
- const char* language = Language::GetNameForLanguageType(m_language);
-
- s->Printf("%p: ", static_cast<const void*>(this));
- s->Indent();
- *s << "CompileUnit" << static_cast<const UserID&>(*this)
- << ", language = \"" << language
- << "\", file = '" << static_cast<const FileSpec&>(*this) << "'\n";
-
-// m_types.Dump(s);
-
- if (m_variables.get())
- {
- s->IndentMore();
- m_variables->Dump(s, show_context);
- s->IndentLess();
- }
+void CompileUnit::Dump(Stream *s, bool show_context) const {
+ const char *language = Language::GetNameForLanguageType(m_language);
- if (!m_functions.empty())
- {
- s->IndentMore();
- std::vector<FunctionSP>::const_iterator pos;
- std::vector<FunctionSP>::const_iterator end = m_functions.end();
- for (pos = m_functions.begin(); pos != end; ++pos)
- {
- (*pos)->Dump(s, show_context);
- }
-
- s->IndentLess();
- s->EOL();
- }
+ s->Printf("%p: ", static_cast<const void *>(this));
+ s->Indent();
+ *s << "CompileUnit" << static_cast<const UserID &>(*this) << ", language = \""
+ << language << "\", file = '" << static_cast<const FileSpec &>(*this)
+ << "'\n";
+
+ // m_types.Dump(s);
+
+ if (m_variables.get()) {
+ s->IndentMore();
+ m_variables->Dump(s, show_context);
+ s->IndentLess();
+ }
+
+ if (!m_functions.empty()) {
+ s->IndentMore();
+ std::vector<FunctionSP>::const_iterator pos;
+ std::vector<FunctionSP>::const_iterator end = m_functions.end();
+ for (pos = m_functions.begin(); pos != end; ++pos) {
+ (*pos)->Dump(s, show_context);
+ }
+
+ s->IndentLess();
+ s->EOL();
+ }
}
//----------------------------------------------------------------------
// Add a function to this compile unit
//----------------------------------------------------------------------
-void
-CompileUnit::AddFunction(FunctionSP& funcSP)
-{
- // TODO: order these by address
- m_functions.push_back(funcSP);
+void CompileUnit::AddFunction(FunctionSP &funcSP) {
+ // TODO: order these by address
+ m_functions.push_back(funcSP);
}
-FunctionSP
-CompileUnit::GetFunctionAtIndex (size_t idx)
-{
- FunctionSP funcSP;
- if (idx < m_functions.size())
- funcSP = m_functions[idx];
- return funcSP;
+FunctionSP CompileUnit::GetFunctionAtIndex(size_t idx) {
+ FunctionSP funcSP;
+ if (idx < m_functions.size())
+ funcSP = m_functions[idx];
+ return funcSP;
}
//----------------------------------------------------------------------
@@ -180,8 +141,8 @@ CompileUnit::GetFunctionAtIndex (size_t
// parsed by the SymbolFile parser plug-ins and registered with each
// Module).
//----------------------------------------------------------------------
-//void
-//CompileUnit::FindFunctions(const Mangled::Tokens& tokens)
+// void
+// CompileUnit::FindFunctions(const Mangled::Tokens& tokens)
//{
// if (!m_functions.empty())
// {
@@ -193,7 +154,8 @@ CompileUnit::GetFunctionAtIndex (size_t
// const ConstString& demangled = (*pos)->Mangled().Demangled();
// if (demangled)
// {
-// const Mangled::Tokens& func_tokens = (*pos)->Mangled().GetTokens();
+// const Mangled::Tokens& func_tokens =
+// (*pos)->Mangled().GetTokens();
// if (func_tokens.MatchesQuery (tokens))
// s << "demangled MATCH found: " << demangled << "\n";
// }
@@ -201,338 +163,272 @@ CompileUnit::GetFunctionAtIndex (size_t
// }
//}
-FunctionSP
-CompileUnit::FindFunctionByUID (lldb::user_id_t func_uid)
-{
- FunctionSP funcSP;
- if (!m_functions.empty())
- {
- std::vector<FunctionSP>::const_iterator pos;
- std::vector<FunctionSP>::const_iterator end = m_functions.end();
- for (pos = m_functions.begin(); pos != end; ++pos)
- {
- if ((*pos)->GetID() == func_uid)
- {
- funcSP = *pos;
- break;
- }
- }
- }
- return funcSP;
-}
-
-
-lldb::LanguageType
-CompileUnit::GetLanguage()
-{
- if (m_language == eLanguageTypeUnknown)
- {
- if (m_flags.IsClear(flagsParsedLanguage))
- {
- m_flags.Set(flagsParsedLanguage);
- SymbolVendor* symbol_vendor = GetModule()->GetSymbolVendor();
- if (symbol_vendor)
- {
- SymbolContext sc;
- CalculateSymbolContext(&sc);
- m_language = symbol_vendor->ParseCompileUnitLanguage(sc);
- }
- }
- }
- return m_language;
-}
-
-LineTable*
-CompileUnit::GetLineTable()
-{
- if (m_line_table_ap.get() == nullptr)
- {
- if (m_flags.IsClear(flagsParsedLineTable))
- {
- m_flags.Set(flagsParsedLineTable);
- SymbolVendor* symbol_vendor = GetModule()->GetSymbolVendor();
- if (symbol_vendor)
- {
- SymbolContext sc;
- CalculateSymbolContext(&sc);
- symbol_vendor->ParseCompileUnitLineTable(sc);
- }
- }
+FunctionSP CompileUnit::FindFunctionByUID(lldb::user_id_t func_uid) {
+ FunctionSP funcSP;
+ if (!m_functions.empty()) {
+ std::vector<FunctionSP>::const_iterator pos;
+ std::vector<FunctionSP>::const_iterator end = m_functions.end();
+ for (pos = m_functions.begin(); pos != end; ++pos) {
+ if ((*pos)->GetID() == func_uid) {
+ funcSP = *pos;
+ break;
+ }
+ }
+ }
+ return funcSP;
+}
+
+lldb::LanguageType CompileUnit::GetLanguage() {
+ if (m_language == eLanguageTypeUnknown) {
+ if (m_flags.IsClear(flagsParsedLanguage)) {
+ m_flags.Set(flagsParsedLanguage);
+ SymbolVendor *symbol_vendor = GetModule()->GetSymbolVendor();
+ if (symbol_vendor) {
+ SymbolContext sc;
+ CalculateSymbolContext(&sc);
+ m_language = symbol_vendor->ParseCompileUnitLanguage(sc);
+ }
}
- return m_line_table_ap.get();
+ }
+ return m_language;
}
-void
-CompileUnit::SetLineTable(LineTable* line_table)
-{
- if (line_table == nullptr)
- m_flags.Clear(flagsParsedLineTable);
- else
- m_flags.Set(flagsParsedLineTable);
- m_line_table_ap.reset(line_table);
-}
-
-DebugMacros*
-CompileUnit::GetDebugMacros()
-{
- if (m_debug_macros_sp.get() == nullptr)
- {
- if (m_flags.IsClear(flagsParsedDebugMacros))
- {
- m_flags.Set(flagsParsedDebugMacros);
- SymbolVendor* symbol_vendor = GetModule()->GetSymbolVendor();
- if (symbol_vendor)
- {
- SymbolContext sc;
- CalculateSymbolContext(&sc);
- symbol_vendor->ParseCompileUnitDebugMacros(sc);
- }
- }
- }
-
- return m_debug_macros_sp.get();
-}
-
-void
-CompileUnit::SetDebugMacros(const DebugMacrosSP &debug_macros_sp)
-{
- if (debug_macros_sp.get() == nullptr)
- m_flags.Clear(flagsParsedDebugMacros);
- else
- m_flags.Set(flagsParsedDebugMacros);
- m_debug_macros_sp = debug_macros_sp;
-}
-
-VariableListSP
-CompileUnit::GetVariableList(bool can_create)
-{
- if (m_variables.get() == nullptr && can_create)
- {
+LineTable *CompileUnit::GetLineTable() {
+ if (m_line_table_ap.get() == nullptr) {
+ if (m_flags.IsClear(flagsParsedLineTable)) {
+ m_flags.Set(flagsParsedLineTable);
+ SymbolVendor *symbol_vendor = GetModule()->GetSymbolVendor();
+ if (symbol_vendor) {
SymbolContext sc;
CalculateSymbolContext(&sc);
- assert(sc.module_sp);
- sc.module_sp->GetSymbolVendor()->ParseVariablesForContext(sc);
+ symbol_vendor->ParseCompileUnitLineTable(sc);
+ }
}
-
- return m_variables;
+ }
+ return m_line_table_ap.get();
}
-uint32_t
-CompileUnit::FindLineEntry (uint32_t start_idx, uint32_t line, const FileSpec* file_spec_ptr, bool exact, LineEntry *line_entry_ptr)
-{
- uint32_t file_idx = 0;
-
- if (file_spec_ptr)
- {
- file_idx = GetSupportFiles().FindFileIndex (1, *file_spec_ptr, true);
- if (file_idx == UINT32_MAX)
- return UINT32_MAX;
- }
- else
- {
- // All the line table entries actually point to the version of the Compile
- // Unit that is in the support files (the one at 0 was artificially added.)
- // So prefer the one further on in the support files if it exists...
- FileSpecList &support_files = GetSupportFiles();
- const bool full = true;
- file_idx = support_files.FindFileIndex (1, support_files.GetFileSpecAtIndex(0), full);
- if (file_idx == UINT32_MAX)
- file_idx = 0;
+void CompileUnit::SetLineTable(LineTable *line_table) {
+ if (line_table == nullptr)
+ m_flags.Clear(flagsParsedLineTable);
+ else
+ m_flags.Set(flagsParsedLineTable);
+ m_line_table_ap.reset(line_table);
+}
+
+DebugMacros *CompileUnit::GetDebugMacros() {
+ if (m_debug_macros_sp.get() == nullptr) {
+ if (m_flags.IsClear(flagsParsedDebugMacros)) {
+ m_flags.Set(flagsParsedDebugMacros);
+ SymbolVendor *symbol_vendor = GetModule()->GetSymbolVendor();
+ if (symbol_vendor) {
+ SymbolContext sc;
+ CalculateSymbolContext(&sc);
+ symbol_vendor->ParseCompileUnitDebugMacros(sc);
+ }
}
- LineTable *line_table = GetLineTable();
- if (line_table)
- return line_table->FindLineEntryIndexByFileIndex (start_idx, file_idx, line, exact, line_entry_ptr);
- return UINT32_MAX;
-}
+ }
-
-
-
-uint32_t
-CompileUnit::ResolveSymbolContext
-(
- const FileSpec& file_spec,
- uint32_t line,
- bool check_inlines,
- bool exact,
- uint32_t resolve_scope,
- SymbolContextList &sc_list
-)
-{
- // First find all of the file indexes that match our "file_spec". If
- // "file_spec" has an empty directory, then only compare the basenames
- // when finding file indexes
- std::vector<uint32_t> file_indexes;
- const bool full_match = (bool)file_spec.GetDirectory();
- const bool remove_backup_dots = true;
- bool file_spec_matches_cu_file_spec = FileSpec::Equal(file_spec, *this, full_match, remove_backup_dots);
-
- // If we are not looking for inlined functions and our file spec doesn't
- // match then we are done...
- if (file_spec_matches_cu_file_spec == false && check_inlines == false)
- return 0;
-
- uint32_t file_idx = GetSupportFiles().FindFileIndex (1, file_spec, true, remove_backup_dots);
- while (file_idx != UINT32_MAX)
- {
- file_indexes.push_back (file_idx);
- file_idx = GetSupportFiles().FindFileIndex (file_idx + 1, file_spec, true, remove_backup_dots);
- }
-
- const size_t num_file_indexes = file_indexes.size();
- if (num_file_indexes == 0)
- return 0;
-
- const uint32_t prev_size = sc_list.GetSize();
-
- SymbolContext sc(GetModule());
- sc.comp_unit = this;
-
-
- if (line != 0)
- {
- LineTable *line_table = sc.comp_unit->GetLineTable();
-
- if (line_table != nullptr)
- {
- uint32_t found_line;
- uint32_t line_idx;
-
- if (num_file_indexes == 1)
- {
- // We only have a single support file that matches, so use
- // the line table function that searches for a line entries
- // that match a single support file index
- LineEntry line_entry;
- line_idx = line_table->FindLineEntryIndexByFileIndex (0, file_indexes.front(), line, exact, &line_entry);
-
- // If "exact == true", then "found_line" will be the same
- // as "line". If "exact == false", the "found_line" will be the
- // closest line entry with a line number greater than "line" and
- // we will use this for our subsequent line exact matches below.
- found_line = line_entry.line;
-
- while (line_idx != UINT32_MAX)
- {
- // If they only asked for the line entry, then we're done, we can just copy that over.
- // But if they wanted more than just the line number, fill it in.
- if (resolve_scope == eSymbolContextLineEntry)
- {
- sc.line_entry = line_entry;
- }
- else
- {
- line_entry.range.GetBaseAddress().CalculateSymbolContext(&sc, resolve_scope);
- }
-
- sc_list.Append(sc);
- line_idx = line_table->FindLineEntryIndexByFileIndex (line_idx + 1, file_indexes.front(), found_line, true, &line_entry);
- }
- }
- else
- {
- // We found multiple support files that match "file_spec" so use
- // the line table function that searches for a line entries
- // that match a multiple support file indexes.
- LineEntry line_entry;
- line_idx = line_table->FindLineEntryIndexByFileIndex (0, file_indexes, line, exact, &line_entry);
-
- // If "exact == true", then "found_line" will be the same
- // as "line". If "exact == false", the "found_line" will be the
- // closest line entry with a line number greater than "line" and
- // we will use this for our subsequent line exact matches below.
- found_line = line_entry.line;
-
- while (line_idx != UINT32_MAX)
- {
- if (resolve_scope == eSymbolContextLineEntry)
- {
- sc.line_entry = line_entry;
- }
- else
- {
- line_entry.range.GetBaseAddress().CalculateSymbolContext(&sc, resolve_scope);
- }
-
- sc_list.Append(sc);
- line_idx = line_table->FindLineEntryIndexByFileIndex (line_idx + 1, file_indexes, found_line, true, &line_entry);
- }
- }
- }
- }
- else if (file_spec_matches_cu_file_spec && !check_inlines)
- {
- // only append the context if we aren't looking for inline call sites
- // by file and line and if the file spec matches that of the compile unit
- sc_list.Append(sc);
- }
- return sc_list.GetSize() - prev_size;
+ return m_debug_macros_sp.get();
}
-bool
-CompileUnit::GetIsOptimized ()
-{
- if (m_is_optimized == eLazyBoolCalculate)
- {
- m_is_optimized = eLazyBoolNo;
- if (SymbolVendor *symbol_vendor = GetModule()->GetSymbolVendor())
- {
- SymbolContext sc;
- CalculateSymbolContext(&sc);
- if (symbol_vendor->ParseCompileUnitIsOptimized(sc))
- m_is_optimized = eLazyBoolYes;
+void CompileUnit::SetDebugMacros(const DebugMacrosSP &debug_macros_sp) {
+ if (debug_macros_sp.get() == nullptr)
+ m_flags.Clear(flagsParsedDebugMacros);
+ else
+ m_flags.Set(flagsParsedDebugMacros);
+ m_debug_macros_sp = debug_macros_sp;
+}
+
+VariableListSP CompileUnit::GetVariableList(bool can_create) {
+ if (m_variables.get() == nullptr && can_create) {
+ SymbolContext sc;
+ CalculateSymbolContext(&sc);
+ assert(sc.module_sp);
+ sc.module_sp->GetSymbolVendor()->ParseVariablesForContext(sc);
+ }
+
+ return m_variables;
+}
+
+uint32_t CompileUnit::FindLineEntry(uint32_t start_idx, uint32_t line,
+ const FileSpec *file_spec_ptr, bool exact,
+ LineEntry *line_entry_ptr) {
+ uint32_t file_idx = 0;
+
+ if (file_spec_ptr) {
+ file_idx = GetSupportFiles().FindFileIndex(1, *file_spec_ptr, true);
+ if (file_idx == UINT32_MAX)
+ return UINT32_MAX;
+ } else {
+ // All the line table entries actually point to the version of the Compile
+ // Unit that is in the support files (the one at 0 was artificially added.)
+ // So prefer the one further on in the support files if it exists...
+ FileSpecList &support_files = GetSupportFiles();
+ const bool full = true;
+ file_idx = support_files.FindFileIndex(
+ 1, support_files.GetFileSpecAtIndex(0), full);
+ if (file_idx == UINT32_MAX)
+ file_idx = 0;
+ }
+ LineTable *line_table = GetLineTable();
+ if (line_table)
+ return line_table->FindLineEntryIndexByFileIndex(start_idx, file_idx, line,
+ exact, line_entry_ptr);
+ return UINT32_MAX;
+}
+
+uint32_t CompileUnit::ResolveSymbolContext(const FileSpec &file_spec,
+ uint32_t line, bool check_inlines,
+ bool exact, uint32_t resolve_scope,
+ SymbolContextList &sc_list) {
+ // First find all of the file indexes that match our "file_spec". If
+ // "file_spec" has an empty directory, then only compare the basenames
+ // when finding file indexes
+ std::vector<uint32_t> file_indexes;
+ const bool full_match = (bool)file_spec.GetDirectory();
+ const bool remove_backup_dots = true;
+ bool file_spec_matches_cu_file_spec =
+ FileSpec::Equal(file_spec, *this, full_match, remove_backup_dots);
+
+ // If we are not looking for inlined functions and our file spec doesn't
+ // match then we are done...
+ if (file_spec_matches_cu_file_spec == false && check_inlines == false)
+ return 0;
+
+ uint32_t file_idx =
+ GetSupportFiles().FindFileIndex(1, file_spec, true, remove_backup_dots);
+ while (file_idx != UINT32_MAX) {
+ file_indexes.push_back(file_idx);
+ file_idx = GetSupportFiles().FindFileIndex(file_idx + 1, file_spec, true,
+ remove_backup_dots);
+ }
+
+ const size_t num_file_indexes = file_indexes.size();
+ if (num_file_indexes == 0)
+ return 0;
+
+ const uint32_t prev_size = sc_list.GetSize();
+
+ SymbolContext sc(GetModule());
+ sc.comp_unit = this;
+
+ if (line != 0) {
+ LineTable *line_table = sc.comp_unit->GetLineTable();
+
+ if (line_table != nullptr) {
+ uint32_t found_line;
+ uint32_t line_idx;
+
+ if (num_file_indexes == 1) {
+ // We only have a single support file that matches, so use
+ // the line table function that searches for a line entries
+ // that match a single support file index
+ LineEntry line_entry;
+ line_idx = line_table->FindLineEntryIndexByFileIndex(
+ 0, file_indexes.front(), line, exact, &line_entry);
+
+ // If "exact == true", then "found_line" will be the same
+ // as "line". If "exact == false", the "found_line" will be the
+ // closest line entry with a line number greater than "line" and
+ // we will use this for our subsequent line exact matches below.
+ found_line = line_entry.line;
+
+ while (line_idx != UINT32_MAX) {
+ // If they only asked for the line entry, then we're done, we can just
+ // copy that over.
+ // But if they wanted more than just the line number, fill it in.
+ if (resolve_scope == eSymbolContextLineEntry) {
+ sc.line_entry = line_entry;
+ } else {
+ line_entry.range.GetBaseAddress().CalculateSymbolContext(
+ &sc, resolve_scope);
+ }
+
+ sc_list.Append(sc);
+ line_idx = line_table->FindLineEntryIndexByFileIndex(
+ line_idx + 1, file_indexes.front(), found_line, true,
+ &line_entry);
}
- }
- return m_is_optimized;
-}
-
-void
-CompileUnit::SetVariableList(VariableListSP &variables)
-{
- m_variables = variables;
-}
-
-const std::vector<ConstString> &
-CompileUnit::GetImportedModules ()
-{
- if (m_imported_modules.empty() &&
- m_flags.IsClear(flagsParsedImportedModules))
- {
- m_flags.Set(flagsParsedImportedModules);
- if (SymbolVendor *symbol_vendor = GetModule()->GetSymbolVendor())
- {
- SymbolContext sc;
- CalculateSymbolContext(&sc);
- symbol_vendor->ParseImportedModules(sc, m_imported_modules);
+ } else {
+ // We found multiple support files that match "file_spec" so use
+ // the line table function that searches for a line entries
+ // that match a multiple support file indexes.
+ LineEntry line_entry;
+ line_idx = line_table->FindLineEntryIndexByFileIndex(
+ 0, file_indexes, line, exact, &line_entry);
+
+ // If "exact == true", then "found_line" will be the same
+ // as "line". If "exact == false", the "found_line" will be the
+ // closest line entry with a line number greater than "line" and
+ // we will use this for our subsequent line exact matches below.
+ found_line = line_entry.line;
+
+ while (line_idx != UINT32_MAX) {
+ if (resolve_scope == eSymbolContextLineEntry) {
+ sc.line_entry = line_entry;
+ } else {
+ line_entry.range.GetBaseAddress().CalculateSymbolContext(
+ &sc, resolve_scope);
+ }
+
+ sc_list.Append(sc);
+ line_idx = line_table->FindLineEntryIndexByFileIndex(
+ line_idx + 1, file_indexes, found_line, true, &line_entry);
}
+ }
}
- return m_imported_modules;
-}
-
-FileSpecList&
-CompileUnit::GetSupportFiles ()
-{
- if (m_support_files.GetSize() == 0)
- {
- if (m_flags.IsClear(flagsParsedSupportFiles))
- {
- m_flags.Set(flagsParsedSupportFiles);
- SymbolVendor* symbol_vendor = GetModule()->GetSymbolVendor();
- if (symbol_vendor)
- {
- SymbolContext sc;
- CalculateSymbolContext(&sc);
- symbol_vendor->ParseCompileUnitSupportFiles(sc, m_support_files);
- }
- }
+ } else if (file_spec_matches_cu_file_spec && !check_inlines) {
+ // only append the context if we aren't looking for inline call sites
+ // by file and line and if the file spec matches that of the compile unit
+ sc_list.Append(sc);
+ }
+ return sc_list.GetSize() - prev_size;
+}
+
+bool CompileUnit::GetIsOptimized() {
+ if (m_is_optimized == eLazyBoolCalculate) {
+ m_is_optimized = eLazyBoolNo;
+ if (SymbolVendor *symbol_vendor = GetModule()->GetSymbolVendor()) {
+ SymbolContext sc;
+ CalculateSymbolContext(&sc);
+ if (symbol_vendor->ParseCompileUnitIsOptimized(sc))
+ m_is_optimized = eLazyBoolYes;
+ }
+ }
+ return m_is_optimized;
+}
+
+void CompileUnit::SetVariableList(VariableListSP &variables) {
+ m_variables = variables;
+}
+
+const std::vector<ConstString> &CompileUnit::GetImportedModules() {
+ if (m_imported_modules.empty() &&
+ m_flags.IsClear(flagsParsedImportedModules)) {
+ m_flags.Set(flagsParsedImportedModules);
+ if (SymbolVendor *symbol_vendor = GetModule()->GetSymbolVendor()) {
+ SymbolContext sc;
+ CalculateSymbolContext(&sc);
+ symbol_vendor->ParseImportedModules(sc, m_imported_modules);
+ }
+ }
+ return m_imported_modules;
+}
+
+FileSpecList &CompileUnit::GetSupportFiles() {
+ if (m_support_files.GetSize() == 0) {
+ if (m_flags.IsClear(flagsParsedSupportFiles)) {
+ m_flags.Set(flagsParsedSupportFiles);
+ SymbolVendor *symbol_vendor = GetModule()->GetSymbolVendor();
+ if (symbol_vendor) {
+ SymbolContext sc;
+ CalculateSymbolContext(&sc);
+ symbol_vendor->ParseCompileUnitSupportFiles(sc, m_support_files);
+ }
}
- return m_support_files;
+ }
+ return m_support_files;
}
-void *
-CompileUnit::GetUserData () const
-{
- return m_user_data;
-}
-
-
+void *CompileUnit::GetUserData() const { return m_user_data; }
Modified: lldb/trunk/source/Symbol/CompilerDecl.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/CompilerDecl.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/CompilerDecl.cpp (original)
+++ lldb/trunk/source/Symbol/CompilerDecl.cpp Tue Sep 6 15:57:50 2016
@@ -13,58 +13,42 @@
using namespace lldb_private;
-bool
-CompilerDecl::IsClang () const
-{
- return IsValid() && m_type_system->getKind() == TypeSystem::eKindClang;
+bool CompilerDecl::IsClang() const {
+ return IsValid() && m_type_system->getKind() == TypeSystem::eKindClang;
}
-ConstString
-CompilerDecl::GetName() const
-{
- return m_type_system->DeclGetName(m_opaque_decl);
+ConstString CompilerDecl::GetName() const {
+ return m_type_system->DeclGetName(m_opaque_decl);
}
-ConstString
-CompilerDecl::GetMangledName () const
-{
- return m_type_system->DeclGetMangledName(m_opaque_decl);
+ConstString CompilerDecl::GetMangledName() const {
+ return m_type_system->DeclGetMangledName(m_opaque_decl);
}
-CompilerDeclContext
-CompilerDecl::GetDeclContext() const
-{
- return m_type_system->DeclGetDeclContext(m_opaque_decl);
+CompilerDeclContext CompilerDecl::GetDeclContext() const {
+ return m_type_system->DeclGetDeclContext(m_opaque_decl);
}
-CompilerType
-CompilerDecl::GetFunctionReturnType() const
-{
- return m_type_system->DeclGetFunctionReturnType(m_opaque_decl);
+CompilerType CompilerDecl::GetFunctionReturnType() const {
+ return m_type_system->DeclGetFunctionReturnType(m_opaque_decl);
}
-size_t
-CompilerDecl::GetNumFunctionArguments() const
-{
- return m_type_system->DeclGetFunctionNumArguments(m_opaque_decl);
+size_t CompilerDecl::GetNumFunctionArguments() const {
+ return m_type_system->DeclGetFunctionNumArguments(m_opaque_decl);
}
-CompilerType
-CompilerDecl::GetFunctionArgumentType (size_t arg_idx) const
-{
- return m_type_system->DeclGetFunctionArgumentType(m_opaque_decl, arg_idx);
+CompilerType CompilerDecl::GetFunctionArgumentType(size_t arg_idx) const {
+ return m_type_system->DeclGetFunctionArgumentType(m_opaque_decl, arg_idx);
}
-bool
-lldb_private::operator == (const lldb_private::CompilerDecl &lhs, const lldb_private::CompilerDecl &rhs)
-{
- return lhs.GetTypeSystem() == rhs.GetTypeSystem() && lhs.GetOpaqueDecl() == rhs.GetOpaqueDecl();
+bool lldb_private::operator==(const lldb_private::CompilerDecl &lhs,
+ const lldb_private::CompilerDecl &rhs) {
+ return lhs.GetTypeSystem() == rhs.GetTypeSystem() &&
+ lhs.GetOpaqueDecl() == rhs.GetOpaqueDecl();
}
-
-bool
-lldb_private::operator != (const lldb_private::CompilerDecl &lhs, const lldb_private::CompilerDecl &rhs)
-{
- return lhs.GetTypeSystem() != rhs.GetTypeSystem() || lhs.GetOpaqueDecl() != rhs.GetOpaqueDecl();
+bool lldb_private::operator!=(const lldb_private::CompilerDecl &lhs,
+ const lldb_private::CompilerDecl &rhs) {
+ return lhs.GetTypeSystem() != rhs.GetTypeSystem() ||
+ lhs.GetOpaqueDecl() != rhs.GetOpaqueDecl();
}
-
Modified: lldb/trunk/source/Symbol/CompilerDeclContext.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/CompilerDeclContext.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/CompilerDeclContext.cpp (original)
+++ lldb/trunk/source/Symbol/CompilerDeclContext.cpp Tue Sep 6 15:57:50 2016
@@ -15,71 +15,59 @@
using namespace lldb_private;
std::vector<CompilerDecl>
-CompilerDeclContext::FindDeclByName (ConstString name, const bool ignore_using_decls)
-{
- if (IsValid())
- return m_type_system->DeclContextFindDeclByName(
- m_opaque_decl_ctx, name, ignore_using_decls);
- else
- return std::vector<CompilerDecl>();
-}
-
-bool
-CompilerDeclContext::IsClang () const
-{
- return IsValid() && m_type_system->getKind() == TypeSystem::eKindClang;
-}
-
-ConstString
-CompilerDeclContext::GetName () const
-{
- if (IsValid())
- return m_type_system->DeclContextGetName(m_opaque_decl_ctx);
- else
- return ConstString();
-}
-
-ConstString
-CompilerDeclContext::GetScopeQualifiedName () const
-{
- if (IsValid())
- return m_type_system->DeclContextGetScopeQualifiedName(m_opaque_decl_ctx);
- else
- return ConstString();
-}
-
-bool
-CompilerDeclContext::IsStructUnionOrClass () const
-{
- if (IsValid())
- return m_type_system->DeclContextIsStructUnionOrClass(m_opaque_decl_ctx);
- else
- return false;
-}
-
-bool
-CompilerDeclContext::IsClassMethod (lldb::LanguageType *language_ptr,
- bool *is_instance_method_ptr,
- ConstString *language_object_name_ptr)
-{
- if (IsValid())
- return m_type_system->DeclContextIsClassMethod (m_opaque_decl_ctx,
- language_ptr,
- is_instance_method_ptr,
- language_object_name_ptr);
- else
- return false;
-}
-
-bool
-lldb_private::operator == (const lldb_private::CompilerDeclContext &lhs, const lldb_private::CompilerDeclContext &rhs)
-{
- return lhs.GetTypeSystem() == rhs.GetTypeSystem() && lhs.GetOpaqueDeclContext() == rhs.GetOpaqueDeclContext();
-}
-
-
-bool
-lldb_private::operator != (const lldb_private::CompilerDeclContext &lhs, const lldb_private::CompilerDeclContext &rhs)
-{
- return lhs.GetTypeSystem() != rhs.GetTypeSystem() || lhs.GetOpaqueDeclContext() != rhs.GetOpaqueDeclContext();
+CompilerDeclContext::FindDeclByName(ConstString name,
+ const bool ignore_using_decls) {
+ if (IsValid())
+ return m_type_system->DeclContextFindDeclByName(m_opaque_decl_ctx, name,
+ ignore_using_decls);
+ else
+ return std::vector<CompilerDecl>();
+}
+
+bool CompilerDeclContext::IsClang() const {
+ return IsValid() && m_type_system->getKind() == TypeSystem::eKindClang;
+}
+
+ConstString CompilerDeclContext::GetName() const {
+ if (IsValid())
+ return m_type_system->DeclContextGetName(m_opaque_decl_ctx);
+ else
+ return ConstString();
+}
+
+ConstString CompilerDeclContext::GetScopeQualifiedName() const {
+ if (IsValid())
+ return m_type_system->DeclContextGetScopeQualifiedName(m_opaque_decl_ctx);
+ else
+ return ConstString();
+}
+
+bool CompilerDeclContext::IsStructUnionOrClass() const {
+ if (IsValid())
+ return m_type_system->DeclContextIsStructUnionOrClass(m_opaque_decl_ctx);
+ else
+ return false;
+}
+
+bool CompilerDeclContext::IsClassMethod(lldb::LanguageType *language_ptr,
+ bool *is_instance_method_ptr,
+ ConstString *language_object_name_ptr) {
+ if (IsValid())
+ return m_type_system->DeclContextIsClassMethod(
+ m_opaque_decl_ctx, language_ptr, is_instance_method_ptr,
+ language_object_name_ptr);
+ else
+ return false;
+}
+
+bool lldb_private::operator==(const lldb_private::CompilerDeclContext &lhs,
+ const lldb_private::CompilerDeclContext &rhs) {
+ return lhs.GetTypeSystem() == rhs.GetTypeSystem() &&
+ lhs.GetOpaqueDeclContext() == rhs.GetOpaqueDeclContext();
+}
+
+bool lldb_private::operator!=(const lldb_private::CompilerDeclContext &lhs,
+ const lldb_private::CompilerDeclContext &rhs) {
+ return lhs.GetTypeSystem() != rhs.GetTypeSystem() ||
+ lhs.GetOpaqueDeclContext() != rhs.GetOpaqueDeclContext();
}
Modified: lldb/trunk/source/Symbol/CompilerType.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/CompilerType.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/CompilerType.cpp (original)
+++ lldb/trunk/source/Symbol/CompilerType.cpp Tue Sep 6 15:57:50 2016
@@ -29,614 +29,465 @@
using namespace lldb;
using namespace lldb_private;
-CompilerType::CompilerType (TypeSystem *type_system,
- lldb::opaque_compiler_type_t type) :
- m_type (type),
- m_type_system (type_system)
-{
-}
-
-CompilerType::CompilerType (clang::ASTContext *ast,
- clang::QualType qual_type) :
- m_type (qual_type.getAsOpaquePtr()),
- m_type_system (ClangASTContext::GetASTContext(ast))
-{
+CompilerType::CompilerType(TypeSystem *type_system,
+ lldb::opaque_compiler_type_t type)
+ : m_type(type), m_type_system(type_system) {}
+
+CompilerType::CompilerType(clang::ASTContext *ast, clang::QualType qual_type)
+ : m_type(qual_type.getAsOpaquePtr()),
+ m_type_system(ClangASTContext::GetASTContext(ast)) {
#ifdef LLDB_CONFIGURATION_DEBUG
- if (m_type)
- assert(m_type_system != nullptr);
+ if (m_type)
+ assert(m_type_system != nullptr);
#endif
}
-CompilerType::~CompilerType()
-{
-}
+CompilerType::~CompilerType() {}
//----------------------------------------------------------------------
// Tests
//----------------------------------------------------------------------
-bool
-CompilerType::IsAggregateType () const
-{
- if (IsValid())
- return m_type_system->IsAggregateType(m_type);
- return false;
+bool CompilerType::IsAggregateType() const {
+ if (IsValid())
+ return m_type_system->IsAggregateType(m_type);
+ return false;
}
-bool
-CompilerType::IsAnonymousType () const
-{
- if (IsValid())
- return m_type_system->IsAnonymousType(m_type);
- return false;
+bool CompilerType::IsAnonymousType() const {
+ if (IsValid())
+ return m_type_system->IsAnonymousType(m_type);
+ return false;
}
-bool
-CompilerType::IsArrayType (CompilerType *element_type_ptr,
- uint64_t *size,
- bool *is_incomplete) const
-{
- if (IsValid())
- return m_type_system->IsArrayType(m_type, element_type_ptr, size, is_incomplete);
-
- if (element_type_ptr)
- element_type_ptr->Clear();
- if (size)
- *size = 0;
- if (is_incomplete)
- *is_incomplete = false;
- return false;
-}
+bool CompilerType::IsArrayType(CompilerType *element_type_ptr, uint64_t *size,
+ bool *is_incomplete) const {
+ if (IsValid())
+ return m_type_system->IsArrayType(m_type, element_type_ptr, size,
+ is_incomplete);
-bool
-CompilerType::IsVectorType (CompilerType *element_type,
- uint64_t *size) const
-{
- if (IsValid())
- return m_type_system->IsVectorType(m_type, element_type, size);
- return false;
+ if (element_type_ptr)
+ element_type_ptr->Clear();
+ if (size)
+ *size = 0;
+ if (is_incomplete)
+ *is_incomplete = false;
+ return false;
}
-bool
-CompilerType::IsRuntimeGeneratedType () const
-{
- if (IsValid())
- return m_type_system->IsRuntimeGeneratedType(m_type);
- return false;
+bool CompilerType::IsVectorType(CompilerType *element_type,
+ uint64_t *size) const {
+ if (IsValid())
+ return m_type_system->IsVectorType(m_type, element_type, size);
+ return false;
}
-bool
-CompilerType::IsCharType () const
-{
- if (IsValid())
- return m_type_system->IsCharType(m_type);
- return false;
+bool CompilerType::IsRuntimeGeneratedType() const {
+ if (IsValid())
+ return m_type_system->IsRuntimeGeneratedType(m_type);
+ return false;
}
+bool CompilerType::IsCharType() const {
+ if (IsValid())
+ return m_type_system->IsCharType(m_type);
+ return false;
+}
-bool
-CompilerType::IsCompleteType () const
-{
- if (IsValid())
- return m_type_system->IsCompleteType(m_type);
- return false;
+bool CompilerType::IsCompleteType() const {
+ if (IsValid())
+ return m_type_system->IsCompleteType(m_type);
+ return false;
}
-bool
-CompilerType::IsConst() const
-{
- if (IsValid())
- return m_type_system->IsConst(m_type);
- return false;
+bool CompilerType::IsConst() const {
+ if (IsValid())
+ return m_type_system->IsConst(m_type);
+ return false;
}
-bool
-CompilerType::IsCStringType (uint32_t &length) const
-{
- if (IsValid())
- return m_type_system->IsCStringType(m_type, length);
- return false;
+bool CompilerType::IsCStringType(uint32_t &length) const {
+ if (IsValid())
+ return m_type_system->IsCStringType(m_type, length);
+ return false;
}
-bool
-CompilerType::IsFunctionType (bool *is_variadic_ptr) const
-{
- if (IsValid())
- return m_type_system->IsFunctionType(m_type, is_variadic_ptr);
- return false;
+bool CompilerType::IsFunctionType(bool *is_variadic_ptr) const {
+ if (IsValid())
+ return m_type_system->IsFunctionType(m_type, is_variadic_ptr);
+ return false;
}
// Used to detect "Homogeneous Floating-point Aggregates"
uint32_t
-CompilerType::IsHomogeneousAggregate (CompilerType* base_type_ptr) const
-{
- if (IsValid())
- return m_type_system->IsHomogeneousAggregate(m_type, base_type_ptr);
- return 0;
+CompilerType::IsHomogeneousAggregate(CompilerType *base_type_ptr) const {
+ if (IsValid())
+ return m_type_system->IsHomogeneousAggregate(m_type, base_type_ptr);
+ return 0;
}
-size_t
-CompilerType::GetNumberOfFunctionArguments () const
-{
- if (IsValid())
- return m_type_system->GetNumberOfFunctionArguments(m_type);
- return 0;
+size_t CompilerType::GetNumberOfFunctionArguments() const {
+ if (IsValid())
+ return m_type_system->GetNumberOfFunctionArguments(m_type);
+ return 0;
}
CompilerType
-CompilerType::GetFunctionArgumentAtIndex (const size_t index) const
-{
- if (IsValid())
- return m_type_system->GetFunctionArgumentAtIndex(m_type, index);
- return CompilerType();
+CompilerType::GetFunctionArgumentAtIndex(const size_t index) const {
+ if (IsValid())
+ return m_type_system->GetFunctionArgumentAtIndex(m_type, index);
+ return CompilerType();
}
-bool
-CompilerType::IsFunctionPointerType () const
-{
- if (IsValid())
- return m_type_system->IsFunctionPointerType(m_type);
- return false;
+bool CompilerType::IsFunctionPointerType() const {
+ if (IsValid())
+ return m_type_system->IsFunctionPointerType(m_type);
+ return false;
}
-bool
-CompilerType::IsBlockPointerType (CompilerType *function_pointer_type_ptr) const
-{
- if (IsValid())
- return m_type_system->IsBlockPointerType(m_type, function_pointer_type_ptr);
- return 0;
+bool CompilerType::IsBlockPointerType(
+ CompilerType *function_pointer_type_ptr) const {
+ if (IsValid())
+ return m_type_system->IsBlockPointerType(m_type, function_pointer_type_ptr);
+ return 0;
}
-bool
-CompilerType::IsIntegerType (bool &is_signed) const
-{
- if (IsValid())
- return m_type_system->IsIntegerType(m_type, is_signed);
- return false;
+bool CompilerType::IsIntegerType(bool &is_signed) const {
+ if (IsValid())
+ return m_type_system->IsIntegerType(m_type, is_signed);
+ return false;
}
-bool
-CompilerType::IsEnumerationType (bool &is_signed) const
-{
- if (IsValid())
- return m_type_system->IsEnumerationType(m_type, is_signed);
- return false;
+bool CompilerType::IsEnumerationType(bool &is_signed) const {
+ if (IsValid())
+ return m_type_system->IsEnumerationType(m_type, is_signed);
+ return false;
}
-bool
-CompilerType::IsIntegerOrEnumerationType (bool &is_signed) const
-{
- return IsIntegerType(is_signed) || IsEnumerationType(is_signed);
+bool CompilerType::IsIntegerOrEnumerationType(bool &is_signed) const {
+ return IsIntegerType(is_signed) || IsEnumerationType(is_signed);
}
-bool
-CompilerType::IsPointerType (CompilerType *pointee_type) const
-{
- if (IsValid())
- {
- return m_type_system->IsPointerType(m_type, pointee_type);
- }
- if (pointee_type)
- pointee_type->Clear();
- return false;
+bool CompilerType::IsPointerType(CompilerType *pointee_type) const {
+ if (IsValid()) {
+ return m_type_system->IsPointerType(m_type, pointee_type);
+ }
+ if (pointee_type)
+ pointee_type->Clear();
+ return false;
}
-
-bool
-CompilerType::IsPointerOrReferenceType (CompilerType *pointee_type) const
-{
- if (IsValid())
- {
- return m_type_system->IsPointerOrReferenceType(m_type, pointee_type);
- }
- if (pointee_type)
- pointee_type->Clear();
- return false;
+bool CompilerType::IsPointerOrReferenceType(CompilerType *pointee_type) const {
+ if (IsValid()) {
+ return m_type_system->IsPointerOrReferenceType(m_type, pointee_type);
+ }
+ if (pointee_type)
+ pointee_type->Clear();
+ return false;
}
+bool CompilerType::IsReferenceType(CompilerType *pointee_type,
+ bool *is_rvalue) const {
+ if (IsValid()) {
+ return m_type_system->IsReferenceType(m_type, pointee_type, is_rvalue);
+ }
+ if (pointee_type)
+ pointee_type->Clear();
+ return false;
+}
-bool
-CompilerType::IsReferenceType (CompilerType *pointee_type, bool* is_rvalue) const
-{
- if (IsValid())
- {
- return m_type_system->IsReferenceType(m_type, pointee_type, is_rvalue);
- }
- if (pointee_type)
- pointee_type->Clear();
- return false;
+bool CompilerType::ShouldTreatScalarValueAsAddress() const {
+ if (IsValid())
+ return m_type_system->ShouldTreatScalarValueAsAddress(m_type);
+ return false;
}
-bool
-CompilerType::ShouldTreatScalarValueAsAddress () const
-{
- if (IsValid())
- return m_type_system->ShouldTreatScalarValueAsAddress(m_type);
- return false;
+bool CompilerType::IsFloatingPointType(uint32_t &count,
+ bool &is_complex) const {
+ if (IsValid()) {
+ return m_type_system->IsFloatingPointType(m_type, count, is_complex);
+ }
+ count = 0;
+ is_complex = false;
+ return false;
}
-bool
-CompilerType::IsFloatingPointType (uint32_t &count, bool &is_complex) const
-{
- if (IsValid())
- {
- return m_type_system->IsFloatingPointType(m_type, count, is_complex);
- }
- count = 0;
- is_complex = false;
- return false;
+bool CompilerType::IsDefined() const {
+ if (IsValid())
+ return m_type_system->IsDefined(m_type);
+ return true;
}
+bool CompilerType::IsPolymorphicClass() const {
+ if (IsValid()) {
+ return m_type_system->IsPolymorphicClass(m_type);
+ }
+ return false;
+}
-bool
-CompilerType::IsDefined() const
-{
- if (IsValid())
- return m_type_system->IsDefined(m_type);
- return true;
+bool CompilerType::IsPossibleDynamicType(CompilerType *dynamic_pointee_type,
+ bool check_cplusplus,
+ bool check_objc) const {
+ if (IsValid())
+ return m_type_system->IsPossibleDynamicType(m_type, dynamic_pointee_type,
+ check_cplusplus, check_objc);
+ return false;
}
-bool
-CompilerType::IsPolymorphicClass () const
-{
- if (IsValid())
- {
- return m_type_system->IsPolymorphicClass(m_type);
- }
+bool CompilerType::IsScalarType() const {
+ if (!IsValid())
return false;
+
+ return m_type_system->IsScalarType(m_type);
}
-bool
-CompilerType::IsPossibleDynamicType (CompilerType *dynamic_pointee_type,
- bool check_cplusplus,
- bool check_objc) const
-{
- if (IsValid())
- return m_type_system->IsPossibleDynamicType(m_type, dynamic_pointee_type, check_cplusplus, check_objc);
+bool CompilerType::IsTypedefType() const {
+ if (!IsValid())
return false;
+ return m_type_system->IsTypedefType(m_type);
}
-
-bool
-CompilerType::IsScalarType () const
-{
- if (!IsValid())
- return false;
-
- return m_type_system->IsScalarType(m_type);
+bool CompilerType::IsVoidType() const {
+ if (!IsValid())
+ return false;
+ return m_type_system->IsVoidType(m_type);
}
-bool
-CompilerType::IsTypedefType () const
-{
- if (!IsValid())
- return false;
- return m_type_system->IsTypedefType(m_type);
-}
+bool CompilerType::IsPointerToScalarType() const {
+ if (!IsValid())
+ return false;
-bool
-CompilerType::IsVoidType () const
-{
- if (!IsValid())
- return false;
- return m_type_system->IsVoidType(m_type);
+ return IsPointerType() && GetPointeeType().IsScalarType();
}
-bool
-CompilerType::IsPointerToScalarType () const
-{
- if (!IsValid())
- return false;
-
- return IsPointerType() && GetPointeeType().IsScalarType();
+bool CompilerType::IsArrayOfScalarType() const {
+ CompilerType element_type;
+ if (IsArrayType(&element_type, nullptr, nullptr))
+ return element_type.IsScalarType();
+ return false;
}
-bool
-CompilerType::IsArrayOfScalarType () const
-{
- CompilerType element_type;
- if (IsArrayType(&element_type, nullptr, nullptr))
- return element_type.IsScalarType();
+bool CompilerType::IsBeingDefined() const {
+ if (!IsValid())
return false;
-}
-
-bool
-CompilerType::IsBeingDefined () const
-{
- if (!IsValid())
- return false;
- return m_type_system->IsBeingDefined(m_type);
+ return m_type_system->IsBeingDefined(m_type);
}
//----------------------------------------------------------------------
// Type Completion
//----------------------------------------------------------------------
-bool
-CompilerType::GetCompleteType () const
-{
- if (!IsValid())
- return false;
- return m_type_system->GetCompleteType(m_type);
+bool CompilerType::GetCompleteType() const {
+ if (!IsValid())
+ return false;
+ return m_type_system->GetCompleteType(m_type);
}
//----------------------------------------------------------------------
// AST related queries
//----------------------------------------------------------------------
-size_t
-CompilerType::GetPointerByteSize () const
-{
- if (m_type_system)
- return m_type_system->GetPointerByteSize();
- return 0;
+size_t CompilerType::GetPointerByteSize() const {
+ if (m_type_system)
+ return m_type_system->GetPointerByteSize();
+ return 0;
}
-ConstString
-CompilerType::GetConstQualifiedTypeName () const
-{
- return GetConstTypeName ();
+ConstString CompilerType::GetConstQualifiedTypeName() const {
+ return GetConstTypeName();
}
-ConstString
-CompilerType::GetConstTypeName () const
-{
- if (IsValid())
- {
- ConstString type_name (GetTypeName());
- if (type_name)
- return type_name;
- }
- return ConstString("<invalid>");
+ConstString CompilerType::GetConstTypeName() const {
+ if (IsValid()) {
+ ConstString type_name(GetTypeName());
+ if (type_name)
+ return type_name;
+ }
+ return ConstString("<invalid>");
}
-ConstString
-CompilerType::GetTypeName () const
-{
- if (IsValid())
- {
- return m_type_system->GetTypeName(m_type);
- }
- return ConstString("<invalid>");
+ConstString CompilerType::GetTypeName() const {
+ if (IsValid()) {
+ return m_type_system->GetTypeName(m_type);
+ }
+ return ConstString("<invalid>");
}
-ConstString
-CompilerType::GetDisplayTypeName () const
-{
- return GetTypeName();
+ConstString CompilerType::GetDisplayTypeName() const { return GetTypeName(); }
+
+uint32_t CompilerType::GetTypeInfo(
+ CompilerType *pointee_or_element_compiler_type) const {
+ if (!IsValid())
+ return 0;
+
+ return m_type_system->GetTypeInfo(m_type, pointee_or_element_compiler_type);
}
-uint32_t
-CompilerType::GetTypeInfo (CompilerType *pointee_or_element_compiler_type) const
-{
- if (!IsValid())
- return 0;
-
- return m_type_system->GetTypeInfo(m_type, pointee_or_element_compiler_type);
+lldb::LanguageType CompilerType::GetMinimumLanguage() {
+ if (!IsValid())
+ return lldb::eLanguageTypeC;
+
+ return m_type_system->GetMinimumLanguage(m_type);
}
+lldb::TypeClass CompilerType::GetTypeClass() const {
+ if (!IsValid())
+ return lldb::eTypeClassInvalid;
+ return m_type_system->GetTypeClass(m_type);
+}
-lldb::LanguageType
-CompilerType::GetMinimumLanguage ()
-{
- if (!IsValid())
- return lldb::eLanguageTypeC;
-
- return m_type_system->GetMinimumLanguage(m_type);
-}
-
-lldb::TypeClass
-CompilerType::GetTypeClass () const
-{
- if (!IsValid())
- return lldb::eTypeClassInvalid;
-
- return m_type_system->GetTypeClass(m_type);
-
-}
-
-void
-CompilerType::SetCompilerType (TypeSystem* type_system, lldb::opaque_compiler_type_t type)
-{
- m_type_system = type_system;
- m_type = type;
-}
-
-void
-CompilerType::SetCompilerType (clang::ASTContext *ast, clang::QualType qual_type)
-{
- m_type_system = ClangASTContext::GetASTContext(ast);
- m_type = qual_type.getAsOpaquePtr();
-}
-
-unsigned
-CompilerType::GetTypeQualifiers() const
-{
- if (IsValid())
- return m_type_system->GetTypeQualifiers(m_type);
- return 0;
+void CompilerType::SetCompilerType(TypeSystem *type_system,
+ lldb::opaque_compiler_type_t type) {
+ m_type_system = type_system;
+ m_type = type;
+}
+
+void CompilerType::SetCompilerType(clang::ASTContext *ast,
+ clang::QualType qual_type) {
+ m_type_system = ClangASTContext::GetASTContext(ast);
+ m_type = qual_type.getAsOpaquePtr();
+}
+
+unsigned CompilerType::GetTypeQualifiers() const {
+ if (IsValid())
+ return m_type_system->GetTypeQualifiers(m_type);
+ return 0;
}
//----------------------------------------------------------------------
// Creating related types
//----------------------------------------------------------------------
-CompilerType
-CompilerType::GetArrayElementType (uint64_t *stride) const
-{
- if (IsValid())
- {
- return m_type_system->GetArrayElementType(m_type, stride);
- }
- return CompilerType();
+CompilerType CompilerType::GetArrayElementType(uint64_t *stride) const {
+ if (IsValid()) {
+ return m_type_system->GetArrayElementType(m_type, stride);
+ }
+ return CompilerType();
}
-CompilerType
-CompilerType::GetArrayType (uint64_t size) const
-{
- if (IsValid())
- {
- return m_type_system->GetArrayType(m_type, size);
- }
- return CompilerType();
+CompilerType CompilerType::GetArrayType(uint64_t size) const {
+ if (IsValid()) {
+ return m_type_system->GetArrayType(m_type, size);
+ }
+ return CompilerType();
}
-CompilerType
-CompilerType::GetCanonicalType () const
-{
- if (IsValid())
- return m_type_system->GetCanonicalType(m_type);
- return CompilerType();
+CompilerType CompilerType::GetCanonicalType() const {
+ if (IsValid())
+ return m_type_system->GetCanonicalType(m_type);
+ return CompilerType();
}
-CompilerType
-CompilerType::GetFullyUnqualifiedType () const
-{
- if (IsValid())
- return m_type_system->GetFullyUnqualifiedType(m_type);
- return CompilerType();
+CompilerType CompilerType::GetFullyUnqualifiedType() const {
+ if (IsValid())
+ return m_type_system->GetFullyUnqualifiedType(m_type);
+ return CompilerType();
}
-
-int
-CompilerType::GetFunctionArgumentCount () const
-{
- if (IsValid())
- {
- return m_type_system->GetFunctionArgumentCount(m_type);
- }
- return -1;
+int CompilerType::GetFunctionArgumentCount() const {
+ if (IsValid()) {
+ return m_type_system->GetFunctionArgumentCount(m_type);
+ }
+ return -1;
}
-CompilerType
-CompilerType::GetFunctionArgumentTypeAtIndex (size_t idx) const
-{
- if (IsValid())
- {
- return m_type_system->GetFunctionArgumentTypeAtIndex(m_type, idx);
- }
- return CompilerType();
+CompilerType CompilerType::GetFunctionArgumentTypeAtIndex(size_t idx) const {
+ if (IsValid()) {
+ return m_type_system->GetFunctionArgumentTypeAtIndex(m_type, idx);
+ }
+ return CompilerType();
}
-CompilerType
-CompilerType::GetFunctionReturnType () const
-{
- if (IsValid())
- {
- return m_type_system->GetFunctionReturnType(m_type);
- }
- return CompilerType();
+CompilerType CompilerType::GetFunctionReturnType() const {
+ if (IsValid()) {
+ return m_type_system->GetFunctionReturnType(m_type);
+ }
+ return CompilerType();
}
-size_t
-CompilerType::GetNumMemberFunctions () const
-{
- if (IsValid())
- {
- return m_type_system->GetNumMemberFunctions(m_type);
- }
- return 0;
+size_t CompilerType::GetNumMemberFunctions() const {
+ if (IsValid()) {
+ return m_type_system->GetNumMemberFunctions(m_type);
+ }
+ return 0;
}
-TypeMemberFunctionImpl
-CompilerType::GetMemberFunctionAtIndex (size_t idx)
-{
- if (IsValid())
- {
- return m_type_system->GetMemberFunctionAtIndex(m_type, idx);
- }
- return TypeMemberFunctionImpl();
+TypeMemberFunctionImpl CompilerType::GetMemberFunctionAtIndex(size_t idx) {
+ if (IsValid()) {
+ return m_type_system->GetMemberFunctionAtIndex(m_type, idx);
+ }
+ return TypeMemberFunctionImpl();
}
-CompilerType
-CompilerType::GetNonReferenceType () const
-{
- if (IsValid())
- return m_type_system->GetNonReferenceType(m_type);
- return CompilerType();
+CompilerType CompilerType::GetNonReferenceType() const {
+ if (IsValid())
+ return m_type_system->GetNonReferenceType(m_type);
+ return CompilerType();
}
-CompilerType
-CompilerType::GetPointeeType () const
-{
- if (IsValid())
- {
- return m_type_system->GetPointeeType(m_type);
- }
- return CompilerType();
+CompilerType CompilerType::GetPointeeType() const {
+ if (IsValid()) {
+ return m_type_system->GetPointeeType(m_type);
+ }
+ return CompilerType();
}
-CompilerType
-CompilerType::GetPointerType () const
-{
- if (IsValid())
- {
- return m_type_system->GetPointerType(m_type);
- }
- return CompilerType();
+CompilerType CompilerType::GetPointerType() const {
+ if (IsValid()) {
+ return m_type_system->GetPointerType(m_type);
+ }
+ return CompilerType();
}
-CompilerType
-CompilerType::GetLValueReferenceType () const
-{
- if (IsValid())
- return m_type_system->GetLValueReferenceType(m_type);
- else
- return CompilerType();
+CompilerType CompilerType::GetLValueReferenceType() const {
+ if (IsValid())
+ return m_type_system->GetLValueReferenceType(m_type);
+ else
+ return CompilerType();
}
-CompilerType
-CompilerType::GetRValueReferenceType () const
-{
- if (IsValid())
- return m_type_system->GetRValueReferenceType(m_type);
- else
- return CompilerType();
+CompilerType CompilerType::GetRValueReferenceType() const {
+ if (IsValid())
+ return m_type_system->GetRValueReferenceType(m_type);
+ else
+ return CompilerType();
}
-CompilerType
-CompilerType::AddConstModifier () const
-{
- if (IsValid())
- return m_type_system->AddConstModifier(m_type);
- else
- return CompilerType();
+CompilerType CompilerType::AddConstModifier() const {
+ if (IsValid())
+ return m_type_system->AddConstModifier(m_type);
+ else
+ return CompilerType();
}
-CompilerType
-CompilerType::AddVolatileModifier () const
-{
- if (IsValid())
- return m_type_system->AddVolatileModifier(m_type);
- else
- return CompilerType();
+CompilerType CompilerType::AddVolatileModifier() const {
+ if (IsValid())
+ return m_type_system->AddVolatileModifier(m_type);
+ else
+ return CompilerType();
}
-CompilerType
-CompilerType::AddRestrictModifier () const
-{
- if (IsValid())
- return m_type_system->AddRestrictModifier(m_type);
- else
- return CompilerType();
+CompilerType CompilerType::AddRestrictModifier() const {
+ if (IsValid())
+ return m_type_system->AddRestrictModifier(m_type);
+ else
+ return CompilerType();
}
CompilerType
-CompilerType::CreateTypedef (const char *name, const CompilerDeclContext &decl_ctx) const
-{
- if (IsValid())
- return m_type_system->CreateTypedef(m_type, name, decl_ctx);
- else
- return CompilerType();
+CompilerType::CreateTypedef(const char *name,
+ const CompilerDeclContext &decl_ctx) const {
+ if (IsValid())
+ return m_type_system->CreateTypedef(m_type, name, decl_ctx);
+ else
+ return CompilerType();
}
-CompilerType
-CompilerType::GetTypedefedType () const
-{
- if (IsValid())
- return m_type_system->GetTypedefedType(m_type);
- else
- return CompilerType();
+CompilerType CompilerType::GetTypedefedType() const {
+ if (IsValid())
+ return m_type_system->GetTypedefedType(m_type);
+ else
+ return CompilerType();
}
//----------------------------------------------------------------------
@@ -644,192 +495,146 @@ CompilerType::GetTypedefedType () const
//----------------------------------------------------------------------
CompilerType
-CompilerType::GetBasicTypeFromAST (lldb::BasicType basic_type) const
-{
- if (IsValid())
- return m_type_system->GetBasicTypeFromAST(basic_type);
- return CompilerType();
+CompilerType::GetBasicTypeFromAST(lldb::BasicType basic_type) const {
+ if (IsValid())
+ return m_type_system->GetBasicTypeFromAST(basic_type);
+ return CompilerType();
}
//----------------------------------------------------------------------
// Exploring the type
//----------------------------------------------------------------------
-uint64_t
-CompilerType::GetBitSize (ExecutionContextScope *exe_scope) const
-{
- if (IsValid())
- {
- return m_type_system->GetBitSize(m_type, exe_scope);
- }
- return 0;
+uint64_t CompilerType::GetBitSize(ExecutionContextScope *exe_scope) const {
+ if (IsValid()) {
+ return m_type_system->GetBitSize(m_type, exe_scope);
+ }
+ return 0;
}
-uint64_t
-CompilerType::GetByteSize (ExecutionContextScope *exe_scope) const
-{
- return (GetBitSize (exe_scope) + 7) / 8;
+uint64_t CompilerType::GetByteSize(ExecutionContextScope *exe_scope) const {
+ return (GetBitSize(exe_scope) + 7) / 8;
}
-
-size_t
-CompilerType::GetTypeBitAlign () const
-{
- if (IsValid())
- return m_type_system->GetTypeBitAlign(m_type);
- return 0;
+size_t CompilerType::GetTypeBitAlign() const {
+ if (IsValid())
+ return m_type_system->GetTypeBitAlign(m_type);
+ return 0;
}
+lldb::Encoding CompilerType::GetEncoding(uint64_t &count) const {
+ if (!IsValid())
+ return lldb::eEncodingInvalid;
-lldb::Encoding
-CompilerType::GetEncoding (uint64_t &count) const
-{
- if (!IsValid())
- return lldb::eEncodingInvalid;
-
- return m_type_system->GetEncoding(m_type, count);
-}
-
-lldb::Format
-CompilerType::GetFormat () const
-{
- if (!IsValid())
- return lldb::eFormatDefault;
-
- return m_type_system->GetFormat(m_type);
+ return m_type_system->GetEncoding(m_type, count);
}
-uint32_t
-CompilerType::GetNumChildren (bool omit_empty_base_classes) const
-{
- if (!IsValid())
- return 0;
- return m_type_system->GetNumChildren(m_type, omit_empty_base_classes);
-}
-
-lldb::BasicType
-CompilerType::GetBasicTypeEnumeration () const
-{
- if (IsValid())
- return m_type_system->GetBasicTypeEnumeration(m_type);
- return eBasicTypeInvalid;
-}
-
-void
-CompilerType::ForEachEnumerator (std::function <bool (const CompilerType &integer_type, const ConstString &name, const llvm::APSInt &value)> const &callback) const
-{
- if (IsValid())
- return m_type_system->ForEachEnumerator (m_type, callback);
-}
+lldb::Format CompilerType::GetFormat() const {
+ if (!IsValid())
+ return lldb::eFormatDefault;
+ return m_type_system->GetFormat(m_type);
+}
-uint32_t
-CompilerType::GetNumFields () const
-{
- if (!IsValid())
- return 0;
- return m_type_system->GetNumFields(m_type);
+uint32_t CompilerType::GetNumChildren(bool omit_empty_base_classes) const {
+ if (!IsValid())
+ return 0;
+ return m_type_system->GetNumChildren(m_type, omit_empty_base_classes);
}
-CompilerType
-CompilerType::GetFieldAtIndex (size_t idx,
- std::string& name,
- uint64_t *bit_offset_ptr,
- uint32_t *bitfield_bit_size_ptr,
- bool *is_bitfield_ptr) const
-{
- if (!IsValid())
- return CompilerType();
- return m_type_system->GetFieldAtIndex(m_type, idx, name, bit_offset_ptr, bitfield_bit_size_ptr, is_bitfield_ptr);
+lldb::BasicType CompilerType::GetBasicTypeEnumeration() const {
+ if (IsValid())
+ return m_type_system->GetBasicTypeEnumeration(m_type);
+ return eBasicTypeInvalid;
}
-uint32_t
-CompilerType::GetNumDirectBaseClasses () const
-{
- if (IsValid())
- return m_type_system->GetNumDirectBaseClasses (m_type);
- return 0;
+void CompilerType::ForEachEnumerator(
+ std::function<bool(const CompilerType &integer_type,
+ const ConstString &name,
+ const llvm::APSInt &value)> const &callback) const {
+ if (IsValid())
+ return m_type_system->ForEachEnumerator(m_type, callback);
}
-uint32_t
-CompilerType::GetNumVirtualBaseClasses () const
-{
- if (IsValid())
- return m_type_system->GetNumVirtualBaseClasses (m_type);
+uint32_t CompilerType::GetNumFields() const {
+ if (!IsValid())
return 0;
+ return m_type_system->GetNumFields(m_type);
}
-CompilerType
-CompilerType::GetDirectBaseClassAtIndex (size_t idx, uint32_t *bit_offset_ptr) const
-{
- if (IsValid())
- return m_type_system->GetDirectBaseClassAtIndex (m_type, idx, bit_offset_ptr);
+CompilerType CompilerType::GetFieldAtIndex(size_t idx, std::string &name,
+ uint64_t *bit_offset_ptr,
+ uint32_t *bitfield_bit_size_ptr,
+ bool *is_bitfield_ptr) const {
+ if (!IsValid())
return CompilerType();
+ return m_type_system->GetFieldAtIndex(m_type, idx, name, bit_offset_ptr,
+ bitfield_bit_size_ptr, is_bitfield_ptr);
}
-CompilerType
-CompilerType::GetVirtualBaseClassAtIndex (size_t idx, uint32_t *bit_offset_ptr) const
-{
- if (IsValid())
- return m_type_system->GetVirtualBaseClassAtIndex (m_type, idx, bit_offset_ptr);
- return CompilerType();
+uint32_t CompilerType::GetNumDirectBaseClasses() const {
+ if (IsValid())
+ return m_type_system->GetNumDirectBaseClasses(m_type);
+ return 0;
+}
+
+uint32_t CompilerType::GetNumVirtualBaseClasses() const {
+ if (IsValid())
+ return m_type_system->GetNumVirtualBaseClasses(m_type);
+ return 0;
}
-uint32_t
-CompilerType::GetIndexOfFieldWithName (const char* name,
- CompilerType* field_compiler_type_ptr,
- uint64_t *bit_offset_ptr,
- uint32_t *bitfield_bit_size_ptr,
- bool *is_bitfield_ptr) const
-{
- unsigned count = GetNumFields();
- std::string field_name;
- for (unsigned index = 0; index < count; index++)
- {
- CompilerType field_compiler_type (GetFieldAtIndex(index, field_name, bit_offset_ptr, bitfield_bit_size_ptr, is_bitfield_ptr));
- if (strcmp(field_name.c_str(), name) == 0)
- {
- if (field_compiler_type_ptr)
- *field_compiler_type_ptr = field_compiler_type;
- return index;
- }
- }
- return UINT32_MAX;
+CompilerType
+CompilerType::GetDirectBaseClassAtIndex(size_t idx,
+ uint32_t *bit_offset_ptr) const {
+ if (IsValid())
+ return m_type_system->GetDirectBaseClassAtIndex(m_type, idx,
+ bit_offset_ptr);
+ return CompilerType();
}
-
CompilerType
-CompilerType::GetChildCompilerTypeAtIndex (ExecutionContext *exe_ctx,
- size_t idx,
- bool transparent_pointers,
- bool omit_empty_base_classes,
- bool ignore_array_bounds,
- std::string& child_name,
- uint32_t &child_byte_size,
- int32_t &child_byte_offset,
- uint32_t &child_bitfield_bit_size,
- uint32_t &child_bitfield_bit_offset,
- bool &child_is_base_class,
- bool &child_is_deref_of_parent,
- ValueObject *valobj,
- uint64_t &language_flags) const
-{
- if (!IsValid())
- return CompilerType();
- return m_type_system->GetChildCompilerTypeAtIndex(m_type,
- exe_ctx,
- idx,
- transparent_pointers,
- omit_empty_base_classes,
- ignore_array_bounds,
- child_name,
- child_byte_size,
- child_byte_offset,
- child_bitfield_bit_size,
- child_bitfield_bit_offset,
- child_is_base_class,
- child_is_deref_of_parent,
- valobj,
- language_flags);
+CompilerType::GetVirtualBaseClassAtIndex(size_t idx,
+ uint32_t *bit_offset_ptr) const {
+ if (IsValid())
+ return m_type_system->GetVirtualBaseClassAtIndex(m_type, idx,
+ bit_offset_ptr);
+ return CompilerType();
+}
+
+uint32_t CompilerType::GetIndexOfFieldWithName(
+ const char *name, CompilerType *field_compiler_type_ptr,
+ uint64_t *bit_offset_ptr, uint32_t *bitfield_bit_size_ptr,
+ bool *is_bitfield_ptr) const {
+ unsigned count = GetNumFields();
+ std::string field_name;
+ for (unsigned index = 0; index < count; index++) {
+ CompilerType field_compiler_type(
+ GetFieldAtIndex(index, field_name, bit_offset_ptr,
+ bitfield_bit_size_ptr, is_bitfield_ptr));
+ if (strcmp(field_name.c_str(), name) == 0) {
+ if (field_compiler_type_ptr)
+ *field_compiler_type_ptr = field_compiler_type;
+ return index;
+ }
+ }
+ return UINT32_MAX;
+}
+
+CompilerType CompilerType::GetChildCompilerTypeAtIndex(
+ ExecutionContext *exe_ctx, size_t idx, bool transparent_pointers,
+ bool omit_empty_base_classes, bool ignore_array_bounds,
+ std::string &child_name, uint32_t &child_byte_size,
+ int32_t &child_byte_offset, uint32_t &child_bitfield_bit_size,
+ uint32_t &child_bitfield_bit_offset, bool &child_is_base_class,
+ bool &child_is_deref_of_parent, ValueObject *valobj,
+ uint64_t &language_flags) const {
+ if (!IsValid())
+ return CompilerType();
+ return m_type_system->GetChildCompilerTypeAtIndex(
+ m_type, exe_ctx, idx, transparent_pointers, omit_empty_base_classes,
+ ignore_array_bounds, child_name, child_byte_size, child_byte_offset,
+ child_bitfield_bit_size, child_bitfield_bit_offset, child_is_base_class,
+ child_is_deref_of_parent, valobj, language_flags);
}
// Look for a child member (doesn't include base classes, but it does include
@@ -856,71 +661,60 @@ CompilerType::GetChildCompilerTypeAtInde
// If we have a clang type that describes "class C", and we wanted to looked
// "m_b" in it:
//
-// With omit_empty_base_classes == false we would get an integer array back with:
+// With omit_empty_base_classes == false we would get an integer array back
+// with:
// { 1, 1 }
// The first index 1 is the child index for "class A" within class C
// The second index 1 is the child index for "m_b" within class A
//
// With omit_empty_base_classes == true we would get an integer array back with:
// { 0, 1 }
-// The first index 0 is the child index for "class A" within class C (since class B doesn't have any members it doesn't count)
+// The first index 0 is the child index for "class A" within class C (since
+// class B doesn't have any members it doesn't count)
// The second index 1 is the child index for "m_b" within class A
-size_t
-CompilerType::GetIndexOfChildMemberWithName (const char *name,
- bool omit_empty_base_classes,
- std::vector<uint32_t>& child_indexes) const
-{
- if (IsValid() && name && name[0])
- {
- return m_type_system->GetIndexOfChildMemberWithName(m_type, name, omit_empty_base_classes, child_indexes);
- }
- return 0;
+size_t CompilerType::GetIndexOfChildMemberWithName(
+ const char *name, bool omit_empty_base_classes,
+ std::vector<uint32_t> &child_indexes) const {
+ if (IsValid() && name && name[0]) {
+ return m_type_system->GetIndexOfChildMemberWithName(
+ m_type, name, omit_empty_base_classes, child_indexes);
+ }
+ return 0;
}
-size_t
-CompilerType::GetNumTemplateArguments () const
-{
- if (IsValid())
- {
- return m_type_system->GetNumTemplateArguments(m_type);
- }
- return 0;
+size_t CompilerType::GetNumTemplateArguments() const {
+ if (IsValid()) {
+ return m_type_system->GetNumTemplateArguments(m_type);
+ }
+ return 0;
}
CompilerType
-CompilerType::GetTemplateArgument (size_t idx,
- lldb::TemplateArgumentKind &kind) const
-{
- if (IsValid())
- {
- return m_type_system->GetTemplateArgument(m_type, idx, kind);
- }
- return CompilerType();
+CompilerType::GetTemplateArgument(size_t idx,
+ lldb::TemplateArgumentKind &kind) const {
+ if (IsValid()) {
+ return m_type_system->GetTemplateArgument(m_type, idx, kind);
+ }
+ return CompilerType();
}
-CompilerType
-CompilerType::GetTypeForFormatters () const
-{
- if (IsValid())
- return m_type_system->GetTypeForFormatters(m_type);
- return CompilerType();
+CompilerType CompilerType::GetTypeForFormatters() const {
+ if (IsValid())
+ return m_type_system->GetTypeForFormatters(m_type);
+ return CompilerType();
}
-LazyBool
-CompilerType::ShouldPrintAsOneLiner (ValueObject* valobj) const
-{
- if (IsValid())
- return m_type_system->ShouldPrintAsOneLiner(m_type, valobj);
- return eLazyBoolCalculate;
+LazyBool CompilerType::ShouldPrintAsOneLiner(ValueObject *valobj) const {
+ if (IsValid())
+ return m_type_system->ShouldPrintAsOneLiner(m_type, valobj);
+ return eLazyBoolCalculate;
}
-bool
-CompilerType::IsMeaninglessWithoutDynamicResolution () const
-{
- if (IsValid())
- return m_type_system->IsMeaninglessWithoutDynamicResolution(m_type);
- return false;
+bool CompilerType::IsMeaninglessWithoutDynamicResolution() const {
+ if (IsValid())
+ return m_type_system->IsMeaninglessWithoutDynamicResolution(m_type);
+ return false;
}
// Get the index of the child of "clang_type" whose name matches. This function
@@ -928,423 +722,351 @@ CompilerType::IsMeaninglessWithoutDynami
// matches can include base class names.
uint32_t
-CompilerType::GetIndexOfChildWithName (const char *name, bool omit_empty_base_classes) const
-{
- if (IsValid() && name && name[0])
- {
- return m_type_system->GetIndexOfChildWithName(m_type, name, omit_empty_base_classes);
- }
- return UINT32_MAX;
+CompilerType::GetIndexOfChildWithName(const char *name,
+ bool omit_empty_base_classes) const {
+ if (IsValid() && name && name[0]) {
+ return m_type_system->GetIndexOfChildWithName(m_type, name,
+ omit_empty_base_classes);
+ }
+ return UINT32_MAX;
}
-size_t
-CompilerType::ConvertStringToFloatValue (const char *s, uint8_t *dst, size_t dst_size) const
-{
- if (IsValid())
- return m_type_system->ConvertStringToFloatValue(m_type, s, dst, dst_size);
- return 0;
+size_t CompilerType::ConvertStringToFloatValue(const char *s, uint8_t *dst,
+ size_t dst_size) const {
+ if (IsValid())
+ return m_type_system->ConvertStringToFloatValue(m_type, s, dst, dst_size);
+ return 0;
}
-
-
//----------------------------------------------------------------------
// Dumping types
//----------------------------------------------------------------------
#define DEPTH_INCREMENT 2
-void
-CompilerType::DumpValue (ExecutionContext *exe_ctx,
- Stream *s,
- lldb::Format format,
- const lldb_private::DataExtractor &data,
- lldb::offset_t data_byte_offset,
- size_t data_byte_size,
- uint32_t bitfield_bit_size,
- uint32_t bitfield_bit_offset,
- bool show_types,
- bool show_summary,
- bool verbose,
- uint32_t depth)
-{
- if (!IsValid())
- return;
- m_type_system->DumpValue(m_type, exe_ctx, s, format, data, data_byte_offset, data_byte_size, bitfield_bit_size, bitfield_bit_offset, show_types, show_summary, verbose, depth);
-}
-
-
-
-
-bool
-CompilerType::DumpTypeValue (Stream *s,
+void CompilerType::DumpValue(ExecutionContext *exe_ctx, Stream *s,
lldb::Format format,
const lldb_private::DataExtractor &data,
- lldb::offset_t byte_offset,
- size_t byte_size,
- uint32_t bitfield_bit_size,
- uint32_t bitfield_bit_offset,
- ExecutionContextScope *exe_scope)
-{
- if (!IsValid())
- return false;
- return m_type_system->DumpTypeValue(m_type, s, format, data, byte_offset, byte_size, bitfield_bit_size, bitfield_bit_offset, exe_scope);
-}
-
-
-
-void
-CompilerType::DumpSummary (ExecutionContext *exe_ctx,
- Stream *s,
- const lldb_private::DataExtractor &data,
- lldb::offset_t data_byte_offset,
- size_t data_byte_size)
-{
- if (IsValid())
- m_type_system->DumpSummary(m_type, exe_ctx, s, data, data_byte_offset, data_byte_size);
-}
-
-void
-CompilerType::DumpTypeDescription () const
-{
- if (IsValid())
- m_type_system->DumpTypeDescription(m_type);
-}
-
-void
-CompilerType::DumpTypeDescription (Stream *s) const
-{
- if (IsValid())
- {
- m_type_system->DumpTypeDescription(m_type, s);
+ lldb::offset_t data_byte_offset,
+ size_t data_byte_size, uint32_t bitfield_bit_size,
+ uint32_t bitfield_bit_offset, bool show_types,
+ bool show_summary, bool verbose, uint32_t depth) {
+ if (!IsValid())
+ return;
+ m_type_system->DumpValue(m_type, exe_ctx, s, format, data, data_byte_offset,
+ data_byte_size, bitfield_bit_size,
+ bitfield_bit_offset, show_types, show_summary,
+ verbose, depth);
+}
+
+bool CompilerType::DumpTypeValue(Stream *s, lldb::Format format,
+ const lldb_private::DataExtractor &data,
+ lldb::offset_t byte_offset, size_t byte_size,
+ uint32_t bitfield_bit_size,
+ uint32_t bitfield_bit_offset,
+ ExecutionContextScope *exe_scope) {
+ if (!IsValid())
+ return false;
+ return m_type_system->DumpTypeValue(m_type, s, format, data, byte_offset,
+ byte_size, bitfield_bit_size,
+ bitfield_bit_offset, exe_scope);
+}
+
+void CompilerType::DumpSummary(ExecutionContext *exe_ctx, Stream *s,
+ const lldb_private::DataExtractor &data,
+ lldb::offset_t data_byte_offset,
+ size_t data_byte_size) {
+ if (IsValid())
+ m_type_system->DumpSummary(m_type, exe_ctx, s, data, data_byte_offset,
+ data_byte_size);
+}
+
+void CompilerType::DumpTypeDescription() const {
+ if (IsValid())
+ m_type_system->DumpTypeDescription(m_type);
+}
+
+void CompilerType::DumpTypeDescription(Stream *s) const {
+ if (IsValid()) {
+ m_type_system->DumpTypeDescription(m_type, s);
+ }
+}
+
+bool CompilerType::GetValueAsScalar(const lldb_private::DataExtractor &data,
+ lldb::offset_t data_byte_offset,
+ size_t data_byte_size,
+ Scalar &value) const {
+ if (!IsValid())
+ return false;
+
+ if (IsAggregateType()) {
+ return false; // Aggregate types don't have scalar values
+ } else {
+ uint64_t count = 0;
+ lldb::Encoding encoding = GetEncoding(count);
+
+ if (encoding == lldb::eEncodingInvalid || count != 1)
+ return false;
+
+ const uint64_t byte_size = GetByteSize(nullptr);
+ lldb::offset_t offset = data_byte_offset;
+ switch (encoding) {
+ case lldb::eEncodingInvalid:
+ break;
+ case lldb::eEncodingVector:
+ break;
+ case lldb::eEncodingUint:
+ if (byte_size <= sizeof(unsigned long long)) {
+ uint64_t uval64 = data.GetMaxU64(&offset, byte_size);
+ if (byte_size <= sizeof(unsigned int)) {
+ value = (unsigned int)uval64;
+ return true;
+ } else if (byte_size <= sizeof(unsigned long)) {
+ value = (unsigned long)uval64;
+ return true;
+ } else if (byte_size <= sizeof(unsigned long long)) {
+ value = (unsigned long long)uval64;
+ return true;
+ } else
+ value.Clear();
+ }
+ break;
+
+ case lldb::eEncodingSint:
+ if (byte_size <= sizeof(long long)) {
+ int64_t sval64 = data.GetMaxS64(&offset, byte_size);
+ if (byte_size <= sizeof(int)) {
+ value = (int)sval64;
+ return true;
+ } else if (byte_size <= sizeof(long)) {
+ value = (long)sval64;
+ return true;
+ } else if (byte_size <= sizeof(long long)) {
+ value = (long long)sval64;
+ return true;
+ } else
+ value.Clear();
+ }
+ break;
+
+ case lldb::eEncodingIEEE754:
+ if (byte_size <= sizeof(long double)) {
+ uint32_t u32;
+ uint64_t u64;
+ if (byte_size == sizeof(float)) {
+ if (sizeof(float) == sizeof(uint32_t)) {
+ u32 = data.GetU32(&offset);
+ value = *((float *)&u32);
+ return true;
+ } else if (sizeof(float) == sizeof(uint64_t)) {
+ u64 = data.GetU64(&offset);
+ value = *((float *)&u64);
+ return true;
+ }
+ } else if (byte_size == sizeof(double)) {
+ if (sizeof(double) == sizeof(uint32_t)) {
+ u32 = data.GetU32(&offset);
+ value = *((double *)&u32);
+ return true;
+ } else if (sizeof(double) == sizeof(uint64_t)) {
+ u64 = data.GetU64(&offset);
+ value = *((double *)&u64);
+ return true;
+ }
+ } else if (byte_size == sizeof(long double)) {
+ if (sizeof(long double) == sizeof(uint32_t)) {
+ u32 = data.GetU32(&offset);
+ value = *((long double *)&u32);
+ return true;
+ } else if (sizeof(long double) == sizeof(uint64_t)) {
+ u64 = data.GetU64(&offset);
+ value = *((long double *)&u64);
+ return true;
+ }
+ }
+ }
+ break;
}
+ }
+ return false;
}
-bool
-CompilerType::GetValueAsScalar (const lldb_private::DataExtractor &data,
- lldb::offset_t data_byte_offset,
- size_t data_byte_size,
- Scalar &value) const
-{
- if (!IsValid())
- return false;
-
- if (IsAggregateType ())
- {
- return false; // Aggregate types don't have scalar values
- }
- else
- {
- uint64_t count = 0;
- lldb::Encoding encoding = GetEncoding (count);
-
- if (encoding == lldb::eEncodingInvalid || count != 1)
- return false;
-
- const uint64_t byte_size = GetByteSize(nullptr);
- lldb::offset_t offset = data_byte_offset;
- switch (encoding)
- {
- case lldb::eEncodingInvalid:
- break;
- case lldb::eEncodingVector:
- break;
- case lldb::eEncodingUint:
- if (byte_size <= sizeof(unsigned long long))
- {
- uint64_t uval64 = data.GetMaxU64 (&offset, byte_size);
- if (byte_size <= sizeof(unsigned int))
- {
- value = (unsigned int)uval64;
- return true;
- }
- else if (byte_size <= sizeof(unsigned long))
- {
- value = (unsigned long)uval64;
- return true;
- }
- else if (byte_size <= sizeof(unsigned long long))
- {
- value = (unsigned long long )uval64;
- return true;
- }
- else
- value.Clear();
- }
- break;
-
- case lldb::eEncodingSint:
- if (byte_size <= sizeof(long long))
- {
- int64_t sval64 = data.GetMaxS64 (&offset, byte_size);
- if (byte_size <= sizeof(int))
- {
- value = (int)sval64;
- return true;
- }
- else if (byte_size <= sizeof(long))
- {
- value = (long)sval64;
- return true;
- }
- else if (byte_size <= sizeof(long long))
- {
- value = (long long )sval64;
- return true;
- }
- else
- value.Clear();
- }
- break;
-
- case lldb::eEncodingIEEE754:
- if (byte_size <= sizeof(long double))
- {
- uint32_t u32;
- uint64_t u64;
- if (byte_size == sizeof(float))
- {
- if (sizeof(float) == sizeof(uint32_t))
- {
- u32 = data.GetU32(&offset);
- value = *((float *)&u32);
- return true;
- }
- else if (sizeof(float) == sizeof(uint64_t))
- {
- u64 = data.GetU64(&offset);
- value = *((float *)&u64);
- return true;
- }
- }
- else
- if (byte_size == sizeof(double))
- {
- if (sizeof(double) == sizeof(uint32_t))
- {
- u32 = data.GetU32(&offset);
- value = *((double *)&u32);
- return true;
- }
- else if (sizeof(double) == sizeof(uint64_t))
- {
- u64 = data.GetU64(&offset);
- value = *((double *)&u64);
- return true;
- }
- }
- else
- if (byte_size == sizeof(long double))
- {
- if (sizeof(long double) == sizeof(uint32_t))
- {
- u32 = data.GetU32(&offset);
- value = *((long double *)&u32);
- return true;
- }
- else if (sizeof(long double) == sizeof(uint64_t))
- {
- u64 = data.GetU64(&offset);
- value = *((long double *)&u64);
- return true;
- }
- }
- }
- break;
+bool CompilerType::SetValueFromScalar(const Scalar &value, Stream &strm) {
+ if (!IsValid())
+ return false;
+
+ // Aggregate types don't have scalar values
+ if (!IsAggregateType()) {
+ strm.GetFlags().Set(Stream::eBinary);
+ uint64_t count = 0;
+ lldb::Encoding encoding = GetEncoding(count);
+
+ if (encoding == lldb::eEncodingInvalid || count != 1)
+ return false;
+
+ const uint64_t bit_width = GetBitSize(nullptr);
+ // This function doesn't currently handle non-byte aligned assignments
+ if ((bit_width % 8) != 0)
+ return false;
+
+ const uint64_t byte_size = (bit_width + 7) / 8;
+ switch (encoding) {
+ case lldb::eEncodingInvalid:
+ break;
+ case lldb::eEncodingVector:
+ break;
+ case lldb::eEncodingUint:
+ switch (byte_size) {
+ case 1:
+ strm.PutHex8(value.UInt());
+ return true;
+ case 2:
+ strm.PutHex16(value.UInt());
+ return true;
+ case 4:
+ strm.PutHex32(value.UInt());
+ return true;
+ case 8:
+ strm.PutHex64(value.ULongLong());
+ return true;
+ default:
+ break;
+ }
+ break;
+
+ case lldb::eEncodingSint:
+ switch (byte_size) {
+ case 1:
+ strm.PutHex8(value.SInt());
+ return true;
+ case 2:
+ strm.PutHex16(value.SInt());
+ return true;
+ case 4:
+ strm.PutHex32(value.SInt());
+ return true;
+ case 8:
+ strm.PutHex64(value.SLongLong());
+ return true;
+ default:
+ break;
+ }
+ break;
+
+ case lldb::eEncodingIEEE754:
+ if (byte_size <= sizeof(long double)) {
+ if (byte_size == sizeof(float)) {
+ strm.PutFloat(value.Float());
+ return true;
+ } else if (byte_size == sizeof(double)) {
+ strm.PutDouble(value.Double());
+ return true;
+ } else if (byte_size == sizeof(long double)) {
+ strm.PutDouble(value.LongDouble());
+ return true;
}
+ }
+ break;
}
- return false;
+ }
+ return false;
}
-bool
-CompilerType::SetValueFromScalar (const Scalar &value, Stream &strm)
-{
- if (!IsValid())
- return false;
-
- // Aggregate types don't have scalar values
- if (!IsAggregateType ())
- {
- strm.GetFlags().Set(Stream::eBinary);
- uint64_t count = 0;
- lldb::Encoding encoding = GetEncoding (count);
-
- if (encoding == lldb::eEncodingInvalid || count != 1)
- return false;
-
- const uint64_t bit_width = GetBitSize(nullptr);
- // This function doesn't currently handle non-byte aligned assignments
- if ((bit_width % 8) != 0)
- return false;
-
- const uint64_t byte_size = (bit_width + 7 ) / 8;
- switch (encoding)
- {
- case lldb::eEncodingInvalid:
- break;
- case lldb::eEncodingVector:
- break;
- case lldb::eEncodingUint:
- switch (byte_size)
- {
- case 1: strm.PutHex8(value.UInt()); return true;
- case 2: strm.PutHex16(value.UInt()); return true;
- case 4: strm.PutHex32(value.UInt()); return true;
- case 8: strm.PutHex64(value.ULongLong()); return true;
- default:
- break;
- }
- break;
-
- case lldb::eEncodingSint:
- switch (byte_size)
- {
- case 1: strm.PutHex8(value.SInt()); return true;
- case 2: strm.PutHex16(value.SInt()); return true;
- case 4: strm.PutHex32(value.SInt()); return true;
- case 8: strm.PutHex64(value.SLongLong()); return true;
- default:
- break;
- }
- break;
-
- case lldb::eEncodingIEEE754:
- if (byte_size <= sizeof(long double))
- {
- if (byte_size == sizeof(float))
- {
- strm.PutFloat(value.Float());
- return true;
- }
- else
- if (byte_size == sizeof(double))
- {
- strm.PutDouble(value.Double());
- return true;
- }
- else
- if (byte_size == sizeof(long double))
- {
- strm.PutDouble(value.LongDouble());
- return true;
- }
- }
- break;
- }
- }
+bool CompilerType::ReadFromMemory(lldb_private::ExecutionContext *exe_ctx,
+ lldb::addr_t addr, AddressType address_type,
+ lldb_private::DataExtractor &data) {
+ if (!IsValid())
return false;
-}
-bool
-CompilerType::ReadFromMemory (lldb_private::ExecutionContext *exe_ctx,
- lldb::addr_t addr,
- AddressType address_type,
- lldb_private::DataExtractor &data)
-{
- if (!IsValid())
- return false;
-
- // Can't convert a file address to anything valid without more
- // context (which Module it came from)
- if (address_type == eAddressTypeFile)
- return false;
-
- if (!GetCompleteType())
- return false;
-
- const uint64_t byte_size = GetByteSize(exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
- if (data.GetByteSize() < byte_size)
- {
- lldb::DataBufferSP data_sp(new DataBufferHeap (byte_size, '\0'));
- data.SetData(data_sp);
- }
-
- uint8_t* dst = const_cast<uint8_t*>(data.PeekData(0, byte_size));
- if (dst != nullptr)
- {
- if (address_type == eAddressTypeHost)
- {
- if (addr == 0)
- return false;
- // The address is an address in this process, so just copy it
- memcpy (dst, (uint8_t*)nullptr + addr, byte_size);
- return true;
- }
- else
- {
- Process *process = nullptr;
- if (exe_ctx)
- process = exe_ctx->GetProcessPtr();
- if (process)
- {
- Error error;
- return process->ReadMemory(addr, dst, byte_size, error) == byte_size;
- }
- }
- }
+ // Can't convert a file address to anything valid without more
+ // context (which Module it came from)
+ if (address_type == eAddressTypeFile)
return false;
-}
-bool
-CompilerType::WriteToMemory (lldb_private::ExecutionContext *exe_ctx,
- lldb::addr_t addr,
- AddressType address_type,
- StreamString &new_value)
-{
- if (!IsValid())
- return false;
-
- // Can't convert a file address to anything valid without more
- // context (which Module it came from)
- if (address_type == eAddressTypeFile)
- return false;
-
- if (!GetCompleteType())
- return false;
-
- const uint64_t byte_size = GetByteSize(exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
-
- if (byte_size > 0)
- {
- if (address_type == eAddressTypeHost)
- {
- // The address is an address in this process, so just copy it
- memcpy ((void *)addr, new_value.GetData(), byte_size);
- return true;
- }
- else
- {
- Process *process = nullptr;
- if (exe_ctx)
- process = exe_ctx->GetProcessPtr();
- if (process)
- {
- Error error;
- return process->WriteMemory(addr, new_value.GetData(), byte_size, error) == byte_size;
- }
- }
- }
+ if (!GetCompleteType())
return false;
-}
-//clang::CXXRecordDecl *
-//CompilerType::GetAsCXXRecordDecl (lldb::opaque_compiler_type_t opaque_compiler_qual_type)
+ const uint64_t byte_size =
+ GetByteSize(exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
+ if (data.GetByteSize() < byte_size) {
+ lldb::DataBufferSP data_sp(new DataBufferHeap(byte_size, '\0'));
+ data.SetData(data_sp);
+ }
+
+ uint8_t *dst = const_cast<uint8_t *>(data.PeekData(0, byte_size));
+ if (dst != nullptr) {
+ if (address_type == eAddressTypeHost) {
+ if (addr == 0)
+ return false;
+ // The address is an address in this process, so just copy it
+ memcpy(dst, (uint8_t *)nullptr + addr, byte_size);
+ return true;
+ } else {
+ Process *process = nullptr;
+ if (exe_ctx)
+ process = exe_ctx->GetProcessPtr();
+ if (process) {
+ Error error;
+ return process->ReadMemory(addr, dst, byte_size, error) == byte_size;
+ }
+ }
+ }
+ return false;
+}
+
+bool CompilerType::WriteToMemory(lldb_private::ExecutionContext *exe_ctx,
+ lldb::addr_t addr, AddressType address_type,
+ StreamString &new_value) {
+ if (!IsValid())
+ return false;
+
+ // Can't convert a file address to anything valid without more
+ // context (which Module it came from)
+ if (address_type == eAddressTypeFile)
+ return false;
+
+ if (!GetCompleteType())
+ return false;
+
+ const uint64_t byte_size =
+ GetByteSize(exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
+
+ if (byte_size > 0) {
+ if (address_type == eAddressTypeHost) {
+ // The address is an address in this process, so just copy it
+ memcpy((void *)addr, new_value.GetData(), byte_size);
+ return true;
+ } else {
+ Process *process = nullptr;
+ if (exe_ctx)
+ process = exe_ctx->GetProcessPtr();
+ if (process) {
+ Error error;
+ return process->WriteMemory(addr, new_value.GetData(), byte_size,
+ error) == byte_size;
+ }
+ }
+ }
+ return false;
+}
+
+// clang::CXXRecordDecl *
+// CompilerType::GetAsCXXRecordDecl (lldb::opaque_compiler_type_t
+// opaque_compiler_qual_type)
//{
// if (opaque_compiler_qual_type)
-// return clang::QualType::getFromOpaquePtr(opaque_compiler_qual_type)->getAsCXXRecordDecl();
+// return
+// clang::QualType::getFromOpaquePtr(opaque_compiler_qual_type)->getAsCXXRecordDecl();
// return NULL;
//}
-bool
-lldb_private::operator == (const lldb_private::CompilerType &lhs, const lldb_private::CompilerType &rhs)
-{
- return lhs.GetTypeSystem() == rhs.GetTypeSystem() && lhs.GetOpaqueQualType() == rhs.GetOpaqueQualType();
+bool lldb_private::operator==(const lldb_private::CompilerType &lhs,
+ const lldb_private::CompilerType &rhs) {
+ return lhs.GetTypeSystem() == rhs.GetTypeSystem() &&
+ lhs.GetOpaqueQualType() == rhs.GetOpaqueQualType();
}
-
-bool
-lldb_private::operator != (const lldb_private::CompilerType &lhs, const lldb_private::CompilerType &rhs)
-{
- return lhs.GetTypeSystem() != rhs.GetTypeSystem() || lhs.GetOpaqueQualType() != rhs.GetOpaqueQualType();
+bool lldb_private::operator!=(const lldb_private::CompilerType &lhs,
+ const lldb_private::CompilerType &rhs) {
+ return lhs.GetTypeSystem() != rhs.GetTypeSystem() ||
+ lhs.GetOpaqueQualType() != rhs.GetOpaqueQualType();
}
-
-
-
Modified: lldb/trunk/source/Symbol/DWARFCallFrameInfo.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/DWARFCallFrameInfo.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/DWARFCallFrameInfo.cpp (original)
+++ lldb/trunk/source/Symbol/DWARFCallFrameInfo.cpp Tue Sep 6 15:57:50 2016
@@ -7,16 +7,15 @@
//
//===----------------------------------------------------------------------===//
-
// C Includes
// C++ Includes
#include <list>
-#include "lldb/Core/Log.h"
-#include "lldb/Core/Section.h"
#include "lldb/Core/ArchSpec.h"
+#include "lldb/Core/Log.h"
#include "lldb/Core/Module.h"
#include "lldb/Core/Section.h"
+#include "lldb/Core/Section.h"
#include "lldb/Core/Timer.h"
#include "lldb/Host/Host.h"
#include "lldb/Symbol/DWARFCallFrameInfo.h"
@@ -28,920 +27,913 @@
using namespace lldb;
using namespace lldb_private;
-DWARFCallFrameInfo::DWARFCallFrameInfo(ObjectFile& objfile, SectionSP& section_sp, lldb::RegisterKind reg_kind, bool is_eh_frame) :
- m_objfile (objfile),
- m_section_sp (section_sp),
- m_reg_kind (reg_kind), // The flavor of registers that the CFI data uses (enum RegisterKind)
- m_flags (),
- m_cie_map (),
- m_cfi_data (),
- m_cfi_data_initialized (false),
- m_fde_index (),
- m_fde_index_initialized (false),
- m_is_eh_frame (is_eh_frame)
-{
-}
-
-DWARFCallFrameInfo::~DWARFCallFrameInfo()
-{
-}
-
-
-bool
-DWARFCallFrameInfo::GetUnwindPlan (Address addr, UnwindPlan& unwind_plan)
-{
- FDEEntryMap::Entry fde_entry;
-
- // Make sure that the Address we're searching for is the same object file
- // as this DWARFCallFrameInfo, we only store File offsets in m_fde_index.
- ModuleSP module_sp = addr.GetModule();
- if (module_sp.get() == nullptr || module_sp->GetObjectFile() == nullptr || module_sp->GetObjectFile() != &m_objfile)
- return false;
-
- if (GetFDEEntryByFileAddress (addr.GetFileAddress(), fde_entry) == false)
- return false;
- return FDEToUnwindPlan (fde_entry.data, addr, unwind_plan);
-}
-
-bool
-DWARFCallFrameInfo::GetAddressRange (Address addr, AddressRange &range)
-{
-
- // Make sure that the Address we're searching for is the same object file
- // as this DWARFCallFrameInfo, we only store File offsets in m_fde_index.
- ModuleSP module_sp = addr.GetModule();
- if (module_sp.get() == nullptr || module_sp->GetObjectFile() == nullptr || module_sp->GetObjectFile() != &m_objfile)
- return false;
-
- if (m_section_sp.get() == nullptr || m_section_sp->IsEncrypted())
- return false;
- GetFDEIndex();
- FDEEntryMap::Entry *fde_entry = m_fde_index.FindEntryThatContains (addr.GetFileAddress());
- if (!fde_entry)
- return false;
-
- range = AddressRange(fde_entry->base, fde_entry->size, m_objfile.GetSectionList());
- return true;
-}
-
-bool
-DWARFCallFrameInfo::GetFDEEntryByFileAddress (addr_t file_addr, FDEEntryMap::Entry &fde_entry)
-{
- if (m_section_sp.get() == nullptr || m_section_sp->IsEncrypted())
- return false;
-
- GetFDEIndex();
-
- if (m_fde_index.IsEmpty())
- return false;
-
- FDEEntryMap::Entry *fde = m_fde_index.FindEntryThatContains (file_addr);
-
- if (fde == nullptr)
- return false;
-
- fde_entry = *fde;
- return true;
-}
-
-void
-DWARFCallFrameInfo::GetFunctionAddressAndSizeVector (FunctionAddressAndSizeVector &function_info)
-{
- GetFDEIndex();
- const size_t count = m_fde_index.GetSize();
- function_info.Clear();
- if (count > 0)
- function_info.Reserve(count);
- for (size_t i = 0; i < count; ++i)
- {
- const FDEEntryMap::Entry *func_offset_data_entry = m_fde_index.GetEntryAtIndex (i);
- if (func_offset_data_entry)
- {
- FunctionAddressAndSizeVector::Entry function_offset_entry (func_offset_data_entry->base, func_offset_data_entry->size);
- function_info.Append (function_offset_entry);
- }
- }
-}
-
-const DWARFCallFrameInfo::CIE*
-DWARFCallFrameInfo::GetCIE(dw_offset_t cie_offset)
-{
- cie_map_t::iterator pos = m_cie_map.find(cie_offset);
-
- if (pos != m_cie_map.end())
- {
- // Parse and cache the CIE
- if (pos->second.get() == nullptr)
- pos->second = ParseCIE (cie_offset);
+DWARFCallFrameInfo::DWARFCallFrameInfo(ObjectFile &objfile,
+ SectionSP §ion_sp,
+ lldb::RegisterKind reg_kind,
+ bool is_eh_frame)
+ : m_objfile(objfile), m_section_sp(section_sp),
+ m_reg_kind(reg_kind), // The flavor of registers that the CFI data uses
+ // (enum RegisterKind)
+ m_flags(), m_cie_map(), m_cfi_data(), m_cfi_data_initialized(false),
+ m_fde_index(), m_fde_index_initialized(false),
+ m_is_eh_frame(is_eh_frame) {}
+
+DWARFCallFrameInfo::~DWARFCallFrameInfo() {}
+
+bool DWARFCallFrameInfo::GetUnwindPlan(Address addr, UnwindPlan &unwind_plan) {
+ FDEEntryMap::Entry fde_entry;
+
+ // Make sure that the Address we're searching for is the same object file
+ // as this DWARFCallFrameInfo, we only store File offsets in m_fde_index.
+ ModuleSP module_sp = addr.GetModule();
+ if (module_sp.get() == nullptr || module_sp->GetObjectFile() == nullptr ||
+ module_sp->GetObjectFile() != &m_objfile)
+ return false;
- return pos->second.get();
- }
- return nullptr;
+ if (GetFDEEntryByFileAddress(addr.GetFileAddress(), fde_entry) == false)
+ return false;
+ return FDEToUnwindPlan(fde_entry.data, addr, unwind_plan);
}
-DWARFCallFrameInfo::CIESP
-DWARFCallFrameInfo::ParseCIE (const dw_offset_t cie_offset)
-{
- CIESP cie_sp(new CIE(cie_offset));
- lldb::offset_t offset = cie_offset;
- if (m_cfi_data_initialized == false)
- GetCFIData();
- uint32_t length = m_cfi_data.GetU32(&offset);
- dw_offset_t cie_id, end_offset;
- bool is_64bit = (length == UINT32_MAX);
- if (is_64bit) {
- length = m_cfi_data.GetU64(&offset);
- cie_id = m_cfi_data.GetU64(&offset);
- end_offset = cie_offset + length + 12;
- } else {
- cie_id = m_cfi_data.GetU32(&offset);
- end_offset = cie_offset + length + 4;
- }
- if (length > 0 && ((!m_is_eh_frame && cie_id == UINT32_MAX) || (m_is_eh_frame && cie_id == 0ul)))
- {
- size_t i;
- // cie.offset = cie_offset;
- // cie.length = length;
- // cie.cieID = cieID;
- cie_sp->ptr_encoding = DW_EH_PE_absptr; // default
- cie_sp->version = m_cfi_data.GetU8(&offset);
+bool DWARFCallFrameInfo::GetAddressRange(Address addr, AddressRange &range) {
- for (i=0; i<CFI_AUG_MAX_SIZE; ++i)
- {
- cie_sp->augmentation[i] = m_cfi_data.GetU8(&offset);
- if (cie_sp->augmentation[i] == '\0')
- {
- // Zero out remaining bytes in augmentation string
- for (size_t j = i+1; j<CFI_AUG_MAX_SIZE; ++j)
- cie_sp->augmentation[j] = '\0';
+ // Make sure that the Address we're searching for is the same object file
+ // as this DWARFCallFrameInfo, we only store File offsets in m_fde_index.
+ ModuleSP module_sp = addr.GetModule();
+ if (module_sp.get() == nullptr || module_sp->GetObjectFile() == nullptr ||
+ module_sp->GetObjectFile() != &m_objfile)
+ return false;
- break;
- }
- }
+ if (m_section_sp.get() == nullptr || m_section_sp->IsEncrypted())
+ return false;
+ GetFDEIndex();
+ FDEEntryMap::Entry *fde_entry =
+ m_fde_index.FindEntryThatContains(addr.GetFileAddress());
+ if (!fde_entry)
+ return false;
- if (i == CFI_AUG_MAX_SIZE && cie_sp->augmentation[CFI_AUG_MAX_SIZE-1] != '\0')
- {
- Host::SystemLog (Host::eSystemLogError, "CIE parse error: CIE augmentation string was too large for the fixed sized buffer of %d bytes.\n", CFI_AUG_MAX_SIZE);
- return cie_sp;
- }
- cie_sp->code_align = (uint32_t)m_cfi_data.GetULEB128(&offset);
- cie_sp->data_align = (int32_t)m_cfi_data.GetSLEB128(&offset);
- cie_sp->return_addr_reg_num = m_cfi_data.GetU8(&offset);
+ range = AddressRange(fde_entry->base, fde_entry->size,
+ m_objfile.GetSectionList());
+ return true;
+}
- if (cie_sp->augmentation[0])
- {
- // Get the length of the eh_frame augmentation data
- // which starts with a ULEB128 length in bytes
- const size_t aug_data_len = (size_t)m_cfi_data.GetULEB128(&offset);
- const size_t aug_data_end = offset + aug_data_len;
- const size_t aug_str_len = strlen(cie_sp->augmentation);
- // A 'z' may be present as the first character of the string.
- // If present, the Augmentation Data field shall be present.
- // The contents of the Augmentation Data shall be interpreted
- // according to other characters in the Augmentation String.
- if (cie_sp->augmentation[0] == 'z')
- {
- // Extract the Augmentation Data
- size_t aug_str_idx = 0;
- for (aug_str_idx = 1; aug_str_idx < aug_str_len; aug_str_idx++)
- {
- char aug = cie_sp->augmentation[aug_str_idx];
- switch (aug)
- {
- case 'L':
- // Indicates the presence of one argument in the
- // Augmentation Data of the CIE, and a corresponding
- // argument in the Augmentation Data of the FDE. The
- // argument in the Augmentation Data of the CIE is
- // 1-byte and represents the pointer encoding used
- // for the argument in the Augmentation Data of the
- // FDE, which is the address of a language-specific
- // data area (LSDA). The size of the LSDA pointer is
- // specified by the pointer encoding used.
- cie_sp->lsda_addr_encoding = m_cfi_data.GetU8(&offset);
- break;
-
- case 'P':
- // Indicates the presence of two arguments in the
- // Augmentation Data of the CIE. The first argument
- // is 1-byte and represents the pointer encoding
- // used for the second argument, which is the
- // address of a personality routine handler. The
- // size of the personality routine pointer is
- // specified by the pointer encoding used.
- //
- // The address of the personality function will
- // be stored at this location. Pre-execution, it
- // will be all zero's so don't read it until we're
- // trying to do an unwind & the reloc has been
- // resolved.
- {
- uint8_t arg_ptr_encoding = m_cfi_data.GetU8(&offset);
- const lldb::addr_t pc_rel_addr = m_section_sp->GetFileAddress();
- cie_sp->personality_loc = m_cfi_data.GetGNUEHPointer(&offset, arg_ptr_encoding, pc_rel_addr, LLDB_INVALID_ADDRESS, LLDB_INVALID_ADDRESS);
- }
- break;
-
- case 'R':
- // A 'R' may be present at any position after the
- // first character of the string. The Augmentation
- // Data shall include a 1 byte argument that
- // represents the pointer encoding for the address
- // pointers used in the FDE.
- // Example: 0x1B == DW_EH_PE_pcrel | DW_EH_PE_sdata4
- cie_sp->ptr_encoding = m_cfi_data.GetU8(&offset);
- break;
- }
- }
- }
- else if (strcmp(cie_sp->augmentation, "eh") == 0)
- {
- // If the Augmentation string has the value "eh", then
- // the EH Data field shall be present
- }
+bool DWARFCallFrameInfo::GetFDEEntryByFileAddress(
+ addr_t file_addr, FDEEntryMap::Entry &fde_entry) {
+ if (m_section_sp.get() == nullptr || m_section_sp->IsEncrypted())
+ return false;
- // Set the offset to be the end of the augmentation data just in case
- // we didn't understand any of the data.
- offset = (uint32_t)aug_data_end;
- }
+ GetFDEIndex();
- if (end_offset > offset)
- {
- cie_sp->inst_offset = offset;
- cie_sp->inst_length = end_offset - offset;
- }
- while (offset < end_offset)
- {
- uint8_t inst = m_cfi_data.GetU8(&offset);
- uint8_t primary_opcode = inst & 0xC0;
- uint8_t extended_opcode = inst & 0x3F;
+ if (m_fde_index.IsEmpty())
+ return false;
- if (!HandleCommonDwarfOpcode(primary_opcode, extended_opcode, cie_sp->data_align, offset, cie_sp->initial_row))
- break; // Stop if we hit an unrecognized opcode
- }
- }
+ FDEEntryMap::Entry *fde = m_fde_index.FindEntryThatContains(file_addr);
+
+ if (fde == nullptr)
+ return false;
- return cie_sp;
+ fde_entry = *fde;
+ return true;
}
-void
-DWARFCallFrameInfo::GetCFIData()
-{
- if (m_cfi_data_initialized == false)
- {
- Log *log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_UNWIND));
- if (log)
- m_objfile.GetModule()->LogMessage(log, "Reading EH frame info");
- m_objfile.ReadSectionData (m_section_sp.get(), m_cfi_data);
- m_cfi_data_initialized = true;
- }
+void DWARFCallFrameInfo::GetFunctionAddressAndSizeVector(
+ FunctionAddressAndSizeVector &function_info) {
+ GetFDEIndex();
+ const size_t count = m_fde_index.GetSize();
+ function_info.Clear();
+ if (count > 0)
+ function_info.Reserve(count);
+ for (size_t i = 0; i < count; ++i) {
+ const FDEEntryMap::Entry *func_offset_data_entry =
+ m_fde_index.GetEntryAtIndex(i);
+ if (func_offset_data_entry) {
+ FunctionAddressAndSizeVector::Entry function_offset_entry(
+ func_offset_data_entry->base, func_offset_data_entry->size);
+ function_info.Append(function_offset_entry);
+ }
+ }
+}
+
+const DWARFCallFrameInfo::CIE *
+DWARFCallFrameInfo::GetCIE(dw_offset_t cie_offset) {
+ cie_map_t::iterator pos = m_cie_map.find(cie_offset);
+
+ if (pos != m_cie_map.end()) {
+ // Parse and cache the CIE
+ if (pos->second.get() == nullptr)
+ pos->second = ParseCIE(cie_offset);
+
+ return pos->second.get();
+ }
+ return nullptr;
}
-// Scan through the eh_frame or debug_frame section looking for FDEs and noting the start/end addresses
-// of the functions and a pointer back to the function's FDE for later expansion.
-// Internalize CIEs as we come across them.
-void
-DWARFCallFrameInfo::GetFDEIndex ()
-{
- if (m_section_sp.get() == nullptr || m_section_sp->IsEncrypted())
- return;
-
- if (m_fde_index_initialized)
- return;
-
- std::lock_guard<std::mutex> guard(m_fde_index_mutex);
-
- if (m_fde_index_initialized) // if two threads hit the locker
- return;
-
- Timer scoped_timer (LLVM_PRETTY_FUNCTION, "%s - %s", LLVM_PRETTY_FUNCTION, m_objfile.GetFileSpec().GetFilename().AsCString(""));
-
- bool clear_address_zeroth_bit = false;
- ArchSpec arch;
- if (m_objfile.GetArchitecture (arch))
- {
- if (arch.GetTriple().getArch() == llvm::Triple::arm || arch.GetTriple().getArch() == llvm::Triple::thumb)
- clear_address_zeroth_bit = true;
- }
-
- lldb::offset_t offset = 0;
- if (m_cfi_data_initialized == false)
- GetCFIData();
- while (m_cfi_data.ValidOffsetForDataOfSize (offset, 8))
- {
- const dw_offset_t current_entry = offset;
- dw_offset_t cie_id, next_entry, cie_offset;
- uint32_t len = m_cfi_data.GetU32 (&offset);
- bool is_64bit = (len == UINT32_MAX);
- if (is_64bit) {
- len = m_cfi_data.GetU64 (&offset);
- cie_id = m_cfi_data.GetU64 (&offset);
- next_entry = current_entry + len + 12;
- cie_offset = current_entry + 12 - cie_id;
- } else {
- cie_id = m_cfi_data.GetU32 (&offset);
- next_entry = current_entry + len + 4;
- cie_offset = current_entry + 4 - cie_id;
- }
+DWARFCallFrameInfo::CIESP
+DWARFCallFrameInfo::ParseCIE(const dw_offset_t cie_offset) {
+ CIESP cie_sp(new CIE(cie_offset));
+ lldb::offset_t offset = cie_offset;
+ if (m_cfi_data_initialized == false)
+ GetCFIData();
+ uint32_t length = m_cfi_data.GetU32(&offset);
+ dw_offset_t cie_id, end_offset;
+ bool is_64bit = (length == UINT32_MAX);
+ if (is_64bit) {
+ length = m_cfi_data.GetU64(&offset);
+ cie_id = m_cfi_data.GetU64(&offset);
+ end_offset = cie_offset + length + 12;
+ } else {
+ cie_id = m_cfi_data.GetU32(&offset);
+ end_offset = cie_offset + length + 4;
+ }
+ if (length > 0 && ((!m_is_eh_frame && cie_id == UINT32_MAX) ||
+ (m_is_eh_frame && cie_id == 0ul))) {
+ size_t i;
+ // cie.offset = cie_offset;
+ // cie.length = length;
+ // cie.cieID = cieID;
+ cie_sp->ptr_encoding = DW_EH_PE_absptr; // default
+ cie_sp->version = m_cfi_data.GetU8(&offset);
+
+ for (i = 0; i < CFI_AUG_MAX_SIZE; ++i) {
+ cie_sp->augmentation[i] = m_cfi_data.GetU8(&offset);
+ if (cie_sp->augmentation[i] == '\0') {
+ // Zero out remaining bytes in augmentation string
+ for (size_t j = i + 1; j < CFI_AUG_MAX_SIZE; ++j)
+ cie_sp->augmentation[j] = '\0';
+
+ break;
+ }
+ }
+
+ if (i == CFI_AUG_MAX_SIZE &&
+ cie_sp->augmentation[CFI_AUG_MAX_SIZE - 1] != '\0') {
+ Host::SystemLog(Host::eSystemLogError,
+ "CIE parse error: CIE augmentation string was too large "
+ "for the fixed sized buffer of %d bytes.\n",
+ CFI_AUG_MAX_SIZE);
+ return cie_sp;
+ }
+ cie_sp->code_align = (uint32_t)m_cfi_data.GetULEB128(&offset);
+ cie_sp->data_align = (int32_t)m_cfi_data.GetSLEB128(&offset);
+ cie_sp->return_addr_reg_num = m_cfi_data.GetU8(&offset);
+
+ if (cie_sp->augmentation[0]) {
+ // Get the length of the eh_frame augmentation data
+ // which starts with a ULEB128 length in bytes
+ const size_t aug_data_len = (size_t)m_cfi_data.GetULEB128(&offset);
+ const size_t aug_data_end = offset + aug_data_len;
+ const size_t aug_str_len = strlen(cie_sp->augmentation);
+ // A 'z' may be present as the first character of the string.
+ // If present, the Augmentation Data field shall be present.
+ // The contents of the Augmentation Data shall be interpreted
+ // according to other characters in the Augmentation String.
+ if (cie_sp->augmentation[0] == 'z') {
+ // Extract the Augmentation Data
+ size_t aug_str_idx = 0;
+ for (aug_str_idx = 1; aug_str_idx < aug_str_len; aug_str_idx++) {
+ char aug = cie_sp->augmentation[aug_str_idx];
+ switch (aug) {
+ case 'L':
+ // Indicates the presence of one argument in the
+ // Augmentation Data of the CIE, and a corresponding
+ // argument in the Augmentation Data of the FDE. The
+ // argument in the Augmentation Data of the CIE is
+ // 1-byte and represents the pointer encoding used
+ // for the argument in the Augmentation Data of the
+ // FDE, which is the address of a language-specific
+ // data area (LSDA). The size of the LSDA pointer is
+ // specified by the pointer encoding used.
+ cie_sp->lsda_addr_encoding = m_cfi_data.GetU8(&offset);
+ break;
- if (next_entry > m_cfi_data.GetByteSize() + 1)
- {
- Host::SystemLog (Host::eSystemLogError,
- "error: Invalid fde/cie next entry offset of 0x%x found in cie/fde at 0x%x\n",
- next_entry,
- current_entry);
- // Don't trust anything in this eh_frame section if we find blatantly
- // invalid data.
- m_fde_index.Clear();
- m_fde_index_initialized = true;
- return;
- }
- if (cie_offset > m_cfi_data.GetByteSize())
- {
- Host::SystemLog (Host::eSystemLogError,
- "error: Invalid cie offset of 0x%x found in cie/fde at 0x%x\n",
- cie_offset,
- current_entry);
- // Don't trust anything in this eh_frame section if we find blatantly
- // invalid data.
- m_fde_index.Clear();
- m_fde_index_initialized = true;
- return;
- }
+ case 'P':
+ // Indicates the presence of two arguments in the
+ // Augmentation Data of the CIE. The first argument
+ // is 1-byte and represents the pointer encoding
+ // used for the second argument, which is the
+ // address of a personality routine handler. The
+ // size of the personality routine pointer is
+ // specified by the pointer encoding used.
+ //
+ // The address of the personality function will
+ // be stored at this location. Pre-execution, it
+ // will be all zero's so don't read it until we're
+ // trying to do an unwind & the reloc has been
+ // resolved.
+ {
+ uint8_t arg_ptr_encoding = m_cfi_data.GetU8(&offset);
+ const lldb::addr_t pc_rel_addr = m_section_sp->GetFileAddress();
+ cie_sp->personality_loc = m_cfi_data.GetGNUEHPointer(
+ &offset, arg_ptr_encoding, pc_rel_addr, LLDB_INVALID_ADDRESS,
+ LLDB_INVALID_ADDRESS);
+ }
+ break;
- if (cie_id == 0 || cie_id == UINT32_MAX || len == 0)
- {
- m_cie_map[current_entry] = ParseCIE (current_entry);
- offset = next_entry;
- continue;
+ case 'R':
+ // A 'R' may be present at any position after the
+ // first character of the string. The Augmentation
+ // Data shall include a 1 byte argument that
+ // represents the pointer encoding for the address
+ // pointers used in the FDE.
+ // Example: 0x1B == DW_EH_PE_pcrel | DW_EH_PE_sdata4
+ cie_sp->ptr_encoding = m_cfi_data.GetU8(&offset);
+ break;
+ }
}
+ } else if (strcmp(cie_sp->augmentation, "eh") == 0) {
+ // If the Augmentation string has the value "eh", then
+ // the EH Data field shall be present
+ }
+
+ // Set the offset to be the end of the augmentation data just in case
+ // we didn't understand any of the data.
+ offset = (uint32_t)aug_data_end;
+ }
+
+ if (end_offset > offset) {
+ cie_sp->inst_offset = offset;
+ cie_sp->inst_length = end_offset - offset;
+ }
+ while (offset < end_offset) {
+ uint8_t inst = m_cfi_data.GetU8(&offset);
+ uint8_t primary_opcode = inst & 0xC0;
+ uint8_t extended_opcode = inst & 0x3F;
+
+ if (!HandleCommonDwarfOpcode(primary_opcode, extended_opcode,
+ cie_sp->data_align, offset,
+ cie_sp->initial_row))
+ break; // Stop if we hit an unrecognized opcode
+ }
+ }
+
+ return cie_sp;
+}
+
+void DWARFCallFrameInfo::GetCFIData() {
+ if (m_cfi_data_initialized == false) {
+ Log *log(GetLogIfAllCategoriesSet(LIBLLDB_LOG_UNWIND));
+ if (log)
+ m_objfile.GetModule()->LogMessage(log, "Reading EH frame info");
+ m_objfile.ReadSectionData(m_section_sp.get(), m_cfi_data);
+ m_cfi_data_initialized = true;
+ }
+}
+// Scan through the eh_frame or debug_frame section looking for FDEs and noting
+// the start/end addresses
+// of the functions and a pointer back to the function's FDE for later
+// expansion.
+// Internalize CIEs as we come across them.
- const CIE *cie = GetCIE (cie_offset);
- if (cie)
- {
- const lldb::addr_t pc_rel_addr = m_section_sp->GetFileAddress();
- const lldb::addr_t text_addr = LLDB_INVALID_ADDRESS;
- const lldb::addr_t data_addr = LLDB_INVALID_ADDRESS;
-
- lldb::addr_t addr = m_cfi_data.GetGNUEHPointer(&offset, cie->ptr_encoding, pc_rel_addr, text_addr, data_addr);
- if (clear_address_zeroth_bit)
- addr &= ~1ull;
-
- lldb::addr_t length = m_cfi_data.GetGNUEHPointer(&offset, cie->ptr_encoding & DW_EH_PE_MASK_ENCODING, pc_rel_addr, text_addr, data_addr);
- FDEEntryMap::Entry fde (addr, length, current_entry);
- m_fde_index.Append(fde);
- }
- else
- {
- Host::SystemLog (Host::eSystemLogError,
- "error: unable to find CIE at 0x%8.8x for cie_id = 0x%8.8x for entry at 0x%8.8x.\n",
- cie_offset,
- cie_id,
- current_entry);
- }
- offset = next_entry;
- }
- m_fde_index.Sort();
- m_fde_index_initialized = true;
-}
-
-bool
-DWARFCallFrameInfo::FDEToUnwindPlan (dw_offset_t dwarf_offset, Address startaddr, UnwindPlan& unwind_plan)
-{
- Log *log = GetLogIfAllCategoriesSet(LIBLLDB_LOG_UNWIND);
- lldb::offset_t offset = dwarf_offset;
- lldb::offset_t current_entry = offset;
-
- if (m_section_sp.get() == nullptr || m_section_sp->IsEncrypted())
- return false;
-
- if (m_cfi_data_initialized == false)
- GetCFIData();
-
- uint32_t length = m_cfi_data.GetU32 (&offset);
- dw_offset_t cie_offset;
- bool is_64bit = (length == UINT32_MAX);
+void DWARFCallFrameInfo::GetFDEIndex() {
+ if (m_section_sp.get() == nullptr || m_section_sp->IsEncrypted())
+ return;
+
+ if (m_fde_index_initialized)
+ return;
+
+ std::lock_guard<std::mutex> guard(m_fde_index_mutex);
+
+ if (m_fde_index_initialized) // if two threads hit the locker
+ return;
+
+ Timer scoped_timer(LLVM_PRETTY_FUNCTION, "%s - %s", LLVM_PRETTY_FUNCTION,
+ m_objfile.GetFileSpec().GetFilename().AsCString(""));
+
+ bool clear_address_zeroth_bit = false;
+ ArchSpec arch;
+ if (m_objfile.GetArchitecture(arch)) {
+ if (arch.GetTriple().getArch() == llvm::Triple::arm ||
+ arch.GetTriple().getArch() == llvm::Triple::thumb)
+ clear_address_zeroth_bit = true;
+ }
+
+ lldb::offset_t offset = 0;
+ if (m_cfi_data_initialized == false)
+ GetCFIData();
+ while (m_cfi_data.ValidOffsetForDataOfSize(offset, 8)) {
+ const dw_offset_t current_entry = offset;
+ dw_offset_t cie_id, next_entry, cie_offset;
+ uint32_t len = m_cfi_data.GetU32(&offset);
+ bool is_64bit = (len == UINT32_MAX);
if (is_64bit) {
- length = m_cfi_data.GetU64 (&offset);
- cie_offset = m_cfi_data.GetU64 (&offset);
+ len = m_cfi_data.GetU64(&offset);
+ cie_id = m_cfi_data.GetU64(&offset);
+ next_entry = current_entry + len + 12;
+ cie_offset = current_entry + 12 - cie_id;
} else {
- cie_offset = m_cfi_data.GetU32 (&offset);
- }
-
- assert (cie_offset != 0 && cie_offset != UINT32_MAX);
-
- // Translate the CIE_id from the eh_frame format, which
- // is relative to the FDE offset, into a __eh_frame section
- // offset
- if (m_is_eh_frame)
- {
- unwind_plan.SetSourceName ("eh_frame CFI");
- cie_offset = current_entry + (is_64bit ? 12 : 4) - cie_offset;
- unwind_plan.SetUnwindPlanValidAtAllInstructions (eLazyBoolNo);
- }
- else
- {
- unwind_plan.SetSourceName ("DWARF CFI");
- // In theory the debug_frame info should be valid at all call sites
- // ("asynchronous unwind info" as it is sometimes called) but in practice
- // gcc et al all emit call frame info for the prologue and call sites, but
- // not for the epilogue or all the other locations during the function reliably.
- unwind_plan.SetUnwindPlanValidAtAllInstructions (eLazyBoolNo);
- }
- unwind_plan.SetSourcedFromCompiler (eLazyBoolYes);
-
- const CIE *cie = GetCIE (cie_offset);
- assert (cie != nullptr);
-
- const dw_offset_t end_offset = current_entry + length + (is_64bit ? 12 : 4);
-
- const lldb::addr_t pc_rel_addr = m_section_sp->GetFileAddress();
- const lldb::addr_t text_addr = LLDB_INVALID_ADDRESS;
- const lldb::addr_t data_addr = LLDB_INVALID_ADDRESS;
- lldb::addr_t range_base = m_cfi_data.GetGNUEHPointer(&offset, cie->ptr_encoding, pc_rel_addr, text_addr, data_addr);
- lldb::addr_t range_len = m_cfi_data.GetGNUEHPointer(&offset, cie->ptr_encoding & DW_EH_PE_MASK_ENCODING, pc_rel_addr, text_addr, data_addr);
- AddressRange range (range_base, m_objfile.GetAddressByteSize(), m_objfile.GetSectionList());
- range.SetByteSize (range_len);
-
- addr_t lsda_data_file_address = LLDB_INVALID_ADDRESS;
-
- if (cie->augmentation[0] == 'z')
- {
- uint32_t aug_data_len = (uint32_t)m_cfi_data.GetULEB128(&offset);
- if (aug_data_len != 0 && cie->lsda_addr_encoding != DW_EH_PE_omit)
- {
- offset_t saved_offset = offset;
- lsda_data_file_address = m_cfi_data.GetGNUEHPointer(&offset, cie->lsda_addr_encoding, pc_rel_addr, text_addr, data_addr);
- if (offset - saved_offset != aug_data_len)
- {
- // There is more in the augmentation region than we know how to process;
- // don't read anything.
- lsda_data_file_address = LLDB_INVALID_ADDRESS;
- }
- offset = saved_offset;
- }
- offset += aug_data_len;
- }
- Address lsda_data;
- Address personality_function_ptr;
-
- if (lsda_data_file_address != LLDB_INVALID_ADDRESS && cie->personality_loc != LLDB_INVALID_ADDRESS)
- {
- m_objfile.GetModule()->ResolveFileAddress (lsda_data_file_address, lsda_data);
- m_objfile.GetModule()->ResolveFileAddress (cie->personality_loc, personality_function_ptr);
- }
-
- if (lsda_data.IsValid() && personality_function_ptr.IsValid())
- {
- unwind_plan.SetLSDAAddress (lsda_data);
- unwind_plan.SetPersonalityFunctionPtr (personality_function_ptr);
- }
-
- uint32_t code_align = cie->code_align;
- int32_t data_align = cie->data_align;
-
- unwind_plan.SetPlanValidAddressRange (range);
- UnwindPlan::Row *cie_initial_row = new UnwindPlan::Row;
- *cie_initial_row = cie->initial_row;
- UnwindPlan::RowSP row(cie_initial_row);
-
- unwind_plan.SetRegisterKind (m_reg_kind);
- unwind_plan.SetReturnAddressRegister (cie->return_addr_reg_num);
-
- std::vector<UnwindPlan::RowSP> stack;
-
- UnwindPlan::Row::RegisterLocation reg_location;
- while (m_cfi_data.ValidOffset(offset) && offset < end_offset)
- {
- uint8_t inst = m_cfi_data.GetU8(&offset);
- uint8_t primary_opcode = inst & 0xC0;
- uint8_t extended_opcode = inst & 0x3F;
-
- if (!HandleCommonDwarfOpcode(primary_opcode, extended_opcode, data_align, offset, *row))
- {
- if (primary_opcode)
- {
- switch (primary_opcode)
- {
- case DW_CFA_advance_loc : // (Row Creation Instruction)
- { // 0x40 - high 2 bits are 0x1, lower 6 bits are delta
- // takes a single argument that represents a constant delta. The
- // required action is to create a new table row with a location
- // value that is computed by taking the current entry's location
- // value and adding (delta * code_align). All other
- // values in the new row are initially identical to the current row.
- unwind_plan.AppendRow(row);
- UnwindPlan::Row *newrow = new UnwindPlan::Row;
- *newrow = *row.get();
- row.reset (newrow);
- row->SlideOffset(extended_opcode * code_align);
- break;
- }
-
- case DW_CFA_restore :
- { // 0xC0 - high 2 bits are 0x3, lower 6 bits are register
- // takes a single argument that represents a register number. The
- // required action is to change the rule for the indicated register
- // to the rule assigned it by the initial_instructions in the CIE.
- uint32_t reg_num = extended_opcode;
- // We only keep enough register locations around to
- // unwind what is in our thread, and these are organized
- // by the register index in that state, so we need to convert our
- // eh_frame register number from the EH frame info, to a register index
-
- if (unwind_plan.IsValidRowIndex(0) && unwind_plan.GetRowAtIndex(0)->GetRegisterInfo(reg_num, reg_location))
- row->SetRegisterInfo (reg_num, reg_location);
- break;
- }
- }
- }
- else
- {
- switch (extended_opcode)
- {
- case DW_CFA_set_loc : // 0x1 (Row Creation Instruction)
- {
- // DW_CFA_set_loc takes a single argument that represents an address.
- // The required action is to create a new table row using the
- // specified address as the location. All other values in the new row
- // are initially identical to the current row. The new location value
- // should always be greater than the current one.
- unwind_plan.AppendRow(row);
- UnwindPlan::Row *newrow = new UnwindPlan::Row;
- *newrow = *row.get();
- row.reset (newrow);
- row->SetOffset(m_cfi_data.GetPointer(&offset) - startaddr.GetFileAddress());
- break;
- }
-
- case DW_CFA_advance_loc1 : // 0x2 (Row Creation Instruction)
- {
- // takes a single uword argument that represents a constant delta.
- // This instruction is identical to DW_CFA_advance_loc except for the
- // encoding and size of the delta argument.
- unwind_plan.AppendRow(row);
- UnwindPlan::Row *newrow = new UnwindPlan::Row;
- *newrow = *row.get();
- row.reset (newrow);
- row->SlideOffset (m_cfi_data.GetU8(&offset) * code_align);
- break;
- }
-
- case DW_CFA_advance_loc2 : // 0x3 (Row Creation Instruction)
- {
- // takes a single uword argument that represents a constant delta.
- // This instruction is identical to DW_CFA_advance_loc except for the
- // encoding and size of the delta argument.
- unwind_plan.AppendRow(row);
- UnwindPlan::Row *newrow = new UnwindPlan::Row;
- *newrow = *row.get();
- row.reset (newrow);
- row->SlideOffset (m_cfi_data.GetU16(&offset) * code_align);
- break;
- }
-
- case DW_CFA_advance_loc4 : // 0x4 (Row Creation Instruction)
- {
- // takes a single uword argument that represents a constant delta.
- // This instruction is identical to DW_CFA_advance_loc except for the
- // encoding and size of the delta argument.
- unwind_plan.AppendRow(row);
- UnwindPlan::Row *newrow = new UnwindPlan::Row;
- *newrow = *row.get();
- row.reset (newrow);
- row->SlideOffset (m_cfi_data.GetU32(&offset) * code_align);
- break;
- }
-
- case DW_CFA_restore_extended : // 0x6
- {
- // takes a single unsigned LEB128 argument that represents a register
- // number. This instruction is identical to DW_CFA_restore except for
- // the encoding and size of the register argument.
- uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
- if (unwind_plan.IsValidRowIndex(0) && unwind_plan.GetRowAtIndex(0)->GetRegisterInfo(reg_num, reg_location))
- row->SetRegisterInfo (reg_num, reg_location);
- break;
- }
-
- case DW_CFA_remember_state : // 0xA
- {
- // These instructions define a stack of information. Encountering the
- // DW_CFA_remember_state instruction means to save the rules for every
- // register on the current row on the stack. Encountering the
- // DW_CFA_restore_state instruction means to pop the set of rules off
- // the stack and place them in the current row. (This operation is
- // useful for compilers that move epilogue code into the body of a
- // function.)
- stack.push_back (row);
- UnwindPlan::Row *newrow = new UnwindPlan::Row;
- *newrow = *row.get();
- row.reset (newrow);
- break;
- }
-
- case DW_CFA_restore_state : // 0xB
- {
- // These instructions define a stack of information. Encountering the
- // DW_CFA_remember_state instruction means to save the rules for every
- // register on the current row on the stack. Encountering the
- // DW_CFA_restore_state instruction means to pop the set of rules off
- // the stack and place them in the current row. (This operation is
- // useful for compilers that move epilogue code into the body of a
- // function.)
- if (stack.empty())
- {
- if (log)
- log->Printf(
- "DWARFCallFrameInfo::%s(dwarf_offset: %" PRIx32 ", startaddr: %" PRIx64
- " encountered DW_CFA_restore_state but state stack is empty. Corrupt unwind info?",
- __FUNCTION__, dwarf_offset, startaddr.GetFileAddress());
- break;
- }
- lldb::addr_t offset = row->GetOffset ();
- row = stack.back ();
- stack.pop_back ();
- row->SetOffset (offset);
- break;
- }
-
- case DW_CFA_GNU_args_size: // 0x2e
- {
- // The DW_CFA_GNU_args_size instruction takes an unsigned LEB128 operand
- // representing an argument size. This instruction specifies the total of
- // the size of the arguments which have been pushed onto the stack.
-
- // TODO: Figure out how we should handle this.
- m_cfi_data.GetULEB128(&offset);
- break;
- }
-
- case DW_CFA_val_offset : // 0x14
- case DW_CFA_val_offset_sf : // 0x15
- default:
- break;
- }
- }
- }
- }
- unwind_plan.AppendRow(row);
-
- return true;
-}
-
-bool
-DWARFCallFrameInfo::HandleCommonDwarfOpcode(uint8_t primary_opcode,
- uint8_t extended_opcode,
- int32_t data_align,
- lldb::offset_t& offset,
- UnwindPlan::Row& row)
-{
- UnwindPlan::Row::RegisterLocation reg_location;
-
- if (primary_opcode)
- {
- switch (primary_opcode)
- {
- case DW_CFA_offset:
- { // 0x80 - high 2 bits are 0x2, lower 6 bits are register
- // takes two arguments: an unsigned LEB128 constant representing a
- // factored offset and a register number. The required action is to
- // change the rule for the register indicated by the register number
- // to be an offset(N) rule with a value of
- // (N = factored offset * data_align).
- uint8_t reg_num = extended_opcode;
- int32_t op_offset = (int32_t)m_cfi_data.GetULEB128(&offset) * data_align;
- reg_location.SetAtCFAPlusOffset(op_offset);
- row.SetRegisterInfo(reg_num, reg_location);
- return true;
- }
- }
- }
- else
- {
- switch (extended_opcode)
- {
- case DW_CFA_nop : // 0x0
- return true;
-
- case DW_CFA_offset_extended : // 0x5
- {
- // takes two unsigned LEB128 arguments representing a register number
- // and a factored offset. This instruction is identical to DW_CFA_offset
- // except for the encoding and size of the register argument.
- uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
- int32_t op_offset = (int32_t)m_cfi_data.GetULEB128(&offset) * data_align;
- UnwindPlan::Row::RegisterLocation reg_location;
- reg_location.SetAtCFAPlusOffset(op_offset);
- row.SetRegisterInfo(reg_num, reg_location);
- return true;
- }
-
- case DW_CFA_undefined : // 0x7
- {
- // takes a single unsigned LEB128 argument that represents a register
- // number. The required action is to set the rule for the specified
- // register to undefined.
- uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
- UnwindPlan::Row::RegisterLocation reg_location;
- reg_location.SetUndefined();
- row.SetRegisterInfo(reg_num, reg_location);
- return true;
- }
-
- case DW_CFA_same_value : // 0x8
- {
- // takes a single unsigned LEB128 argument that represents a register
- // number. The required action is to set the rule for the specified
- // register to same value.
- uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
- UnwindPlan::Row::RegisterLocation reg_location;
- reg_location.SetSame();
- row.SetRegisterInfo (reg_num, reg_location);
- return true;
- }
-
- case DW_CFA_register : // 0x9
- {
- // takes two unsigned LEB128 arguments representing register numbers.
- // The required action is to set the rule for the first register to be
- // the second register.
- uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
- uint32_t other_reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
- UnwindPlan::Row::RegisterLocation reg_location;
- reg_location.SetInRegister(other_reg_num);
- row.SetRegisterInfo (reg_num, reg_location);
- return true;
- }
-
- case DW_CFA_def_cfa : // 0xC (CFA Definition Instruction)
- {
- // Takes two unsigned LEB128 operands representing a register
- // number and a (non-factored) offset. The required action
- // is to define the current CFA rule to use the provided
- // register and offset.
- uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
- int32_t op_offset = (int32_t)m_cfi_data.GetULEB128(&offset);
- row.GetCFAValue().SetIsRegisterPlusOffset (reg_num, op_offset);
- return true;
- }
-
- case DW_CFA_def_cfa_register : // 0xD (CFA Definition Instruction)
- {
- // takes a single unsigned LEB128 argument representing a register
- // number. The required action is to define the current CFA rule to
- // use the provided register (but to keep the old offset).
- uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
- row.GetCFAValue().SetIsRegisterPlusOffset (reg_num, row.GetCFAValue().GetOffset());
- return true;
- }
-
- case DW_CFA_def_cfa_offset : // 0xE (CFA Definition Instruction)
- {
- // Takes a single unsigned LEB128 operand representing a
- // (non-factored) offset. The required action is to define
- // the current CFA rule to use the provided offset (but
- // to keep the old register).
- int32_t op_offset = (int32_t)m_cfi_data.GetULEB128(&offset);
- row.GetCFAValue().SetIsRegisterPlusOffset(row.GetCFAValue().GetRegisterNumber(), op_offset);
- return true;
- }
-
- case DW_CFA_def_cfa_expression : // 0xF (CFA Definition Instruction)
- {
- size_t block_len = (size_t)m_cfi_data.GetULEB128(&offset);
- const uint8_t *block_data = static_cast<const uint8_t*>(m_cfi_data.GetData(&offset, block_len));
- row.GetCFAValue().SetIsDWARFExpression(block_data, block_len);
- return true;
- }
-
- case DW_CFA_expression : // 0x10
- {
- // Takes two operands: an unsigned LEB128 value representing
- // a register number, and a DW_FORM_block value representing a DWARF
- // expression. The required action is to change the rule for the
- // register indicated by the register number to be an expression(E)
- // rule where E is the DWARF expression. That is, the DWARF
- // expression computes the address. The value of the CFA is
- // pushed on the DWARF evaluation stack prior to execution of
- // the DWARF expression.
- uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
- uint32_t block_len = (uint32_t)m_cfi_data.GetULEB128(&offset);
- const uint8_t *block_data = static_cast<const uint8_t*>(m_cfi_data.GetData(&offset, block_len));
- UnwindPlan::Row::RegisterLocation reg_location;
- reg_location.SetAtDWARFExpression(block_data, block_len);
- row.SetRegisterInfo(reg_num, reg_location);
- return true;
- }
-
- case DW_CFA_offset_extended_sf : // 0x11
- {
- // takes two operands: an unsigned LEB128 value representing a
- // register number and a signed LEB128 factored offset. This
- // instruction is identical to DW_CFA_offset_extended except
- //that the second operand is signed and factored.
- uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
- int32_t op_offset = (int32_t)m_cfi_data.GetSLEB128(&offset) * data_align;
- UnwindPlan::Row::RegisterLocation reg_location;
- reg_location.SetAtCFAPlusOffset(op_offset);
- row.SetRegisterInfo(reg_num, reg_location);
- return true;
- }
-
- case DW_CFA_def_cfa_sf : // 0x12 (CFA Definition Instruction)
- {
- // Takes two operands: an unsigned LEB128 value representing
- // a register number and a signed LEB128 factored offset.
- // This instruction is identical to DW_CFA_def_cfa except
- // that the second operand is signed and factored.
- uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
- int32_t op_offset = (int32_t)m_cfi_data.GetSLEB128(&offset) * data_align;
- row.GetCFAValue().SetIsRegisterPlusOffset (reg_num, op_offset);
- return true;
- }
-
- case DW_CFA_def_cfa_offset_sf : // 0x13 (CFA Definition Instruction)
- {
- // takes a signed LEB128 operand representing a factored
- // offset. This instruction is identical to DW_CFA_def_cfa_offset
- // except that the operand is signed and factored.
- int32_t op_offset = (int32_t)m_cfi_data.GetSLEB128(&offset) * data_align;
- uint32_t cfa_regnum = row.GetCFAValue().GetRegisterNumber();
- row.GetCFAValue().SetIsRegisterPlusOffset(cfa_regnum, op_offset);
- return true;
- }
+ cie_id = m_cfi_data.GetU32(&offset);
+ next_entry = current_entry + len + 4;
+ cie_offset = current_entry + 4 - cie_id;
+ }
+
+ if (next_entry > m_cfi_data.GetByteSize() + 1) {
+ Host::SystemLog(Host::eSystemLogError, "error: Invalid fde/cie next "
+ "entry offset of 0x%x found in "
+ "cie/fde at 0x%x\n",
+ next_entry, current_entry);
+ // Don't trust anything in this eh_frame section if we find blatantly
+ // invalid data.
+ m_fde_index.Clear();
+ m_fde_index_initialized = true;
+ return;
+ }
+ if (cie_offset > m_cfi_data.GetByteSize()) {
+ Host::SystemLog(
+ Host::eSystemLogError,
+ "error: Invalid cie offset of 0x%x found in cie/fde at 0x%x\n",
+ cie_offset, current_entry);
+ // Don't trust anything in this eh_frame section if we find blatantly
+ // invalid data.
+ m_fde_index.Clear();
+ m_fde_index_initialized = true;
+ return;
+ }
+
+ if (cie_id == 0 || cie_id == UINT32_MAX || len == 0) {
+ m_cie_map[current_entry] = ParseCIE(current_entry);
+ offset = next_entry;
+ continue;
+ }
+
+ const CIE *cie = GetCIE(cie_offset);
+ if (cie) {
+ const lldb::addr_t pc_rel_addr = m_section_sp->GetFileAddress();
+ const lldb::addr_t text_addr = LLDB_INVALID_ADDRESS;
+ const lldb::addr_t data_addr = LLDB_INVALID_ADDRESS;
+
+ lldb::addr_t addr = m_cfi_data.GetGNUEHPointer(
+ &offset, cie->ptr_encoding, pc_rel_addr, text_addr, data_addr);
+ if (clear_address_zeroth_bit)
+ addr &= ~1ull;
+
+ lldb::addr_t length = m_cfi_data.GetGNUEHPointer(
+ &offset, cie->ptr_encoding & DW_EH_PE_MASK_ENCODING, pc_rel_addr,
+ text_addr, data_addr);
+ FDEEntryMap::Entry fde(addr, length, current_entry);
+ m_fde_index.Append(fde);
+ } else {
+ Host::SystemLog(Host::eSystemLogError, "error: unable to find CIE at "
+ "0x%8.8x for cie_id = 0x%8.8x for "
+ "entry at 0x%8.8x.\n",
+ cie_offset, cie_id, current_entry);
+ }
+ offset = next_entry;
+ }
+ m_fde_index.Sort();
+ m_fde_index_initialized = true;
+}
+
+bool DWARFCallFrameInfo::FDEToUnwindPlan(dw_offset_t dwarf_offset,
+ Address startaddr,
+ UnwindPlan &unwind_plan) {
+ Log *log = GetLogIfAllCategoriesSet(LIBLLDB_LOG_UNWIND);
+ lldb::offset_t offset = dwarf_offset;
+ lldb::offset_t current_entry = offset;
- case DW_CFA_val_expression : // 0x16
- {
- // takes two operands: an unsigned LEB128 value representing a register
- // number, and a DW_FORM_block value representing a DWARF expression.
- // The required action is to change the rule for the register indicated
- // by the register number to be a val_expression(E) rule where E is the
- // DWARF expression. That is, the DWARF expression computes the value of
- // the given register. The value of the CFA is pushed on the DWARF
- // evaluation stack prior to execution of the DWARF expression.
- uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
- uint32_t block_len = (uint32_t)m_cfi_data.GetULEB128(&offset);
- const uint8_t* block_data = (const uint8_t*)m_cfi_data.GetData(&offset, block_len);
-//#if defined(__i386__) || defined(__x86_64__)
-// // The EH frame info for EIP and RIP contains code that looks for traps to
-// // be a specific type and increments the PC.
-// // For i386:
-// // DW_CFA_val_expression where:
-// // eip = DW_OP_breg6(+28), DW_OP_deref, DW_OP_dup, DW_OP_plus_uconst(0x34),
-// // DW_OP_deref, DW_OP_swap, DW_OP_plus_uconst(0), DW_OP_deref,
-// // DW_OP_dup, DW_OP_lit3, DW_OP_ne, DW_OP_swap, DW_OP_lit4, DW_OP_ne,
-// // DW_OP_and, DW_OP_plus
-// // This basically does a:
-// // eip = ucontenxt.mcontext32->gpr.eip;
-// // if (ucontenxt.mcontext32->exc.trapno != 3 && ucontenxt.mcontext32->exc.trapno != 4)
-// // eip++;
-// //
-// // For x86_64:
-// // DW_CFA_val_expression where:
-// // rip = DW_OP_breg3(+48), DW_OP_deref, DW_OP_dup, DW_OP_plus_uconst(0x90), DW_OP_deref,
-// // DW_OP_swap, DW_OP_plus_uconst(0), DW_OP_deref_size(4), DW_OP_dup, DW_OP_lit3,
-// // DW_OP_ne, DW_OP_swap, DW_OP_lit4, DW_OP_ne, DW_OP_and, DW_OP_plus
-// // This basically does a:
-// // rip = ucontenxt.mcontext64->gpr.rip;
-// // if (ucontenxt.mcontext64->exc.trapno != 3 && ucontenxt.mcontext64->exc.trapno != 4)
-// // rip++;
-// // The trap comparisons and increments are not needed as it hoses up the unwound PC which
-// // is expected to point at least past the instruction that causes the fault/trap. So we
-// // take it out by trimming the expression right at the first "DW_OP_swap" opcodes
-// if (block_data != NULL && thread->GetPCRegNum(Thread::GCC) == reg_num)
-// {
-// if (thread->Is64Bit())
-// {
-// if (block_len > 9 && block_data[8] == DW_OP_swap && block_data[9] == DW_OP_plus_uconst)
-// block_len = 8;
-// }
-// else
-// {
-// if (block_len > 8 && block_data[7] == DW_OP_swap && block_data[8] == DW_OP_plus_uconst)
-// block_len = 7;
-// }
-// }
-//#endif
- reg_location.SetIsDWARFExpression(block_data, block_len);
- row.SetRegisterInfo (reg_num, reg_location);
- return true;
- }
- }
- }
+ if (m_section_sp.get() == nullptr || m_section_sp->IsEncrypted())
return false;
-}
-void
-DWARFCallFrameInfo::ForEachFDEEntries(
- const std::function<bool(lldb::addr_t, uint32_t, dw_offset_t)>& callback)
-{
- GetFDEIndex();
+ if (m_cfi_data_initialized == false)
+ GetCFIData();
- for (size_t i = 0, c = m_fde_index.GetSize(); i < c; ++i)
- {
- const FDEEntryMap::Entry& entry = m_fde_index.GetEntryRef(i);
- if (!callback(entry.base, entry.size, entry.data))
+ uint32_t length = m_cfi_data.GetU32(&offset);
+ dw_offset_t cie_offset;
+ bool is_64bit = (length == UINT32_MAX);
+ if (is_64bit) {
+ length = m_cfi_data.GetU64(&offset);
+ cie_offset = m_cfi_data.GetU64(&offset);
+ } else {
+ cie_offset = m_cfi_data.GetU32(&offset);
+ }
+
+ assert(cie_offset != 0 && cie_offset != UINT32_MAX);
+
+ // Translate the CIE_id from the eh_frame format, which
+ // is relative to the FDE offset, into a __eh_frame section
+ // offset
+ if (m_is_eh_frame) {
+ unwind_plan.SetSourceName("eh_frame CFI");
+ cie_offset = current_entry + (is_64bit ? 12 : 4) - cie_offset;
+ unwind_plan.SetUnwindPlanValidAtAllInstructions(eLazyBoolNo);
+ } else {
+ unwind_plan.SetSourceName("DWARF CFI");
+ // In theory the debug_frame info should be valid at all call sites
+ // ("asynchronous unwind info" as it is sometimes called) but in practice
+ // gcc et al all emit call frame info for the prologue and call sites, but
+ // not for the epilogue or all the other locations during the function
+ // reliably.
+ unwind_plan.SetUnwindPlanValidAtAllInstructions(eLazyBoolNo);
+ }
+ unwind_plan.SetSourcedFromCompiler(eLazyBoolYes);
+
+ const CIE *cie = GetCIE(cie_offset);
+ assert(cie != nullptr);
+
+ const dw_offset_t end_offset = current_entry + length + (is_64bit ? 12 : 4);
+
+ const lldb::addr_t pc_rel_addr = m_section_sp->GetFileAddress();
+ const lldb::addr_t text_addr = LLDB_INVALID_ADDRESS;
+ const lldb::addr_t data_addr = LLDB_INVALID_ADDRESS;
+ lldb::addr_t range_base = m_cfi_data.GetGNUEHPointer(
+ &offset, cie->ptr_encoding, pc_rel_addr, text_addr, data_addr);
+ lldb::addr_t range_len = m_cfi_data.GetGNUEHPointer(
+ &offset, cie->ptr_encoding & DW_EH_PE_MASK_ENCODING, pc_rel_addr,
+ text_addr, data_addr);
+ AddressRange range(range_base, m_objfile.GetAddressByteSize(),
+ m_objfile.GetSectionList());
+ range.SetByteSize(range_len);
+
+ addr_t lsda_data_file_address = LLDB_INVALID_ADDRESS;
+
+ if (cie->augmentation[0] == 'z') {
+ uint32_t aug_data_len = (uint32_t)m_cfi_data.GetULEB128(&offset);
+ if (aug_data_len != 0 && cie->lsda_addr_encoding != DW_EH_PE_omit) {
+ offset_t saved_offset = offset;
+ lsda_data_file_address = m_cfi_data.GetGNUEHPointer(
+ &offset, cie->lsda_addr_encoding, pc_rel_addr, text_addr, data_addr);
+ if (offset - saved_offset != aug_data_len) {
+ // There is more in the augmentation region than we know how to process;
+ // don't read anything.
+ lsda_data_file_address = LLDB_INVALID_ADDRESS;
+ }
+ offset = saved_offset;
+ }
+ offset += aug_data_len;
+ }
+ Address lsda_data;
+ Address personality_function_ptr;
+
+ if (lsda_data_file_address != LLDB_INVALID_ADDRESS &&
+ cie->personality_loc != LLDB_INVALID_ADDRESS) {
+ m_objfile.GetModule()->ResolveFileAddress(lsda_data_file_address,
+ lsda_data);
+ m_objfile.GetModule()->ResolveFileAddress(cie->personality_loc,
+ personality_function_ptr);
+ }
+
+ if (lsda_data.IsValid() && personality_function_ptr.IsValid()) {
+ unwind_plan.SetLSDAAddress(lsda_data);
+ unwind_plan.SetPersonalityFunctionPtr(personality_function_ptr);
+ }
+
+ uint32_t code_align = cie->code_align;
+ int32_t data_align = cie->data_align;
+
+ unwind_plan.SetPlanValidAddressRange(range);
+ UnwindPlan::Row *cie_initial_row = new UnwindPlan::Row;
+ *cie_initial_row = cie->initial_row;
+ UnwindPlan::RowSP row(cie_initial_row);
+
+ unwind_plan.SetRegisterKind(m_reg_kind);
+ unwind_plan.SetReturnAddressRegister(cie->return_addr_reg_num);
+
+ std::vector<UnwindPlan::RowSP> stack;
+
+ UnwindPlan::Row::RegisterLocation reg_location;
+ while (m_cfi_data.ValidOffset(offset) && offset < end_offset) {
+ uint8_t inst = m_cfi_data.GetU8(&offset);
+ uint8_t primary_opcode = inst & 0xC0;
+ uint8_t extended_opcode = inst & 0x3F;
+
+ if (!HandleCommonDwarfOpcode(primary_opcode, extended_opcode, data_align,
+ offset, *row)) {
+ if (primary_opcode) {
+ switch (primary_opcode) {
+ case DW_CFA_advance_loc: // (Row Creation Instruction)
+ { // 0x40 - high 2 bits are 0x1, lower 6 bits are delta
+ // takes a single argument that represents a constant delta. The
+ // required action is to create a new table row with a location
+ // value that is computed by taking the current entry's location
+ // value and adding (delta * code_align). All other
+ // values in the new row are initially identical to the current row.
+ unwind_plan.AppendRow(row);
+ UnwindPlan::Row *newrow = new UnwindPlan::Row;
+ *newrow = *row.get();
+ row.reset(newrow);
+ row->SlideOffset(extended_opcode * code_align);
+ break;
+ }
+
+ case DW_CFA_restore: { // 0xC0 - high 2 bits are 0x3, lower 6 bits are
+ // register
+ // takes a single argument that represents a register number. The
+ // required action is to change the rule for the indicated register
+ // to the rule assigned it by the initial_instructions in the CIE.
+ uint32_t reg_num = extended_opcode;
+ // We only keep enough register locations around to
+ // unwind what is in our thread, and these are organized
+ // by the register index in that state, so we need to convert our
+ // eh_frame register number from the EH frame info, to a register
+ // index
+
+ if (unwind_plan.IsValidRowIndex(0) &&
+ unwind_plan.GetRowAtIndex(0)->GetRegisterInfo(reg_num,
+ reg_location))
+ row->SetRegisterInfo(reg_num, reg_location);
+ break;
+ }
+ }
+ } else {
+ switch (extended_opcode) {
+ case DW_CFA_set_loc: // 0x1 (Row Creation Instruction)
+ {
+ // DW_CFA_set_loc takes a single argument that represents an address.
+ // The required action is to create a new table row using the
+ // specified address as the location. All other values in the new row
+ // are initially identical to the current row. The new location value
+ // should always be greater than the current one.
+ unwind_plan.AppendRow(row);
+ UnwindPlan::Row *newrow = new UnwindPlan::Row;
+ *newrow = *row.get();
+ row.reset(newrow);
+ row->SetOffset(m_cfi_data.GetPointer(&offset) -
+ startaddr.GetFileAddress());
+ break;
+ }
+
+ case DW_CFA_advance_loc1: // 0x2 (Row Creation Instruction)
+ {
+ // takes a single uword argument that represents a constant delta.
+ // This instruction is identical to DW_CFA_advance_loc except for the
+ // encoding and size of the delta argument.
+ unwind_plan.AppendRow(row);
+ UnwindPlan::Row *newrow = new UnwindPlan::Row;
+ *newrow = *row.get();
+ row.reset(newrow);
+ row->SlideOffset(m_cfi_data.GetU8(&offset) * code_align);
+ break;
+ }
+
+ case DW_CFA_advance_loc2: // 0x3 (Row Creation Instruction)
+ {
+ // takes a single uword argument that represents a constant delta.
+ // This instruction is identical to DW_CFA_advance_loc except for the
+ // encoding and size of the delta argument.
+ unwind_plan.AppendRow(row);
+ UnwindPlan::Row *newrow = new UnwindPlan::Row;
+ *newrow = *row.get();
+ row.reset(newrow);
+ row->SlideOffset(m_cfi_data.GetU16(&offset) * code_align);
+ break;
+ }
+
+ case DW_CFA_advance_loc4: // 0x4 (Row Creation Instruction)
+ {
+ // takes a single uword argument that represents a constant delta.
+ // This instruction is identical to DW_CFA_advance_loc except for the
+ // encoding and size of the delta argument.
+ unwind_plan.AppendRow(row);
+ UnwindPlan::Row *newrow = new UnwindPlan::Row;
+ *newrow = *row.get();
+ row.reset(newrow);
+ row->SlideOffset(m_cfi_data.GetU32(&offset) * code_align);
+ break;
+ }
+
+ case DW_CFA_restore_extended: // 0x6
+ {
+ // takes a single unsigned LEB128 argument that represents a register
+ // number. This instruction is identical to DW_CFA_restore except for
+ // the encoding and size of the register argument.
+ uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
+ if (unwind_plan.IsValidRowIndex(0) &&
+ unwind_plan.GetRowAtIndex(0)->GetRegisterInfo(reg_num,
+ reg_location))
+ row->SetRegisterInfo(reg_num, reg_location);
+ break;
+ }
+
+ case DW_CFA_remember_state: // 0xA
+ {
+ // These instructions define a stack of information. Encountering the
+ // DW_CFA_remember_state instruction means to save the rules for every
+ // register on the current row on the stack. Encountering the
+ // DW_CFA_restore_state instruction means to pop the set of rules off
+ // the stack and place them in the current row. (This operation is
+ // useful for compilers that move epilogue code into the body of a
+ // function.)
+ stack.push_back(row);
+ UnwindPlan::Row *newrow = new UnwindPlan::Row;
+ *newrow = *row.get();
+ row.reset(newrow);
+ break;
+ }
+
+ case DW_CFA_restore_state: // 0xB
+ {
+ // These instructions define a stack of information. Encountering the
+ // DW_CFA_remember_state instruction means to save the rules for every
+ // register on the current row on the stack. Encountering the
+ // DW_CFA_restore_state instruction means to pop the set of rules off
+ // the stack and place them in the current row. (This operation is
+ // useful for compilers that move epilogue code into the body of a
+ // function.)
+ if (stack.empty()) {
+ if (log)
+ log->Printf("DWARFCallFrameInfo::%s(dwarf_offset: %" PRIx32
+ ", startaddr: %" PRIx64
+ " encountered DW_CFA_restore_state but state stack "
+ "is empty. Corrupt unwind info?",
+ __FUNCTION__, dwarf_offset,
+ startaddr.GetFileAddress());
break;
- }
+ }
+ lldb::addr_t offset = row->GetOffset();
+ row = stack.back();
+ stack.pop_back();
+ row->SetOffset(offset);
+ break;
+ }
+
+ case DW_CFA_GNU_args_size: // 0x2e
+ {
+ // The DW_CFA_GNU_args_size instruction takes an unsigned LEB128
+ // operand
+ // representing an argument size. This instruction specifies the total
+ // of
+ // the size of the arguments which have been pushed onto the stack.
+
+ // TODO: Figure out how we should handle this.
+ m_cfi_data.GetULEB128(&offset);
+ break;
+ }
+
+ case DW_CFA_val_offset: // 0x14
+ case DW_CFA_val_offset_sf: // 0x15
+ default:
+ break;
+ }
+ }
+ }
+ }
+ unwind_plan.AppendRow(row);
+
+ return true;
+}
+
+bool DWARFCallFrameInfo::HandleCommonDwarfOpcode(uint8_t primary_opcode,
+ uint8_t extended_opcode,
+ int32_t data_align,
+ lldb::offset_t &offset,
+ UnwindPlan::Row &row) {
+ UnwindPlan::Row::RegisterLocation reg_location;
+
+ if (primary_opcode) {
+ switch (primary_opcode) {
+ case DW_CFA_offset: { // 0x80 - high 2 bits are 0x2, lower 6 bits are
+ // register
+ // takes two arguments: an unsigned LEB128 constant representing a
+ // factored offset and a register number. The required action is to
+ // change the rule for the register indicated by the register number
+ // to be an offset(N) rule with a value of
+ // (N = factored offset * data_align).
+ uint8_t reg_num = extended_opcode;
+ int32_t op_offset = (int32_t)m_cfi_data.GetULEB128(&offset) * data_align;
+ reg_location.SetAtCFAPlusOffset(op_offset);
+ row.SetRegisterInfo(reg_num, reg_location);
+ return true;
+ }
+ }
+ } else {
+ switch (extended_opcode) {
+ case DW_CFA_nop: // 0x0
+ return true;
+
+ case DW_CFA_offset_extended: // 0x5
+ {
+ // takes two unsigned LEB128 arguments representing a register number
+ // and a factored offset. This instruction is identical to DW_CFA_offset
+ // except for the encoding and size of the register argument.
+ uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
+ int32_t op_offset = (int32_t)m_cfi_data.GetULEB128(&offset) * data_align;
+ UnwindPlan::Row::RegisterLocation reg_location;
+ reg_location.SetAtCFAPlusOffset(op_offset);
+ row.SetRegisterInfo(reg_num, reg_location);
+ return true;
+ }
+
+ case DW_CFA_undefined: // 0x7
+ {
+ // takes a single unsigned LEB128 argument that represents a register
+ // number. The required action is to set the rule for the specified
+ // register to undefined.
+ uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
+ UnwindPlan::Row::RegisterLocation reg_location;
+ reg_location.SetUndefined();
+ row.SetRegisterInfo(reg_num, reg_location);
+ return true;
+ }
+
+ case DW_CFA_same_value: // 0x8
+ {
+ // takes a single unsigned LEB128 argument that represents a register
+ // number. The required action is to set the rule for the specified
+ // register to same value.
+ uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
+ UnwindPlan::Row::RegisterLocation reg_location;
+ reg_location.SetSame();
+ row.SetRegisterInfo(reg_num, reg_location);
+ return true;
+ }
+
+ case DW_CFA_register: // 0x9
+ {
+ // takes two unsigned LEB128 arguments representing register numbers.
+ // The required action is to set the rule for the first register to be
+ // the second register.
+ uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
+ uint32_t other_reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
+ UnwindPlan::Row::RegisterLocation reg_location;
+ reg_location.SetInRegister(other_reg_num);
+ row.SetRegisterInfo(reg_num, reg_location);
+ return true;
+ }
+
+ case DW_CFA_def_cfa: // 0xC (CFA Definition Instruction)
+ {
+ // Takes two unsigned LEB128 operands representing a register
+ // number and a (non-factored) offset. The required action
+ // is to define the current CFA rule to use the provided
+ // register and offset.
+ uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
+ int32_t op_offset = (int32_t)m_cfi_data.GetULEB128(&offset);
+ row.GetCFAValue().SetIsRegisterPlusOffset(reg_num, op_offset);
+ return true;
+ }
+
+ case DW_CFA_def_cfa_register: // 0xD (CFA Definition Instruction)
+ {
+ // takes a single unsigned LEB128 argument representing a register
+ // number. The required action is to define the current CFA rule to
+ // use the provided register (but to keep the old offset).
+ uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
+ row.GetCFAValue().SetIsRegisterPlusOffset(reg_num,
+ row.GetCFAValue().GetOffset());
+ return true;
+ }
+
+ case DW_CFA_def_cfa_offset: // 0xE (CFA Definition Instruction)
+ {
+ // Takes a single unsigned LEB128 operand representing a
+ // (non-factored) offset. The required action is to define
+ // the current CFA rule to use the provided offset (but
+ // to keep the old register).
+ int32_t op_offset = (int32_t)m_cfi_data.GetULEB128(&offset);
+ row.GetCFAValue().SetIsRegisterPlusOffset(
+ row.GetCFAValue().GetRegisterNumber(), op_offset);
+ return true;
+ }
+
+ case DW_CFA_def_cfa_expression: // 0xF (CFA Definition Instruction)
+ {
+ size_t block_len = (size_t)m_cfi_data.GetULEB128(&offset);
+ const uint8_t *block_data =
+ static_cast<const uint8_t *>(m_cfi_data.GetData(&offset, block_len));
+ row.GetCFAValue().SetIsDWARFExpression(block_data, block_len);
+ return true;
+ }
+
+ case DW_CFA_expression: // 0x10
+ {
+ // Takes two operands: an unsigned LEB128 value representing
+ // a register number, and a DW_FORM_block value representing a DWARF
+ // expression. The required action is to change the rule for the
+ // register indicated by the register number to be an expression(E)
+ // rule where E is the DWARF expression. That is, the DWARF
+ // expression computes the address. The value of the CFA is
+ // pushed on the DWARF evaluation stack prior to execution of
+ // the DWARF expression.
+ uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
+ uint32_t block_len = (uint32_t)m_cfi_data.GetULEB128(&offset);
+ const uint8_t *block_data =
+ static_cast<const uint8_t *>(m_cfi_data.GetData(&offset, block_len));
+ UnwindPlan::Row::RegisterLocation reg_location;
+ reg_location.SetAtDWARFExpression(block_data, block_len);
+ row.SetRegisterInfo(reg_num, reg_location);
+ return true;
+ }
+
+ case DW_CFA_offset_extended_sf: // 0x11
+ {
+ // takes two operands: an unsigned LEB128 value representing a
+ // register number and a signed LEB128 factored offset. This
+ // instruction is identical to DW_CFA_offset_extended except
+ // that the second operand is signed and factored.
+ uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
+ int32_t op_offset = (int32_t)m_cfi_data.GetSLEB128(&offset) * data_align;
+ UnwindPlan::Row::RegisterLocation reg_location;
+ reg_location.SetAtCFAPlusOffset(op_offset);
+ row.SetRegisterInfo(reg_num, reg_location);
+ return true;
+ }
+
+ case DW_CFA_def_cfa_sf: // 0x12 (CFA Definition Instruction)
+ {
+ // Takes two operands: an unsigned LEB128 value representing
+ // a register number and a signed LEB128 factored offset.
+ // This instruction is identical to DW_CFA_def_cfa except
+ // that the second operand is signed and factored.
+ uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
+ int32_t op_offset = (int32_t)m_cfi_data.GetSLEB128(&offset) * data_align;
+ row.GetCFAValue().SetIsRegisterPlusOffset(reg_num, op_offset);
+ return true;
+ }
+
+ case DW_CFA_def_cfa_offset_sf: // 0x13 (CFA Definition Instruction)
+ {
+ // takes a signed LEB128 operand representing a factored
+ // offset. This instruction is identical to DW_CFA_def_cfa_offset
+ // except that the operand is signed and factored.
+ int32_t op_offset = (int32_t)m_cfi_data.GetSLEB128(&offset) * data_align;
+ uint32_t cfa_regnum = row.GetCFAValue().GetRegisterNumber();
+ row.GetCFAValue().SetIsRegisterPlusOffset(cfa_regnum, op_offset);
+ return true;
+ }
+
+ case DW_CFA_val_expression: // 0x16
+ {
+ // takes two operands: an unsigned LEB128 value representing a register
+ // number, and a DW_FORM_block value representing a DWARF expression.
+ // The required action is to change the rule for the register indicated
+ // by the register number to be a val_expression(E) rule where E is the
+ // DWARF expression. That is, the DWARF expression computes the value of
+ // the given register. The value of the CFA is pushed on the DWARF
+ // evaluation stack prior to execution of the DWARF expression.
+ uint32_t reg_num = (uint32_t)m_cfi_data.GetULEB128(&offset);
+ uint32_t block_len = (uint32_t)m_cfi_data.GetULEB128(&offset);
+ const uint8_t *block_data =
+ (const uint8_t *)m_cfi_data.GetData(&offset, block_len);
+ //#if defined(__i386__) || defined(__x86_64__)
+ // // The EH frame info for EIP and RIP contains code that
+ // looks for traps to
+ // // be a specific type and increments the PC.
+ // // For i386:
+ // // DW_CFA_val_expression where:
+ // // eip = DW_OP_breg6(+28), DW_OP_deref, DW_OP_dup,
+ // DW_OP_plus_uconst(0x34),
+ // // DW_OP_deref, DW_OP_swap, DW_OP_plus_uconst(0),
+ // DW_OP_deref,
+ // // DW_OP_dup, DW_OP_lit3, DW_OP_ne, DW_OP_swap,
+ // DW_OP_lit4, DW_OP_ne,
+ // // DW_OP_and, DW_OP_plus
+ // // This basically does a:
+ // // eip = ucontenxt.mcontext32->gpr.eip;
+ // // if (ucontenxt.mcontext32->exc.trapno != 3 &&
+ // ucontenxt.mcontext32->exc.trapno != 4)
+ // // eip++;
+ // //
+ // // For x86_64:
+ // // DW_CFA_val_expression where:
+ // // rip = DW_OP_breg3(+48), DW_OP_deref, DW_OP_dup,
+ // DW_OP_plus_uconst(0x90), DW_OP_deref,
+ // // DW_OP_swap, DW_OP_plus_uconst(0),
+ // DW_OP_deref_size(4), DW_OP_dup, DW_OP_lit3,
+ // // DW_OP_ne, DW_OP_swap, DW_OP_lit4, DW_OP_ne,
+ // DW_OP_and, DW_OP_plus
+ // // This basically does a:
+ // // rip = ucontenxt.mcontext64->gpr.rip;
+ // // if (ucontenxt.mcontext64->exc.trapno != 3 &&
+ // ucontenxt.mcontext64->exc.trapno != 4)
+ // // rip++;
+ // // The trap comparisons and increments are not needed as
+ // it hoses up the unwound PC which
+ // // is expected to point at least past the instruction that
+ // causes the fault/trap. So we
+ // // take it out by trimming the expression right at the
+ // first "DW_OP_swap" opcodes
+ // if (block_data != NULL && thread->GetPCRegNum(Thread::GCC)
+ // == reg_num)
+ // {
+ // if (thread->Is64Bit())
+ // {
+ // if (block_len > 9 && block_data[8] == DW_OP_swap
+ // && block_data[9] == DW_OP_plus_uconst)
+ // block_len = 8;
+ // }
+ // else
+ // {
+ // if (block_len > 8 && block_data[7] == DW_OP_swap
+ // && block_data[8] == DW_OP_plus_uconst)
+ // block_len = 7;
+ // }
+ // }
+ //#endif
+ reg_location.SetIsDWARFExpression(block_data, block_len);
+ row.SetRegisterInfo(reg_num, reg_location);
+ return true;
+ }
+ }
+ }
+ return false;
+}
+
+void DWARFCallFrameInfo::ForEachFDEEntries(
+ const std::function<bool(lldb::addr_t, uint32_t, dw_offset_t)> &callback) {
+ GetFDEIndex();
+
+ for (size_t i = 0, c = m_fde_index.GetSize(); i < c; ++i) {
+ const FDEEntryMap::Entry &entry = m_fde_index.GetEntryRef(i);
+ if (!callback(entry.base, entry.size, entry.data))
+ break;
+ }
}
Modified: lldb/trunk/source/Symbol/DebugMacros.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/DebugMacros.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/DebugMacros.cpp (original)
+++ lldb/trunk/source/Symbol/DebugMacros.cpp Tue Sep 6 15:57:50 2016
@@ -13,53 +13,42 @@
using namespace lldb_private;
-DebugMacroEntry::DebugMacroEntry(EntryType type,
- uint32_t line,
- uint32_t debug_line_file_idx,
- const char *str)
- : m_type(type),
- m_line(line),
- m_debug_line_file_idx(debug_line_file_idx),
- m_str(str)
-{ }
+DebugMacroEntry::DebugMacroEntry(EntryType type, uint32_t line,
+ uint32_t debug_line_file_idx, const char *str)
+ : m_type(type), m_line(line), m_debug_line_file_idx(debug_line_file_idx),
+ m_str(str) {}
DebugMacroEntry::DebugMacroEntry(EntryType type,
const DebugMacrosSP &debug_macros_sp)
- : m_type(type), m_line(0), m_debug_line_file_idx(0), m_debug_macros_sp(debug_macros_sp)
-{ }
+ : m_type(type), m_line(0), m_debug_line_file_idx(0),
+ m_debug_macros_sp(debug_macros_sp) {}
-const FileSpec&
-DebugMacroEntry::GetFileSpec(CompileUnit *comp_unit) const
-{
- return comp_unit->GetSupportFiles().GetFileSpecAtIndex(m_debug_line_file_idx);
+const FileSpec &DebugMacroEntry::GetFileSpec(CompileUnit *comp_unit) const {
+ return comp_unit->GetSupportFiles().GetFileSpecAtIndex(m_debug_line_file_idx);
}
-DebugMacroEntry
-DebugMacroEntry::CreateDefineEntry(uint32_t line, const char *str)
-{
- return DebugMacroEntry(DebugMacroEntry::DEFINE, line, 0, str);
+DebugMacroEntry DebugMacroEntry::CreateDefineEntry(uint32_t line,
+ const char *str) {
+ return DebugMacroEntry(DebugMacroEntry::DEFINE, line, 0, str);
}
-DebugMacroEntry
-DebugMacroEntry::CreateUndefEntry(uint32_t line, const char *str)
-{
- return DebugMacroEntry(DebugMacroEntry::UNDEF, line, 0, str);
+DebugMacroEntry DebugMacroEntry::CreateUndefEntry(uint32_t line,
+ const char *str) {
+ return DebugMacroEntry(DebugMacroEntry::UNDEF, line, 0, str);
}
DebugMacroEntry
-DebugMacroEntry::CreateStartFileEntry(uint32_t line, uint32_t debug_line_file_idx)
-{
- return DebugMacroEntry(DebugMacroEntry::START_FILE, line, debug_line_file_idx, nullptr);
+DebugMacroEntry::CreateStartFileEntry(uint32_t line,
+ uint32_t debug_line_file_idx) {
+ return DebugMacroEntry(DebugMacroEntry::START_FILE, line, debug_line_file_idx,
+ nullptr);
}
-DebugMacroEntry
-DebugMacroEntry::CreateEndFileEntry()
-{
- return DebugMacroEntry(DebugMacroEntry::END_FILE, 0, 0, nullptr);
+DebugMacroEntry DebugMacroEntry::CreateEndFileEntry() {
+ return DebugMacroEntry(DebugMacroEntry::END_FILE, 0, 0, nullptr);
}
DebugMacroEntry
-DebugMacroEntry::CreateIndirectEntry(const DebugMacrosSP &debug_macros_sp)
-{
- return DebugMacroEntry(DebugMacroEntry::INDIRECT, debug_macros_sp);
+DebugMacroEntry::CreateIndirectEntry(const DebugMacrosSP &debug_macros_sp) {
+ return DebugMacroEntry(DebugMacroEntry::INDIRECT, debug_macros_sp);
}
Modified: lldb/trunk/source/Symbol/Declaration.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/Declaration.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/Declaration.cpp (original)
+++ lldb/trunk/source/Symbol/Declaration.cpp Tue Sep 6 15:57:50 2016
@@ -12,106 +12,86 @@
using namespace lldb_private;
-void
-Declaration::Dump(Stream *s, bool show_fullpaths) const
-{
- if (m_file)
- {
- *s << ", decl = ";
- if (show_fullpaths)
- *s << m_file;
- else
- *s << m_file.GetFilename();
- if (m_line > 0)
- s->Printf(":%u", m_line);
-#ifdef LLDB_ENABLE_DECLARATION_COLUMNS
- if (m_column > 0)
- s->Printf(":%u", m_column);
-#endif
- }
+void Declaration::Dump(Stream *s, bool show_fullpaths) const {
+ if (m_file) {
+ *s << ", decl = ";
+ if (show_fullpaths)
+ *s << m_file;
else
- {
- if (m_line > 0)
- {
- s->Printf(", line = %u", m_line);
+ *s << m_file.GetFilename();
+ if (m_line > 0)
+ s->Printf(":%u", m_line);
+#ifdef LLDB_ENABLE_DECLARATION_COLUMNS
+ if (m_column > 0)
+ s->Printf(":%u", m_column);
+#endif
+ } else {
+ if (m_line > 0) {
+ s->Printf(", line = %u", m_line);
#ifdef LLDB_ENABLE_DECLARATION_COLUMNS
- if (m_column > 0)
- s->Printf(":%u", m_column);
+ if (m_column > 0)
+ s->Printf(":%u", m_column);
#endif
- }
+ }
#ifdef LLDB_ENABLE_DECLARATION_COLUMNS
- else if (m_column > 0)
- s->Printf(", column = %u", m_column);
+ else if (m_column > 0)
+ s->Printf(", column = %u", m_column);
#endif
- }
+ }
}
-bool
-Declaration::DumpStopContext (Stream *s, bool show_fullpaths) const
-{
- if (m_file)
- {
- if (show_fullpaths || s->GetVerbose())
- *s << m_file;
- else
- m_file.GetFilename().Dump(s);
+bool Declaration::DumpStopContext(Stream *s, bool show_fullpaths) const {
+ if (m_file) {
+ if (show_fullpaths || s->GetVerbose())
+ *s << m_file;
+ else
+ m_file.GetFilename().Dump(s);
- if (m_line > 0)
- s->Printf(":%u", m_line);
+ if (m_line > 0)
+ s->Printf(":%u", m_line);
#ifdef LLDB_ENABLE_DECLARATION_COLUMNS
- if (m_column > 0)
- s->Printf(":%u", m_column);
+ if (m_column > 0)
+ s->Printf(":%u", m_column);
#endif
- return true;
- }
- else if (m_line > 0)
- {
- s->Printf(" line %u", m_line);
+ return true;
+ } else if (m_line > 0) {
+ s->Printf(" line %u", m_line);
#ifdef LLDB_ENABLE_DECLARATION_COLUMNS
- if (m_column > 0)
- s->Printf(":%u", m_column);
+ if (m_column > 0)
+ s->Printf(":%u", m_column);
#endif
- return true;
- }
- return false;
+ return true;
+ }
+ return false;
}
-size_t
-Declaration::MemorySize() const
-{
- return sizeof(Declaration);
-}
+size_t Declaration::MemorySize() const { return sizeof(Declaration); }
-int
-Declaration::Compare(const Declaration& a, const Declaration& b)
-{
- int result = FileSpec::Compare(a.m_file, b.m_file, true);
- if (result)
- return result;
- if (a.m_line < b.m_line)
- return -1;
- else if (a.m_line > b.m_line)
- return 1;
-#ifdef LLDB_ENABLE_DECLARATION_COLUMNS
- if (a.m_column < b.m_column)
- return -1;
- else if (a.m_column > b.m_column)
- return 1;
+int Declaration::Compare(const Declaration &a, const Declaration &b) {
+ int result = FileSpec::Compare(a.m_file, b.m_file, true);
+ if (result)
+ return result;
+ if (a.m_line < b.m_line)
+ return -1;
+ else if (a.m_line > b.m_line)
+ return 1;
+#ifdef LLDB_ENABLE_DECLARATION_COLUMNS
+ if (a.m_column < b.m_column)
+ return -1;
+ else if (a.m_column > b.m_column)
+ return 1;
#endif
- return 0;
+ return 0;
}
-bool
-lldb_private::operator == (const Declaration &lhs, const Declaration &rhs)
-{
-#ifdef LLDB_ENABLE_DECLARATION_COLUMNS
- if (lhs.GetColumn () == rhs.GetColumn ())
- if (lhs.GetLine () == rhs.GetLine ())
- return lhs.GetFile() == rhs.GetFile();
+bool lldb_private::operator==(const Declaration &lhs, const Declaration &rhs) {
+#ifdef LLDB_ENABLE_DECLARATION_COLUMNS
+ if (lhs.GetColumn() == rhs.GetColumn())
+ if (lhs.GetLine() == rhs.GetLine())
+ return lhs.GetFile() == rhs.GetFile();
#else
- if (lhs.GetLine () == rhs.GetLine ())
- return FileSpec::Equal(lhs.GetFile(),rhs.GetFile(), true, true);
+ if (lhs.GetLine() == rhs.GetLine())
+ return FileSpec::Equal(lhs.GetFile(), rhs.GetFile(), true, true);
#endif
- return false;
+ return false;
}
-
Modified: lldb/trunk/source/Symbol/FuncUnwinders.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/FuncUnwinders.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/FuncUnwinders.cpp (original)
+++ lldb/trunk/source/Symbol/FuncUnwinders.cpp Tue Sep 6 15:57:50 2016
@@ -7,20 +7,20 @@
//
//===----------------------------------------------------------------------===//
-#include "lldb/Core/AddressRange.h"
-#include "lldb/Core/Address.h"
#include "lldb/Symbol/FuncUnwinders.h"
+#include "lldb/Core/Address.h"
+#include "lldb/Core/AddressRange.h"
#include "lldb/Symbol/ArmUnwindInfo.h"
-#include "lldb/Symbol/DWARFCallFrameInfo.h"
#include "lldb/Symbol/CompactUnwindInfo.h"
+#include "lldb/Symbol/DWARFCallFrameInfo.h"
#include "lldb/Symbol/ObjectFile.h"
#include "lldb/Symbol/UnwindPlan.h"
#include "lldb/Symbol/UnwindTable.h"
#include "lldb/Target/ABI.h"
#include "lldb/Target/ExecutionContext.h"
#include "lldb/Target/Process.h"
-#include "lldb/Target/Thread.h"
#include "lldb/Target/Target.h"
+#include "lldb/Target/Thread.h"
#include "lldb/Target/UnwindAssembly.h"
#include "lldb/Utility/RegisterNumber.h"
@@ -32,421 +32,390 @@ using namespace lldb_private;
//------------------------------------------------
FuncUnwinders::FuncUnwinders(UnwindTable &unwind_table, AddressRange range)
- : m_unwind_table(unwind_table),
- m_range(range),
- m_mutex(),
- m_unwind_plan_assembly_sp(),
- m_unwind_plan_eh_frame_sp(),
- m_unwind_plan_eh_frame_augmented_sp(),
- m_unwind_plan_compact_unwind(),
- m_unwind_plan_arm_unwind_sp(),
- m_unwind_plan_fast_sp(),
+ : m_unwind_table(unwind_table), m_range(range), m_mutex(),
+ m_unwind_plan_assembly_sp(), m_unwind_plan_eh_frame_sp(),
+ m_unwind_plan_eh_frame_augmented_sp(), m_unwind_plan_compact_unwind(),
+ m_unwind_plan_arm_unwind_sp(), m_unwind_plan_fast_sp(),
m_unwind_plan_arch_default_sp(),
m_unwind_plan_arch_default_at_func_entry_sp(),
- m_tried_unwind_plan_assembly(false),
- m_tried_unwind_plan_eh_frame(false),
+ m_tried_unwind_plan_assembly(false), m_tried_unwind_plan_eh_frame(false),
m_tried_unwind_plan_eh_frame_augmented(false),
m_tried_unwind_plan_compact_unwind(false),
- m_tried_unwind_plan_arm_unwind(false),
- m_tried_unwind_fast(false),
+ m_tried_unwind_plan_arm_unwind(false), m_tried_unwind_fast(false),
m_tried_unwind_arch_default(false),
m_tried_unwind_arch_default_at_func_entry(false),
- m_first_non_prologue_insn()
-{
-}
+ m_first_non_prologue_insn() {}
//------------------------------------------------
/// destructor
//------------------------------------------------
-FuncUnwinders::~FuncUnwinders ()
-{
-}
+FuncUnwinders::~FuncUnwinders() {}
-UnwindPlanSP
-FuncUnwinders::GetUnwindPlanAtCallSite (Target &target, int current_offset)
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- UnwindPlanSP unwind_plan_sp = GetEHFrameUnwindPlan (target, current_offset);
- if (unwind_plan_sp)
- return unwind_plan_sp;
-
- unwind_plan_sp = GetCompactUnwindUnwindPlan (target, current_offset);
- if (unwind_plan_sp)
- return unwind_plan_sp;
-
- unwind_plan_sp = GetArmUnwindUnwindPlan (target, current_offset);
- if (unwind_plan_sp)
- return unwind_plan_sp;
+UnwindPlanSP FuncUnwinders::GetUnwindPlanAtCallSite(Target &target,
+ int current_offset) {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ UnwindPlanSP unwind_plan_sp = GetEHFrameUnwindPlan(target, current_offset);
+ if (unwind_plan_sp)
+ return unwind_plan_sp;
+
+ unwind_plan_sp = GetCompactUnwindUnwindPlan(target, current_offset);
+ if (unwind_plan_sp)
+ return unwind_plan_sp;
- return nullptr;
+ unwind_plan_sp = GetArmUnwindUnwindPlan(target, current_offset);
+ if (unwind_plan_sp)
+ return unwind_plan_sp;
+
+ return nullptr;
}
-UnwindPlanSP
-FuncUnwinders::GetCompactUnwindUnwindPlan (Target &target, int current_offset)
-{
- if (m_unwind_plan_compact_unwind.size() > 0)
- return m_unwind_plan_compact_unwind[0]; // FIXME support multiple compact unwind plans for one func
- if (m_tried_unwind_plan_compact_unwind)
- return UnwindPlanSP();
-
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
- m_tried_unwind_plan_compact_unwind = true;
- if (m_range.GetBaseAddress().IsValid())
- {
- Address current_pc (m_range.GetBaseAddress ());
- if (current_offset != -1)
- current_pc.SetOffset (current_pc.GetOffset() + current_offset);
- CompactUnwindInfo *compact_unwind = m_unwind_table.GetCompactUnwindInfo();
- if (compact_unwind)
- {
- UnwindPlanSP unwind_plan_sp (new UnwindPlan (lldb::eRegisterKindGeneric));
- if (compact_unwind->GetUnwindPlan (target, current_pc, *unwind_plan_sp))
- {
- m_unwind_plan_compact_unwind.push_back (unwind_plan_sp);
- return m_unwind_plan_compact_unwind[0]; // FIXME support multiple compact unwind plans for one func
- }
- }
- }
+UnwindPlanSP FuncUnwinders::GetCompactUnwindUnwindPlan(Target &target,
+ int current_offset) {
+ if (m_unwind_plan_compact_unwind.size() > 0)
+ return m_unwind_plan_compact_unwind[0]; // FIXME support multiple compact
+ // unwind plans for one func
+ if (m_tried_unwind_plan_compact_unwind)
return UnwindPlanSP();
-}
-UnwindPlanSP
-FuncUnwinders::GetEHFrameUnwindPlan (Target &target, int current_offset)
-{
- if (m_unwind_plan_eh_frame_sp.get() || m_tried_unwind_plan_eh_frame)
- return m_unwind_plan_eh_frame_sp;
-
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
- m_tried_unwind_plan_eh_frame = true;
- if (m_range.GetBaseAddress().IsValid())
- {
- Address current_pc (m_range.GetBaseAddress ());
- if (current_offset != -1)
- current_pc.SetOffset (current_pc.GetOffset() + current_offset);
- DWARFCallFrameInfo *eh_frame = m_unwind_table.GetEHFrameInfo();
- if (eh_frame)
- {
- m_unwind_plan_eh_frame_sp.reset (new UnwindPlan (lldb::eRegisterKindGeneric));
- if (!eh_frame->GetUnwindPlan (current_pc, *m_unwind_plan_eh_frame_sp))
- m_unwind_plan_eh_frame_sp.reset();
- }
- }
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+ m_tried_unwind_plan_compact_unwind = true;
+ if (m_range.GetBaseAddress().IsValid()) {
+ Address current_pc(m_range.GetBaseAddress());
+ if (current_offset != -1)
+ current_pc.SetOffset(current_pc.GetOffset() + current_offset);
+ CompactUnwindInfo *compact_unwind = m_unwind_table.GetCompactUnwindInfo();
+ if (compact_unwind) {
+ UnwindPlanSP unwind_plan_sp(new UnwindPlan(lldb::eRegisterKindGeneric));
+ if (compact_unwind->GetUnwindPlan(target, current_pc, *unwind_plan_sp)) {
+ m_unwind_plan_compact_unwind.push_back(unwind_plan_sp);
+ return m_unwind_plan_compact_unwind[0]; // FIXME support multiple
+ // compact unwind plans for one
+ // func
+ }
+ }
+ }
+ return UnwindPlanSP();
+}
+
+UnwindPlanSP FuncUnwinders::GetEHFrameUnwindPlan(Target &target,
+ int current_offset) {
+ if (m_unwind_plan_eh_frame_sp.get() || m_tried_unwind_plan_eh_frame)
return m_unwind_plan_eh_frame_sp;
-}
-UnwindPlanSP
-FuncUnwinders::GetArmUnwindUnwindPlan (Target &target, int current_offset)
-{
- if (m_unwind_plan_arm_unwind_sp.get() || m_tried_unwind_plan_arm_unwind)
- return m_unwind_plan_arm_unwind_sp;
-
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
- m_tried_unwind_plan_arm_unwind = true;
- if (m_range.GetBaseAddress().IsValid())
- {
- Address current_pc (m_range.GetBaseAddress ());
- if (current_offset != -1)
- current_pc.SetOffset (current_pc.GetOffset() + current_offset);
- ArmUnwindInfo *arm_unwind_info = m_unwind_table.GetArmUnwindInfo();
- if (arm_unwind_info)
- {
- m_unwind_plan_arm_unwind_sp.reset (new UnwindPlan (lldb::eRegisterKindGeneric));
- if (!arm_unwind_info->GetUnwindPlan (target, current_pc, *m_unwind_plan_arm_unwind_sp))
- m_unwind_plan_arm_unwind_sp.reset();
- }
- }
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+ m_tried_unwind_plan_eh_frame = true;
+ if (m_range.GetBaseAddress().IsValid()) {
+ Address current_pc(m_range.GetBaseAddress());
+ if (current_offset != -1)
+ current_pc.SetOffset(current_pc.GetOffset() + current_offset);
+ DWARFCallFrameInfo *eh_frame = m_unwind_table.GetEHFrameInfo();
+ if (eh_frame) {
+ m_unwind_plan_eh_frame_sp.reset(
+ new UnwindPlan(lldb::eRegisterKindGeneric));
+ if (!eh_frame->GetUnwindPlan(current_pc, *m_unwind_plan_eh_frame_sp))
+ m_unwind_plan_eh_frame_sp.reset();
+ }
+ }
+ return m_unwind_plan_eh_frame_sp;
+}
+
+UnwindPlanSP FuncUnwinders::GetArmUnwindUnwindPlan(Target &target,
+ int current_offset) {
+ if (m_unwind_plan_arm_unwind_sp.get() || m_tried_unwind_plan_arm_unwind)
return m_unwind_plan_arm_unwind_sp;
-}
-UnwindPlanSP
-FuncUnwinders::GetEHFrameAugmentedUnwindPlan (Target &target, Thread &thread, int current_offset)
-{
- if (m_unwind_plan_eh_frame_augmented_sp.get() || m_tried_unwind_plan_eh_frame_augmented)
- return m_unwind_plan_eh_frame_augmented_sp;
-
- // Only supported on x86 architectures where we get eh_frame from the compiler that describes
- // the prologue instructions perfectly, and sometimes the epilogue instructions too.
- if (target.GetArchitecture().GetCore() != ArchSpec::eCore_x86_32_i386
- && target.GetArchitecture().GetCore() != ArchSpec::eCore_x86_64_x86_64
- && target.GetArchitecture().GetCore() != ArchSpec::eCore_x86_64_x86_64h)
- {
- m_tried_unwind_plan_eh_frame_augmented = true;
- return m_unwind_plan_eh_frame_augmented_sp;
- }
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+ m_tried_unwind_plan_arm_unwind = true;
+ if (m_range.GetBaseAddress().IsValid()) {
+ Address current_pc(m_range.GetBaseAddress());
+ if (current_offset != -1)
+ current_pc.SetOffset(current_pc.GetOffset() + current_offset);
+ ArmUnwindInfo *arm_unwind_info = m_unwind_table.GetArmUnwindInfo();
+ if (arm_unwind_info) {
+ m_unwind_plan_arm_unwind_sp.reset(
+ new UnwindPlan(lldb::eRegisterKindGeneric));
+ if (!arm_unwind_info->GetUnwindPlan(target, current_pc,
+ *m_unwind_plan_arm_unwind_sp))
+ m_unwind_plan_arm_unwind_sp.reset();
+ }
+ }
+ return m_unwind_plan_arm_unwind_sp;
+}
+
+UnwindPlanSP FuncUnwinders::GetEHFrameAugmentedUnwindPlan(Target &target,
+ Thread &thread,
+ int current_offset) {
+ if (m_unwind_plan_eh_frame_augmented_sp.get() ||
+ m_tried_unwind_plan_eh_frame_augmented)
+ return m_unwind_plan_eh_frame_augmented_sp;
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
+ // Only supported on x86 architectures where we get eh_frame from the compiler
+ // that describes
+ // the prologue instructions perfectly, and sometimes the epilogue
+ // instructions too.
+ if (target.GetArchitecture().GetCore() != ArchSpec::eCore_x86_32_i386 &&
+ target.GetArchitecture().GetCore() != ArchSpec::eCore_x86_64_x86_64 &&
+ target.GetArchitecture().GetCore() != ArchSpec::eCore_x86_64_x86_64h) {
m_tried_unwind_plan_eh_frame_augmented = true;
+ return m_unwind_plan_eh_frame_augmented_sp;
+ }
- UnwindPlanSP eh_frame_plan = GetEHFrameUnwindPlan (target, current_offset);
- if (!eh_frame_plan)
- return m_unwind_plan_eh_frame_augmented_sp;
-
- m_unwind_plan_eh_frame_augmented_sp.reset(new UnwindPlan(*eh_frame_plan));
-
- // Augment the eh_frame instructions with epilogue descriptions if necessary so the
- // UnwindPlan can be used at any instruction in the function.
-
- UnwindAssemblySP assembly_profiler_sp (GetUnwindAssemblyProfiler(target));
- if (assembly_profiler_sp)
- {
- if (!assembly_profiler_sp->AugmentUnwindPlanFromCallSite (m_range, thread, *m_unwind_plan_eh_frame_augmented_sp))
- {
- m_unwind_plan_eh_frame_augmented_sp.reset();
- }
- }
- else
- {
- m_unwind_plan_eh_frame_augmented_sp.reset();
- }
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+ m_tried_unwind_plan_eh_frame_augmented = true;
+
+ UnwindPlanSP eh_frame_plan = GetEHFrameUnwindPlan(target, current_offset);
+ if (!eh_frame_plan)
return m_unwind_plan_eh_frame_augmented_sp;
-}
+ m_unwind_plan_eh_frame_augmented_sp.reset(new UnwindPlan(*eh_frame_plan));
-UnwindPlanSP
-FuncUnwinders::GetAssemblyUnwindPlan (Target &target, Thread &thread, int current_offset)
-{
- if (m_unwind_plan_assembly_sp.get()
- || m_tried_unwind_plan_assembly
- || m_unwind_table.GetAllowAssemblyEmulationUnwindPlans () == false)
- {
- return m_unwind_plan_assembly_sp;
- }
+ // Augment the eh_frame instructions with epilogue descriptions if necessary
+ // so the
+ // UnwindPlan can be used at any instruction in the function.
+
+ UnwindAssemblySP assembly_profiler_sp(GetUnwindAssemblyProfiler(target));
+ if (assembly_profiler_sp) {
+ if (!assembly_profiler_sp->AugmentUnwindPlanFromCallSite(
+ m_range, thread, *m_unwind_plan_eh_frame_augmented_sp)) {
+ m_unwind_plan_eh_frame_augmented_sp.reset();
+ }
+ } else {
+ m_unwind_plan_eh_frame_augmented_sp.reset();
+ }
+ return m_unwind_plan_eh_frame_augmented_sp;
+}
+
+UnwindPlanSP FuncUnwinders::GetAssemblyUnwindPlan(Target &target,
+ Thread &thread,
+ int current_offset) {
+ if (m_unwind_plan_assembly_sp.get() || m_tried_unwind_plan_assembly ||
+ m_unwind_table.GetAllowAssemblyEmulationUnwindPlans() == false) {
+ return m_unwind_plan_assembly_sp;
+ }
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
- m_tried_unwind_plan_assembly = true;
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+ m_tried_unwind_plan_assembly = true;
- UnwindAssemblySP assembly_profiler_sp (GetUnwindAssemblyProfiler(target));
- if (assembly_profiler_sp)
- {
- m_unwind_plan_assembly_sp.reset (new UnwindPlan (lldb::eRegisterKindGeneric));
- if (!assembly_profiler_sp->GetNonCallSiteUnwindPlanFromAssembly (m_range, thread, *m_unwind_plan_assembly_sp))
- {
- m_unwind_plan_assembly_sp.reset();
- }
+ UnwindAssemblySP assembly_profiler_sp(GetUnwindAssemblyProfiler(target));
+ if (assembly_profiler_sp) {
+ m_unwind_plan_assembly_sp.reset(new UnwindPlan(lldb::eRegisterKindGeneric));
+ if (!assembly_profiler_sp->GetNonCallSiteUnwindPlanFromAssembly(
+ m_range, thread, *m_unwind_plan_assembly_sp)) {
+ m_unwind_plan_assembly_sp.reset();
}
- return m_unwind_plan_assembly_sp;
+ }
+ return m_unwind_plan_assembly_sp;
}
// This method compares the pc unwind rule in the first row of two UnwindPlans.
-// If they have the same way of getting the pc value (e.g. "CFA - 8" + "CFA is sp"),
+// If they have the same way of getting the pc value (e.g. "CFA - 8" + "CFA is
+// sp"),
// then it will return LazyBoolTrue.
-LazyBool
-FuncUnwinders::CompareUnwindPlansForIdenticalInitialPCLocation (Thread& thread, const UnwindPlanSP &a, const UnwindPlanSP &b)
-{
- LazyBool plans_are_identical = eLazyBoolCalculate;
-
- RegisterNumber pc_reg (thread, eRegisterKindGeneric, LLDB_REGNUM_GENERIC_PC);
- uint32_t pc_reg_lldb_regnum = pc_reg.GetAsKind (eRegisterKindLLDB);
-
- if (a.get() && b.get())
- {
- UnwindPlan::RowSP a_first_row = a->GetRowAtIndex (0);
- UnwindPlan::RowSP b_first_row = b->GetRowAtIndex (0);
-
- if (a_first_row.get() && b_first_row.get())
- {
- UnwindPlan::Row::RegisterLocation a_pc_regloc;
- UnwindPlan::Row::RegisterLocation b_pc_regloc;
-
- a_first_row->GetRegisterInfo (pc_reg_lldb_regnum, a_pc_regloc);
- b_first_row->GetRegisterInfo (pc_reg_lldb_regnum, b_pc_regloc);
-
- plans_are_identical = eLazyBoolYes;
-
- if (a_first_row->GetCFAValue() != b_first_row->GetCFAValue())
- {
- plans_are_identical = eLazyBoolNo;
- }
- if (a_pc_regloc != b_pc_regloc)
- {
- plans_are_identical = eLazyBoolNo;
- }
- }
- }
- return plans_are_identical;
-}
+LazyBool FuncUnwinders::CompareUnwindPlansForIdenticalInitialPCLocation(
+ Thread &thread, const UnwindPlanSP &a, const UnwindPlanSP &b) {
+ LazyBool plans_are_identical = eLazyBoolCalculate;
+
+ RegisterNumber pc_reg(thread, eRegisterKindGeneric, LLDB_REGNUM_GENERIC_PC);
+ uint32_t pc_reg_lldb_regnum = pc_reg.GetAsKind(eRegisterKindLLDB);
+
+ if (a.get() && b.get()) {
+ UnwindPlan::RowSP a_first_row = a->GetRowAtIndex(0);
+ UnwindPlan::RowSP b_first_row = b->GetRowAtIndex(0);
+
+ if (a_first_row.get() && b_first_row.get()) {
+ UnwindPlan::Row::RegisterLocation a_pc_regloc;
+ UnwindPlan::Row::RegisterLocation b_pc_regloc;
+
+ a_first_row->GetRegisterInfo(pc_reg_lldb_regnum, a_pc_regloc);
+ b_first_row->GetRegisterInfo(pc_reg_lldb_regnum, b_pc_regloc);
+
+ plans_are_identical = eLazyBoolYes;
+
+ if (a_first_row->GetCFAValue() != b_first_row->GetCFAValue()) {
+ plans_are_identical = eLazyBoolNo;
+ }
+ if (a_pc_regloc != b_pc_regloc) {
+ plans_are_identical = eLazyBoolNo;
+ }
+ }
+ }
+ return plans_are_identical;
+}
+
+UnwindPlanSP FuncUnwinders::GetUnwindPlanAtNonCallSite(Target &target,
+ Thread &thread,
+ int current_offset) {
+ UnwindPlanSP eh_frame_sp = GetEHFrameUnwindPlan(target, current_offset);
+ UnwindPlanSP arch_default_at_entry_sp =
+ GetUnwindPlanArchitectureDefaultAtFunctionEntry(thread);
+ UnwindPlanSP arch_default_sp = GetUnwindPlanArchitectureDefault(thread);
+ UnwindPlanSP assembly_sp =
+ GetAssemblyUnwindPlan(target, thread, current_offset);
+
+ // This point of this code is to detect when a function is using a
+ // non-standard ABI, and the eh_frame
+ // correctly describes that alternate ABI. This is addressing a specific
+ // situation on x86_64 linux
+ // systems where one function in a library pushes a value on the stack and
+ // jumps to another function.
+ // So using an assembly instruction based unwind will not work when you're in
+ // the second function -
+ // the stack has been modified in a non-ABI way. But we have eh_frame that
+ // correctly describes how to
+ // unwind from this location. So we're looking to see if the initial pc
+ // register save location from
+ // the eh_frame is different from the assembly unwind, the arch default
+ // unwind, and the arch default at
+ // initial function entry.
+ //
+ // We may have eh_frame that describes the entire function -- or we may have
+ // eh_frame that only describes
+ // the unwind after the prologue has executed -- so we need to check both the
+ // arch default (once the prologue
+ // has executed) and the arch default at initial function entry. And we may
+ // be running on a target where
+ // we have only some of the assembly/arch default unwind plans available.
+
+ if (CompareUnwindPlansForIdenticalInitialPCLocation(
+ thread, eh_frame_sp, arch_default_at_entry_sp) == eLazyBoolNo &&
+ CompareUnwindPlansForIdenticalInitialPCLocation(
+ thread, eh_frame_sp, arch_default_sp) == eLazyBoolNo &&
+ CompareUnwindPlansForIdenticalInitialPCLocation(
+ thread, assembly_sp, arch_default_sp) == eLazyBoolNo) {
+ return eh_frame_sp;
+ }
+
+ UnwindPlanSP eh_frame_augmented_sp =
+ GetEHFrameAugmentedUnwindPlan(target, thread, current_offset);
+ if (eh_frame_augmented_sp) {
+ return eh_frame_augmented_sp;
+ }
+
+ return assembly_sp;
+}
+
+UnwindPlanSP FuncUnwinders::GetUnwindPlanFastUnwind(Target &target,
+ Thread &thread) {
+ if (m_unwind_plan_fast_sp.get() || m_tried_unwind_fast)
+ return m_unwind_plan_fast_sp;
-UnwindPlanSP
-FuncUnwinders::GetUnwindPlanAtNonCallSite (Target& target, Thread& thread, int current_offset)
-{
- UnwindPlanSP eh_frame_sp = GetEHFrameUnwindPlan (target, current_offset);
- UnwindPlanSP arch_default_at_entry_sp = GetUnwindPlanArchitectureDefaultAtFunctionEntry (thread);
- UnwindPlanSP arch_default_sp = GetUnwindPlanArchitectureDefault (thread);
- UnwindPlanSP assembly_sp = GetAssemblyUnwindPlan (target, thread, current_offset);
-
- // This point of this code is to detect when a function is using a non-standard ABI, and the eh_frame
- // correctly describes that alternate ABI. This is addressing a specific situation on x86_64 linux
- // systems where one function in a library pushes a value on the stack and jumps to another function.
- // So using an assembly instruction based unwind will not work when you're in the second function -
- // the stack has been modified in a non-ABI way. But we have eh_frame that correctly describes how to
- // unwind from this location. So we're looking to see if the initial pc register save location from
- // the eh_frame is different from the assembly unwind, the arch default unwind, and the arch default at
- // initial function entry.
- //
- // We may have eh_frame that describes the entire function -- or we may have eh_frame that only describes
- // the unwind after the prologue has executed -- so we need to check both the arch default (once the prologue
- // has executed) and the arch default at initial function entry. And we may be running on a target where
- // we have only some of the assembly/arch default unwind plans available.
-
- if (CompareUnwindPlansForIdenticalInitialPCLocation (thread, eh_frame_sp, arch_default_at_entry_sp) == eLazyBoolNo
- && CompareUnwindPlansForIdenticalInitialPCLocation (thread, eh_frame_sp, arch_default_sp) == eLazyBoolNo
- && CompareUnwindPlansForIdenticalInitialPCLocation (thread, assembly_sp, arch_default_sp) == eLazyBoolNo)
- {
- return eh_frame_sp;
- }
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+ m_tried_unwind_fast = true;
- UnwindPlanSP eh_frame_augmented_sp = GetEHFrameAugmentedUnwindPlan (target, thread, current_offset);
- if (eh_frame_augmented_sp)
- {
- return eh_frame_augmented_sp;
+ UnwindAssemblySP assembly_profiler_sp(GetUnwindAssemblyProfiler(target));
+ if (assembly_profiler_sp) {
+ m_unwind_plan_fast_sp.reset(new UnwindPlan(lldb::eRegisterKindGeneric));
+ if (!assembly_profiler_sp->GetFastUnwindPlan(m_range, thread,
+ *m_unwind_plan_fast_sp)) {
+ m_unwind_plan_fast_sp.reset();
}
-
- return assembly_sp;
+ }
+ return m_unwind_plan_fast_sp;
}
-UnwindPlanSP
-FuncUnwinders::GetUnwindPlanFastUnwind (Target& target, Thread& thread)
-{
- if (m_unwind_plan_fast_sp.get() || m_tried_unwind_fast)
- return m_unwind_plan_fast_sp;
-
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
- m_tried_unwind_fast = true;
-
- UnwindAssemblySP assembly_profiler_sp (GetUnwindAssemblyProfiler(target));
- if (assembly_profiler_sp)
- {
- m_unwind_plan_fast_sp.reset (new UnwindPlan (lldb::eRegisterKindGeneric));
- if (!assembly_profiler_sp->GetFastUnwindPlan (m_range, thread, *m_unwind_plan_fast_sp))
- {
- m_unwind_plan_fast_sp.reset();
- }
- }
- return m_unwind_plan_fast_sp;
-}
+UnwindPlanSP FuncUnwinders::GetUnwindPlanArchitectureDefault(Thread &thread) {
+ if (m_unwind_plan_arch_default_sp.get() || m_tried_unwind_arch_default)
+ return m_unwind_plan_arch_default_sp;
-UnwindPlanSP
-FuncUnwinders::GetUnwindPlanArchitectureDefault (Thread& thread)
-{
- if (m_unwind_plan_arch_default_sp.get() || m_tried_unwind_arch_default)
- return m_unwind_plan_arch_default_sp;
-
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
- m_tried_unwind_arch_default = true;
-
- Address current_pc;
- ProcessSP process_sp (thread.CalculateProcess());
- if (process_sp)
- {
- ABI *abi = process_sp->GetABI().get();
- if (abi)
- {
- m_unwind_plan_arch_default_sp.reset (new UnwindPlan (lldb::eRegisterKindGeneric));
- if (!abi->CreateDefaultUnwindPlan(*m_unwind_plan_arch_default_sp))
- {
- m_unwind_plan_arch_default_sp.reset();
- }
- }
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+ m_tried_unwind_arch_default = true;
+
+ Address current_pc;
+ ProcessSP process_sp(thread.CalculateProcess());
+ if (process_sp) {
+ ABI *abi = process_sp->GetABI().get();
+ if (abi) {
+ m_unwind_plan_arch_default_sp.reset(
+ new UnwindPlan(lldb::eRegisterKindGeneric));
+ if (!abi->CreateDefaultUnwindPlan(*m_unwind_plan_arch_default_sp)) {
+ m_unwind_plan_arch_default_sp.reset();
+ }
}
+ }
- return m_unwind_plan_arch_default_sp;
+ return m_unwind_plan_arch_default_sp;
}
UnwindPlanSP
-FuncUnwinders::GetUnwindPlanArchitectureDefaultAtFunctionEntry (Thread& thread)
-{
- if (m_unwind_plan_arch_default_at_func_entry_sp.get() || m_tried_unwind_arch_default_at_func_entry)
- return m_unwind_plan_arch_default_at_func_entry_sp;
-
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
- m_tried_unwind_arch_default_at_func_entry = true;
-
- Address current_pc;
- ProcessSP process_sp (thread.CalculateProcess());
- if (process_sp)
- {
- ABI *abi = process_sp->GetABI().get();
- if (abi)
- {
- m_unwind_plan_arch_default_at_func_entry_sp.reset (new UnwindPlan (lldb::eRegisterKindGeneric));
- if (!abi->CreateFunctionEntryUnwindPlan(*m_unwind_plan_arch_default_at_func_entry_sp))
- {
- m_unwind_plan_arch_default_at_func_entry_sp.reset();
- }
- }
- }
-
+FuncUnwinders::GetUnwindPlanArchitectureDefaultAtFunctionEntry(Thread &thread) {
+ if (m_unwind_plan_arch_default_at_func_entry_sp.get() ||
+ m_tried_unwind_arch_default_at_func_entry)
return m_unwind_plan_arch_default_at_func_entry_sp;
-}
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+ m_tried_unwind_arch_default_at_func_entry = true;
-Address&
-FuncUnwinders::GetFirstNonPrologueInsn (Target& target)
-{
- if (m_first_non_prologue_insn.IsValid())
- return m_first_non_prologue_insn;
-
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
- ExecutionContext exe_ctx (target.shared_from_this(), false);
- UnwindAssemblySP assembly_profiler_sp (GetUnwindAssemblyProfiler(target));
- if (assembly_profiler_sp)
- assembly_profiler_sp->FirstNonPrologueInsn (m_range, exe_ctx, m_first_non_prologue_insn);
- return m_first_non_prologue_insn;
-}
+ Address current_pc;
+ ProcessSP process_sp(thread.CalculateProcess());
+ if (process_sp) {
+ ABI *abi = process_sp->GetABI().get();
+ if (abi) {
+ m_unwind_plan_arch_default_at_func_entry_sp.reset(
+ new UnwindPlan(lldb::eRegisterKindGeneric));
+ if (!abi->CreateFunctionEntryUnwindPlan(
+ *m_unwind_plan_arch_default_at_func_entry_sp)) {
+ m_unwind_plan_arch_default_at_func_entry_sp.reset();
+ }
+ }
+ }
-const Address&
-FuncUnwinders::GetFunctionStartAddress () const
-{
- return m_range.GetBaseAddress();
+ return m_unwind_plan_arch_default_at_func_entry_sp;
}
-lldb::UnwindAssemblySP
-FuncUnwinders::GetUnwindAssemblyProfiler (Target& target)
-{
- UnwindAssemblySP assembly_profiler_sp;
- ArchSpec arch;
- if (m_unwind_table.GetArchitecture (arch))
- {
- arch.MergeFrom (target.GetArchitecture ());
- assembly_profiler_sp = UnwindAssembly::FindPlugin (arch);
- }
- return assembly_profiler_sp;
-}
+Address &FuncUnwinders::GetFirstNonPrologueInsn(Target &target) {
+ if (m_first_non_prologue_insn.IsValid())
+ return m_first_non_prologue_insn;
-Address
-FuncUnwinders::GetLSDAAddress (Target &target)
-{
- Address lsda_addr;
-
- UnwindPlanSP unwind_plan_sp = GetEHFrameUnwindPlan (target, -1);
- if (unwind_plan_sp.get() == nullptr)
- {
- unwind_plan_sp = GetCompactUnwindUnwindPlan (target, -1);
- }
- if (unwind_plan_sp.get() && unwind_plan_sp->GetLSDAAddress().IsValid())
- {
- lsda_addr = unwind_plan_sp->GetLSDAAddress();
- }
- return lsda_addr;
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+ ExecutionContext exe_ctx(target.shared_from_this(), false);
+ UnwindAssemblySP assembly_profiler_sp(GetUnwindAssemblyProfiler(target));
+ if (assembly_profiler_sp)
+ assembly_profiler_sp->FirstNonPrologueInsn(m_range, exe_ctx,
+ m_first_non_prologue_insn);
+ return m_first_non_prologue_insn;
}
+const Address &FuncUnwinders::GetFunctionStartAddress() const {
+ return m_range.GetBaseAddress();
+}
-Address
-FuncUnwinders::GetPersonalityRoutinePtrAddress (Target &target)
-{
- Address personality_addr;
-
- UnwindPlanSP unwind_plan_sp = GetEHFrameUnwindPlan (target, -1);
- if (unwind_plan_sp.get() == nullptr)
- {
- unwind_plan_sp = GetCompactUnwindUnwindPlan (target, -1);
- }
- if (unwind_plan_sp.get() && unwind_plan_sp->GetPersonalityFunctionPtr().IsValid())
- {
- personality_addr = unwind_plan_sp->GetPersonalityFunctionPtr();
- }
+lldb::UnwindAssemblySP
+FuncUnwinders::GetUnwindAssemblyProfiler(Target &target) {
+ UnwindAssemblySP assembly_profiler_sp;
+ ArchSpec arch;
+ if (m_unwind_table.GetArchitecture(arch)) {
+ arch.MergeFrom(target.GetArchitecture());
+ assembly_profiler_sp = UnwindAssembly::FindPlugin(arch);
+ }
+ return assembly_profiler_sp;
+}
+
+Address FuncUnwinders::GetLSDAAddress(Target &target) {
+ Address lsda_addr;
+
+ UnwindPlanSP unwind_plan_sp = GetEHFrameUnwindPlan(target, -1);
+ if (unwind_plan_sp.get() == nullptr) {
+ unwind_plan_sp = GetCompactUnwindUnwindPlan(target, -1);
+ }
+ if (unwind_plan_sp.get() && unwind_plan_sp->GetLSDAAddress().IsValid()) {
+ lsda_addr = unwind_plan_sp->GetLSDAAddress();
+ }
+ return lsda_addr;
+}
+
+Address FuncUnwinders::GetPersonalityRoutinePtrAddress(Target &target) {
+ Address personality_addr;
+
+ UnwindPlanSP unwind_plan_sp = GetEHFrameUnwindPlan(target, -1);
+ if (unwind_plan_sp.get() == nullptr) {
+ unwind_plan_sp = GetCompactUnwindUnwindPlan(target, -1);
+ }
+ if (unwind_plan_sp.get() &&
+ unwind_plan_sp->GetPersonalityFunctionPtr().IsValid()) {
+ personality_addr = unwind_plan_sp->GetPersonalityFunctionPtr();
+ }
- return personality_addr;
+ return personality_addr;
}
Modified: lldb/trunk/source/Symbol/Function.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/Function.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/Function.cpp (original)
+++ lldb/trunk/source/Symbol/Function.cpp Tue Sep 6 15:57:50 2016
@@ -12,8 +12,8 @@
#include "lldb/Core/Module.h"
#include "lldb/Core/Section.h"
#include "lldb/Host/Host.h"
-#include "lldb/Symbol/CompilerType.h"
#include "lldb/Symbol/CompileUnit.h"
+#include "lldb/Symbol/CompilerType.h"
#include "lldb/Symbol/LineTable.h"
#include "lldb/Symbol/SymbolFile.h"
#include "lldb/Symbol/SymbolVendor.h"
@@ -28,685 +28,508 @@ using namespace lldb_private;
// It is designed to contain the name, linkage name, and declaration
// location.
//----------------------------------------------------------------------
-FunctionInfo::FunctionInfo (const char *name, const Declaration *decl_ptr) :
- m_name(name),
- m_declaration(decl_ptr)
-{
+FunctionInfo::FunctionInfo(const char *name, const Declaration *decl_ptr)
+ : m_name(name), m_declaration(decl_ptr) {}
+
+FunctionInfo::FunctionInfo(const ConstString &name, const Declaration *decl_ptr)
+ : m_name(name), m_declaration(decl_ptr) {}
+
+FunctionInfo::~FunctionInfo() {}
+
+void FunctionInfo::Dump(Stream *s, bool show_fullpaths) const {
+ if (m_name)
+ *s << ", name = \"" << m_name << "\"";
+ m_declaration.Dump(s, show_fullpaths);
}
+int FunctionInfo::Compare(const FunctionInfo &a, const FunctionInfo &b) {
+ int result = ConstString::Compare(a.GetName(), b.GetName());
+ if (result)
+ return result;
-FunctionInfo::FunctionInfo (const ConstString& name, const Declaration *decl_ptr) :
- m_name(name),
- m_declaration(decl_ptr)
-{
+ return Declaration::Compare(a.m_declaration, b.m_declaration);
}
+Declaration &FunctionInfo::GetDeclaration() { return m_declaration; }
-FunctionInfo::~FunctionInfo()
-{
+const Declaration &FunctionInfo::GetDeclaration() const {
+ return m_declaration;
}
-void
-FunctionInfo::Dump(Stream *s, bool show_fullpaths) const
-{
- if (m_name)
- *s << ", name = \"" << m_name << "\"";
- m_declaration.Dump(s, show_fullpaths);
+ConstString FunctionInfo::GetName() const { return m_name; }
+
+size_t FunctionInfo::MemorySize() const {
+ return m_name.MemorySize() + m_declaration.MemorySize();
}
+InlineFunctionInfo::InlineFunctionInfo(const char *name, const char *mangled,
+ const Declaration *decl_ptr,
+ const Declaration *call_decl_ptr)
+ : FunctionInfo(name, decl_ptr), m_mangled(ConstString(mangled), true),
+ m_call_decl(call_decl_ptr) {}
+
+InlineFunctionInfo::InlineFunctionInfo(const ConstString &name,
+ const Mangled &mangled,
+ const Declaration *decl_ptr,
+ const Declaration *call_decl_ptr)
+ : FunctionInfo(name, decl_ptr), m_mangled(mangled),
+ m_call_decl(call_decl_ptr) {}
+
+InlineFunctionInfo::~InlineFunctionInfo() {}
-int
-FunctionInfo::Compare(const FunctionInfo& a, const FunctionInfo& b)
-{
- int result = ConstString::Compare(a.GetName(), b.GetName());
- if (result)
- return result;
+int InlineFunctionInfo::Compare(const InlineFunctionInfo &a,
+ const InlineFunctionInfo &b) {
- return Declaration::Compare(a.m_declaration, b.m_declaration);
+ int result = FunctionInfo::Compare(a, b);
+ if (result)
+ return result;
+ // only compare the mangled names if both have them
+ return Mangled::Compare(a.m_mangled, a.m_mangled);
}
+void InlineFunctionInfo::Dump(Stream *s, bool show_fullpaths) const {
+ FunctionInfo::Dump(s, show_fullpaths);
+ if (m_mangled)
+ m_mangled.Dump(s);
+}
-Declaration&
-FunctionInfo::GetDeclaration()
-{
- return m_declaration;
+void InlineFunctionInfo::DumpStopContext(Stream *s,
+ LanguageType language) const {
+ // s->Indent("[inlined] ");
+ s->Indent();
+ if (m_mangled)
+ s->PutCString(m_mangled.GetName(language).AsCString());
+ else
+ s->PutCString(m_name.AsCString());
}
-const Declaration&
-FunctionInfo::GetDeclaration() const
-{
- return m_declaration;
+ConstString InlineFunctionInfo::GetName(LanguageType language) const {
+ if (m_mangled)
+ return m_mangled.GetName(language);
+ return m_name;
}
-ConstString
-FunctionInfo::GetName() const
-{
- return m_name;
+ConstString InlineFunctionInfo::GetDisplayName(LanguageType language) const {
+ if (m_mangled)
+ return m_mangled.GetDisplayDemangledName(language);
+ return m_name;
}
-size_t
-FunctionInfo::MemorySize() const
-{
- return m_name.MemorySize() + m_declaration.MemorySize();
+Declaration &InlineFunctionInfo::GetCallSite() { return m_call_decl; }
+
+const Declaration &InlineFunctionInfo::GetCallSite() const {
+ return m_call_decl;
}
+Mangled &InlineFunctionInfo::GetMangled() { return m_mangled; }
-InlineFunctionInfo::InlineFunctionInfo
-(
- const char *name,
- const char *mangled,
- const Declaration *decl_ptr,
- const Declaration *call_decl_ptr
-) :
- FunctionInfo(name, decl_ptr),
- m_mangled(ConstString(mangled), true),
- m_call_decl (call_decl_ptr)
-{
+const Mangled &InlineFunctionInfo::GetMangled() const { return m_mangled; }
+
+size_t InlineFunctionInfo::MemorySize() const {
+ return FunctionInfo::MemorySize() + m_mangled.MemorySize();
}
-InlineFunctionInfo::InlineFunctionInfo
-(
- const ConstString& name,
- const Mangled &mangled,
- const Declaration *decl_ptr,
- const Declaration *call_decl_ptr
-) :
- FunctionInfo(name, decl_ptr),
- m_mangled(mangled),
- m_call_decl (call_decl_ptr)
-{
+//----------------------------------------------------------------------
+//
+//----------------------------------------------------------------------
+Function::Function(CompileUnit *comp_unit, lldb::user_id_t func_uid,
+ lldb::user_id_t type_uid, const Mangled &mangled, Type *type,
+ const AddressRange &range)
+ : UserID(func_uid), m_comp_unit(comp_unit), m_type_uid(type_uid),
+ m_type(type), m_mangled(mangled), m_block(func_uid), m_range(range),
+ m_frame_base(nullptr), m_flags(), m_prologue_byte_size(0) {
+ m_block.SetParentScope(this);
+ assert(comp_unit != nullptr);
+}
+
+Function::Function(CompileUnit *comp_unit, lldb::user_id_t func_uid,
+ lldb::user_id_t type_uid, const char *mangled, Type *type,
+ const AddressRange &range)
+ : UserID(func_uid), m_comp_unit(comp_unit), m_type_uid(type_uid),
+ m_type(type), m_mangled(ConstString(mangled), true), m_block(func_uid),
+ m_range(range), m_frame_base(nullptr), m_flags(),
+ m_prologue_byte_size(0) {
+ m_block.SetParentScope(this);
+ assert(comp_unit != nullptr);
+}
+
+Function::~Function() {}
+
+void Function::GetStartLineSourceInfo(FileSpec &source_file,
+ uint32_t &line_no) {
+ line_no = 0;
+ source_file.Clear();
+
+ if (m_comp_unit == nullptr)
+ return;
+
+ if (m_type != nullptr && m_type->GetDeclaration().GetLine() != 0) {
+ source_file = m_type->GetDeclaration().GetFile();
+ line_no = m_type->GetDeclaration().GetLine();
+ } else {
+ LineTable *line_table = m_comp_unit->GetLineTable();
+ if (line_table == nullptr)
+ return;
+
+ LineEntry line_entry;
+ if (line_table->FindLineEntryByAddress(GetAddressRange().GetBaseAddress(),
+ line_entry, nullptr)) {
+ line_no = line_entry.line;
+ source_file = line_entry.file;
+ }
+ }
}
-InlineFunctionInfo::~InlineFunctionInfo()
-{
+void Function::GetEndLineSourceInfo(FileSpec &source_file, uint32_t &line_no) {
+ line_no = 0;
+ source_file.Clear();
+
+ // The -1 is kind of cheesy, but I want to get the last line entry for the
+ // given function, not the
+ // first entry of the next.
+ Address scratch_addr(GetAddressRange().GetBaseAddress());
+ scratch_addr.SetOffset(scratch_addr.GetOffset() +
+ GetAddressRange().GetByteSize() - 1);
+
+ LineTable *line_table = m_comp_unit->GetLineTable();
+ if (line_table == nullptr)
+ return;
+
+ LineEntry line_entry;
+ if (line_table->FindLineEntryByAddress(scratch_addr, line_entry, nullptr)) {
+ line_no = line_entry.line;
+ source_file = line_entry.file;
+ }
+}
+
+Block &Function::GetBlock(bool can_create) {
+ if (!m_block.BlockInfoHasBeenParsed() && can_create) {
+ SymbolContext sc;
+ CalculateSymbolContext(&sc);
+ if (sc.module_sp) {
+ sc.module_sp->GetSymbolVendor()->ParseFunctionBlocks(sc);
+ } else {
+ Host::SystemLog(Host::eSystemLogError, "error: unable to find module "
+ "shared pointer for function '%s' "
+ "in %s\n",
+ GetName().GetCString(), m_comp_unit->GetPath().c_str());
+ }
+ m_block.SetBlockInfoHasBeenParsed(true, true);
+ }
+ return m_block;
}
-int
-InlineFunctionInfo::Compare(const InlineFunctionInfo& a, const InlineFunctionInfo& b)
-{
+CompileUnit *Function::GetCompileUnit() { return m_comp_unit; }
+
+const CompileUnit *Function::GetCompileUnit() const { return m_comp_unit; }
+
+void Function::GetDescription(Stream *s, lldb::DescriptionLevel level,
+ Target *target) {
+ Type *func_type = GetType();
+ const char *name = func_type ? func_type->GetName().AsCString() : "<unknown>";
+
+ *s << "id = " << (const UserID &)*this << ", name = \"" << name
+ << "\", range = ";
- int result = FunctionInfo::Compare(a, b);
- if (result)
- return result;
- // only compare the mangled names if both have them
- return Mangled::Compare(a.m_mangled, a.m_mangled);
+ Address::DumpStyle fallback_style;
+ if (level == eDescriptionLevelVerbose)
+ fallback_style = Address::DumpStyleModuleWithFileAddress;
+ else
+ fallback_style = Address::DumpStyleFileAddress;
+ GetAddressRange().Dump(s, target, Address::DumpStyleLoadAddress,
+ fallback_style);
}
-void
-InlineFunctionInfo::Dump(Stream *s, bool show_fullpaths) const
-{
- FunctionInfo::Dump(s, show_fullpaths);
- if (m_mangled)
- m_mangled.Dump(s);
+void Function::Dump(Stream *s, bool show_context) const {
+ s->Printf("%p: ", static_cast<const void *>(this));
+ s->Indent();
+ *s << "Function" << static_cast<const UserID &>(*this);
+
+ m_mangled.Dump(s);
+
+ if (m_type)
+ s->Printf(", type = %p", static_cast<void *>(m_type));
+ else if (m_type_uid != LLDB_INVALID_UID)
+ s->Printf(", type_uid = 0x%8.8" PRIx64, m_type_uid);
+
+ s->EOL();
+ // Dump the root object
+ if (m_block.BlockInfoHasBeenParsed())
+ m_block.Dump(s, m_range.GetBaseAddress().GetFileAddress(), INT_MAX,
+ show_context);
}
-void
-InlineFunctionInfo::DumpStopContext (Stream *s, LanguageType language) const
-{
-// s->Indent("[inlined] ");
- s->Indent();
- if (m_mangled)
- s->PutCString (m_mangled.GetName(language).AsCString());
- else
- s->PutCString (m_name.AsCString());
+void Function::CalculateSymbolContext(SymbolContext *sc) {
+ sc->function = this;
+ m_comp_unit->CalculateSymbolContext(sc);
}
+ModuleSP Function::CalculateSymbolContextModule() {
+ SectionSP section_sp(m_range.GetBaseAddress().GetSection());
+ if (section_sp)
+ return section_sp->GetModule();
-ConstString
-InlineFunctionInfo::GetName (LanguageType language) const
-{
- if (m_mangled)
- return m_mangled.GetName(language);
- return m_name;
+ return this->GetCompileUnit()->GetModule();
}
-ConstString
-InlineFunctionInfo::GetDisplayName (LanguageType language) const
-{
- if (m_mangled)
- return m_mangled.GetDisplayDemangledName(language);
- return m_name;
+CompileUnit *Function::CalculateSymbolContextCompileUnit() {
+ return this->GetCompileUnit();
}
-Declaration &
-InlineFunctionInfo::GetCallSite ()
-{
- return m_call_decl;
+Function *Function::CalculateSymbolContextFunction() { return this; }
+
+lldb::DisassemblerSP Function::GetInstructions(const ExecutionContext &exe_ctx,
+ const char *flavor,
+ bool prefer_file_cache) {
+ ModuleSP module_sp(GetAddressRange().GetBaseAddress().GetModule());
+ if (module_sp) {
+ const bool prefer_file_cache = false;
+ return Disassembler::DisassembleRange(module_sp->GetArchitecture(), nullptr,
+ flavor, exe_ctx, GetAddressRange(),
+ prefer_file_cache);
+ }
+ return lldb::DisassemblerSP();
}
-const Declaration &
-InlineFunctionInfo::GetCallSite () const
-{
- return m_call_decl;
+bool Function::GetDisassembly(const ExecutionContext &exe_ctx,
+ const char *flavor, bool prefer_file_cache,
+ Stream &strm) {
+ lldb::DisassemblerSP disassembler_sp =
+ GetInstructions(exe_ctx, flavor, prefer_file_cache);
+ if (disassembler_sp) {
+ const bool show_address = true;
+ const bool show_bytes = false;
+ disassembler_sp->GetInstructionList().Dump(&strm, show_address, show_bytes,
+ &exe_ctx);
+ return true;
+ }
+ return false;
}
+// Symbol *
+// Function::CalculateSymbolContextSymbol ()
+//{
+// return // TODO: find the symbol for the function???
+//}
-Mangled&
-InlineFunctionInfo::GetMangled()
-{
- return m_mangled;
+void Function::DumpSymbolContext(Stream *s) {
+ m_comp_unit->DumpSymbolContext(s);
+ s->Printf(", Function{0x%8.8" PRIx64 "}", GetID());
}
-const Mangled&
-InlineFunctionInfo::GetMangled() const
-{
- return m_mangled;
+size_t Function::MemorySize() const {
+ size_t mem_size = sizeof(Function) + m_block.MemorySize();
+ return mem_size;
}
-size_t
-InlineFunctionInfo::MemorySize() const
-{
- return FunctionInfo::MemorySize() + m_mangled.MemorySize();
+bool Function::GetIsOptimized() {
+ bool result = false;
+
+ // Currently optimization is only indicted by the
+ // vendor extension DW_AT_APPLE_optimized which
+ // is set on a compile unit level.
+ if (m_comp_unit) {
+ result = m_comp_unit->GetIsOptimized();
+ }
+ return result;
}
-//----------------------------------------------------------------------
-//
-//----------------------------------------------------------------------
-Function::Function
-(
- CompileUnit *comp_unit,
- lldb::user_id_t func_uid,
- lldb::user_id_t type_uid,
- const Mangled &mangled,
- Type * type,
- const AddressRange& range
-) :
- UserID (func_uid),
- m_comp_unit (comp_unit),
- m_type_uid (type_uid),
- m_type (type),
- m_mangled (mangled),
- m_block (func_uid),
- m_range (range),
- m_frame_base (nullptr),
- m_flags (),
- m_prologue_byte_size (0)
-{
- m_block.SetParentScope(this);
- assert(comp_unit != nullptr);
-}
-
-Function::Function
-(
- CompileUnit *comp_unit,
- lldb::user_id_t func_uid,
- lldb::user_id_t type_uid,
- const char *mangled,
- Type *type,
- const AddressRange &range
-) :
- UserID (func_uid),
- m_comp_unit (comp_unit),
- m_type_uid (type_uid),
- m_type (type),
- m_mangled (ConstString(mangled), true),
- m_block (func_uid),
- m_range (range),
- m_frame_base (nullptr),
- m_flags (),
- m_prologue_byte_size (0)
-{
- m_block.SetParentScope(this);
- assert(comp_unit != nullptr);
-}
-
-
-Function::~Function()
-{
-}
-
-void
-Function::GetStartLineSourceInfo (FileSpec &source_file, uint32_t &line_no)
-{
- line_no = 0;
- source_file.Clear();
-
- if (m_comp_unit == nullptr)
- return;
-
- if (m_type != nullptr && m_type->GetDeclaration().GetLine() != 0)
- {
- source_file = m_type->GetDeclaration().GetFile();
- line_no = m_type->GetDeclaration().GetLine();
- }
- else
- {
- LineTable *line_table = m_comp_unit->GetLineTable();
- if (line_table == nullptr)
- return;
-
- LineEntry line_entry;
- if (line_table->FindLineEntryByAddress (GetAddressRange().GetBaseAddress(), line_entry, nullptr))
- {
- line_no = line_entry.line;
- source_file = line_entry.file;
- }
- }
+bool Function::IsTopLevelFunction() {
+ bool result = false;
+
+ if (Language *language = Language::FindPlugin(GetLanguage()))
+ result = language->IsTopLevelFunction(*this);
+
+ return result;
}
-void
-Function::GetEndLineSourceInfo (FileSpec &source_file, uint32_t &line_no)
-{
- line_no = 0;
- source_file.Clear();
-
- // The -1 is kind of cheesy, but I want to get the last line entry for the given function, not the
- // first entry of the next.
- Address scratch_addr(GetAddressRange().GetBaseAddress());
- scratch_addr.SetOffset (scratch_addr.GetOffset() + GetAddressRange().GetByteSize() - 1);
-
- LineTable *line_table = m_comp_unit->GetLineTable();
- if (line_table == nullptr)
- return;
-
- LineEntry line_entry;
- if (line_table->FindLineEntryByAddress (scratch_addr, line_entry, nullptr))
- {
- line_no = line_entry.line;
- source_file = line_entry.file;
- }
+ConstString Function::GetDisplayName() const {
+ if (!m_mangled)
+ return ConstString();
+ return m_mangled.GetDisplayDemangledName(GetLanguage());
}
-Block &
-Function::GetBlock (bool can_create)
-{
- if (!m_block.BlockInfoHasBeenParsed() && can_create)
- {
- SymbolContext sc;
- CalculateSymbolContext(&sc);
- if (sc.module_sp)
- {
- sc.module_sp->GetSymbolVendor()->ParseFunctionBlocks(sc);
- }
- else
- {
- Host::SystemLog (Host::eSystemLogError,
- "error: unable to find module shared pointer for function '%s' in %s\n",
- GetName().GetCString(),
- m_comp_unit->GetPath().c_str());
- }
- m_block.SetBlockInfoHasBeenParsed (true, true);
+CompilerDeclContext Function::GetDeclContext() {
+ ModuleSP module_sp = CalculateSymbolContextModule();
+
+ if (module_sp) {
+ SymbolVendor *sym_vendor = module_sp->GetSymbolVendor();
+
+ if (sym_vendor) {
+ SymbolFile *sym_file = sym_vendor->GetSymbolFile();
+
+ if (sym_file)
+ return sym_file->GetDeclContextForUID(GetID());
}
- return m_block;
+ }
+ return CompilerDeclContext();
}
-CompileUnit*
-Function::GetCompileUnit()
-{
- return m_comp_unit;
-}
-
-const CompileUnit*
-Function::GetCompileUnit() const
-{
- return m_comp_unit;
-}
+Type *Function::GetType() {
+ if (m_type == nullptr) {
+ SymbolContext sc;
+ CalculateSymbolContext(&sc);
-void
-Function::GetDescription(Stream *s, lldb::DescriptionLevel level, Target *target)
-{
- Type* func_type = GetType();
- const char *name = func_type ? func_type->GetName().AsCString() : "<unknown>";
-
- *s << "id = " << (const UserID&)*this << ", name = \"" << name << "\", range = ";
-
- Address::DumpStyle fallback_style;
- if (level == eDescriptionLevelVerbose)
- fallback_style = Address::DumpStyleModuleWithFileAddress;
- else
- fallback_style = Address::DumpStyleFileAddress;
- GetAddressRange().Dump(s, target, Address::DumpStyleLoadAddress, fallback_style);
-}
-
-void
-Function::Dump(Stream *s, bool show_context) const
-{
- s->Printf("%p: ", static_cast<const void*>(this));
- s->Indent();
- *s << "Function" << static_cast<const UserID&>(*this);
+ if (!sc.module_sp)
+ return nullptr;
- m_mangled.Dump(s);
+ SymbolVendor *sym_vendor = sc.module_sp->GetSymbolVendor();
- if (m_type)
- s->Printf(", type = %p", static_cast<void*>(m_type));
- else if (m_type_uid != LLDB_INVALID_UID)
- s->Printf(", type_uid = 0x%8.8" PRIx64, m_type_uid);
-
- s->EOL();
- // Dump the root object
- if (m_block.BlockInfoHasBeenParsed ())
- m_block.Dump(s, m_range.GetBaseAddress().GetFileAddress(), INT_MAX, show_context);
-}
+ if (sym_vendor == nullptr)
+ return nullptr;
+ SymbolFile *sym_file = sym_vendor->GetSymbolFile();
-void
-Function::CalculateSymbolContext(SymbolContext* sc)
-{
- sc->function = this;
- m_comp_unit->CalculateSymbolContext(sc);
-}
-
-ModuleSP
-Function::CalculateSymbolContextModule ()
-{
- SectionSP section_sp (m_range.GetBaseAddress().GetSection());
- if (section_sp)
- return section_sp->GetModule();
-
- return this->GetCompileUnit()->GetModule();
-}
-
-CompileUnit *
-Function::CalculateSymbolContextCompileUnit ()
-{
- return this->GetCompileUnit();
-}
-
-Function *
-Function::CalculateSymbolContextFunction ()
-{
- return this;
-}
-
-lldb::DisassemblerSP
-Function::GetInstructions (const ExecutionContext &exe_ctx,
- const char *flavor,
- bool prefer_file_cache)
-{
- ModuleSP module_sp (GetAddressRange().GetBaseAddress().GetModule());
- if (module_sp)
- {
- const bool prefer_file_cache = false;
- return Disassembler::DisassembleRange (module_sp->GetArchitecture(),
- nullptr,
- flavor,
- exe_ctx,
- GetAddressRange(),
- prefer_file_cache);
- }
- return lldb::DisassemblerSP();
+ if (sym_file == nullptr)
+ return nullptr;
+
+ m_type = sym_file->ResolveTypeUID(m_type_uid);
+ }
+ return m_type;
}
-bool
-Function::GetDisassembly (const ExecutionContext &exe_ctx,
- const char *flavor,
- bool prefer_file_cache,
- Stream &strm)
-{
- lldb::DisassemblerSP disassembler_sp = GetInstructions (exe_ctx, flavor, prefer_file_cache);
- if (disassembler_sp)
- {
- const bool show_address = true;
- const bool show_bytes = false;
- disassembler_sp->GetInstructionList().Dump (&strm, show_address, show_bytes, &exe_ctx);
- return true;
- }
- return false;
+const Type *Function::GetType() const { return m_type; }
+
+CompilerType Function::GetCompilerType() {
+ Type *function_type = GetType();
+ if (function_type)
+ return function_type->GetFullCompilerType();
+ return CompilerType();
}
+uint32_t Function::GetPrologueByteSize() {
+ if (m_prologue_byte_size == 0 &&
+ m_flags.IsClear(flagsCalculatedPrologueSize)) {
+ m_flags.Set(flagsCalculatedPrologueSize);
+ LineTable *line_table = m_comp_unit->GetLineTable();
+ uint32_t prologue_end_line_idx = 0;
-//Symbol *
-//Function::CalculateSymbolContextSymbol ()
-//{
-// return // TODO: find the symbol for the function???
-//}
+ if (line_table) {
+ LineEntry first_line_entry;
+ uint32_t first_line_entry_idx = UINT32_MAX;
+ if (line_table->FindLineEntryByAddress(GetAddressRange().GetBaseAddress(),
+ first_line_entry,
+ &first_line_entry_idx)) {
+ // Make sure the first line entry isn't already the end of the prologue
+ addr_t prologue_end_file_addr = LLDB_INVALID_ADDRESS;
+ addr_t line_zero_end_file_addr = LLDB_INVALID_ADDRESS;
+
+ if (first_line_entry.is_prologue_end) {
+ prologue_end_file_addr =
+ first_line_entry.range.GetBaseAddress().GetFileAddress();
+ prologue_end_line_idx = first_line_entry_idx;
+ } else {
+ // Check the first few instructions and look for one that has
+ // is_prologue_end set to true.
+ const uint32_t last_line_entry_idx = first_line_entry_idx + 6;
+ for (uint32_t idx = first_line_entry_idx + 1;
+ idx < last_line_entry_idx; ++idx) {
+ LineEntry line_entry;
+ if (line_table->GetLineEntryAtIndex(idx, line_entry)) {
+ if (line_entry.is_prologue_end) {
+ prologue_end_file_addr =
+ line_entry.range.GetBaseAddress().GetFileAddress();
+ prologue_end_line_idx = idx;
+ break;
+ }
+ }
+ }
+ }
+ // If we didn't find the end of the prologue in the line tables,
+ // then just use the end address of the first line table entry
+ if (prologue_end_file_addr == LLDB_INVALID_ADDRESS) {
+ // Check the first few instructions and look for one that has
+ // a line number that's different than the first entry.
+ uint32_t last_line_entry_idx = first_line_entry_idx + 6;
+ for (uint32_t idx = first_line_entry_idx + 1;
+ idx < last_line_entry_idx; ++idx) {
+ LineEntry line_entry;
+ if (line_table->GetLineEntryAtIndex(idx, line_entry)) {
+ if (line_entry.line != first_line_entry.line) {
+ prologue_end_file_addr =
+ line_entry.range.GetBaseAddress().GetFileAddress();
+ prologue_end_line_idx = idx;
+ break;
+ }
+ }
+ }
-void
-Function::DumpSymbolContext(Stream *s)
-{
- m_comp_unit->DumpSymbolContext(s);
- s->Printf(", Function{0x%8.8" PRIx64 "}", GetID());
-}
-
-size_t
-Function::MemorySize () const
-{
- size_t mem_size = sizeof(Function) + m_block.MemorySize();
- return mem_size;
-}
-
-bool
-Function::GetIsOptimized ()
-{
- bool result = false;
-
- // Currently optimization is only indicted by the
- // vendor extension DW_AT_APPLE_optimized which
- // is set on a compile unit level.
- if (m_comp_unit)
- {
- result = m_comp_unit->GetIsOptimized();
- }
- return result;
-}
+ if (prologue_end_file_addr == LLDB_INVALID_ADDRESS) {
+ prologue_end_file_addr =
+ first_line_entry.range.GetBaseAddress().GetFileAddress() +
+ first_line_entry.range.GetByteSize();
+ prologue_end_line_idx = first_line_entry_idx;
+ }
+ }
-bool
-Function::IsTopLevelFunction ()
-{
- bool result = false;
-
- if (Language* language = Language::FindPlugin(GetLanguage()))
- result = language->IsTopLevelFunction(*this);
-
- return result;
-}
+ const addr_t func_start_file_addr =
+ m_range.GetBaseAddress().GetFileAddress();
+ const addr_t func_end_file_addr =
+ func_start_file_addr + m_range.GetByteSize();
+
+ // Now calculate the offset to pass the subsequent line 0 entries.
+ uint32_t first_non_zero_line = prologue_end_line_idx;
+ while (1) {
+ LineEntry line_entry;
+ if (line_table->GetLineEntryAtIndex(first_non_zero_line,
+ line_entry)) {
+ if (line_entry.line != 0)
+ break;
+ }
+ if (line_entry.range.GetBaseAddress().GetFileAddress() >=
+ func_end_file_addr)
+ break;
-ConstString
-Function::GetDisplayName () const
-{
- if (!m_mangled)
- return ConstString();
- return m_mangled.GetDisplayDemangledName(GetLanguage());
-}
-
-CompilerDeclContext
-Function::GetDeclContext()
-{
- ModuleSP module_sp = CalculateSymbolContextModule ();
-
- if (module_sp)
- {
- SymbolVendor *sym_vendor = module_sp->GetSymbolVendor();
-
- if (sym_vendor)
- {
- SymbolFile *sym_file = sym_vendor->GetSymbolFile();
+ first_non_zero_line++;
+ }
- if (sym_file)
- return sym_file->GetDeclContextForUID (GetID());
+ if (first_non_zero_line > prologue_end_line_idx) {
+ LineEntry first_non_zero_entry;
+ if (line_table->GetLineEntryAtIndex(first_non_zero_line,
+ first_non_zero_entry)) {
+ line_zero_end_file_addr =
+ first_non_zero_entry.range.GetBaseAddress().GetFileAddress();
+ }
}
- }
- return CompilerDeclContext();
-}
-Type*
-Function::GetType()
-{
- if (m_type == nullptr)
- {
- SymbolContext sc;
-
- CalculateSymbolContext (&sc);
-
- if (!sc.module_sp)
- return nullptr;
-
- SymbolVendor *sym_vendor = sc.module_sp->GetSymbolVendor();
-
- if (sym_vendor == nullptr)
- return nullptr;
-
- SymbolFile *sym_file = sym_vendor->GetSymbolFile();
-
- if (sym_file == nullptr)
- return nullptr;
-
- m_type = sym_file->ResolveTypeUID(m_type_uid);
- }
- return m_type;
-}
+ // Verify that this prologue end file address in the function's
+ // address range just to be sure
+ if (func_start_file_addr < prologue_end_file_addr &&
+ prologue_end_file_addr < func_end_file_addr) {
+ m_prologue_byte_size = prologue_end_file_addr - func_start_file_addr;
+ }
-const Type*
-Function::GetType() const
-{
- return m_type;
-}
-
-CompilerType
-Function::GetCompilerType()
-{
- Type *function_type = GetType();
- if (function_type)
- return function_type->GetFullCompilerType ();
- return CompilerType();
-}
-
-uint32_t
-Function::GetPrologueByteSize ()
-{
- if (m_prologue_byte_size == 0 && m_flags.IsClear(flagsCalculatedPrologueSize))
- {
- m_flags.Set(flagsCalculatedPrologueSize);
- LineTable* line_table = m_comp_unit->GetLineTable ();
- uint32_t prologue_end_line_idx = 0;
-
- if (line_table)
- {
- LineEntry first_line_entry;
- uint32_t first_line_entry_idx = UINT32_MAX;
- if (line_table->FindLineEntryByAddress(GetAddressRange().GetBaseAddress(), first_line_entry, &first_line_entry_idx))
- {
- // Make sure the first line entry isn't already the end of the prologue
- addr_t prologue_end_file_addr = LLDB_INVALID_ADDRESS;
- addr_t line_zero_end_file_addr = LLDB_INVALID_ADDRESS;
-
- if (first_line_entry.is_prologue_end)
- {
- prologue_end_file_addr = first_line_entry.range.GetBaseAddress().GetFileAddress();
- prologue_end_line_idx = first_line_entry_idx;
- }
- else
- {
- // Check the first few instructions and look for one that has
- // is_prologue_end set to true.
- const uint32_t last_line_entry_idx = first_line_entry_idx + 6;
- for (uint32_t idx = first_line_entry_idx + 1; idx < last_line_entry_idx; ++idx)
- {
- LineEntry line_entry;
- if (line_table->GetLineEntryAtIndex (idx, line_entry))
- {
- if (line_entry.is_prologue_end)
- {
- prologue_end_file_addr = line_entry.range.GetBaseAddress().GetFileAddress();
- prologue_end_line_idx = idx;
- break;
- }
- }
- }
- }
-
- // If we didn't find the end of the prologue in the line tables,
- // then just use the end address of the first line table entry
- if (prologue_end_file_addr == LLDB_INVALID_ADDRESS)
- {
- // Check the first few instructions and look for one that has
- // a line number that's different than the first entry.
- uint32_t last_line_entry_idx = first_line_entry_idx + 6;
- for (uint32_t idx = first_line_entry_idx + 1; idx < last_line_entry_idx; ++idx)
- {
- LineEntry line_entry;
- if (line_table->GetLineEntryAtIndex (idx, line_entry))
- {
- if (line_entry.line != first_line_entry.line)
- {
- prologue_end_file_addr = line_entry.range.GetBaseAddress().GetFileAddress();
- prologue_end_line_idx = idx;
- break;
- }
- }
- }
-
- if (prologue_end_file_addr == LLDB_INVALID_ADDRESS)
- {
- prologue_end_file_addr = first_line_entry.range.GetBaseAddress().GetFileAddress() + first_line_entry.range.GetByteSize();
- prologue_end_line_idx = first_line_entry_idx;
- }
- }
-
- const addr_t func_start_file_addr = m_range.GetBaseAddress().GetFileAddress();
- const addr_t func_end_file_addr = func_start_file_addr + m_range.GetByteSize();
-
- // Now calculate the offset to pass the subsequent line 0 entries.
- uint32_t first_non_zero_line = prologue_end_line_idx;
- while (1)
- {
- LineEntry line_entry;
- if (line_table->GetLineEntryAtIndex(first_non_zero_line, line_entry))
- {
- if (line_entry.line != 0)
- break;
- }
- if (line_entry.range.GetBaseAddress().GetFileAddress() >= func_end_file_addr)
- break;
-
- first_non_zero_line++;
- }
-
- if (first_non_zero_line > prologue_end_line_idx)
- {
- LineEntry first_non_zero_entry;
- if (line_table->GetLineEntryAtIndex(first_non_zero_line, first_non_zero_entry))
- {
- line_zero_end_file_addr = first_non_zero_entry.range.GetBaseAddress().GetFileAddress();
- }
- }
-
- // Verify that this prologue end file address in the function's
- // address range just to be sure
- if (func_start_file_addr < prologue_end_file_addr && prologue_end_file_addr < func_end_file_addr)
- {
- m_prologue_byte_size = prologue_end_file_addr - func_start_file_addr;
- }
-
- if (prologue_end_file_addr < line_zero_end_file_addr && line_zero_end_file_addr < func_end_file_addr)
- {
- m_prologue_byte_size += line_zero_end_file_addr - prologue_end_file_addr;
- }
- }
+ if (prologue_end_file_addr < line_zero_end_file_addr &&
+ line_zero_end_file_addr < func_end_file_addr) {
+ m_prologue_byte_size +=
+ line_zero_end_file_addr - prologue_end_file_addr;
}
+ }
}
-
- return m_prologue_byte_size;
-}
+ }
-lldb::LanguageType
-Function::GetLanguage() const
-{
- if (m_comp_unit)
- return m_comp_unit->GetLanguage();
- else
- return lldb::eLanguageTypeUnknown;
-}
-
-ConstString
-Function::GetName() const
-{
- LanguageType language = lldb::eLanguageTypeUnknown;
- if (m_comp_unit)
- language = m_comp_unit->GetLanguage();
- return m_mangled.GetName(language);
+ return m_prologue_byte_size;
}
-ConstString
-Function::GetNameNoArguments() const
-{
- LanguageType language = lldb::eLanguageTypeUnknown;
- if (m_comp_unit)
- language = m_comp_unit->GetLanguage();
- return m_mangled.GetName(language, Mangled::ePreferDemangledWithoutArguments);
+lldb::LanguageType Function::GetLanguage() const {
+ if (m_comp_unit)
+ return m_comp_unit->GetLanguage();
+ else
+ return lldb::eLanguageTypeUnknown;
}
+ConstString Function::GetName() const {
+ LanguageType language = lldb::eLanguageTypeUnknown;
+ if (m_comp_unit)
+ language = m_comp_unit->GetLanguage();
+ return m_mangled.GetName(language);
+}
-
+ConstString Function::GetNameNoArguments() const {
+ LanguageType language = lldb::eLanguageTypeUnknown;
+ if (m_comp_unit)
+ language = m_comp_unit->GetLanguage();
+ return m_mangled.GetName(language, Mangled::ePreferDemangledWithoutArguments);
+}
Modified: lldb/trunk/source/Symbol/GoASTContext.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/GoASTContext.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/GoASTContext.cpp (original)
+++ lldb/trunk/source/Symbol/GoASTContext.cpp Tue Sep 6 15:57:50 2016
@@ -18,9 +18,9 @@
#include "lldb/Core/ValueObject.h"
#include "lldb/DataFormatters/StringPrinter.h"
#include "lldb/Symbol/CompilerType.h"
+#include "lldb/Symbol/GoASTContext.h"
#include "lldb/Symbol/ObjectFile.h"
#include "lldb/Symbol/SymbolFile.h"
-#include "lldb/Symbol/GoASTContext.h"
#include "lldb/Symbol/Type.h"
#include "lldb/Target/ExecutionContext.h"
#include "lldb/Target/Target.h"
@@ -30,781 +30,610 @@
using namespace lldb;
-namespace lldb_private
-{
+namespace lldb_private {
class GoArray;
class GoFunction;
class GoStruct;
-class GoType
-{
- public:
- enum
- {
- KIND_BOOL = 1,
- KIND_INT = 2,
- KIND_INT8 = 3,
- KIND_INT16 = 4,
- KIND_INT32 = 5,
- KIND_INT64 = 6,
- KIND_UINT = 7,
- KIND_UINT8 = 8,
- KIND_UINT16 = 9,
- KIND_UINT32 = 10,
- KIND_UINT64 = 11,
- KIND_UINTPTR = 12,
- KIND_FLOAT32 = 13,
- KIND_FLOAT64 = 14,
- KIND_COMPLEX64 = 15,
- KIND_COMPLEX128 = 16,
- KIND_ARRAY = 17,
- KIND_CHAN = 18,
- KIND_FUNC = 19,
- KIND_INTERFACE = 20,
- KIND_MAP = 21,
- KIND_PTR = 22,
- KIND_SLICE = 23,
- KIND_STRING = 24,
- KIND_STRUCT = 25,
- KIND_UNSAFEPOINTER = 26,
- KIND_LLDB_VOID, // Extension for LLDB, not used by go runtime.
- KIND_MASK = (1 << 5) - 1,
- KIND_DIRECT_IFACE = 1 << 5
- };
- GoType(int kind, const ConstString &name)
- : m_kind(kind & KIND_MASK)
- , m_name(name)
- {
- if (m_kind == KIND_FUNC)
- m_kind = KIND_FUNC;
- }
- virtual ~GoType() {}
-
- int
- GetGoKind() const
- {
- return m_kind;
- }
- const ConstString &
- GetName() const
- {
- return m_name;
- }
- virtual CompilerType
- GetElementType() const
- {
- return CompilerType();
- }
-
- bool
- IsTypedef() const
- {
- switch (m_kind)
- {
- case KIND_CHAN:
- case KIND_MAP:
- case KIND_INTERFACE:
- return true;
- default:
- return false;
- }
- }
-
- GoArray *GetArray();
- GoFunction *GetFunction();
- GoStruct *GetStruct();
-
- private:
- int m_kind;
- ConstString m_name;
- GoType(const GoType &) = delete;
- const GoType &operator=(const GoType &) = delete;
+class GoType {
+public:
+ enum {
+ KIND_BOOL = 1,
+ KIND_INT = 2,
+ KIND_INT8 = 3,
+ KIND_INT16 = 4,
+ KIND_INT32 = 5,
+ KIND_INT64 = 6,
+ KIND_UINT = 7,
+ KIND_UINT8 = 8,
+ KIND_UINT16 = 9,
+ KIND_UINT32 = 10,
+ KIND_UINT64 = 11,
+ KIND_UINTPTR = 12,
+ KIND_FLOAT32 = 13,
+ KIND_FLOAT64 = 14,
+ KIND_COMPLEX64 = 15,
+ KIND_COMPLEX128 = 16,
+ KIND_ARRAY = 17,
+ KIND_CHAN = 18,
+ KIND_FUNC = 19,
+ KIND_INTERFACE = 20,
+ KIND_MAP = 21,
+ KIND_PTR = 22,
+ KIND_SLICE = 23,
+ KIND_STRING = 24,
+ KIND_STRUCT = 25,
+ KIND_UNSAFEPOINTER = 26,
+ KIND_LLDB_VOID, // Extension for LLDB, not used by go runtime.
+ KIND_MASK = (1 << 5) - 1,
+ KIND_DIRECT_IFACE = 1 << 5
+ };
+ GoType(int kind, const ConstString &name)
+ : m_kind(kind & KIND_MASK), m_name(name) {
+ if (m_kind == KIND_FUNC)
+ m_kind = KIND_FUNC;
+ }
+ virtual ~GoType() {}
+
+ int GetGoKind() const { return m_kind; }
+ const ConstString &GetName() const { return m_name; }
+ virtual CompilerType GetElementType() const { return CompilerType(); }
+
+ bool IsTypedef() const {
+ switch (m_kind) {
+ case KIND_CHAN:
+ case KIND_MAP:
+ case KIND_INTERFACE:
+ return true;
+ default:
+ return false;
+ }
+ }
+
+ GoArray *GetArray();
+ GoFunction *GetFunction();
+ GoStruct *GetStruct();
+
+private:
+ int m_kind;
+ ConstString m_name;
+ GoType(const GoType &) = delete;
+ const GoType &operator=(const GoType &) = delete;
};
-class GoElem : public GoType
-{
- public:
- GoElem(int kind, const ConstString &name, const CompilerType &elem)
- : GoType(kind, name)
- , m_elem(elem)
- {
- }
- virtual CompilerType
- GetElementType() const
- {
- return m_elem;
- }
+class GoElem : public GoType {
+public:
+ GoElem(int kind, const ConstString &name, const CompilerType &elem)
+ : GoType(kind, name), m_elem(elem) {}
+ virtual CompilerType GetElementType() const { return m_elem; }
+
+private:
+ // TODO: should we store this differently?
+ CompilerType m_elem;
- private:
- // TODO: should we store this differently?
- CompilerType m_elem;
-
- GoElem(const GoElem &) = delete;
- const GoElem &operator=(const GoElem &) = delete;
+ GoElem(const GoElem &) = delete;
+ const GoElem &operator=(const GoElem &) = delete;
};
-class GoArray : public GoElem
-{
- public:
- GoArray(const ConstString &name, uint64_t length, const CompilerType &elem)
- : GoElem(KIND_ARRAY, name, elem)
- , m_length(length)
- {
- }
-
- uint64_t
- GetLength() const
- {
- return m_length;
- }
-
- private:
- uint64_t m_length;
- GoArray(const GoArray &) = delete;
- const GoArray &operator=(const GoArray &) = delete;
+class GoArray : public GoElem {
+public:
+ GoArray(const ConstString &name, uint64_t length, const CompilerType &elem)
+ : GoElem(KIND_ARRAY, name, elem), m_length(length) {}
+
+ uint64_t GetLength() const { return m_length; }
+
+private:
+ uint64_t m_length;
+ GoArray(const GoArray &) = delete;
+ const GoArray &operator=(const GoArray &) = delete;
};
-class GoFunction : public GoType
-{
- public:
- GoFunction(const ConstString &name, bool is_variadic)
- : GoType(KIND_FUNC, name)
- , m_is_variadic(is_variadic)
- {
- }
-
- bool
- IsVariadic() const
- {
- return m_is_variadic;
- }
-
- private:
- bool m_is_variadic;
- GoFunction(const GoFunction &) = delete;
- const GoFunction &operator=(const GoFunction &) = delete;
+class GoFunction : public GoType {
+public:
+ GoFunction(const ConstString &name, bool is_variadic)
+ : GoType(KIND_FUNC, name), m_is_variadic(is_variadic) {}
+
+ bool IsVariadic() const { return m_is_variadic; }
+
+private:
+ bool m_is_variadic;
+ GoFunction(const GoFunction &) = delete;
+ const GoFunction &operator=(const GoFunction &) = delete;
};
-class GoStruct : public GoType
-{
- public:
- struct Field
- {
- Field(const ConstString &name, const CompilerType &type, uint64_t offset)
- : m_name(name)
- , m_type(type)
- , m_byte_offset(offset)
- {
- }
- ConstString m_name;
- CompilerType m_type;
- uint64_t m_byte_offset;
- };
-
- GoStruct(int kind, const ConstString &name, int64_t byte_size)
- : GoType(kind == 0 ? KIND_STRUCT : kind, name), m_is_complete(false), m_byte_size(byte_size)
- {
- }
-
- uint32_t
- GetNumFields() const
- {
- return m_fields.size();
- }
-
- const Field *
- GetField(uint32_t i) const
- {
- if (i < m_fields.size())
- return &m_fields[i];
- return nullptr;
- }
+class GoStruct : public GoType {
+public:
+ struct Field {
+ Field(const ConstString &name, const CompilerType &type, uint64_t offset)
+ : m_name(name), m_type(type), m_byte_offset(offset) {}
+ ConstString m_name;
+ CompilerType m_type;
+ uint64_t m_byte_offset;
+ };
+
+ GoStruct(int kind, const ConstString &name, int64_t byte_size)
+ : GoType(kind == 0 ? KIND_STRUCT : kind, name), m_is_complete(false),
+ m_byte_size(byte_size) {}
+
+ uint32_t GetNumFields() const { return m_fields.size(); }
+
+ const Field *GetField(uint32_t i) const {
+ if (i < m_fields.size())
+ return &m_fields[i];
+ return nullptr;
+ }
- void
- AddField(const ConstString &name, const CompilerType &type, uint64_t offset)
- {
- m_fields.push_back(Field(name, type, offset));
- }
+ void AddField(const ConstString &name, const CompilerType &type,
+ uint64_t offset) {
+ m_fields.push_back(Field(name, type, offset));
+ }
- bool
- IsComplete() const
- {
- return m_is_complete;
- }
+ bool IsComplete() const { return m_is_complete; }
- void
- SetComplete()
- {
- m_is_complete = true;
- }
+ void SetComplete() { m_is_complete = true; }
- int64_t
- GetByteSize() const
- {
- return m_byte_size;
- }
+ int64_t GetByteSize() const { return m_byte_size; }
- private:
- bool m_is_complete;
- int64_t m_byte_size;
- std::vector<Field> m_fields;
+private:
+ bool m_is_complete;
+ int64_t m_byte_size;
+ std::vector<Field> m_fields;
- GoStruct(const GoStruct &) = delete;
- const GoStruct &operator=(const GoStruct &) = delete;
+ GoStruct(const GoStruct &) = delete;
+ const GoStruct &operator=(const GoStruct &) = delete;
};
-GoArray *
-GoType::GetArray()
-{
- if (m_kind == KIND_ARRAY)
- {
- return static_cast<GoArray *>(this);
- }
- return nullptr;
-}
-
-GoFunction *
-GoType::GetFunction()
-{
- if (m_kind == KIND_FUNC)
- {
- return static_cast<GoFunction *>(this);
- }
- return nullptr;
-}
-
-GoStruct *
-GoType::GetStruct()
-{
- switch (m_kind)
- {
- case KIND_STRING:
- case KIND_STRUCT:
- case KIND_SLICE:
- return static_cast<GoStruct *>(this);
- }
- return nullptr;
+GoArray *GoType::GetArray() {
+ if (m_kind == KIND_ARRAY) {
+ return static_cast<GoArray *>(this);
+ }
+ return nullptr;
+}
+
+GoFunction *GoType::GetFunction() {
+ if (m_kind == KIND_FUNC) {
+ return static_cast<GoFunction *>(this);
+ }
+ return nullptr;
+}
+
+GoStruct *GoType::GetStruct() {
+ switch (m_kind) {
+ case KIND_STRING:
+ case KIND_STRUCT:
+ case KIND_SLICE:
+ return static_cast<GoStruct *>(this);
+ }
+ return nullptr;
}
} // namespace lldb_private
using namespace lldb_private;
GoASTContext::GoASTContext()
- : TypeSystem(eKindGo)
- , m_pointer_byte_size(0)
- , m_int_byte_size(0)
- , m_types(new TypeMap)
-{
-}
-GoASTContext::~GoASTContext()
-{
-}
+ : TypeSystem(eKindGo), m_pointer_byte_size(0), m_int_byte_size(0),
+ m_types(new TypeMap) {}
+GoASTContext::~GoASTContext() {}
//------------------------------------------------------------------
// PluginInterface functions
//------------------------------------------------------------------
-ConstString
-GoASTContext::GetPluginNameStatic()
-{
- return ConstString("go");
-}
+ConstString GoASTContext::GetPluginNameStatic() { return ConstString("go"); }
-ConstString
-GoASTContext::GetPluginName()
-{
- return GoASTContext::GetPluginNameStatic();
+ConstString GoASTContext::GetPluginName() {
+ return GoASTContext::GetPluginNameStatic();
}
-uint32_t
-GoASTContext::GetPluginVersion()
-{
- return 1;
-}
+uint32_t GoASTContext::GetPluginVersion() { return 1; }
-lldb::TypeSystemSP
-GoASTContext::CreateInstance (lldb::LanguageType language, Module *module, Target *target)
-{
- if (language == eLanguageTypeGo)
- {
- ArchSpec arch;
- std::shared_ptr<GoASTContext> go_ast_sp;
- if (module)
- {
- arch = module->GetArchitecture();
- go_ast_sp = std::shared_ptr<GoASTContext>(new GoASTContext);
- }
- else if (target)
- {
- arch = target->GetArchitecture();
- go_ast_sp = std::shared_ptr<GoASTContextForExpr>(new GoASTContextForExpr(target->shared_from_this()));
- }
+lldb::TypeSystemSP GoASTContext::CreateInstance(lldb::LanguageType language,
+ Module *module,
+ Target *target) {
+ if (language == eLanguageTypeGo) {
+ ArchSpec arch;
+ std::shared_ptr<GoASTContext> go_ast_sp;
+ if (module) {
+ arch = module->GetArchitecture();
+ go_ast_sp = std::shared_ptr<GoASTContext>(new GoASTContext);
+ } else if (target) {
+ arch = target->GetArchitecture();
+ go_ast_sp = std::shared_ptr<GoASTContextForExpr>(
+ new GoASTContextForExpr(target->shared_from_this()));
+ }
- if (arch.IsValid())
- {
- go_ast_sp->SetAddressByteSize(arch.GetAddressByteSize());
- return go_ast_sp;
- }
+ if (arch.IsValid()) {
+ go_ast_sp->SetAddressByteSize(arch.GetAddressByteSize());
+ return go_ast_sp;
}
- return lldb::TypeSystemSP();
+ }
+ return lldb::TypeSystemSP();
}
-void
-GoASTContext::EnumerateSupportedLanguages(std::set<lldb::LanguageType> &languages_for_types, std::set<lldb::LanguageType> &languages_for_expressions)
-{
- static std::vector<lldb::LanguageType> s_supported_languages_for_types({
- lldb::eLanguageTypeGo});
-
- static std::vector<lldb::LanguageType> s_supported_languages_for_expressions({});
-
- languages_for_types.insert(s_supported_languages_for_types.begin(), s_supported_languages_for_types.end());
- languages_for_expressions.insert(s_supported_languages_for_expressions.begin(), s_supported_languages_for_expressions.end());
-}
+void GoASTContext::EnumerateSupportedLanguages(
+ std::set<lldb::LanguageType> &languages_for_types,
+ std::set<lldb::LanguageType> &languages_for_expressions) {
+ static std::vector<lldb::LanguageType> s_supported_languages_for_types(
+ {lldb::eLanguageTypeGo});
+ static std::vector<lldb::LanguageType> s_supported_languages_for_expressions(
+ {});
-void
-GoASTContext::Initialize()
-{
- PluginManager::RegisterPlugin (GetPluginNameStatic(),
- "AST context plug-in",
- CreateInstance,
- EnumerateSupportedLanguages);
-}
-
-void
-GoASTContext::Terminate()
-{
- PluginManager::UnregisterPlugin (CreateInstance);
+ languages_for_types.insert(s_supported_languages_for_types.begin(),
+ s_supported_languages_for_types.end());
+ languages_for_expressions.insert(
+ s_supported_languages_for_expressions.begin(),
+ s_supported_languages_for_expressions.end());
}
+void GoASTContext::Initialize() {
+ PluginManager::RegisterPlugin(GetPluginNameStatic(), "AST context plug-in",
+ CreateInstance, EnumerateSupportedLanguages);
+}
+
+void GoASTContext::Terminate() {
+ PluginManager::UnregisterPlugin(CreateInstance);
+}
//----------------------------------------------------------------------
// Tests
//----------------------------------------------------------------------
-bool
-GoASTContext::IsArrayType(lldb::opaque_compiler_type_t type, CompilerType *element_type, uint64_t *size, bool *is_incomplete)
-{
- if (element_type)
- element_type->Clear();
+bool GoASTContext::IsArrayType(lldb::opaque_compiler_type_t type,
+ CompilerType *element_type, uint64_t *size,
+ bool *is_incomplete) {
+ if (element_type)
+ element_type->Clear();
+ if (size)
+ *size = 0;
+ if (is_incomplete)
+ *is_incomplete = false;
+ GoArray *array = static_cast<GoType *>(type)->GetArray();
+ if (array) {
if (size)
- *size = 0;
- if (is_incomplete)
- *is_incomplete = false;
- GoArray *array = static_cast<GoType *>(type)->GetArray();
- if (array)
- {
- if (size)
- *size = array->GetLength();
- if (element_type)
- *element_type = array->GetElementType();
- return true;
- }
- return false;
-}
-
-bool
-GoASTContext::IsVectorType(lldb::opaque_compiler_type_t type, CompilerType *element_type, uint64_t *size)
-{
+ *size = array->GetLength();
if (element_type)
- element_type->Clear();
- if (size)
- *size = 0;
- return false;
-}
-
-bool
-GoASTContext::IsAggregateType(lldb::opaque_compiler_type_t type)
-{
- int kind = static_cast<GoType *>(type)->GetGoKind();
- if (kind < GoType::KIND_ARRAY)
- return false;
- if (kind == GoType::KIND_PTR)
- return false;
- if (kind == GoType::KIND_CHAN)
- return false;
- if (kind == GoType::KIND_MAP)
- return false;
- if (kind == GoType::KIND_STRING)
- return false;
- if (kind == GoType::KIND_UNSAFEPOINTER)
- return false;
+ *element_type = array->GetElementType();
return true;
+ }
+ return false;
}
-bool
-GoASTContext::IsBeingDefined(lldb::opaque_compiler_type_t type)
-{
+bool GoASTContext::IsVectorType(lldb::opaque_compiler_type_t type,
+ CompilerType *element_type, uint64_t *size) {
+ if (element_type)
+ element_type->Clear();
+ if (size)
+ *size = 0;
+ return false;
+}
+
+bool GoASTContext::IsAggregateType(lldb::opaque_compiler_type_t type) {
+ int kind = static_cast<GoType *>(type)->GetGoKind();
+ if (kind < GoType::KIND_ARRAY)
return false;
-}
-
-bool
-GoASTContext::IsCharType(lldb::opaque_compiler_type_t type)
-{
- // Go's DWARF doesn't distinguish between rune and int32.
+ if (kind == GoType::KIND_PTR)
return false;
-}
-
-bool
-GoASTContext::IsCompleteType(lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return false;
- GoType *t = static_cast<GoType *>(type);
- if (GoStruct *s = t->GetStruct())
- return s->IsComplete();
- if (t->IsTypedef() || t->GetGoKind() == GoType::KIND_PTR)
- return t->GetElementType().IsCompleteType();
- return true;
-}
-
-bool
-GoASTContext::IsConst(lldb::opaque_compiler_type_t type)
-{
+ if (kind == GoType::KIND_CHAN)
+ return false;
+ if (kind == GoType::KIND_MAP)
+ return false;
+ if (kind == GoType::KIND_STRING)
return false;
+ if (kind == GoType::KIND_UNSAFEPOINTER)
+ return false;
+ return true;
}
-bool
-GoASTContext::IsCStringType(lldb::opaque_compiler_type_t type, uint32_t &length)
-{
- return false;
+bool GoASTContext::IsBeingDefined(lldb::opaque_compiler_type_t type) {
+ return false;
}
-bool
-GoASTContext::IsDefined(lldb::opaque_compiler_type_t type)
-{
- return type != nullptr;
+bool GoASTContext::IsCharType(lldb::opaque_compiler_type_t type) {
+ // Go's DWARF doesn't distinguish between rune and int32.
+ return false;
}
-bool
-GoASTContext::IsFloatingPointType(lldb::opaque_compiler_type_t type, uint32_t &count, bool &is_complex)
-{
- int kind = static_cast<GoType *>(type)->GetGoKind();
- if (kind >= GoType::KIND_FLOAT32 && kind <= GoType::KIND_COMPLEX128)
- {
- if (kind >= GoType::KIND_COMPLEX64)
- {
- is_complex = true;
- count = 2;
- }
- else
- {
- is_complex = false;
- count = 1;
- }
- return true;
- }
- count = 0;
- is_complex = false;
+bool GoASTContext::IsCompleteType(lldb::opaque_compiler_type_t type) {
+ if (!type)
return false;
+ GoType *t = static_cast<GoType *>(type);
+ if (GoStruct *s = t->GetStruct())
+ return s->IsComplete();
+ if (t->IsTypedef() || t->GetGoKind() == GoType::KIND_PTR)
+ return t->GetElementType().IsCompleteType();
+ return true;
+}
+
+bool GoASTContext::IsConst(lldb::opaque_compiler_type_t type) { return false; }
+
+bool GoASTContext::IsCStringType(lldb::opaque_compiler_type_t type,
+ uint32_t &length) {
+ return false;
+}
+
+bool GoASTContext::IsDefined(lldb::opaque_compiler_type_t type) {
+ return type != nullptr;
+}
+
+bool GoASTContext::IsFloatingPointType(lldb::opaque_compiler_type_t type,
+ uint32_t &count, bool &is_complex) {
+ int kind = static_cast<GoType *>(type)->GetGoKind();
+ if (kind >= GoType::KIND_FLOAT32 && kind <= GoType::KIND_COMPLEX128) {
+ if (kind >= GoType::KIND_COMPLEX64) {
+ is_complex = true;
+ count = 2;
+ } else {
+ is_complex = false;
+ count = 1;
+ }
+ return true;
+ }
+ count = 0;
+ is_complex = false;
+ return false;
}
-bool
-GoASTContext::IsFunctionType(lldb::opaque_compiler_type_t type, bool *is_variadic_ptr)
-{
- GoFunction *func = static_cast<GoType *>(type)->GetFunction();
- if (func)
- {
- if (is_variadic_ptr)
- *is_variadic_ptr = func->IsVariadic();
- return true;
- }
+bool GoASTContext::IsFunctionType(lldb::opaque_compiler_type_t type,
+ bool *is_variadic_ptr) {
+ GoFunction *func = static_cast<GoType *>(type)->GetFunction();
+ if (func) {
if (is_variadic_ptr)
- *is_variadic_ptr = false;
- return false;
+ *is_variadic_ptr = func->IsVariadic();
+ return true;
+ }
+ if (is_variadic_ptr)
+ *is_variadic_ptr = false;
+ return false;
}
-uint32_t
-GoASTContext::IsHomogeneousAggregate(lldb::opaque_compiler_type_t type, CompilerType *base_type_ptr)
-{
- return false;
+uint32_t GoASTContext::IsHomogeneousAggregate(lldb::opaque_compiler_type_t type,
+ CompilerType *base_type_ptr) {
+ return false;
}
size_t
-GoASTContext::GetNumberOfFunctionArguments(lldb::opaque_compiler_type_t type)
-{
- return 0;
+GoASTContext::GetNumberOfFunctionArguments(lldb::opaque_compiler_type_t type) {
+ return 0;
}
CompilerType
-GoASTContext::GetFunctionArgumentAtIndex(lldb::opaque_compiler_type_t type, const size_t index)
-{
- return CompilerType();
+GoASTContext::GetFunctionArgumentAtIndex(lldb::opaque_compiler_type_t type,
+ const size_t index) {
+ return CompilerType();
}
-bool
-GoASTContext::IsFunctionPointerType(lldb::opaque_compiler_type_t type)
-{
- return IsFunctionType(type);
+bool GoASTContext::IsFunctionPointerType(lldb::opaque_compiler_type_t type) {
+ return IsFunctionType(type);
}
-bool
-GoASTContext::IsBlockPointerType (lldb::opaque_compiler_type_t type, CompilerType *function_pointer_type_ptr)
-{
- return false;
+bool GoASTContext::IsBlockPointerType(lldb::opaque_compiler_type_t type,
+ CompilerType *function_pointer_type_ptr) {
+ return false;
}
-bool
-GoASTContext::IsIntegerType(lldb::opaque_compiler_type_t type, bool &is_signed)
-{
- is_signed = false;
- // TODO: Is bool an integer?
- if (type)
- {
- int kind = static_cast<GoType *>(type)->GetGoKind();
- if (kind <= GoType::KIND_UINTPTR)
- {
- is_signed = (kind != GoType::KIND_BOOL) & (kind <= GoType::KIND_INT64);
- return true;
- }
+bool GoASTContext::IsIntegerType(lldb::opaque_compiler_type_t type,
+ bool &is_signed) {
+ is_signed = false;
+ // TODO: Is bool an integer?
+ if (type) {
+ int kind = static_cast<GoType *>(type)->GetGoKind();
+ if (kind <= GoType::KIND_UINTPTR) {
+ is_signed = (kind != GoType::KIND_BOOL) & (kind <= GoType::KIND_INT64);
+ return true;
}
- return false;
+ }
+ return false;
}
-bool
-GoASTContext::IsPolymorphicClass(lldb::opaque_compiler_type_t type)
-{
- return false;
+bool GoASTContext::IsPolymorphicClass(lldb::opaque_compiler_type_t type) {
+ return false;
}
-bool
-GoASTContext::IsPossibleDynamicType(lldb::opaque_compiler_type_t type,
- CompilerType *target_type, // Can pass NULL
- bool check_cplusplus, bool check_objc)
-{
- if (target_type)
- target_type->Clear();
- if (type)
- return static_cast<GoType *>(type)->GetGoKind() == GoType::KIND_INTERFACE;
- return false;
+bool GoASTContext::IsPossibleDynamicType(
+ lldb::opaque_compiler_type_t type,
+ CompilerType *target_type, // Can pass NULL
+ bool check_cplusplus, bool check_objc) {
+ if (target_type)
+ target_type->Clear();
+ if (type)
+ return static_cast<GoType *>(type)->GetGoKind() == GoType::KIND_INTERFACE;
+ return false;
}
-bool
-GoASTContext::IsRuntimeGeneratedType(lldb::opaque_compiler_type_t type)
-{
- return false;
+bool GoASTContext::IsRuntimeGeneratedType(lldb::opaque_compiler_type_t type) {
+ return false;
}
-bool
-GoASTContext::IsPointerType(lldb::opaque_compiler_type_t type, CompilerType *pointee_type)
-{
- if (!type)
- return false;
- GoType *t = static_cast<GoType *>(type);
- if (pointee_type)
- {
- *pointee_type = t->GetElementType();
- }
- switch (t->GetGoKind())
- {
- case GoType::KIND_PTR:
- case GoType::KIND_UNSAFEPOINTER:
- case GoType::KIND_CHAN:
- case GoType::KIND_MAP:
- // TODO: is function a pointer?
- return true;
- default:
- return false;
- }
+bool GoASTContext::IsPointerType(lldb::opaque_compiler_type_t type,
+ CompilerType *pointee_type) {
+ if (!type)
+ return false;
+ GoType *t = static_cast<GoType *>(type);
+ if (pointee_type) {
+ *pointee_type = t->GetElementType();
+ }
+ switch (t->GetGoKind()) {
+ case GoType::KIND_PTR:
+ case GoType::KIND_UNSAFEPOINTER:
+ case GoType::KIND_CHAN:
+ case GoType::KIND_MAP:
+ // TODO: is function a pointer?
+ return true;
+ default:
+ return false;
+ }
}
-bool
-GoASTContext::IsPointerOrReferenceType(lldb::opaque_compiler_type_t type, CompilerType *pointee_type)
-{
- return IsPointerType(type, pointee_type);
+bool GoASTContext::IsPointerOrReferenceType(lldb::opaque_compiler_type_t type,
+ CompilerType *pointee_type) {
+ return IsPointerType(type, pointee_type);
}
-bool
-GoASTContext::IsReferenceType(lldb::opaque_compiler_type_t type, CompilerType *pointee_type, bool *is_rvalue)
-{
- return false;
+bool GoASTContext::IsReferenceType(lldb::opaque_compiler_type_t type,
+ CompilerType *pointee_type,
+ bool *is_rvalue) {
+ return false;
}
-bool
-GoASTContext::IsScalarType(lldb::opaque_compiler_type_t type)
-{
- return !IsAggregateType(type);
+bool GoASTContext::IsScalarType(lldb::opaque_compiler_type_t type) {
+ return !IsAggregateType(type);
}
-bool
-GoASTContext::IsTypedefType(lldb::opaque_compiler_type_t type)
-{
- if (type)
- return static_cast<GoType *>(type)->IsTypedef();
- return false;
+bool GoASTContext::IsTypedefType(lldb::opaque_compiler_type_t type) {
+ if (type)
+ return static_cast<GoType *>(type)->IsTypedef();
+ return false;
}
-bool
-GoASTContext::IsVoidType(lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return false;
- return static_cast<GoType *>(type)->GetGoKind() == GoType::KIND_LLDB_VOID;
+bool GoASTContext::IsVoidType(lldb::opaque_compiler_type_t type) {
+ if (!type)
+ return false;
+ return static_cast<GoType *>(type)->GetGoKind() == GoType::KIND_LLDB_VOID;
}
-bool
-GoASTContext::SupportsLanguage (lldb::LanguageType language)
-{
- return language == eLanguageTypeGo;
+bool GoASTContext::SupportsLanguage(lldb::LanguageType language) {
+ return language == eLanguageTypeGo;
}
//----------------------------------------------------------------------
// Type Completion
//----------------------------------------------------------------------
-bool
-GoASTContext::GetCompleteType(lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return false;
- GoType *t = static_cast<GoType *>(type);
- if (t->IsTypedef() || t->GetGoKind() == GoType::KIND_PTR || t->GetArray())
- return t->GetElementType().GetCompleteType();
- if (GoStruct *s = t->GetStruct())
- {
- if (s->IsComplete())
- return true;
- CompilerType compiler_type(this, s);
- SymbolFile *symbols = GetSymbolFile();
- return symbols && symbols->CompleteType(compiler_type);
- }
- return true;
+bool GoASTContext::GetCompleteType(lldb::opaque_compiler_type_t type) {
+ if (!type)
+ return false;
+ GoType *t = static_cast<GoType *>(type);
+ if (t->IsTypedef() || t->GetGoKind() == GoType::KIND_PTR || t->GetArray())
+ return t->GetElementType().GetCompleteType();
+ if (GoStruct *s = t->GetStruct()) {
+ if (s->IsComplete())
+ return true;
+ CompilerType compiler_type(this, s);
+ SymbolFile *symbols = GetSymbolFile();
+ return symbols && symbols->CompleteType(compiler_type);
+ }
+ return true;
}
//----------------------------------------------------------------------
// AST related queries
//----------------------------------------------------------------------
-uint32_t
-GoASTContext::GetPointerByteSize()
-{
- return m_pointer_byte_size;
-}
+uint32_t GoASTContext::GetPointerByteSize() { return m_pointer_byte_size; }
//----------------------------------------------------------------------
// Accessors
//----------------------------------------------------------------------
-ConstString
-GoASTContext::GetTypeName(lldb::opaque_compiler_type_t type)
-{
- if (type)
- return static_cast<GoType *>(type)->GetName();
- return ConstString();
+ConstString GoASTContext::GetTypeName(lldb::opaque_compiler_type_t type) {
+ if (type)
+ return static_cast<GoType *>(type)->GetName();
+ return ConstString();
}
uint32_t
-GoASTContext::GetTypeInfo(lldb::opaque_compiler_type_t type, CompilerType *pointee_or_element_compiler_type)
-{
- if (pointee_or_element_compiler_type)
- pointee_or_element_compiler_type->Clear();
- if (!type)
- return 0;
- GoType *t = static_cast<GoType *>(type);
- if (pointee_or_element_compiler_type)
- *pointee_or_element_compiler_type = t->GetElementType();
- int kind = t->GetGoKind();
- if (kind == GoType::KIND_ARRAY)
- return eTypeHasChildren | eTypeIsArray;
- if (kind < GoType::KIND_ARRAY)
- {
- uint32_t builtin_type_flags = eTypeIsBuiltIn | eTypeHasValue;
- if (kind < GoType::KIND_FLOAT32)
- {
- builtin_type_flags |= eTypeIsInteger | eTypeIsScalar;
- if (kind >= GoType::KIND_INT && kind <= GoType::KIND_INT64)
- builtin_type_flags |= eTypeIsSigned;
- }
- else
- {
- builtin_type_flags |= eTypeIsFloat;
- if (kind < GoType::KIND_COMPLEX64)
- builtin_type_flags |= eTypeIsComplex;
- else
- builtin_type_flags |= eTypeIsScalar;
- }
- return builtin_type_flags;
- }
- if (kind == GoType::KIND_STRING)
- return eTypeHasValue | eTypeIsBuiltIn;
- if (kind == GoType::KIND_FUNC)
- return eTypeIsFuncPrototype | eTypeHasValue;
- if (IsPointerType(type))
- return eTypeIsPointer | eTypeHasValue | eTypeHasChildren;
- if (kind == GoType::KIND_LLDB_VOID)
- return 0;
- return eTypeHasChildren | eTypeIsStructUnion;
-}
-
-lldb::TypeClass
-GoASTContext::GetTypeClass(lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return eTypeClassInvalid;
- int kind = static_cast<GoType *>(type)->GetGoKind();
- if (kind == GoType::KIND_FUNC)
- return eTypeClassFunction;
- if (IsPointerType(type))
- return eTypeClassPointer;
- if (kind < GoType::KIND_COMPLEX64)
- return eTypeClassBuiltin;
- if (kind <= GoType::KIND_COMPLEX128)
- return eTypeClassComplexFloat;
- if (kind == GoType::KIND_LLDB_VOID)
- return eTypeClassInvalid;
- return eTypeClassStruct;
+GoASTContext::GetTypeInfo(lldb::opaque_compiler_type_t type,
+ CompilerType *pointee_or_element_compiler_type) {
+ if (pointee_or_element_compiler_type)
+ pointee_or_element_compiler_type->Clear();
+ if (!type)
+ return 0;
+ GoType *t = static_cast<GoType *>(type);
+ if (pointee_or_element_compiler_type)
+ *pointee_or_element_compiler_type = t->GetElementType();
+ int kind = t->GetGoKind();
+ if (kind == GoType::KIND_ARRAY)
+ return eTypeHasChildren | eTypeIsArray;
+ if (kind < GoType::KIND_ARRAY) {
+ uint32_t builtin_type_flags = eTypeIsBuiltIn | eTypeHasValue;
+ if (kind < GoType::KIND_FLOAT32) {
+ builtin_type_flags |= eTypeIsInteger | eTypeIsScalar;
+ if (kind >= GoType::KIND_INT && kind <= GoType::KIND_INT64)
+ builtin_type_flags |= eTypeIsSigned;
+ } else {
+ builtin_type_flags |= eTypeIsFloat;
+ if (kind < GoType::KIND_COMPLEX64)
+ builtin_type_flags |= eTypeIsComplex;
+ else
+ builtin_type_flags |= eTypeIsScalar;
+ }
+ return builtin_type_flags;
+ }
+ if (kind == GoType::KIND_STRING)
+ return eTypeHasValue | eTypeIsBuiltIn;
+ if (kind == GoType::KIND_FUNC)
+ return eTypeIsFuncPrototype | eTypeHasValue;
+ if (IsPointerType(type))
+ return eTypeIsPointer | eTypeHasValue | eTypeHasChildren;
+ if (kind == GoType::KIND_LLDB_VOID)
+ return 0;
+ return eTypeHasChildren | eTypeIsStructUnion;
+}
+
+lldb::TypeClass GoASTContext::GetTypeClass(lldb::opaque_compiler_type_t type) {
+ if (!type)
+ return eTypeClassInvalid;
+ int kind = static_cast<GoType *>(type)->GetGoKind();
+ if (kind == GoType::KIND_FUNC)
+ return eTypeClassFunction;
+ if (IsPointerType(type))
+ return eTypeClassPointer;
+ if (kind < GoType::KIND_COMPLEX64)
+ return eTypeClassBuiltin;
+ if (kind <= GoType::KIND_COMPLEX128)
+ return eTypeClassComplexFloat;
+ if (kind == GoType::KIND_LLDB_VOID)
+ return eTypeClassInvalid;
+ return eTypeClassStruct;
}
lldb::BasicType
-GoASTContext::GetBasicTypeEnumeration(lldb::opaque_compiler_type_t type)
-{
- ConstString name = GetTypeName(type);
- if (name)
- {
- typedef UniqueCStringMap<lldb::BasicType> TypeNameToBasicTypeMap;
- static TypeNameToBasicTypeMap g_type_map;
- static std::once_flag g_once_flag;
- std::call_once(g_once_flag, [](){
- // "void"
- g_type_map.Append(ConstString("void").GetCString(), eBasicTypeVoid);
- // "int"
- g_type_map.Append(ConstString("int").GetCString(), eBasicTypeInt);
- g_type_map.Append(ConstString("uint").GetCString(), eBasicTypeUnsignedInt);
-
- // Miscellaneous
- g_type_map.Append(ConstString("bool").GetCString(), eBasicTypeBool);
-
- // Others. Should these map to C types?
- g_type_map.Append(ConstString("byte").GetCString(), eBasicTypeOther);
- g_type_map.Append(ConstString("uint8").GetCString(), eBasicTypeOther);
- g_type_map.Append(ConstString("uint16").GetCString(), eBasicTypeOther);
- g_type_map.Append(ConstString("uint32").GetCString(), eBasicTypeOther);
- g_type_map.Append(ConstString("uint64").GetCString(), eBasicTypeOther);
- g_type_map.Append(ConstString("int8").GetCString(), eBasicTypeOther);
- g_type_map.Append(ConstString("int16").GetCString(), eBasicTypeOther);
- g_type_map.Append(ConstString("int32").GetCString(), eBasicTypeOther);
- g_type_map.Append(ConstString("int64").GetCString(), eBasicTypeOther);
- g_type_map.Append(ConstString("float32").GetCString(), eBasicTypeOther);
- g_type_map.Append(ConstString("float64").GetCString(), eBasicTypeOther);
- g_type_map.Append(ConstString("uintptr").GetCString(), eBasicTypeOther);
-
- g_type_map.Sort();
- });
-
- return g_type_map.Find(name.GetCString(), eBasicTypeInvalid);
- }
- return eBasicTypeInvalid;
+GoASTContext::GetBasicTypeEnumeration(lldb::opaque_compiler_type_t type) {
+ ConstString name = GetTypeName(type);
+ if (name) {
+ typedef UniqueCStringMap<lldb::BasicType> TypeNameToBasicTypeMap;
+ static TypeNameToBasicTypeMap g_type_map;
+ static std::once_flag g_once_flag;
+ std::call_once(g_once_flag, []() {
+ // "void"
+ g_type_map.Append(ConstString("void").GetCString(), eBasicTypeVoid);
+ // "int"
+ g_type_map.Append(ConstString("int").GetCString(), eBasicTypeInt);
+ g_type_map.Append(ConstString("uint").GetCString(),
+ eBasicTypeUnsignedInt);
+
+ // Miscellaneous
+ g_type_map.Append(ConstString("bool").GetCString(), eBasicTypeBool);
+
+ // Others. Should these map to C types?
+ g_type_map.Append(ConstString("byte").GetCString(), eBasicTypeOther);
+ g_type_map.Append(ConstString("uint8").GetCString(), eBasicTypeOther);
+ g_type_map.Append(ConstString("uint16").GetCString(), eBasicTypeOther);
+ g_type_map.Append(ConstString("uint32").GetCString(), eBasicTypeOther);
+ g_type_map.Append(ConstString("uint64").GetCString(), eBasicTypeOther);
+ g_type_map.Append(ConstString("int8").GetCString(), eBasicTypeOther);
+ g_type_map.Append(ConstString("int16").GetCString(), eBasicTypeOther);
+ g_type_map.Append(ConstString("int32").GetCString(), eBasicTypeOther);
+ g_type_map.Append(ConstString("int64").GetCString(), eBasicTypeOther);
+ g_type_map.Append(ConstString("float32").GetCString(), eBasicTypeOther);
+ g_type_map.Append(ConstString("float64").GetCString(), eBasicTypeOther);
+ g_type_map.Append(ConstString("uintptr").GetCString(), eBasicTypeOther);
+
+ g_type_map.Sort();
+ });
+
+ return g_type_map.Find(name.GetCString(), eBasicTypeInvalid);
+ }
+ return eBasicTypeInvalid;
}
lldb::LanguageType
-GoASTContext::GetMinimumLanguage(lldb::opaque_compiler_type_t type)
-{
- return lldb::eLanguageTypeGo;
+GoASTContext::GetMinimumLanguage(lldb::opaque_compiler_type_t type) {
+ return lldb::eLanguageTypeGo;
}
-unsigned
-GoASTContext::GetTypeQualifiers(lldb::opaque_compiler_type_t type)
-{
- return 0;
+unsigned GoASTContext::GetTypeQualifiers(lldb::opaque_compiler_type_t type) {
+ return 0;
}
//----------------------------------------------------------------------
@@ -812,853 +641,806 @@ GoASTContext::GetTypeQualifiers(lldb::op
//----------------------------------------------------------------------
CompilerType
-GoASTContext::GetArrayElementType(lldb::opaque_compiler_type_t type, uint64_t *stride)
-{
- GoArray *array = static_cast<GoType *>(type)->GetArray();
- if (array)
- {
- if (stride)
- {
- *stride = array->GetElementType().GetByteSize(nullptr);
- }
- return array->GetElementType();
- }
- return CompilerType();
-}
-
-CompilerType
-GoASTContext::GetCanonicalType(lldb::opaque_compiler_type_t type)
-{
- GoType *t = static_cast<GoType *>(type);
- if (t->IsTypedef())
- return t->GetElementType();
- return CompilerType(this, type);
+GoASTContext::GetArrayElementType(lldb::opaque_compiler_type_t type,
+ uint64_t *stride) {
+ GoArray *array = static_cast<GoType *>(type)->GetArray();
+ if (array) {
+ if (stride) {
+ *stride = array->GetElementType().GetByteSize(nullptr);
+ }
+ return array->GetElementType();
+ }
+ return CompilerType();
+}
+
+CompilerType GoASTContext::GetCanonicalType(lldb::opaque_compiler_type_t type) {
+ GoType *t = static_cast<GoType *>(type);
+ if (t->IsTypedef())
+ return t->GetElementType();
+ return CompilerType(this, type);
}
CompilerType
-GoASTContext::GetFullyUnqualifiedType(lldb::opaque_compiler_type_t type)
-{
- return CompilerType(this, type);
+GoASTContext::GetFullyUnqualifiedType(lldb::opaque_compiler_type_t type) {
+ return CompilerType(this, type);
}
-// Returns -1 if this isn't a function of if the function doesn't have a prototype
+// Returns -1 if this isn't a function of if the function doesn't have a
+// prototype
// Returns a value >= 0 if there is a prototype.
-int
-GoASTContext::GetFunctionArgumentCount(lldb::opaque_compiler_type_t type)
-{
- return GetNumberOfFunctionArguments(type);
+int GoASTContext::GetFunctionArgumentCount(lldb::opaque_compiler_type_t type) {
+ return GetNumberOfFunctionArguments(type);
}
CompilerType
-GoASTContext::GetFunctionArgumentTypeAtIndex(lldb::opaque_compiler_type_t type, size_t idx)
-{
- return GetFunctionArgumentAtIndex(type, idx);
+GoASTContext::GetFunctionArgumentTypeAtIndex(lldb::opaque_compiler_type_t type,
+ size_t idx) {
+ return GetFunctionArgumentAtIndex(type, idx);
}
CompilerType
-GoASTContext::GetFunctionReturnType(lldb::opaque_compiler_type_t type)
-{
- CompilerType result;
- if (type)
- {
- GoType *t = static_cast<GoType *>(type);
- if (t->GetGoKind() == GoType::KIND_FUNC)
- result = t->GetElementType();
- }
- return result;
+GoASTContext::GetFunctionReturnType(lldb::opaque_compiler_type_t type) {
+ CompilerType result;
+ if (type) {
+ GoType *t = static_cast<GoType *>(type);
+ if (t->GetGoKind() == GoType::KIND_FUNC)
+ result = t->GetElementType();
+ }
+ return result;
}
-size_t
-GoASTContext::GetNumMemberFunctions(lldb::opaque_compiler_type_t type)
-{
- return 0;
+size_t GoASTContext::GetNumMemberFunctions(lldb::opaque_compiler_type_t type) {
+ return 0;
}
TypeMemberFunctionImpl
-GoASTContext::GetMemberFunctionAtIndex(lldb::opaque_compiler_type_t type, size_t idx)
-{
- return TypeMemberFunctionImpl();
+GoASTContext::GetMemberFunctionAtIndex(lldb::opaque_compiler_type_t type,
+ size_t idx) {
+ return TypeMemberFunctionImpl();
}
CompilerType
-GoASTContext::GetNonReferenceType(lldb::opaque_compiler_type_t type)
-{
- return CompilerType(this, type);
+GoASTContext::GetNonReferenceType(lldb::opaque_compiler_type_t type) {
+ return CompilerType(this, type);
}
-CompilerType
-GoASTContext::GetPointeeType(lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return CompilerType();
- return static_cast<GoType *>(type)->GetElementType();
+CompilerType GoASTContext::GetPointeeType(lldb::opaque_compiler_type_t type) {
+ if (!type)
+ return CompilerType();
+ return static_cast<GoType *>(type)->GetElementType();
}
-CompilerType
-GoASTContext::GetPointerType(lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return CompilerType();
- ConstString type_name = GetTypeName(type);
- ConstString pointer_name(std::string("*") + type_name.GetCString());
- GoType *pointer = (*m_types)[pointer_name].get();
- if (pointer == nullptr)
- {
- pointer = new GoElem(GoType::KIND_PTR, pointer_name, CompilerType(this, type));
- (*m_types)[pointer_name].reset(pointer);
- }
- return CompilerType(this, pointer);
+CompilerType GoASTContext::GetPointerType(lldb::opaque_compiler_type_t type) {
+ if (!type)
+ return CompilerType();
+ ConstString type_name = GetTypeName(type);
+ ConstString pointer_name(std::string("*") + type_name.GetCString());
+ GoType *pointer = (*m_types)[pointer_name].get();
+ if (pointer == nullptr) {
+ pointer =
+ new GoElem(GoType::KIND_PTR, pointer_name, CompilerType(this, type));
+ (*m_types)[pointer_name].reset(pointer);
+ }
+ return CompilerType(this, pointer);
}
// If the current object represents a typedef type, get the underlying type
-CompilerType
-GoASTContext::GetTypedefedType(lldb::opaque_compiler_type_t type)
-{
- if (IsTypedefType(type))
- return static_cast<GoType *>(type)->GetElementType();
- return CompilerType();
+CompilerType GoASTContext::GetTypedefedType(lldb::opaque_compiler_type_t type) {
+ if (IsTypedefType(type))
+ return static_cast<GoType *>(type)->GetElementType();
+ return CompilerType();
}
//----------------------------------------------------------------------
// Create related types using the current type's AST
//----------------------------------------------------------------------
-CompilerType
-GoASTContext::GetBasicTypeFromAST(lldb::BasicType basic_type)
-{
- return CompilerType();
+CompilerType GoASTContext::GetBasicTypeFromAST(lldb::BasicType basic_type) {
+ return CompilerType();
}
CompilerType
-GoASTContext::GetBuiltinTypeForEncodingAndBitSize (lldb::Encoding encoding,
- size_t bit_size)
-{
- return CompilerType();
+GoASTContext::GetBuiltinTypeForEncodingAndBitSize(lldb::Encoding encoding,
+ size_t bit_size) {
+ return CompilerType();
}
-
//----------------------------------------------------------------------
// Exploring the type
//----------------------------------------------------------------------
-uint64_t
-GoASTContext::GetBitSize(lldb::opaque_compiler_type_t type, ExecutionContextScope *exe_scope)
-{
- if (!type)
- return 0;
- if (!GetCompleteType(type))
- return 0;
- GoType *t = static_cast<GoType *>(type);
- GoArray *array = nullptr;
- switch (t->GetGoKind())
- {
- case GoType::KIND_BOOL:
- case GoType::KIND_INT8:
- case GoType::KIND_UINT8:
- return 8;
- case GoType::KIND_INT16:
- case GoType::KIND_UINT16:
- return 16;
- case GoType::KIND_INT32:
- case GoType::KIND_UINT32:
- case GoType::KIND_FLOAT32:
- return 32;
- case GoType::KIND_INT64:
- case GoType::KIND_UINT64:
- case GoType::KIND_FLOAT64:
- case GoType::KIND_COMPLEX64:
- return 64;
- case GoType::KIND_COMPLEX128:
- return 128;
- case GoType::KIND_INT:
- case GoType::KIND_UINT:
- return m_int_byte_size * 8;
- case GoType::KIND_UINTPTR:
- case GoType::KIND_FUNC: // I assume this is a pointer?
- case GoType::KIND_CHAN:
- case GoType::KIND_PTR:
- case GoType::KIND_UNSAFEPOINTER:
- case GoType::KIND_MAP:
- return m_pointer_byte_size * 8;
- case GoType::KIND_ARRAY:
- array = t->GetArray();
- return array->GetLength() * array->GetElementType().GetBitSize(exe_scope);
- case GoType::KIND_INTERFACE:
- return t->GetElementType().GetBitSize(exe_scope);
- case GoType::KIND_SLICE:
- case GoType::KIND_STRING:
- case GoType::KIND_STRUCT:
- return t->GetStruct()->GetByteSize() * 8;
- default:
- assert(false);
- }
+uint64_t GoASTContext::GetBitSize(lldb::opaque_compiler_type_t type,
+ ExecutionContextScope *exe_scope) {
+ if (!type)
return 0;
-}
-
-lldb::Encoding
-GoASTContext::GetEncoding(lldb::opaque_compiler_type_t type, uint64_t &count)
-{
- count = 1;
- bool is_signed;
- if (IsIntegerType(type, is_signed))
- return is_signed ? lldb::eEncodingSint : eEncodingUint;
- bool is_complex;
- uint32_t complex_count;
- if (IsFloatingPointType(type, complex_count, is_complex))
- {
- count = complex_count;
- return eEncodingIEEE754;
- }
- if (IsPointerType(type))
- return eEncodingUint;
- return eEncodingInvalid;
-}
-
-lldb::Format
-GoASTContext::GetFormat(lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return eFormatDefault;
- switch (static_cast<GoType *>(type)->GetGoKind())
- {
- case GoType::KIND_BOOL:
- return eFormatBoolean;
- case GoType::KIND_INT:
- case GoType::KIND_INT8:
- case GoType::KIND_INT16:
- case GoType::KIND_INT32:
- case GoType::KIND_INT64:
- return eFormatDecimal;
- case GoType::KIND_UINT:
- case GoType::KIND_UINT8:
- case GoType::KIND_UINT16:
- case GoType::KIND_UINT32:
- case GoType::KIND_UINT64:
- return eFormatUnsigned;
- case GoType::KIND_FLOAT32:
- case GoType::KIND_FLOAT64:
- return eFormatFloat;
- case GoType::KIND_COMPLEX64:
- case GoType::KIND_COMPLEX128:
- return eFormatComplexFloat;
- case GoType::KIND_UINTPTR:
- case GoType::KIND_CHAN:
- case GoType::KIND_PTR:
- case GoType::KIND_MAP:
- case GoType::KIND_UNSAFEPOINTER:
- return eFormatHex;
- case GoType::KIND_STRING:
- return eFormatCString;
- case GoType::KIND_ARRAY:
- case GoType::KIND_INTERFACE:
- case GoType::KIND_SLICE:
- case GoType::KIND_STRUCT:
- default:
- // Don't know how to display this.
- return eFormatBytes;
- }
-}
-
-size_t
-GoASTContext::GetTypeBitAlign(lldb::opaque_compiler_type_t type)
-{
+ if (!GetCompleteType(type))
return 0;
+ GoType *t = static_cast<GoType *>(type);
+ GoArray *array = nullptr;
+ switch (t->GetGoKind()) {
+ case GoType::KIND_BOOL:
+ case GoType::KIND_INT8:
+ case GoType::KIND_UINT8:
+ return 8;
+ case GoType::KIND_INT16:
+ case GoType::KIND_UINT16:
+ return 16;
+ case GoType::KIND_INT32:
+ case GoType::KIND_UINT32:
+ case GoType::KIND_FLOAT32:
+ return 32;
+ case GoType::KIND_INT64:
+ case GoType::KIND_UINT64:
+ case GoType::KIND_FLOAT64:
+ case GoType::KIND_COMPLEX64:
+ return 64;
+ case GoType::KIND_COMPLEX128:
+ return 128;
+ case GoType::KIND_INT:
+ case GoType::KIND_UINT:
+ return m_int_byte_size * 8;
+ case GoType::KIND_UINTPTR:
+ case GoType::KIND_FUNC: // I assume this is a pointer?
+ case GoType::KIND_CHAN:
+ case GoType::KIND_PTR:
+ case GoType::KIND_UNSAFEPOINTER:
+ case GoType::KIND_MAP:
+ return m_pointer_byte_size * 8;
+ case GoType::KIND_ARRAY:
+ array = t->GetArray();
+ return array->GetLength() * array->GetElementType().GetBitSize(exe_scope);
+ case GoType::KIND_INTERFACE:
+ return t->GetElementType().GetBitSize(exe_scope);
+ case GoType::KIND_SLICE:
+ case GoType::KIND_STRING:
+ case GoType::KIND_STRUCT:
+ return t->GetStruct()->GetByteSize() * 8;
+ default:
+ assert(false);
+ }
+ return 0;
}
-uint32_t
-GoASTContext::GetNumChildren(lldb::opaque_compiler_type_t type, bool omit_empty_base_classes)
-{
- if (!type || !GetCompleteType(type))
- return 0;
- GoType *t = static_cast<GoType *>(type);
- if (t->GetGoKind() == GoType::KIND_PTR)
- {
- CompilerType elem = t->GetElementType();
- if (elem.IsAggregateType())
- return elem.GetNumChildren(omit_empty_base_classes);
- return 1;
- }
- else if (GoArray *array = t->GetArray())
- {
- return array->GetLength();
- }
- else if (t->IsTypedef())
- {
- return t->GetElementType().GetNumChildren(omit_empty_base_classes);
- }
+lldb::Encoding GoASTContext::GetEncoding(lldb::opaque_compiler_type_t type,
+ uint64_t &count) {
+ count = 1;
+ bool is_signed;
+ if (IsIntegerType(type, is_signed))
+ return is_signed ? lldb::eEncodingSint : eEncodingUint;
+ bool is_complex;
+ uint32_t complex_count;
+ if (IsFloatingPointType(type, complex_count, is_complex)) {
+ count = complex_count;
+ return eEncodingIEEE754;
+ }
+ if (IsPointerType(type))
+ return eEncodingUint;
+ return eEncodingInvalid;
+}
+
+lldb::Format GoASTContext::GetFormat(lldb::opaque_compiler_type_t type) {
+ if (!type)
+ return eFormatDefault;
+ switch (static_cast<GoType *>(type)->GetGoKind()) {
+ case GoType::KIND_BOOL:
+ return eFormatBoolean;
+ case GoType::KIND_INT:
+ case GoType::KIND_INT8:
+ case GoType::KIND_INT16:
+ case GoType::KIND_INT32:
+ case GoType::KIND_INT64:
+ return eFormatDecimal;
+ case GoType::KIND_UINT:
+ case GoType::KIND_UINT8:
+ case GoType::KIND_UINT16:
+ case GoType::KIND_UINT32:
+ case GoType::KIND_UINT64:
+ return eFormatUnsigned;
+ case GoType::KIND_FLOAT32:
+ case GoType::KIND_FLOAT64:
+ return eFormatFloat;
+ case GoType::KIND_COMPLEX64:
+ case GoType::KIND_COMPLEX128:
+ return eFormatComplexFloat;
+ case GoType::KIND_UINTPTR:
+ case GoType::KIND_CHAN:
+ case GoType::KIND_PTR:
+ case GoType::KIND_MAP:
+ case GoType::KIND_UNSAFEPOINTER:
+ return eFormatHex;
+ case GoType::KIND_STRING:
+ return eFormatCString;
+ case GoType::KIND_ARRAY:
+ case GoType::KIND_INTERFACE:
+ case GoType::KIND_SLICE:
+ case GoType::KIND_STRUCT:
+ default:
+ // Don't know how to display this.
+ return eFormatBytes;
+ }
+}
+
+size_t GoASTContext::GetTypeBitAlign(lldb::opaque_compiler_type_t type) {
+ return 0;
+}
+
+uint32_t GoASTContext::GetNumChildren(lldb::opaque_compiler_type_t type,
+ bool omit_empty_base_classes) {
+ if (!type || !GetCompleteType(type))
+ return 0;
+ GoType *t = static_cast<GoType *>(type);
+ if (t->GetGoKind() == GoType::KIND_PTR) {
+ CompilerType elem = t->GetElementType();
+ if (elem.IsAggregateType())
+ return elem.GetNumChildren(omit_empty_base_classes);
+ return 1;
+ } else if (GoArray *array = t->GetArray()) {
+ return array->GetLength();
+ } else if (t->IsTypedef()) {
+ return t->GetElementType().GetNumChildren(omit_empty_base_classes);
+ }
- return GetNumFields(type);
+ return GetNumFields(type);
}
-uint32_t
-GoASTContext::GetNumFields(lldb::opaque_compiler_type_t type)
-{
- if (!type || !GetCompleteType(type))
- return 0;
- GoType *t = static_cast<GoType *>(type);
- if (t->IsTypedef())
- return t->GetElementType().GetNumFields();
- GoStruct *s = t->GetStruct();
- if (s)
- return s->GetNumFields();
+uint32_t GoASTContext::GetNumFields(lldb::opaque_compiler_type_t type) {
+ if (!type || !GetCompleteType(type))
return 0;
-}
-
-CompilerType
-GoASTContext::GetFieldAtIndex(lldb::opaque_compiler_type_t type, size_t idx, std::string &name, uint64_t *bit_offset_ptr,
- uint32_t *bitfield_bit_size_ptr, bool *is_bitfield_ptr)
-{
- if (bit_offset_ptr)
- *bit_offset_ptr = 0;
- if (bitfield_bit_size_ptr)
- *bitfield_bit_size_ptr = 0;
- if (is_bitfield_ptr)
- *is_bitfield_ptr = false;
-
- if (!type || !GetCompleteType(type))
- return CompilerType();
+ GoType *t = static_cast<GoType *>(type);
+ if (t->IsTypedef())
+ return t->GetElementType().GetNumFields();
+ GoStruct *s = t->GetStruct();
+ if (s)
+ return s->GetNumFields();
+ return 0;
+}
+
+CompilerType GoASTContext::GetFieldAtIndex(lldb::opaque_compiler_type_t type,
+ size_t idx, std::string &name,
+ uint64_t *bit_offset_ptr,
+ uint32_t *bitfield_bit_size_ptr,
+ bool *is_bitfield_ptr) {
+ if (bit_offset_ptr)
+ *bit_offset_ptr = 0;
+ if (bitfield_bit_size_ptr)
+ *bitfield_bit_size_ptr = 0;
+ if (is_bitfield_ptr)
+ *is_bitfield_ptr = false;
- GoType *t = static_cast<GoType *>(type);
- if (t->IsTypedef())
- return t->GetElementType().GetFieldAtIndex(idx, name, bit_offset_ptr, bitfield_bit_size_ptr, is_bitfield_ptr);
-
- GoStruct *s = t->GetStruct();
- if (s)
- {
- const auto *field = s->GetField(idx);
- if (field)
- {
- name = field->m_name.GetStringRef();
- if (bit_offset_ptr)
- *bit_offset_ptr = field->m_byte_offset * 8;
- return field->m_type;
- }
- }
+ if (!type || !GetCompleteType(type))
return CompilerType();
-}
-
-CompilerType
-GoASTContext::GetChildCompilerTypeAtIndex(lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx, size_t idx, bool transparent_pointers,
- bool omit_empty_base_classes, bool ignore_array_bounds, std::string &child_name,
- uint32_t &child_byte_size, int32_t &child_byte_offset,
- uint32_t &child_bitfield_bit_size, uint32_t &child_bitfield_bit_offset,
- bool &child_is_base_class, bool &child_is_deref_of_parent, ValueObject *valobj, uint64_t &language_flags)
-{
- child_name.clear();
- child_byte_size = 0;
- child_byte_offset = 0;
- child_bitfield_bit_size = 0;
- child_bitfield_bit_offset = 0;
- child_is_base_class = false;
- child_is_deref_of_parent = false;
- language_flags = 0;
- if (!type || !GetCompleteType(type))
- return CompilerType();
+ GoType *t = static_cast<GoType *>(type);
+ if (t->IsTypedef())
+ return t->GetElementType().GetFieldAtIndex(
+ idx, name, bit_offset_ptr, bitfield_bit_size_ptr, is_bitfield_ptr);
+
+ GoStruct *s = t->GetStruct();
+ if (s) {
+ const auto *field = s->GetField(idx);
+ if (field) {
+ name = field->m_name.GetStringRef();
+ if (bit_offset_ptr)
+ *bit_offset_ptr = field->m_byte_offset * 8;
+ return field->m_type;
+ }
+ }
+ return CompilerType();
+}
+
+CompilerType GoASTContext::GetChildCompilerTypeAtIndex(
+ lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx, size_t idx,
+ bool transparent_pointers, bool omit_empty_base_classes,
+ bool ignore_array_bounds, std::string &child_name,
+ uint32_t &child_byte_size, int32_t &child_byte_offset,
+ uint32_t &child_bitfield_bit_size, uint32_t &child_bitfield_bit_offset,
+ bool &child_is_base_class, bool &child_is_deref_of_parent,
+ ValueObject *valobj, uint64_t &language_flags) {
+ child_name.clear();
+ child_byte_size = 0;
+ child_byte_offset = 0;
+ child_bitfield_bit_size = 0;
+ child_bitfield_bit_offset = 0;
+ child_is_base_class = false;
+ child_is_deref_of_parent = false;
+ language_flags = 0;
- GoType *t = static_cast<GoType *>(type);
- if (t->GetStruct())
- {
- uint64_t bit_offset;
- CompilerType ret = GetFieldAtIndex(type, idx, child_name, &bit_offset, nullptr, nullptr);
- child_byte_size = ret.GetByteSize(exe_ctx ? exe_ctx->GetBestExecutionContextScope() : nullptr);
- child_byte_offset = bit_offset / 8;
- return ret;
- }
- else if (t->GetGoKind() == GoType::KIND_PTR)
- {
- CompilerType pointee = t->GetElementType();
- if (!pointee.IsValid() || pointee.IsVoidType())
- return CompilerType();
- if (transparent_pointers && pointee.IsAggregateType())
- {
- bool tmp_child_is_deref_of_parent = false;
- return pointee.GetChildCompilerTypeAtIndex(exe_ctx, idx, transparent_pointers, omit_empty_base_classes,
- ignore_array_bounds, child_name, child_byte_size, child_byte_offset,
- child_bitfield_bit_size, child_bitfield_bit_offset,
- child_is_base_class, tmp_child_is_deref_of_parent, valobj, language_flags);
- }
- else
- {
- child_is_deref_of_parent = true;
- const char *parent_name = valobj ? valobj->GetName().GetCString() : NULL;
- if (parent_name)
- {
- child_name.assign(1, '*');
- child_name += parent_name;
- }
-
- // We have a pointer to an simple type
- if (idx == 0 && pointee.GetCompleteType())
- {
- child_byte_size = pointee.GetByteSize(exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
- child_byte_offset = 0;
- return pointee;
- }
- }
- }
- else if (GoArray *a = t->GetArray())
- {
- if (ignore_array_bounds || idx < a->GetLength())
- {
- CompilerType element_type = a->GetElementType();
- if (element_type.GetCompleteType())
- {
- char element_name[64];
- ::snprintf(element_name, sizeof(element_name), "[%zu]", idx);
- child_name.assign(element_name);
- child_byte_size = element_type.GetByteSize(exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
- child_byte_offset = (int32_t)idx * (int32_t)child_byte_size;
- return element_type;
- }
- }
- }
- else if (t->IsTypedef())
- {
- return t->GetElementType().GetChildCompilerTypeAtIndex(
- exe_ctx, idx, transparent_pointers, omit_empty_base_classes, ignore_array_bounds, child_name,
- child_byte_size, child_byte_offset, child_bitfield_bit_size, child_bitfield_bit_offset, child_is_base_class,
- child_is_deref_of_parent, valobj, language_flags);
- }
+ if (!type || !GetCompleteType(type))
return CompilerType();
+
+ GoType *t = static_cast<GoType *>(type);
+ if (t->GetStruct()) {
+ uint64_t bit_offset;
+ CompilerType ret =
+ GetFieldAtIndex(type, idx, child_name, &bit_offset, nullptr, nullptr);
+ child_byte_size = ret.GetByteSize(
+ exe_ctx ? exe_ctx->GetBestExecutionContextScope() : nullptr);
+ child_byte_offset = bit_offset / 8;
+ return ret;
+ } else if (t->GetGoKind() == GoType::KIND_PTR) {
+ CompilerType pointee = t->GetElementType();
+ if (!pointee.IsValid() || pointee.IsVoidType())
+ return CompilerType();
+ if (transparent_pointers && pointee.IsAggregateType()) {
+ bool tmp_child_is_deref_of_parent = false;
+ return pointee.GetChildCompilerTypeAtIndex(
+ exe_ctx, idx, transparent_pointers, omit_empty_base_classes,
+ ignore_array_bounds, child_name, child_byte_size, child_byte_offset,
+ child_bitfield_bit_size, child_bitfield_bit_offset,
+ child_is_base_class, tmp_child_is_deref_of_parent, valobj,
+ language_flags);
+ } else {
+ child_is_deref_of_parent = true;
+ const char *parent_name = valobj ? valobj->GetName().GetCString() : NULL;
+ if (parent_name) {
+ child_name.assign(1, '*');
+ child_name += parent_name;
+ }
+
+ // We have a pointer to an simple type
+ if (idx == 0 && pointee.GetCompleteType()) {
+ child_byte_size = pointee.GetByteSize(
+ exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
+ child_byte_offset = 0;
+ return pointee;
+ }
+ }
+ } else if (GoArray *a = t->GetArray()) {
+ if (ignore_array_bounds || idx < a->GetLength()) {
+ CompilerType element_type = a->GetElementType();
+ if (element_type.GetCompleteType()) {
+ char element_name[64];
+ ::snprintf(element_name, sizeof(element_name), "[%zu]", idx);
+ child_name.assign(element_name);
+ child_byte_size = element_type.GetByteSize(
+ exe_ctx ? exe_ctx->GetBestExecutionContextScope() : NULL);
+ child_byte_offset = (int32_t)idx * (int32_t)child_byte_size;
+ return element_type;
+ }
+ }
+ } else if (t->IsTypedef()) {
+ return t->GetElementType().GetChildCompilerTypeAtIndex(
+ exe_ctx, idx, transparent_pointers, omit_empty_base_classes,
+ ignore_array_bounds, child_name, child_byte_size, child_byte_offset,
+ child_bitfield_bit_size, child_bitfield_bit_offset, child_is_base_class,
+ child_is_deref_of_parent, valobj, language_flags);
+ }
+ return CompilerType();
}
// Lookup a child given a name. This function will match base class names
// and member member names in "clang_type" only, not descendants.
uint32_t
-GoASTContext::GetIndexOfChildWithName(lldb::opaque_compiler_type_t type, const char *name, bool omit_empty_base_classes)
-{
- if (!type || !GetCompleteType(type))
- return UINT_MAX;
-
- GoType *t = static_cast<GoType *>(type);
- GoStruct *s = t->GetStruct();
- if (s)
- {
- for (uint32_t i = 0; i < s->GetNumFields(); ++i)
- {
- const GoStruct::Field *f = s->GetField(i);
- if (f->m_name.GetStringRef() == name)
- return i;
- }
- }
- else if (t->GetGoKind() == GoType::KIND_PTR || t->IsTypedef())
- {
- return t->GetElementType().GetIndexOfChildWithName(name, omit_empty_base_classes);
- }
+GoASTContext::GetIndexOfChildWithName(lldb::opaque_compiler_type_t type,
+ const char *name,
+ bool omit_empty_base_classes) {
+ if (!type || !GetCompleteType(type))
return UINT_MAX;
+
+ GoType *t = static_cast<GoType *>(type);
+ GoStruct *s = t->GetStruct();
+ if (s) {
+ for (uint32_t i = 0; i < s->GetNumFields(); ++i) {
+ const GoStruct::Field *f = s->GetField(i);
+ if (f->m_name.GetStringRef() == name)
+ return i;
+ }
+ } else if (t->GetGoKind() == GoType::KIND_PTR || t->IsTypedef()) {
+ return t->GetElementType().GetIndexOfChildWithName(name,
+ omit_empty_base_classes);
+ }
+ return UINT_MAX;
}
// Lookup a child member given a name. This function will match member names
// only and will descend into "clang_type" children in search for the first
// member in this class, or any base class that matches "name".
-// TODO: Return all matches for a given name by returning a vector<vector<uint32_t>>
+// TODO: Return all matches for a given name by returning a
+// vector<vector<uint32_t>>
// so we catch all names that match a given child name, not just the first.
-size_t
-GoASTContext::GetIndexOfChildMemberWithName(lldb::opaque_compiler_type_t type, const char *name, bool omit_empty_base_classes,
- std::vector<uint32_t> &child_indexes)
-{
- uint32_t index = GetIndexOfChildWithName(type, name, omit_empty_base_classes);
- if (index == UINT_MAX)
- return 0;
- child_indexes.push_back(index);
- return 1;
+size_t GoASTContext::GetIndexOfChildMemberWithName(
+ lldb::opaque_compiler_type_t type, const char *name,
+ bool omit_empty_base_classes, std::vector<uint32_t> &child_indexes) {
+ uint32_t index = GetIndexOfChildWithName(type, name, omit_empty_base_classes);
+ if (index == UINT_MAX)
+ return 0;
+ child_indexes.push_back(index);
+ return 1;
}
// Converts "s" to a floating point value and place resulting floating
// point bytes in the "dst" buffer.
size_t
-GoASTContext::ConvertStringToFloatValue(lldb::opaque_compiler_type_t type, const char *s, uint8_t *dst, size_t dst_size)
-{
- assert(false);
- return 0;
+GoASTContext::ConvertStringToFloatValue(lldb::opaque_compiler_type_t type,
+ const char *s, uint8_t *dst,
+ size_t dst_size) {
+ assert(false);
+ return 0;
}
//----------------------------------------------------------------------
// Dumping types
//----------------------------------------------------------------------
#define DEPTH_INCREMENT 2
-void
-GoASTContext::DumpValue(lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx, Stream *s, lldb::Format format,
- const DataExtractor &data, lldb::offset_t data_byte_offset, size_t data_byte_size,
- uint32_t bitfield_bit_size, uint32_t bitfield_bit_offset, bool show_types, bool show_summary,
- bool verbose, uint32_t depth)
-{
- if (IsTypedefType(type))
- type = GetTypedefedType(type).GetOpaqueQualType();
- if (!type)
- return;
- GoType *t = static_cast<GoType *>(type);
-
- if (GoStruct *st = t->GetStruct())
- {
- if (GetCompleteType(type))
- {
- uint32_t field_idx = 0;
- for (auto* field = st->GetField(field_idx); field != nullptr; field_idx++)
- {
- // Print the starting squiggly bracket (if this is the
- // first member) or comma (for member 2 and beyond) for
- // the struct/union/class member.
- if (field_idx == 0)
- s->PutChar('{');
- else
- s->PutChar(',');
-
- // Indent
- s->Printf("\n%*s", depth + DEPTH_INCREMENT, "");
-
- // Print the member type if requested
- if (show_types)
- {
- ConstString field_type_name = field->m_type.GetTypeName();
- s->Printf("(%s) ", field_type_name.AsCString());
- }
- // Print the member name and equal sign
- s->Printf("%s = ", field->m_name.AsCString());
-
-
- // Dump the value of the member
- CompilerType field_type = field->m_type;
- field_type.DumpValue (exe_ctx,
- s, // Stream to dump to
- field_type.GetFormat(), // The format with which to display the member
- data, // Data buffer containing all bytes for this type
- data_byte_offset + field->m_byte_offset,// Offset into "data" where to grab value from
- field->m_type.GetByteSize(exe_ctx->GetBestExecutionContextScope()), // Size of this type in bytes
- 0, // Bitfield bit size
- 0, // Bitfield bit offset
- show_types, // Boolean indicating if we should show the variable types
- show_summary, // Boolean indicating if we should show a summary for the current type
- verbose, // Verbose output?
- depth + DEPTH_INCREMENT); // Scope depth for any types that have children
- }
-
- // Indent the trailing squiggly bracket
- if (field_idx > 0)
- s->Printf("\n%*s}", depth, "");
-
- }
- }
-
- if (GoArray *a = t->GetArray()) {
- CompilerType element_clang_type = a->GetElementType();
- lldb::Format element_format = element_clang_type.GetFormat();
- uint32_t element_byte_size = element_clang_type.GetByteSize(exe_ctx->GetBestExecutionContextScope());
-
- uint64_t element_idx;
- for (element_idx = 0; element_idx < a->GetLength(); ++element_idx)
- {
- // Print the starting squiggly bracket (if this is the
- // first member) or comman (for member 2 and beyong) for
- // the struct/union/class member.
- if (element_idx == 0)
- s->PutChar('{');
- else
- s->PutChar(',');
-
- // Indent and print the index
- s->Printf("\n%*s[%" PRIu64 "] ", depth + DEPTH_INCREMENT, "", element_idx);
-
- // Figure out the field offset within the current struct/union/class type
- uint64_t element_offset = element_idx * element_byte_size;
-
- // Dump the value of the member
- element_clang_type.DumpValue (exe_ctx,
- s, // Stream to dump to
- element_format, // The format with which to display the element
- data, // Data buffer containing all bytes for this type
- data_byte_offset + element_offset,// Offset into "data" where to grab value from
- element_byte_size, // Size of this type in bytes
- 0, // Bitfield bit size
- 0, // Bitfield bit offset
- show_types, // Boolean indicating if we should show the variable types
- show_summary, // Boolean indicating if we should show a summary for the current type
- verbose, // Verbose output?
- depth + DEPTH_INCREMENT); // Scope depth for any types that have children
- }
-
- // Indent the trailing squiggly bracket
- if (element_idx > 0)
- s->Printf("\n%*s}", depth, "");
- }
-
- if (show_summary)
- DumpSummary (type, exe_ctx, s, data, data_byte_offset, data_byte_size);
-}
-
-bool
-GoASTContext::DumpTypeValue(lldb::opaque_compiler_type_t type, Stream *s, lldb::Format format, const DataExtractor &data,
- lldb::offset_t byte_offset, size_t byte_size, uint32_t bitfield_bit_size,
- uint32_t bitfield_bit_offset, ExecutionContextScope *exe_scope)
-{
- if (!type)
- return false;
- if (IsAggregateType(type))
- {
- return false;
- }
- else
- {
- GoType *t = static_cast<GoType *>(type);
- if (t->IsTypedef())
- {
- CompilerType typedef_compiler_type = t->GetElementType();
- if (format == eFormatDefault)
- format = typedef_compiler_type.GetFormat();
- uint64_t typedef_byte_size = typedef_compiler_type.GetByteSize(exe_scope);
-
- return typedef_compiler_type.DumpTypeValue(
- s,
- format, // The format with which to display the element
- data, // Data buffer containing all bytes for this type
- byte_offset, // Offset into "data" where to grab value from
- typedef_byte_size, // Size of this type in bytes
- bitfield_bit_size, // Size in bits of a bitfield value, if zero don't treat as a bitfield
- bitfield_bit_offset, // Offset in bits of a bitfield value if bitfield_bit_size != 0
- exe_scope);
- }
+void GoASTContext::DumpValue(lldb::opaque_compiler_type_t type,
+ ExecutionContext *exe_ctx, Stream *s,
+ lldb::Format format, const DataExtractor &data,
+ lldb::offset_t data_byte_offset,
+ size_t data_byte_size, uint32_t bitfield_bit_size,
+ uint32_t bitfield_bit_offset, bool show_types,
+ bool show_summary, bool verbose, uint32_t depth) {
+ if (IsTypedefType(type))
+ type = GetTypedefedType(type).GetOpaqueQualType();
+ if (!type)
+ return;
+ GoType *t = static_cast<GoType *>(type);
+
+ if (GoStruct *st = t->GetStruct()) {
+ if (GetCompleteType(type)) {
+ uint32_t field_idx = 0;
+ for (auto *field = st->GetField(field_idx); field != nullptr;
+ field_idx++) {
+ // Print the starting squiggly bracket (if this is the
+ // first member) or comma (for member 2 and beyond) for
+ // the struct/union/class member.
+ if (field_idx == 0)
+ s->PutChar('{');
+ else
+ s->PutChar(',');
- uint32_t item_count = 1;
- // A few formats, we might need to modify our size and count for depending
- // on how we are trying to display the value...
- switch (format)
- {
- default:
- case eFormatBoolean:
- case eFormatBinary:
- case eFormatComplex:
- case eFormatCString: // NULL terminated C strings
- case eFormatDecimal:
- case eFormatEnum:
- case eFormatHex:
- case eFormatHexUppercase:
- case eFormatFloat:
- case eFormatOctal:
- case eFormatOSType:
- case eFormatUnsigned:
- case eFormatPointer:
- case eFormatVectorOfChar:
- case eFormatVectorOfSInt8:
- case eFormatVectorOfUInt8:
- case eFormatVectorOfSInt16:
- case eFormatVectorOfUInt16:
- case eFormatVectorOfSInt32:
- case eFormatVectorOfUInt32:
- case eFormatVectorOfSInt64:
- case eFormatVectorOfUInt64:
- case eFormatVectorOfFloat32:
- case eFormatVectorOfFloat64:
- case eFormatVectorOfUInt128:
- break;
-
- case eFormatChar:
- case eFormatCharPrintable:
- case eFormatCharArray:
- case eFormatBytes:
- case eFormatBytesWithASCII:
- item_count = byte_size;
- byte_size = 1;
- break;
-
- case eFormatUnicode16:
- item_count = byte_size / 2;
- byte_size = 2;
- break;
-
- case eFormatUnicode32:
- item_count = byte_size / 4;
- byte_size = 4;
- break;
- }
- return data.Dump(s, byte_offset, format, byte_size, item_count, UINT32_MAX, LLDB_INVALID_ADDRESS,
- bitfield_bit_size, bitfield_bit_offset, exe_scope);
- }
- return 0;
-}
+ // Indent
+ s->Printf("\n%*s", depth + DEPTH_INCREMENT, "");
-void
-GoASTContext::DumpSummary(lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx, Stream *s, const DataExtractor &data,
- lldb::offset_t data_offset, size_t data_byte_size)
-{
- if (type && GoType::KIND_STRING == static_cast<GoType *>(type)->GetGoKind())
- {
- // TODO(ribrdb): read length and data
- }
+ // Print the member type if requested
+ if (show_types) {
+ ConstString field_type_name = field->m_type.GetTypeName();
+ s->Printf("(%s) ", field_type_name.AsCString());
+ }
+ // Print the member name and equal sign
+ s->Printf("%s = ", field->m_name.AsCString());
+
+ // Dump the value of the member
+ CompilerType field_type = field->m_type;
+ field_type.DumpValue(
+ exe_ctx,
+ s, // Stream to dump to
+ field_type
+ .GetFormat(), // The format with which to display the member
+ data, // Data buffer containing all bytes for this type
+ data_byte_offset + field->m_byte_offset, // Offset into "data" where
+ // to grab value from
+ field->m_type.GetByteSize(
+ exe_ctx->GetBestExecutionContextScope()), // Size of this type
+ // in bytes
+ 0, // Bitfield bit size
+ 0, // Bitfield bit offset
+ show_types, // Boolean indicating if we should show the variable
+ // types
+ show_summary, // Boolean indicating if we should show a summary for
+ // the current type
+ verbose, // Verbose output?
+ depth + DEPTH_INCREMENT); // Scope depth for any types that have
+ // children
+ }
+
+ // Indent the trailing squiggly bracket
+ if (field_idx > 0)
+ s->Printf("\n%*s}", depth, "");
+ }
+ }
+
+ if (GoArray *a = t->GetArray()) {
+ CompilerType element_clang_type = a->GetElementType();
+ lldb::Format element_format = element_clang_type.GetFormat();
+ uint32_t element_byte_size =
+ element_clang_type.GetByteSize(exe_ctx->GetBestExecutionContextScope());
+
+ uint64_t element_idx;
+ for (element_idx = 0; element_idx < a->GetLength(); ++element_idx) {
+ // Print the starting squiggly bracket (if this is the
+ // first member) or comman (for member 2 and beyong) for
+ // the struct/union/class member.
+ if (element_idx == 0)
+ s->PutChar('{');
+ else
+ s->PutChar(',');
+
+ // Indent and print the index
+ s->Printf("\n%*s[%" PRIu64 "] ", depth + DEPTH_INCREMENT, "",
+ element_idx);
+
+ // Figure out the field offset within the current struct/union/class type
+ uint64_t element_offset = element_idx * element_byte_size;
+
+ // Dump the value of the member
+ element_clang_type.DumpValue(
+ exe_ctx,
+ s, // Stream to dump to
+ element_format, // The format with which to display the element
+ data, // Data buffer containing all bytes for this type
+ data_byte_offset +
+ element_offset, // Offset into "data" where to grab value from
+ element_byte_size, // Size of this type in bytes
+ 0, // Bitfield bit size
+ 0, // Bitfield bit offset
+ show_types, // Boolean indicating if we should show the variable types
+ show_summary, // Boolean indicating if we should show a summary for
+ // the current type
+ verbose, // Verbose output?
+ depth +
+ DEPTH_INCREMENT); // Scope depth for any types that have children
+ }
+
+ // Indent the trailing squiggly bracket
+ if (element_idx > 0)
+ s->Printf("\n%*s}", depth, "");
+ }
+
+ if (show_summary)
+ DumpSummary(type, exe_ctx, s, data, data_byte_offset, data_byte_size);
+}
+
+bool GoASTContext::DumpTypeValue(lldb::opaque_compiler_type_t type, Stream *s,
+ lldb::Format format, const DataExtractor &data,
+ lldb::offset_t byte_offset, size_t byte_size,
+ uint32_t bitfield_bit_size,
+ uint32_t bitfield_bit_offset,
+ ExecutionContextScope *exe_scope) {
+ if (!type)
+ return false;
+ if (IsAggregateType(type)) {
+ return false;
+ } else {
+ GoType *t = static_cast<GoType *>(type);
+ if (t->IsTypedef()) {
+ CompilerType typedef_compiler_type = t->GetElementType();
+ if (format == eFormatDefault)
+ format = typedef_compiler_type.GetFormat();
+ uint64_t typedef_byte_size = typedef_compiler_type.GetByteSize(exe_scope);
+
+ return typedef_compiler_type.DumpTypeValue(
+ s,
+ format, // The format with which to display the element
+ data, // Data buffer containing all bytes for this type
+ byte_offset, // Offset into "data" where to grab value from
+ typedef_byte_size, // Size of this type in bytes
+ bitfield_bit_size, // Size in bits of a bitfield value, if zero don't
+ // treat as a bitfield
+ bitfield_bit_offset, // Offset in bits of a bitfield value if
+ // bitfield_bit_size != 0
+ exe_scope);
+ }
+
+ uint32_t item_count = 1;
+ // A few formats, we might need to modify our size and count for depending
+ // on how we are trying to display the value...
+ switch (format) {
+ default:
+ case eFormatBoolean:
+ case eFormatBinary:
+ case eFormatComplex:
+ case eFormatCString: // NULL terminated C strings
+ case eFormatDecimal:
+ case eFormatEnum:
+ case eFormatHex:
+ case eFormatHexUppercase:
+ case eFormatFloat:
+ case eFormatOctal:
+ case eFormatOSType:
+ case eFormatUnsigned:
+ case eFormatPointer:
+ case eFormatVectorOfChar:
+ case eFormatVectorOfSInt8:
+ case eFormatVectorOfUInt8:
+ case eFormatVectorOfSInt16:
+ case eFormatVectorOfUInt16:
+ case eFormatVectorOfSInt32:
+ case eFormatVectorOfUInt32:
+ case eFormatVectorOfSInt64:
+ case eFormatVectorOfUInt64:
+ case eFormatVectorOfFloat32:
+ case eFormatVectorOfFloat64:
+ case eFormatVectorOfUInt128:
+ break;
+
+ case eFormatChar:
+ case eFormatCharPrintable:
+ case eFormatCharArray:
+ case eFormatBytes:
+ case eFormatBytesWithASCII:
+ item_count = byte_size;
+ byte_size = 1;
+ break;
+
+ case eFormatUnicode16:
+ item_count = byte_size / 2;
+ byte_size = 2;
+ break;
+
+ case eFormatUnicode32:
+ item_count = byte_size / 4;
+ byte_size = 4;
+ break;
+ }
+ return data.Dump(s, byte_offset, format, byte_size, item_count, UINT32_MAX,
+ LLDB_INVALID_ADDRESS, bitfield_bit_size,
+ bitfield_bit_offset, exe_scope);
+ }
+ return 0;
+}
+
+void GoASTContext::DumpSummary(lldb::opaque_compiler_type_t type,
+ ExecutionContext *exe_ctx, Stream *s,
+ const DataExtractor &data,
+ lldb::offset_t data_offset,
+ size_t data_byte_size) {
+ if (type && GoType::KIND_STRING == static_cast<GoType *>(type)->GetGoKind()) {
+ // TODO(ribrdb): read length and data
+ }
+}
+
+void GoASTContext::DumpTypeDescription(lldb::opaque_compiler_type_t type) {
+ // Dump to stdout
+ StreamFile s(stdout, false);
+ DumpTypeDescription(type, &s);
+}
+
+void GoASTContext::DumpTypeDescription(lldb::opaque_compiler_type_t type,
+ Stream *s) {
+ if (!type)
+ return;
+ ConstString name = GetTypeName(type);
+ GoType *t = static_cast<GoType *>(type);
+
+ if (GoStruct *st = t->GetStruct()) {
+ if (GetCompleteType(type)) {
+ if (NULL == strchr(name.AsCString(), '{'))
+ s->Printf("type %s ", name.AsCString());
+ s->PutCString("struct {");
+ if (st->GetNumFields() == 0) {
+ s->PutChar('}');
+ return;
+ }
+ s->IndentMore();
+ uint32_t field_idx = 0;
+ for (auto *field = st->GetField(field_idx); field != nullptr;
+ field_idx++) {
+ s->PutChar('\n');
+ s->Indent();
+ s->Printf("%s %s", field->m_name.AsCString(),
+ field->m_type.GetTypeName().AsCString());
+ }
+ s->IndentLess();
+ s->PutChar('\n');
+ s->Indent("}");
+ return;
+ }
+ }
+
+ s->PutCString(name.AsCString());
+}
+
+CompilerType GoASTContext::CreateArrayType(const ConstString &name,
+ const CompilerType &element_type,
+ uint64_t length) {
+ GoType *type = new GoArray(name, length, element_type);
+ (*m_types)[name].reset(type);
+ return CompilerType(this, type);
+}
+
+CompilerType GoASTContext::CreateBaseType(int go_kind,
+ const lldb_private::ConstString &name,
+ uint64_t byte_size) {
+ if (go_kind == GoType::KIND_UINT || go_kind == GoType::KIND_INT)
+ m_int_byte_size = byte_size;
+ GoType *type = new GoType(go_kind, name);
+ (*m_types)[name].reset(type);
+ return CompilerType(this, type);
+}
+
+CompilerType GoASTContext::CreateTypedefType(int kind, const ConstString &name,
+ CompilerType impl) {
+ GoType *type = new GoElem(kind, name, impl);
+ (*m_types)[name].reset(type);
+ return CompilerType(this, type);
}
-void
-GoASTContext::DumpTypeDescription(lldb::opaque_compiler_type_t type)
-{
- // Dump to stdout
- StreamFile s (stdout, false);
- DumpTypeDescription (type, &s);
+CompilerType
+GoASTContext::CreateVoidType(const lldb_private::ConstString &name) {
+ GoType *type = new GoType(GoType::KIND_LLDB_VOID, name);
+ (*m_types)[name].reset(type);
+ return CompilerType(this, type);
}
-void
-GoASTContext::DumpTypeDescription(lldb::opaque_compiler_type_t type, Stream *s)
-{
- if (!type)
- return;
- ConstString name = GetTypeName(type);
- GoType *t = static_cast<GoType *>(type);
-
- if (GoStruct *st = t->GetStruct())
- {
- if (GetCompleteType(type))
- {
- if (NULL == strchr(name.AsCString(), '{'))
- s->Printf("type %s ", name.AsCString());
- s->PutCString("struct {");
- if (st->GetNumFields() == 0) {
- s->PutChar('}');
- return;
- }
- s->IndentMore();
- uint32_t field_idx = 0;
- for (auto* field = st->GetField(field_idx); field != nullptr; field_idx++)
- {
- s->PutChar('\n');
- s->Indent();
- s->Printf("%s %s", field->m_name.AsCString(), field->m_type.GetTypeName().AsCString());
- }
- s->IndentLess();
- s->PutChar('\n');
- s->Indent("}");
- return;
- }
- }
-
- s->PutCString(name.AsCString());
+CompilerType
+GoASTContext::CreateStructType(int kind, const lldb_private::ConstString &name,
+ uint32_t byte_size) {
+ GoType *type = new GoStruct(kind, name, byte_size);
+ (*m_types)[name].reset(type);
+ return CompilerType(this, type);
+}
+
+void GoASTContext::AddFieldToStruct(
+ const lldb_private::CompilerType &struct_type,
+ const lldb_private::ConstString &name,
+ const lldb_private::CompilerType &field_type, uint32_t byte_offset) {
+ if (!struct_type)
+ return;
+ GoASTContext *ast =
+ llvm::dyn_cast_or_null<GoASTContext>(struct_type.GetTypeSystem());
+ if (!ast)
+ return;
+ GoType *type = static_cast<GoType *>(struct_type.GetOpaqueQualType());
+ if (GoStruct *s = type->GetStruct())
+ s->AddField(name, field_type, byte_offset);
+}
+
+void GoASTContext::CompleteStructType(
+ const lldb_private::CompilerType &struct_type) {
+ if (!struct_type)
+ return;
+ GoASTContext *ast =
+ llvm::dyn_cast_or_null<GoASTContext>(struct_type.GetTypeSystem());
+ if (!ast)
+ return;
+ GoType *type = static_cast<GoType *>(struct_type.GetOpaqueQualType());
+ if (GoStruct *s = type->GetStruct())
+ s->SetComplete();
}
CompilerType
-GoASTContext::CreateArrayType(const ConstString &name, const CompilerType &element_type, uint64_t length)
-{
- GoType *type = new GoArray(name, length, element_type);
- (*m_types)[name].reset(type);
- return CompilerType(this, type);
+GoASTContext::CreateFunctionType(const lldb_private::ConstString &name,
+ CompilerType *params, size_t params_count,
+ bool is_variadic) {
+ GoType *type = new GoFunction(name, is_variadic);
+ (*m_types)[name].reset(type);
+ return CompilerType(this, type);
}
-CompilerType
-GoASTContext::CreateBaseType(int go_kind, const lldb_private::ConstString &name, uint64_t byte_size)
-{
- if (go_kind == GoType::KIND_UINT || go_kind == GoType::KIND_INT)
- m_int_byte_size = byte_size;
- GoType *type = new GoType(go_kind, name);
- (*m_types)[name].reset(type);
- return CompilerType(this, type);
+bool GoASTContext::IsGoString(const lldb_private::CompilerType &type) {
+ if (!type.IsValid() ||
+ !llvm::dyn_cast_or_null<GoASTContext>(type.GetTypeSystem()))
+ return false;
+ return GoType::KIND_STRING ==
+ static_cast<GoType *>(type.GetOpaqueQualType())->GetGoKind();
}
-CompilerType
-GoASTContext::CreateTypedefType(int kind, const ConstString &name, CompilerType impl)
-{
- GoType *type = new GoElem(kind, name, impl);
- (*m_types)[name].reset(type);
- return CompilerType(this, type);
+bool GoASTContext::IsGoSlice(const lldb_private::CompilerType &type) {
+ if (!type.IsValid() ||
+ !llvm::dyn_cast_or_null<GoASTContext>(type.GetTypeSystem()))
+ return false;
+ return GoType::KIND_SLICE ==
+ static_cast<GoType *>(type.GetOpaqueQualType())->GetGoKind();
}
-CompilerType
-GoASTContext::CreateVoidType(const lldb_private::ConstString &name)
-{
- GoType *type = new GoType(GoType::KIND_LLDB_VOID, name);
- (*m_types)[name].reset(type);
- return CompilerType(this, type);
+bool GoASTContext::IsGoInterface(const lldb_private::CompilerType &type) {
+ if (!type.IsValid() ||
+ !llvm::dyn_cast_or_null<GoASTContext>(type.GetTypeSystem()))
+ return false;
+ return GoType::KIND_INTERFACE ==
+ static_cast<GoType *>(type.GetOpaqueQualType())->GetGoKind();
}
-CompilerType
-GoASTContext::CreateStructType(int kind, const lldb_private::ConstString &name, uint32_t byte_size)
-{
- GoType *type = new GoStruct(kind, name, byte_size);
- (*m_types)[name].reset(type);
- return CompilerType(this, type);
+bool GoASTContext::IsPointerKind(uint8_t kind) {
+ return (kind & GoType::KIND_MASK) == GoType::KIND_PTR;
}
-void
-GoASTContext::AddFieldToStruct(const lldb_private::CompilerType &struct_type, const lldb_private::ConstString &name,
- const lldb_private::CompilerType &field_type, uint32_t byte_offset)
-{
- if (!struct_type)
- return;
- GoASTContext *ast = llvm::dyn_cast_or_null<GoASTContext>(struct_type.GetTypeSystem());
- if (!ast)
- return;
- GoType *type = static_cast<GoType *>(struct_type.GetOpaqueQualType());
- if (GoStruct *s = type->GetStruct())
- s->AddField(name, field_type, byte_offset);
+bool GoASTContext::IsDirectIface(uint8_t kind) {
+ return (kind & GoType::KIND_DIRECT_IFACE) == GoType::KIND_DIRECT_IFACE;
}
-void
-GoASTContext::CompleteStructType(const lldb_private::CompilerType &struct_type)
-{
- if (!struct_type)
- return;
- GoASTContext *ast = llvm::dyn_cast_or_null<GoASTContext>(struct_type.GetTypeSystem());
- if (!ast)
- return;
- GoType *type = static_cast<GoType *>(struct_type.GetOpaqueQualType());
- if (GoStruct *s = type->GetStruct())
- s->SetComplete();
+DWARFASTParser *GoASTContext::GetDWARFParser() {
+ if (!m_dwarf_ast_parser_ap)
+ m_dwarf_ast_parser_ap.reset(new DWARFASTParserGo(*this));
+ return m_dwarf_ast_parser_ap.get();
}
-CompilerType
-GoASTContext::CreateFunctionType(const lldb_private::ConstString &name, CompilerType *params, size_t params_count,
- bool is_variadic)
-{
- GoType *type = new GoFunction(name, is_variadic);
- (*m_types)[name].reset(type);
- return CompilerType(this, type);
-}
-
-bool
-GoASTContext::IsGoString(const lldb_private::CompilerType &type)
-{
- if (!type.IsValid() || !llvm::dyn_cast_or_null<GoASTContext>(type.GetTypeSystem()))
- return false;
- return GoType::KIND_STRING == static_cast<GoType *>(type.GetOpaqueQualType())->GetGoKind();
-}
-
-bool
-GoASTContext::IsGoSlice(const lldb_private::CompilerType &type)
-{
- if (!type.IsValid() || !llvm::dyn_cast_or_null<GoASTContext>(type.GetTypeSystem()))
- return false;
- return GoType::KIND_SLICE == static_cast<GoType *>(type.GetOpaqueQualType())->GetGoKind();
-}
-
-bool
-GoASTContext::IsGoInterface(const lldb_private::CompilerType &type)
-{
- if (!type.IsValid() || !llvm::dyn_cast_or_null<GoASTContext>(type.GetTypeSystem()))
- return false;
- return GoType::KIND_INTERFACE == static_cast<GoType *>(type.GetOpaqueQualType())->GetGoKind();
-}
-
-bool
-GoASTContext::IsPointerKind(uint8_t kind)
-{
- return (kind & GoType::KIND_MASK) == GoType::KIND_PTR;
-}
-
-bool
-GoASTContext::IsDirectIface(uint8_t kind)
-{
- return (kind & GoType::KIND_DIRECT_IFACE) == GoType::KIND_DIRECT_IFACE;
-}
-
-DWARFASTParser *
-GoASTContext::GetDWARFParser()
-{
- if (!m_dwarf_ast_parser_ap)
- m_dwarf_ast_parser_ap.reset(new DWARFASTParserGo(*this));
- return m_dwarf_ast_parser_ap.get();
-}
-
-UserExpression *
-GoASTContextForExpr::GetUserExpression(const char *expr, const char *expr_prefix, lldb::LanguageType language,
- Expression::ResultType desired_type, const EvaluateExpressionOptions &options)
-{
- TargetSP target = m_target_wp.lock();
- if (target)
- return new GoUserExpression(*target, expr, expr_prefix, language, desired_type, options);
- return nullptr;
+UserExpression *GoASTContextForExpr::GetUserExpression(
+ const char *expr, const char *expr_prefix, lldb::LanguageType language,
+ Expression::ResultType desired_type,
+ const EvaluateExpressionOptions &options) {
+ TargetSP target = m_target_wp.lock();
+ if (target)
+ return new GoUserExpression(*target, expr, expr_prefix, language,
+ desired_type, options);
+ return nullptr;
}
Modified: lldb/trunk/source/Symbol/JavaASTContext.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/JavaASTContext.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/JavaASTContext.cpp (original)
+++ lldb/trunk/source/Symbol/JavaASTContext.cpp Tue Sep 6 15:57:50 2016
@@ -28,1534 +28,1306 @@
using namespace lldb;
using namespace lldb_private;
-namespace lldb_private
-{
+namespace lldb_private {
-class JavaASTContext::JavaType
-{
+class JavaASTContext::JavaType {
public:
- enum LLVMCastKind
- {
- eKindPrimitive,
- eKindObject,
- eKindReference,
- eKindArray,
- kNumKinds
- };
-
- JavaType(LLVMCastKind kind) : m_kind(kind) {}
-
- virtual ~JavaType() = default;
-
- virtual ConstString
- GetName() = 0;
-
- virtual void
- Dump(Stream *s) = 0;
-
- virtual bool
- IsCompleteType() = 0;
-
- LLVMCastKind
- getKind() const
- {
- return m_kind;
- }
+ enum LLVMCastKind {
+ eKindPrimitive,
+ eKindObject,
+ eKindReference,
+ eKindArray,
+ kNumKinds
+ };
+
+ JavaType(LLVMCastKind kind) : m_kind(kind) {}
+
+ virtual ~JavaType() = default;
+
+ virtual ConstString GetName() = 0;
+
+ virtual void Dump(Stream *s) = 0;
+
+ virtual bool IsCompleteType() = 0;
+
+ LLVMCastKind getKind() const { return m_kind; }
private:
- LLVMCastKind m_kind;
+ LLVMCastKind m_kind;
};
} // end of namespace lldb_private
-namespace
-{
+namespace {
-class JavaPrimitiveType : public JavaASTContext::JavaType
-{
+class JavaPrimitiveType : public JavaASTContext::JavaType {
public:
- enum TypeKind
- {
- eTypeByte,
- eTypeShort,
- eTypeInt,
- eTypeLong,
- eTypeFloat,
- eTypeDouble,
- eTypeBoolean,
- eTypeChar,
- };
-
- JavaPrimitiveType(TypeKind type_kind) : JavaType(JavaType::eKindPrimitive), m_type_kind(type_kind) {}
-
- ConstString
- GetName() override
- {
- switch (m_type_kind)
- {
- case eTypeByte:
- return ConstString("byte");
- case eTypeShort:
- return ConstString("short");
- case eTypeInt:
- return ConstString("int");
- case eTypeLong:
- return ConstString("long");
- case eTypeFloat:
- return ConstString("float");
- case eTypeDouble:
- return ConstString("double");
- case eTypeBoolean:
- return ConstString("boolean");
- case eTypeChar:
- return ConstString("char");
- }
- return ConstString();
+ enum TypeKind {
+ eTypeByte,
+ eTypeShort,
+ eTypeInt,
+ eTypeLong,
+ eTypeFloat,
+ eTypeDouble,
+ eTypeBoolean,
+ eTypeChar,
+ };
+
+ JavaPrimitiveType(TypeKind type_kind)
+ : JavaType(JavaType::eKindPrimitive), m_type_kind(type_kind) {}
+
+ ConstString GetName() override {
+ switch (m_type_kind) {
+ case eTypeByte:
+ return ConstString("byte");
+ case eTypeShort:
+ return ConstString("short");
+ case eTypeInt:
+ return ConstString("int");
+ case eTypeLong:
+ return ConstString("long");
+ case eTypeFloat:
+ return ConstString("float");
+ case eTypeDouble:
+ return ConstString("double");
+ case eTypeBoolean:
+ return ConstString("boolean");
+ case eTypeChar:
+ return ConstString("char");
}
+ return ConstString();
+ }
- TypeKind
- GetTypeKind()
- {
- return m_type_kind;
- }
+ TypeKind GetTypeKind() { return m_type_kind; }
- void
- Dump(Stream *s) override
- {
- s->Printf("%s\n", GetName().GetCString());
- }
+ void Dump(Stream *s) override { s->Printf("%s\n", GetName().GetCString()); }
- bool
- IsCompleteType() override
- {
- return true;
- }
+ bool IsCompleteType() override { return true; }
- static bool
- classof(const JavaType *jt)
- {
- return jt->getKind() == JavaType::eKindPrimitive;
- }
+ static bool classof(const JavaType *jt) {
+ return jt->getKind() == JavaType::eKindPrimitive;
+ }
private:
- const TypeKind m_type_kind;
+ const TypeKind m_type_kind;
};
-class JavaDynamicType : public JavaASTContext::JavaType
-{
+class JavaDynamicType : public JavaASTContext::JavaType {
public:
- JavaDynamicType(LLVMCastKind kind, const ConstString &linkage_name) :
- JavaType(kind),
- m_linkage_name(linkage_name),
- m_dynamic_type_id(nullptr)
- {
- }
-
- ConstString
- GetLinkageName() const
- {
- return m_linkage_name;
+ JavaDynamicType(LLVMCastKind kind, const ConstString &linkage_name)
+ : JavaType(kind), m_linkage_name(linkage_name),
+ m_dynamic_type_id(nullptr) {}
+
+ ConstString GetLinkageName() const { return m_linkage_name; }
+
+ void SetDynamicTypeId(const DWARFExpression &type_id) {
+ m_dynamic_type_id = type_id;
+ }
+
+ uint64_t CalculateDynamicTypeId(ExecutionContext *exe_ctx,
+ ValueObject &value_obj) {
+ if (!m_dynamic_type_id.IsValid())
+ return UINT64_MAX;
+
+ Value obj_load_address = value_obj.GetValue();
+ obj_load_address.ResolveValue(exe_ctx);
+ obj_load_address.SetValueType(Value::eValueTypeLoadAddress);
+
+ Value result;
+ if (m_dynamic_type_id.Evaluate(exe_ctx->GetBestExecutionContextScope(),
+ nullptr, nullptr, 0, &obj_load_address,
+ nullptr, result, nullptr)) {
+ Error error;
+
+ lldb::addr_t type_id_addr = result.GetScalar().UInt();
+ lldb::ProcessSP process_sp = exe_ctx->GetProcessSP();
+ if (process_sp)
+ return process_sp->ReadUnsignedIntegerFromMemory(
+ type_id_addr, process_sp->GetAddressByteSize(), UINT64_MAX, error);
}
- void
- SetDynamicTypeId(const DWARFExpression &type_id)
- {
- m_dynamic_type_id = type_id;
- }
-
- uint64_t
- CalculateDynamicTypeId(ExecutionContext *exe_ctx, ValueObject &value_obj)
- {
- if (!m_dynamic_type_id.IsValid())
- return UINT64_MAX;
-
- Value obj_load_address = value_obj.GetValue();
- obj_load_address.ResolveValue(exe_ctx);
- obj_load_address.SetValueType(Value::eValueTypeLoadAddress);
-
- Value result;
- if (m_dynamic_type_id.Evaluate(exe_ctx->GetBestExecutionContextScope(), nullptr, nullptr, 0, &obj_load_address,
- nullptr, result, nullptr))
- {
- Error error;
-
- lldb::addr_t type_id_addr = result.GetScalar().UInt();
- lldb::ProcessSP process_sp = exe_ctx->GetProcessSP();
- if (process_sp)
- return process_sp->ReadUnsignedIntegerFromMemory(type_id_addr, process_sp->GetAddressByteSize(),
- UINT64_MAX, error);
- }
-
- return UINT64_MAX;
- }
+ return UINT64_MAX;
+ }
public:
- ConstString m_linkage_name;
- DWARFExpression m_dynamic_type_id;
+ ConstString m_linkage_name;
+ DWARFExpression m_dynamic_type_id;
};
-class JavaObjectType : public JavaDynamicType
-{
+class JavaObjectType : public JavaDynamicType {
public:
- struct Field
- {
- ConstString m_name;
- CompilerType m_type;
- uint32_t m_offset;
- };
-
- JavaObjectType(const ConstString &name, const ConstString &linkage_name, uint32_t byte_size)
- : JavaDynamicType(JavaType::eKindObject, linkage_name),
- m_name(name),
- m_byte_size(byte_size),
- m_base_class_offset(0),
- m_is_complete(false)
- {
- }
-
- ConstString
- GetName() override
- {
- return m_name;
- }
-
- uint32_t
- GetByteSize() const
- {
- return m_byte_size;
- }
-
- uint32_t
- GetNumFields()
- {
- return m_fields.size();
- }
-
- void
- Dump(Stream *s) override
- {
- if (m_base_class.IsValid())
- s->Printf("%s : %s\n", GetName().GetCString(), m_base_class.GetTypeName().GetCString());
- else
- s->Printf("%s\n", GetName().GetCString());
-
- s->IndentMore();
- for (const Field &f : m_fields)
- s->Printf("%s %s\n", f.m_type.GetTypeName().GetCString(), f.m_name.GetCString());
- s->IndentLess();
- }
-
- Field *
- GetFieldAtIndex(size_t idx)
- {
- if (idx < m_fields.size())
- return &m_fields[idx];
- return nullptr;
- }
-
- CompilerType
- GetBaseClass()
- {
- return m_base_class;
- }
-
- uint32_t
- GetBaseClassOffset()
- {
- return m_base_class_offset;
- }
-
- uint32_t
- GetNumInterfaces()
- {
- return m_interfaces.size();
- }
-
- CompilerType
- GetInterfaceAtIndex(uint32_t idx)
- {
- if (m_interfaces.size() < idx)
- return m_interfaces[idx];
- return CompilerType();
- }
-
- bool
- IsCompleteType() override
- {
- return m_is_complete;
- }
-
- void
- SetCompleteType(bool is_complete)
- {
- m_is_complete = is_complete;
- if (m_byte_size == 0)
- {
- // Try to calcualte the size of the object based on it's values
- for (const Field &field : m_fields)
- {
- uint32_t field_end = field.m_offset + field.m_type.GetByteSize(nullptr);
- if (field_end > m_byte_size)
- m_byte_size = field_end;
- }
- }
- }
+ struct Field {
+ ConstString m_name;
+ CompilerType m_type;
+ uint32_t m_offset;
+ };
+
+ JavaObjectType(const ConstString &name, const ConstString &linkage_name,
+ uint32_t byte_size)
+ : JavaDynamicType(JavaType::eKindObject, linkage_name), m_name(name),
+ m_byte_size(byte_size), m_base_class_offset(0), m_is_complete(false) {}
+
+ ConstString GetName() override { return m_name; }
+
+ uint32_t GetByteSize() const { return m_byte_size; }
+
+ uint32_t GetNumFields() { return m_fields.size(); }
+
+ void Dump(Stream *s) override {
+ if (m_base_class.IsValid())
+ s->Printf("%s : %s\n", GetName().GetCString(),
+ m_base_class.GetTypeName().GetCString());
+ else
+ s->Printf("%s\n", GetName().GetCString());
+
+ s->IndentMore();
+ for (const Field &f : m_fields)
+ s->Printf("%s %s\n", f.m_type.GetTypeName().GetCString(),
+ f.m_name.GetCString());
+ s->IndentLess();
+ }
+
+ Field *GetFieldAtIndex(size_t idx) {
+ if (idx < m_fields.size())
+ return &m_fields[idx];
+ return nullptr;
+ }
+
+ CompilerType GetBaseClass() { return m_base_class; }
+
+ uint32_t GetBaseClassOffset() { return m_base_class_offset; }
+
+ uint32_t GetNumInterfaces() { return m_interfaces.size(); }
+
+ CompilerType GetInterfaceAtIndex(uint32_t idx) {
+ if (m_interfaces.size() < idx)
+ return m_interfaces[idx];
+ return CompilerType();
+ }
- void
- AddBaseClass(const CompilerType &type, uint32_t offset)
- {
- // TODO: Check if type is an interface and add it to the interface list in that case
- m_base_class = type;
- m_base_class_offset = offset;
- }
+ bool IsCompleteType() override { return m_is_complete; }
- void
- AddField(const ConstString &name, const CompilerType &type, uint32_t offset)
- {
- m_fields.push_back({name, type, offset});
- }
-
- static bool
- classof(const JavaType *jt)
- {
- return jt->getKind() == JavaType::eKindObject;
- }
+ void SetCompleteType(bool is_complete) {
+ m_is_complete = is_complete;
+ if (m_byte_size == 0) {
+ // Try to calcualte the size of the object based on it's values
+ for (const Field &field : m_fields) {
+ uint32_t field_end = field.m_offset + field.m_type.GetByteSize(nullptr);
+ if (field_end > m_byte_size)
+ m_byte_size = field_end;
+ }
+ }
+ }
+
+ void AddBaseClass(const CompilerType &type, uint32_t offset) {
+ // TODO: Check if type is an interface and add it to the interface list in
+ // that case
+ m_base_class = type;
+ m_base_class_offset = offset;
+ }
+
+ void AddField(const ConstString &name, const CompilerType &type,
+ uint32_t offset) {
+ m_fields.push_back({name, type, offset});
+ }
+
+ static bool classof(const JavaType *jt) {
+ return jt->getKind() == JavaType::eKindObject;
+ }
private:
- ConstString m_name;
- uint32_t m_byte_size;
- CompilerType m_base_class;
- uint32_t m_base_class_offset;
- std::vector<CompilerType> m_interfaces;
- std::vector<Field> m_fields;
- bool m_is_complete;
+ ConstString m_name;
+ uint32_t m_byte_size;
+ CompilerType m_base_class;
+ uint32_t m_base_class_offset;
+ std::vector<CompilerType> m_interfaces;
+ std::vector<Field> m_fields;
+ bool m_is_complete;
};
-class JavaReferenceType : public JavaASTContext::JavaType
-{
+class JavaReferenceType : public JavaASTContext::JavaType {
public:
- JavaReferenceType(CompilerType pointee_type) : JavaType(JavaType::eKindReference), m_pointee_type(pointee_type) {}
-
- static bool
- classof(const JavaType *jt)
- {
- return jt->getKind() == JavaType::eKindReference;
- }
-
- CompilerType
- GetPointeeType()
- {
- return m_pointee_type;
- }
-
- ConstString
- GetName() override
- {
- ConstString pointee_type_name = static_cast<JavaType *>(GetPointeeType().GetOpaqueQualType())->GetName();
- return ConstString(std::string(pointee_type_name.AsCString()) + "&");
- }
+ JavaReferenceType(CompilerType pointee_type)
+ : JavaType(JavaType::eKindReference), m_pointee_type(pointee_type) {}
- void
- Dump(Stream *s) override
- {
- static_cast<JavaType *>(m_pointee_type.GetOpaqueQualType())->Dump(s);
- }
+ static bool classof(const JavaType *jt) {
+ return jt->getKind() == JavaType::eKindReference;
+ }
+
+ CompilerType GetPointeeType() { return m_pointee_type; }
+
+ ConstString GetName() override {
+ ConstString pointee_type_name =
+ static_cast<JavaType *>(GetPointeeType().GetOpaqueQualType())
+ ->GetName();
+ return ConstString(std::string(pointee_type_name.AsCString()) + "&");
+ }
+
+ void Dump(Stream *s) override {
+ static_cast<JavaType *>(m_pointee_type.GetOpaqueQualType())->Dump(s);
+ }
- bool
- IsCompleteType() override
- {
- return m_pointee_type.IsCompleteType();
- }
+ bool IsCompleteType() override { return m_pointee_type.IsCompleteType(); }
private:
- CompilerType m_pointee_type;
+ CompilerType m_pointee_type;
};
-class JavaArrayType : public JavaDynamicType
-{
+class JavaArrayType : public JavaDynamicType {
public:
- JavaArrayType(const ConstString& linkage_name, CompilerType element_type, const DWARFExpression &length_expression,
- lldb::addr_t data_offset)
- : JavaDynamicType(JavaType::eKindArray, linkage_name),
- m_element_type(element_type),
- m_length_expression(length_expression),
- m_data_offset(data_offset)
- {
- }
-
- static bool
- classof(const JavaType *jt)
- {
- return jt->getKind() == JavaType::eKindArray;
- }
-
- CompilerType
- GetElementType()
- {
- return m_element_type;
- }
-
- ConstString
- GetName() override
- {
- ConstString element_type_name = static_cast<JavaType *>(GetElementType().GetOpaqueQualType())->GetName();
- return ConstString(std::string(element_type_name.AsCString()) + "[]");
- }
-
- void
- Dump(Stream *s) override
- {
- s->Printf("%s\n", GetName().GetCString());
- }
-
- bool
- IsCompleteType() override
- {
- return m_length_expression.IsValid();
- }
-
- uint32_t
- GetNumElements(ValueObject *value_obj)
- {
- if (!m_length_expression.IsValid())
- return UINT32_MAX;
-
- Error error;
- ValueObjectSP address_obj = value_obj->AddressOf(error);
- if (error.Fail())
- return UINT32_MAX;
-
- Value obj_load_address = address_obj->GetValue();
- obj_load_address.SetValueType(Value::eValueTypeLoadAddress);
-
- Value result;
- ExecutionContextScope* exec_ctx_scope = value_obj->GetExecutionContextRef().Lock(true).GetBestExecutionContextScope();
- if (m_length_expression.Evaluate(exec_ctx_scope, nullptr, nullptr, 0, nullptr, &obj_load_address, result, nullptr))
- return result.GetScalar().UInt();
+ JavaArrayType(const ConstString &linkage_name, CompilerType element_type,
+ const DWARFExpression &length_expression,
+ lldb::addr_t data_offset)
+ : JavaDynamicType(JavaType::eKindArray, linkage_name),
+ m_element_type(element_type), m_length_expression(length_expression),
+ m_data_offset(data_offset) {}
+
+ static bool classof(const JavaType *jt) {
+ return jt->getKind() == JavaType::eKindArray;
+ }
+
+ CompilerType GetElementType() { return m_element_type; }
+
+ ConstString GetName() override {
+ ConstString element_type_name =
+ static_cast<JavaType *>(GetElementType().GetOpaqueQualType())
+ ->GetName();
+ return ConstString(std::string(element_type_name.AsCString()) + "[]");
+ }
+
+ void Dump(Stream *s) override { s->Printf("%s\n", GetName().GetCString()); }
+
+ bool IsCompleteType() override { return m_length_expression.IsValid(); }
+
+ uint32_t GetNumElements(ValueObject *value_obj) {
+ if (!m_length_expression.IsValid())
+ return UINT32_MAX;
+
+ Error error;
+ ValueObjectSP address_obj = value_obj->AddressOf(error);
+ if (error.Fail())
+ return UINT32_MAX;
+
+ Value obj_load_address = address_obj->GetValue();
+ obj_load_address.SetValueType(Value::eValueTypeLoadAddress);
+
+ Value result;
+ ExecutionContextScope *exec_ctx_scope = value_obj->GetExecutionContextRef()
+ .Lock(true)
+ .GetBestExecutionContextScope();
+ if (m_length_expression.Evaluate(exec_ctx_scope, nullptr, nullptr, 0,
+ nullptr, &obj_load_address, result,
+ nullptr))
+ return result.GetScalar().UInt();
- return UINT32_MAX;
- }
+ return UINT32_MAX;
+ }
- uint64_t
- GetElementOffset(size_t idx)
- {
- return m_data_offset + idx * m_element_type.GetByteSize(nullptr);
- }
+ uint64_t GetElementOffset(size_t idx) {
+ return m_data_offset + idx * m_element_type.GetByteSize(nullptr);
+ }
private:
- CompilerType m_element_type;
- DWARFExpression m_length_expression;
- lldb::addr_t m_data_offset;
+ CompilerType m_element_type;
+ DWARFExpression m_length_expression;
+ lldb::addr_t m_data_offset;
};
} // end of anonymous namespace
-ConstString
-JavaASTContext::GetPluginNameStatic()
-{
- return ConstString("java");
+ConstString JavaASTContext::GetPluginNameStatic() {
+ return ConstString("java");
}
-ConstString
-JavaASTContext::GetPluginName()
-{
- return JavaASTContext::GetPluginNameStatic();
+ConstString JavaASTContext::GetPluginName() {
+ return JavaASTContext::GetPluginNameStatic();
}
-uint32_t
-JavaASTContext::GetPluginVersion()
-{
- return 1;
-}
+uint32_t JavaASTContext::GetPluginVersion() { return 1; }
-lldb::TypeSystemSP
-JavaASTContext::CreateInstance(lldb::LanguageType language, Module *module, Target *target)
-{
- if (language == eLanguageTypeJava)
- {
- if (module)
- return std::make_shared<JavaASTContext>(module->GetArchitecture());
- if (target)
- return std::make_shared<JavaASTContext>(target->GetArchitecture());
- assert(false && "Either a module or a target has to be specifed to create a JavaASTContext");
- }
- return lldb::TypeSystemSP();
+lldb::TypeSystemSP JavaASTContext::CreateInstance(lldb::LanguageType language,
+ Module *module,
+ Target *target) {
+ if (language == eLanguageTypeJava) {
+ if (module)
+ return std::make_shared<JavaASTContext>(module->GetArchitecture());
+ if (target)
+ return std::make_shared<JavaASTContext>(target->GetArchitecture());
+ assert(false && "Either a module or a target has to be specifed to create "
+ "a JavaASTContext");
+ }
+ return lldb::TypeSystemSP();
}
-void
-JavaASTContext::EnumerateSupportedLanguages(std::set<lldb::LanguageType> &languages_for_types,
- std::set<lldb::LanguageType> &languages_for_expressions)
-{
- static std::vector<lldb::LanguageType> s_languages_for_types({lldb::eLanguageTypeJava});
- static std::vector<lldb::LanguageType> s_languages_for_expressions({});
+void JavaASTContext::EnumerateSupportedLanguages(
+ std::set<lldb::LanguageType> &languages_for_types,
+ std::set<lldb::LanguageType> &languages_for_expressions) {
+ static std::vector<lldb::LanguageType> s_languages_for_types(
+ {lldb::eLanguageTypeJava});
+ static std::vector<lldb::LanguageType> s_languages_for_expressions({});
- languages_for_types.insert(s_languages_for_types.begin(), s_languages_for_types.end());
- languages_for_expressions.insert(s_languages_for_expressions.begin(), s_languages_for_expressions.end());
+ languages_for_types.insert(s_languages_for_types.begin(),
+ s_languages_for_types.end());
+ languages_for_expressions.insert(s_languages_for_expressions.begin(),
+ s_languages_for_expressions.end());
}
-void
-JavaASTContext::Initialize()
-{
- PluginManager::RegisterPlugin(GetPluginNameStatic(), "AST context plug-in", CreateInstance,
- EnumerateSupportedLanguages);
+void JavaASTContext::Initialize() {
+ PluginManager::RegisterPlugin(GetPluginNameStatic(), "AST context plug-in",
+ CreateInstance, EnumerateSupportedLanguages);
}
-void
-JavaASTContext::Terminate()
-{
- PluginManager::UnregisterPlugin(CreateInstance);
+void JavaASTContext::Terminate() {
+ PluginManager::UnregisterPlugin(CreateInstance);
}
JavaASTContext::JavaASTContext(const ArchSpec &arch)
- : TypeSystem(eKindJava), m_pointer_byte_size(arch.GetAddressByteSize())
-{
-}
+ : TypeSystem(eKindJava), m_pointer_byte_size(arch.GetAddressByteSize()) {}
-JavaASTContext::~JavaASTContext()
-{
+JavaASTContext::~JavaASTContext() {}
+
+uint32_t JavaASTContext::GetPointerByteSize() { return m_pointer_byte_size; }
+
+DWARFASTParser *JavaASTContext::GetDWARFParser() {
+ if (!m_dwarf_ast_parser_ap)
+ m_dwarf_ast_parser_ap.reset(new DWARFASTParserJava(*this));
+ return m_dwarf_ast_parser_ap.get();
}
-uint32_t
-JavaASTContext::GetPointerByteSize()
-{
- return m_pointer_byte_size;
-}
-
-DWARFASTParser *
-JavaASTContext::GetDWARFParser()
-{
- if (!m_dwarf_ast_parser_ap)
- m_dwarf_ast_parser_ap.reset(new DWARFASTParserJava(*this));
- return m_dwarf_ast_parser_ap.get();
-}
-
-ConstString
-JavaASTContext::DeclGetName(void *opaque_decl)
-{
- return ConstString();
+ConstString JavaASTContext::DeclGetName(void *opaque_decl) {
+ return ConstString();
}
-std::vector<CompilerDecl>
-JavaASTContext::DeclContextFindDeclByName(void *opaque_decl_ctx, ConstString name, const bool ignore_imported_decls)
-{
- return std::vector<CompilerDecl>();
+std::vector<CompilerDecl> JavaASTContext::DeclContextFindDeclByName(
+ void *opaque_decl_ctx, ConstString name, const bool ignore_imported_decls) {
+ return std::vector<CompilerDecl>();
}
-bool
-JavaASTContext::DeclContextIsStructUnionOrClass(void *opaque_decl_ctx)
-{
- return false;
+bool JavaASTContext::DeclContextIsStructUnionOrClass(void *opaque_decl_ctx) {
+ return false;
}
-ConstString
-JavaASTContext::DeclContextGetName(void *opaque_decl_ctx)
-{
- return ConstString();
+ConstString JavaASTContext::DeclContextGetName(void *opaque_decl_ctx) {
+ return ConstString();
}
-bool
-JavaASTContext::DeclContextIsClassMethod(void *opaque_decl_ctx, lldb::LanguageType *language_ptr,
- bool *is_instance_method_ptr, ConstString *language_object_name_ptr)
-{
- return false;
+bool JavaASTContext::DeclContextIsClassMethod(
+ void *opaque_decl_ctx, lldb::LanguageType *language_ptr,
+ bool *is_instance_method_ptr, ConstString *language_object_name_ptr) {
+ return false;
}
-bool
-JavaASTContext::IsArrayType(lldb::opaque_compiler_type_t type, CompilerType *element_type, uint64_t *size,
- bool *is_incomplete)
-{
+bool JavaASTContext::IsArrayType(lldb::opaque_compiler_type_t type,
+ CompilerType *element_type, uint64_t *size,
+ bool *is_incomplete) {
+ if (element_type)
+ element_type->Clear();
+ if (size)
+ *size = 0;
+ if (is_incomplete)
+ *is_incomplete = false;
+
+ if (JavaArrayType *array =
+ llvm::dyn_cast<JavaArrayType>(static_cast<JavaType *>(type))) {
if (element_type)
- element_type->Clear();
- if (size)
- *size = 0;
- if (is_incomplete)
- *is_incomplete = false;
-
- if (JavaArrayType *array = llvm::dyn_cast<JavaArrayType>(static_cast<JavaType *>(type)))
- {
- if (element_type)
- *element_type = array->GetElementType();
- return true;
- }
- return false;
+ *element_type = array->GetElementType();
+ return true;
+ }
+ return false;
+}
+
+bool JavaASTContext::IsAggregateType(lldb::opaque_compiler_type_t type) {
+ return llvm::isa<JavaObjectType>(static_cast<JavaType *>(type));
}
-bool
-JavaASTContext::IsAggregateType(lldb::opaque_compiler_type_t type)
-{
- return llvm::isa<JavaObjectType>(static_cast<JavaType *>(type));
-}
-
-bool
-JavaASTContext::IsCharType(lldb::opaque_compiler_type_t type)
-{
- if (JavaPrimitiveType *ptype = llvm::dyn_cast<JavaPrimitiveType>(static_cast<JavaType *>(type)))
- return ptype->GetTypeKind() == JavaPrimitiveType::eTypeChar;
- return false;
-}
-
-bool
-JavaASTContext::IsFloatingPointType(lldb::opaque_compiler_type_t type, uint32_t &count, bool &is_complex)
-{
- is_complex = true;
-
- if (JavaPrimitiveType *ptype = llvm::dyn_cast<JavaPrimitiveType>(static_cast<JavaType *>(type)))
- {
- switch (ptype->GetTypeKind())
- {
- case JavaPrimitiveType::eTypeFloat:
- case JavaPrimitiveType::eTypeDouble:
- count = 1;
- return true;
- default:
- break;
- }
+bool JavaASTContext::IsCharType(lldb::opaque_compiler_type_t type) {
+ if (JavaPrimitiveType *ptype =
+ llvm::dyn_cast<JavaPrimitiveType>(static_cast<JavaType *>(type)))
+ return ptype->GetTypeKind() == JavaPrimitiveType::eTypeChar;
+ return false;
+}
+
+bool JavaASTContext::IsFloatingPointType(lldb::opaque_compiler_type_t type,
+ uint32_t &count, bool &is_complex) {
+ is_complex = true;
+
+ if (JavaPrimitiveType *ptype =
+ llvm::dyn_cast<JavaPrimitiveType>(static_cast<JavaType *>(type))) {
+ switch (ptype->GetTypeKind()) {
+ case JavaPrimitiveType::eTypeFloat:
+ case JavaPrimitiveType::eTypeDouble:
+ count = 1;
+ return true;
+ default:
+ break;
}
+ }
- count = 0;
- return false;
+ count = 0;
+ return false;
}
-bool
-JavaASTContext::IsFunctionType(lldb::opaque_compiler_type_t type, bool *is_variadic_ptr)
-{
- if (is_variadic_ptr)
- *is_variadic_ptr = false;
- return false;
+bool JavaASTContext::IsFunctionType(lldb::opaque_compiler_type_t type,
+ bool *is_variadic_ptr) {
+ if (is_variadic_ptr)
+ *is_variadic_ptr = false;
+ return false;
}
-size_t
-JavaASTContext::GetNumberOfFunctionArguments(lldb::opaque_compiler_type_t type)
-{
- return 0;
+size_t JavaASTContext::GetNumberOfFunctionArguments(
+ lldb::opaque_compiler_type_t type) {
+ return 0;
}
CompilerType
-JavaASTContext::GetFunctionArgumentAtIndex(lldb::opaque_compiler_type_t type, const size_t index)
-{
- return CompilerType();
+JavaASTContext::GetFunctionArgumentAtIndex(lldb::opaque_compiler_type_t type,
+ const size_t index) {
+ return CompilerType();
+}
+
+bool JavaASTContext::IsFunctionPointerType(lldb::opaque_compiler_type_t type) {
+ return false;
}
-bool
-JavaASTContext::IsFunctionPointerType(lldb::opaque_compiler_type_t type)
-{
- return false;
-}
-
-bool
-JavaASTContext::IsBlockPointerType (lldb::opaque_compiler_type_t type, CompilerType *function_pointer_type_ptr)
-{
- return false;
-}
-
-bool
-JavaASTContext::IsIntegerType(lldb::opaque_compiler_type_t type, bool &is_signed)
-{
- if (JavaPrimitiveType *ptype = llvm::dyn_cast<JavaPrimitiveType>(static_cast<JavaType *>(type)))
- {
- switch (ptype->GetTypeKind())
- {
- case JavaPrimitiveType::eTypeByte:
- case JavaPrimitiveType::eTypeShort:
- case JavaPrimitiveType::eTypeInt:
- case JavaPrimitiveType::eTypeLong:
- is_signed = true;
- return true;
- default:
- break;
- }
+bool JavaASTContext::IsBlockPointerType(
+ lldb::opaque_compiler_type_t type,
+ CompilerType *function_pointer_type_ptr) {
+ return false;
+}
+
+bool JavaASTContext::IsIntegerType(lldb::opaque_compiler_type_t type,
+ bool &is_signed) {
+ if (JavaPrimitiveType *ptype =
+ llvm::dyn_cast<JavaPrimitiveType>(static_cast<JavaType *>(type))) {
+ switch (ptype->GetTypeKind()) {
+ case JavaPrimitiveType::eTypeByte:
+ case JavaPrimitiveType::eTypeShort:
+ case JavaPrimitiveType::eTypeInt:
+ case JavaPrimitiveType::eTypeLong:
+ is_signed = true;
+ return true;
+ default:
+ break;
}
+ }
- is_signed = false;
- return false;
+ is_signed = false;
+ return false;
}
-bool
-JavaASTContext::IsPossibleDynamicType(lldb::opaque_compiler_type_t type, CompilerType *target_type,
- bool check_cplusplus, bool check_objc)
-{
- return llvm::isa<JavaReferenceType>(static_cast<JavaType *>(type));
+bool JavaASTContext::IsPossibleDynamicType(lldb::opaque_compiler_type_t type,
+ CompilerType *target_type,
+ bool check_cplusplus,
+ bool check_objc) {
+ return llvm::isa<JavaReferenceType>(static_cast<JavaType *>(type));
}
-bool
-JavaASTContext::IsPointerType(lldb::opaque_compiler_type_t type, CompilerType *pointee_type)
-{
- if (pointee_type)
- pointee_type->Clear();
- return false;
+bool JavaASTContext::IsPointerType(lldb::opaque_compiler_type_t type,
+ CompilerType *pointee_type) {
+ if (pointee_type)
+ pointee_type->Clear();
+ return false;
}
-bool
-JavaASTContext::IsReferenceType(lldb::opaque_compiler_type_t type, CompilerType *pointee_type, bool *is_rvalue)
-{
- if (is_rvalue)
- *is_rvalue = false;
-
- if (JavaReferenceType *ref = llvm::dyn_cast<JavaReferenceType>(static_cast<JavaType *>(type)))
- {
- if (pointee_type)
- *pointee_type = ref->GetPointeeType();
- return true;
- }
+bool JavaASTContext::IsReferenceType(lldb::opaque_compiler_type_t type,
+ CompilerType *pointee_type,
+ bool *is_rvalue) {
+ if (is_rvalue)
+ *is_rvalue = false;
+ if (JavaReferenceType *ref =
+ llvm::dyn_cast<JavaReferenceType>(static_cast<JavaType *>(type))) {
if (pointee_type)
- pointee_type->Clear();
- return false;
+ *pointee_type = ref->GetPointeeType();
+ return true;
+ }
+
+ if (pointee_type)
+ pointee_type->Clear();
+ return false;
}
-bool
-JavaASTContext::IsScalarType(lldb::opaque_compiler_type_t type)
-{
- return llvm::isa<JavaReferenceType>(static_cast<JavaType *>(type)) ||
- llvm::isa<JavaPrimitiveType>(static_cast<JavaType *>(type));
+bool JavaASTContext::IsScalarType(lldb::opaque_compiler_type_t type) {
+ return llvm::isa<JavaReferenceType>(static_cast<JavaType *>(type)) ||
+ llvm::isa<JavaPrimitiveType>(static_cast<JavaType *>(type));
}
-bool
-JavaASTContext::IsVoidType(lldb::opaque_compiler_type_t type)
-{
- return false; // TODO: Implement if we introduce the void type
+bool JavaASTContext::IsVoidType(lldb::opaque_compiler_type_t type) {
+ return false; // TODO: Implement if we introduce the void type
}
-bool
-JavaASTContext::SupportsLanguage(lldb::LanguageType language)
-{
- return language == lldb::eLanguageTypeJava;
+bool JavaASTContext::SupportsLanguage(lldb::LanguageType language) {
+ return language == lldb::eLanguageTypeJava;
}
-bool
-JavaASTContext::IsRuntimeGeneratedType(lldb::opaque_compiler_type_t type)
-{
- return true;
+bool JavaASTContext::IsRuntimeGeneratedType(lldb::opaque_compiler_type_t type) {
+ return true;
}
-bool
-JavaASTContext::IsPointerOrReferenceType(lldb::opaque_compiler_type_t type, CompilerType *pointee_type)
-{
- return IsPointerType(type, pointee_type) || IsReferenceType(type, pointee_type);
+bool JavaASTContext::IsPointerOrReferenceType(lldb::opaque_compiler_type_t type,
+ CompilerType *pointee_type) {
+ return IsPointerType(type, pointee_type) ||
+ IsReferenceType(type, pointee_type);
}
-bool
-JavaASTContext::IsCStringType(lldb::opaque_compiler_type_t type, uint32_t &length)
-{
- return false; // TODO: Implement it if we need it for string literals
+bool JavaASTContext::IsCStringType(lldb::opaque_compiler_type_t type,
+ uint32_t &length) {
+ return false; // TODO: Implement it if we need it for string literals
}
-bool
-JavaASTContext::IsTypedefType(lldb::opaque_compiler_type_t type)
-{
- return false;
+bool JavaASTContext::IsTypedefType(lldb::opaque_compiler_type_t type) {
+ return false;
}
-bool
-JavaASTContext::IsVectorType(lldb::opaque_compiler_type_t type, CompilerType *element_type, uint64_t *size)
-{
- if (element_type)
- element_type->Clear();
- if (size)
- *size = 0;
- return false;
+bool JavaASTContext::IsVectorType(lldb::opaque_compiler_type_t type,
+ CompilerType *element_type, uint64_t *size) {
+ if (element_type)
+ element_type->Clear();
+ if (size)
+ *size = 0;
+ return false;
}
-bool
-JavaASTContext::IsPolymorphicClass(lldb::opaque_compiler_type_t type)
-{
- return llvm::isa<JavaObjectType>(static_cast<JavaType *>(type));
+bool JavaASTContext::IsPolymorphicClass(lldb::opaque_compiler_type_t type) {
+ return llvm::isa<JavaObjectType>(static_cast<JavaType *>(type));
}
uint32_t
-JavaASTContext::IsHomogeneousAggregate(lldb::opaque_compiler_type_t type, CompilerType *base_type_ptr)
-{
- return false;
+JavaASTContext::IsHomogeneousAggregate(lldb::opaque_compiler_type_t type,
+ CompilerType *base_type_ptr) {
+ return false;
}
-bool
-JavaASTContext::IsCompleteType(lldb::opaque_compiler_type_t type)
-{
- return static_cast<JavaType *>(type)->IsCompleteType();
+bool JavaASTContext::IsCompleteType(lldb::opaque_compiler_type_t type) {
+ return static_cast<JavaType *>(type)->IsCompleteType();
}
-bool
-JavaASTContext::IsConst(lldb::opaque_compiler_type_t type)
-{
- return false;
+bool JavaASTContext::IsConst(lldb::opaque_compiler_type_t type) {
+ return false;
}
-bool
-JavaASTContext::IsBeingDefined(lldb::opaque_compiler_type_t type)
-{
- return false;
+bool JavaASTContext::IsBeingDefined(lldb::opaque_compiler_type_t type) {
+ return false;
}
-bool
-JavaASTContext::IsDefined(lldb::opaque_compiler_type_t type)
-{
- return type != nullptr;
+bool JavaASTContext::IsDefined(lldb::opaque_compiler_type_t type) {
+ return type != nullptr;
}
-bool
-JavaASTContext::GetCompleteType(lldb::opaque_compiler_type_t type)
-{
- if (IsCompleteType(type))
- return true;
-
- if (JavaArrayType *array = llvm::dyn_cast<JavaArrayType>(static_cast<JavaType *>(type)))
- return GetCompleteType(array->GetElementType().GetOpaqueQualType());
-
- if (JavaReferenceType *reference = llvm::dyn_cast<JavaReferenceType>(static_cast<JavaType *>(type)))
- return GetCompleteType(reference->GetPointeeType().GetOpaqueQualType());
-
- if (llvm::isa<JavaObjectType>(static_cast<JavaType *>(type)))
- {
- SymbolFile *symbol_file = GetSymbolFile();
- if (!symbol_file)
- return false;
-
- CompilerType object_type(this, type);
- return symbol_file->CompleteType(object_type);
- }
- return false;
-}
+bool JavaASTContext::GetCompleteType(lldb::opaque_compiler_type_t type) {
+ if (IsCompleteType(type))
+ return true;
-ConstString
-JavaASTContext::GetTypeName(lldb::opaque_compiler_type_t type)
-{
- if (type)
- return static_cast<JavaType *>(type)->GetName();
- return ConstString();
+ if (JavaArrayType *array =
+ llvm::dyn_cast<JavaArrayType>(static_cast<JavaType *>(type)))
+ return GetCompleteType(array->GetElementType().GetOpaqueQualType());
+
+ if (JavaReferenceType *reference =
+ llvm::dyn_cast<JavaReferenceType>(static_cast<JavaType *>(type)))
+ return GetCompleteType(reference->GetPointeeType().GetOpaqueQualType());
+
+ if (llvm::isa<JavaObjectType>(static_cast<JavaType *>(type))) {
+ SymbolFile *symbol_file = GetSymbolFile();
+ if (!symbol_file)
+ return false;
+
+ CompilerType object_type(this, type);
+ return symbol_file->CompleteType(object_type);
+ }
+ return false;
+}
+
+ConstString JavaASTContext::GetTypeName(lldb::opaque_compiler_type_t type) {
+ if (type)
+ return static_cast<JavaType *>(type)->GetName();
+ return ConstString();
}
uint32_t
-JavaASTContext::GetTypeInfo(lldb::opaque_compiler_type_t type, CompilerType *pointee_or_element_compiler_type)
-{
- if (pointee_or_element_compiler_type)
- pointee_or_element_compiler_type->Clear();
- if (!type)
- return 0;
+JavaASTContext::GetTypeInfo(lldb::opaque_compiler_type_t type,
+ CompilerType *pointee_or_element_compiler_type) {
+ if (pointee_or_element_compiler_type)
+ pointee_or_element_compiler_type->Clear();
+ if (!type)
+ return 0;
- if (IsReferenceType(type, pointee_or_element_compiler_type))
- return eTypeHasChildren | eTypeHasValue | eTypeIsReference;
- if (IsArrayType(type, pointee_or_element_compiler_type, nullptr, nullptr))
- return eTypeHasChildren | eTypeIsArray;
- if (llvm::isa<JavaObjectType>(static_cast<JavaType *>(type)))
- return eTypeHasChildren | eTypeIsClass;
-
- if (JavaPrimitiveType *ptype = llvm::dyn_cast<JavaPrimitiveType>(static_cast<JavaType *>(type)))
- {
- switch (ptype->GetTypeKind())
- {
- case JavaPrimitiveType::eTypeByte:
- case JavaPrimitiveType::eTypeShort:
- case JavaPrimitiveType::eTypeInt:
- case JavaPrimitiveType::eTypeLong:
- return eTypeHasValue | eTypeIsBuiltIn | eTypeIsScalar | eTypeIsInteger | eTypeIsSigned;
- case JavaPrimitiveType::eTypeFloat:
- case JavaPrimitiveType::eTypeDouble:
- return eTypeHasValue | eTypeIsBuiltIn | eTypeIsScalar | eTypeIsFloat | eTypeIsSigned;
- case JavaPrimitiveType::eTypeBoolean:
- return eTypeHasValue | eTypeIsBuiltIn | eTypeIsScalar;
- case JavaPrimitiveType::eTypeChar:
- return eTypeHasValue | eTypeIsBuiltIn | eTypeIsScalar;
- }
+ if (IsReferenceType(type, pointee_or_element_compiler_type))
+ return eTypeHasChildren | eTypeHasValue | eTypeIsReference;
+ if (IsArrayType(type, pointee_or_element_compiler_type, nullptr, nullptr))
+ return eTypeHasChildren | eTypeIsArray;
+ if (llvm::isa<JavaObjectType>(static_cast<JavaType *>(type)))
+ return eTypeHasChildren | eTypeIsClass;
+
+ if (JavaPrimitiveType *ptype =
+ llvm::dyn_cast<JavaPrimitiveType>(static_cast<JavaType *>(type))) {
+ switch (ptype->GetTypeKind()) {
+ case JavaPrimitiveType::eTypeByte:
+ case JavaPrimitiveType::eTypeShort:
+ case JavaPrimitiveType::eTypeInt:
+ case JavaPrimitiveType::eTypeLong:
+ return eTypeHasValue | eTypeIsBuiltIn | eTypeIsScalar | eTypeIsInteger |
+ eTypeIsSigned;
+ case JavaPrimitiveType::eTypeFloat:
+ case JavaPrimitiveType::eTypeDouble:
+ return eTypeHasValue | eTypeIsBuiltIn | eTypeIsScalar | eTypeIsFloat |
+ eTypeIsSigned;
+ case JavaPrimitiveType::eTypeBoolean:
+ return eTypeHasValue | eTypeIsBuiltIn | eTypeIsScalar;
+ case JavaPrimitiveType::eTypeChar:
+ return eTypeHasValue | eTypeIsBuiltIn | eTypeIsScalar;
}
- return 0;
+ }
+ return 0;
}
lldb::TypeClass
-JavaASTContext::GetTypeClass(lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return eTypeClassInvalid;
- if (llvm::isa<JavaReferenceType>(static_cast<JavaType *>(type)))
- return eTypeClassReference;
- if (llvm::isa<JavaArrayType>(static_cast<JavaType *>(type)))
- return eTypeClassArray;
- if (llvm::isa<JavaObjectType>(static_cast<JavaType *>(type)))
- return eTypeClassClass;
- if (llvm::isa<JavaPrimitiveType>(static_cast<JavaType *>(type)))
- return eTypeClassBuiltin;
- assert(false && "Java type with unhandled type class");
+JavaASTContext::GetTypeClass(lldb::opaque_compiler_type_t type) {
+ if (!type)
return eTypeClassInvalid;
+ if (llvm::isa<JavaReferenceType>(static_cast<JavaType *>(type)))
+ return eTypeClassReference;
+ if (llvm::isa<JavaArrayType>(static_cast<JavaType *>(type)))
+ return eTypeClassArray;
+ if (llvm::isa<JavaObjectType>(static_cast<JavaType *>(type)))
+ return eTypeClassClass;
+ if (llvm::isa<JavaPrimitiveType>(static_cast<JavaType *>(type)))
+ return eTypeClassBuiltin;
+ assert(false && "Java type with unhandled type class");
+ return eTypeClassInvalid;
}
lldb::LanguageType
-JavaASTContext::GetMinimumLanguage(lldb::opaque_compiler_type_t type)
-{
- return lldb::eLanguageTypeJava;
+JavaASTContext::GetMinimumLanguage(lldb::opaque_compiler_type_t type) {
+ return lldb::eLanguageTypeJava;
}
CompilerType
-JavaASTContext::GetArrayElementType(lldb::opaque_compiler_type_t type, uint64_t *stride)
-{
- if (stride)
- *stride = 0;
-
- CompilerType element_type;
- if (IsArrayType(type, &element_type, nullptr, nullptr))
- return element_type;
- return CompilerType();
+JavaASTContext::GetArrayElementType(lldb::opaque_compiler_type_t type,
+ uint64_t *stride) {
+ if (stride)
+ *stride = 0;
+
+ CompilerType element_type;
+ if (IsArrayType(type, &element_type, nullptr, nullptr))
+ return element_type;
+ return CompilerType();
}
-CompilerType
-JavaASTContext::GetPointeeType(lldb::opaque_compiler_type_t type)
-{
- CompilerType pointee_type;
- if (IsPointerType(type, &pointee_type))
- return pointee_type;
- return CompilerType();
+CompilerType JavaASTContext::GetPointeeType(lldb::opaque_compiler_type_t type) {
+ CompilerType pointee_type;
+ if (IsPointerType(type, &pointee_type))
+ return pointee_type;
+ return CompilerType();
}
-CompilerType
-JavaASTContext::GetPointerType(lldb::opaque_compiler_type_t type)
-{
- return CompilerType(); // No pointer types in java
+CompilerType JavaASTContext::GetPointerType(lldb::opaque_compiler_type_t type) {
+ return CompilerType(); // No pointer types in java
}
CompilerType
-JavaASTContext::GetCanonicalType(lldb::opaque_compiler_type_t type)
-{
- return CompilerType(this, type);
+JavaASTContext::GetCanonicalType(lldb::opaque_compiler_type_t type) {
+ return CompilerType(this, type);
}
CompilerType
-JavaASTContext::GetFullyUnqualifiedType(lldb::opaque_compiler_type_t type)
-{
- return CompilerType(this, type);
+JavaASTContext::GetFullyUnqualifiedType(lldb::opaque_compiler_type_t type) {
+ return CompilerType(this, type);
}
CompilerType
-JavaASTContext::GetNonReferenceType(lldb::opaque_compiler_type_t type)
-{
- CompilerType pointee_type;
- if (IsReferenceType(type, &pointee_type))
- return pointee_type;
- return CompilerType(this, type);
+JavaASTContext::GetNonReferenceType(lldb::opaque_compiler_type_t type) {
+ CompilerType pointee_type;
+ if (IsReferenceType(type, &pointee_type))
+ return pointee_type;
+ return CompilerType(this, type);
}
CompilerType
-JavaASTContext::GetTypedefedType(lldb::opaque_compiler_type_t type)
-{
- return CompilerType();
+JavaASTContext::GetTypedefedType(lldb::opaque_compiler_type_t type) {
+ return CompilerType();
}
-CompilerType
-JavaASTContext::GetBasicTypeFromAST(lldb::BasicType basic_type)
-{
- return CompilerType();
+CompilerType JavaASTContext::GetBasicTypeFromAST(lldb::BasicType basic_type) {
+ return CompilerType();
}
CompilerType
-JavaASTContext::GetBuiltinTypeForEncodingAndBitSize(lldb::Encoding encoding, size_t bit_size)
-{
- return CompilerType();
+JavaASTContext::GetBuiltinTypeForEncodingAndBitSize(lldb::Encoding encoding,
+ size_t bit_size) {
+ return CompilerType();
}
-size_t
-JavaASTContext::GetTypeBitAlign(lldb::opaque_compiler_type_t type)
-{
- return 0;
+size_t JavaASTContext::GetTypeBitAlign(lldb::opaque_compiler_type_t type) {
+ return 0;
}
lldb::BasicType
-JavaASTContext::GetBasicTypeEnumeration(lldb::opaque_compiler_type_t type)
-{
- if (JavaPrimitiveType *ptype = llvm::dyn_cast<JavaPrimitiveType>(static_cast<JavaType *>(type)))
- {
- switch (ptype->GetTypeKind())
- {
- case JavaPrimitiveType::eTypeByte:
- return eBasicTypeOther;
- case JavaPrimitiveType::eTypeShort:
- return eBasicTypeShort;
- case JavaPrimitiveType::eTypeInt:
- return eBasicTypeInt;
- case JavaPrimitiveType::eTypeLong:
- return eBasicTypeLong;
- case JavaPrimitiveType::eTypeFloat:
- return eBasicTypeFloat;
- case JavaPrimitiveType::eTypeDouble:
- return eBasicTypeDouble;
- case JavaPrimitiveType::eTypeBoolean:
- return eBasicTypeBool;
- case JavaPrimitiveType::eTypeChar:
- return eBasicTypeChar;
- }
- }
- return eBasicTypeInvalid;
-}
-
-uint64_t
-JavaASTContext::GetBitSize(lldb::opaque_compiler_type_t type, ExecutionContextScope *exe_scope)
-{
- if (JavaPrimitiveType *ptype = llvm::dyn_cast<JavaPrimitiveType>(static_cast<JavaType *>(type)))
- {
- switch (ptype->GetTypeKind())
- {
- case JavaPrimitiveType::eTypeByte:
- return 8;
- case JavaPrimitiveType::eTypeShort:
- return 16;
- case JavaPrimitiveType::eTypeInt:
- return 32;
- case JavaPrimitiveType::eTypeLong:
- return 64;
- case JavaPrimitiveType::eTypeFloat:
- return 32;
- case JavaPrimitiveType::eTypeDouble:
- return 64;
- case JavaPrimitiveType::eTypeBoolean:
- return 1;
- case JavaPrimitiveType::eTypeChar:
- return 16;
- }
- }
- else if (llvm::isa<JavaReferenceType>(static_cast<JavaType *>(type)))
- {
- return 32; // References are always 4 byte long in java
- }
- else if (llvm::isa<JavaArrayType>(static_cast<JavaType *>(type)))
- {
- return 64;
- }
- else if (JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type)))
- {
- return obj->GetByteSize() * 8;
- }
- return 0;
+JavaASTContext::GetBasicTypeEnumeration(lldb::opaque_compiler_type_t type) {
+ if (JavaPrimitiveType *ptype =
+ llvm::dyn_cast<JavaPrimitiveType>(static_cast<JavaType *>(type))) {
+ switch (ptype->GetTypeKind()) {
+ case JavaPrimitiveType::eTypeByte:
+ return eBasicTypeOther;
+ case JavaPrimitiveType::eTypeShort:
+ return eBasicTypeShort;
+ case JavaPrimitiveType::eTypeInt:
+ return eBasicTypeInt;
+ case JavaPrimitiveType::eTypeLong:
+ return eBasicTypeLong;
+ case JavaPrimitiveType::eTypeFloat:
+ return eBasicTypeFloat;
+ case JavaPrimitiveType::eTypeDouble:
+ return eBasicTypeDouble;
+ case JavaPrimitiveType::eTypeBoolean:
+ return eBasicTypeBool;
+ case JavaPrimitiveType::eTypeChar:
+ return eBasicTypeChar;
+ }
+ }
+ return eBasicTypeInvalid;
+}
+
+uint64_t JavaASTContext::GetBitSize(lldb::opaque_compiler_type_t type,
+ ExecutionContextScope *exe_scope) {
+ if (JavaPrimitiveType *ptype =
+ llvm::dyn_cast<JavaPrimitiveType>(static_cast<JavaType *>(type))) {
+ switch (ptype->GetTypeKind()) {
+ case JavaPrimitiveType::eTypeByte:
+ return 8;
+ case JavaPrimitiveType::eTypeShort:
+ return 16;
+ case JavaPrimitiveType::eTypeInt:
+ return 32;
+ case JavaPrimitiveType::eTypeLong:
+ return 64;
+ case JavaPrimitiveType::eTypeFloat:
+ return 32;
+ case JavaPrimitiveType::eTypeDouble:
+ return 64;
+ case JavaPrimitiveType::eTypeBoolean:
+ return 1;
+ case JavaPrimitiveType::eTypeChar:
+ return 16;
+ }
+ } else if (llvm::isa<JavaReferenceType>(static_cast<JavaType *>(type))) {
+ return 32; // References are always 4 byte long in java
+ } else if (llvm::isa<JavaArrayType>(static_cast<JavaType *>(type))) {
+ return 64;
+ } else if (JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(
+ static_cast<JavaType *>(type))) {
+ return obj->GetByteSize() * 8;
+ }
+ return 0;
+}
+
+lldb::Encoding JavaASTContext::GetEncoding(lldb::opaque_compiler_type_t type,
+ uint64_t &count) {
+ count = 1;
+
+ if (JavaPrimitiveType *ptype =
+ llvm::dyn_cast<JavaPrimitiveType>(static_cast<JavaType *>(type))) {
+ switch (ptype->GetTypeKind()) {
+ case JavaPrimitiveType::eTypeByte:
+ case JavaPrimitiveType::eTypeShort:
+ case JavaPrimitiveType::eTypeInt:
+ case JavaPrimitiveType::eTypeLong:
+ return eEncodingSint;
+ case JavaPrimitiveType::eTypeFloat:
+ case JavaPrimitiveType::eTypeDouble:
+ return eEncodingIEEE754;
+ case JavaPrimitiveType::eTypeBoolean:
+ case JavaPrimitiveType::eTypeChar:
+ return eEncodingUint;
+ }
+ }
+ if (IsReferenceType(type))
+ return eEncodingUint;
+ return eEncodingInvalid;
+}
+
+lldb::Format JavaASTContext::GetFormat(lldb::opaque_compiler_type_t type) {
+ if (JavaPrimitiveType *ptype =
+ llvm::dyn_cast<JavaPrimitiveType>(static_cast<JavaType *>(type))) {
+ switch (ptype->GetTypeKind()) {
+ case JavaPrimitiveType::eTypeByte:
+ case JavaPrimitiveType::eTypeShort:
+ case JavaPrimitiveType::eTypeInt:
+ case JavaPrimitiveType::eTypeLong:
+ return eFormatDecimal;
+ case JavaPrimitiveType::eTypeFloat:
+ case JavaPrimitiveType::eTypeDouble:
+ return eFormatFloat;
+ case JavaPrimitiveType::eTypeBoolean:
+ return eFormatBoolean;
+ case JavaPrimitiveType::eTypeChar:
+ return eFormatUnicode16;
+ }
+ }
+ if (IsReferenceType(type))
+ return eFormatHex;
+ return eFormatDefault;
}
-lldb::Encoding
-JavaASTContext::GetEncoding(lldb::opaque_compiler_type_t type, uint64_t &count)
-{
- count = 1;
-
- if (JavaPrimitiveType *ptype = llvm::dyn_cast<JavaPrimitiveType>(static_cast<JavaType *>(type)))
- {
- switch (ptype->GetTypeKind())
- {
- case JavaPrimitiveType::eTypeByte:
- case JavaPrimitiveType::eTypeShort:
- case JavaPrimitiveType::eTypeInt:
- case JavaPrimitiveType::eTypeLong:
- return eEncodingSint;
- case JavaPrimitiveType::eTypeFloat:
- case JavaPrimitiveType::eTypeDouble:
- return eEncodingIEEE754;
- case JavaPrimitiveType::eTypeBoolean:
- case JavaPrimitiveType::eTypeChar:
- return eEncodingUint;
- }
- }
- if (IsReferenceType(type))
- return eEncodingUint;
- return eEncodingInvalid;
-}
-
-lldb::Format
-JavaASTContext::GetFormat(lldb::opaque_compiler_type_t type)
-{
- if (JavaPrimitiveType *ptype = llvm::dyn_cast<JavaPrimitiveType>(static_cast<JavaType *>(type)))
- {
- switch (ptype->GetTypeKind())
- {
- case JavaPrimitiveType::eTypeByte:
- case JavaPrimitiveType::eTypeShort:
- case JavaPrimitiveType::eTypeInt:
- case JavaPrimitiveType::eTypeLong:
- return eFormatDecimal;
- case JavaPrimitiveType::eTypeFloat:
- case JavaPrimitiveType::eTypeDouble:
- return eFormatFloat;
- case JavaPrimitiveType::eTypeBoolean:
- return eFormatBoolean;
- case JavaPrimitiveType::eTypeChar:
- return eFormatUnicode16;
- }
- }
- if (IsReferenceType(type))
- return eFormatHex;
- return eFormatDefault;
-}
-
-unsigned
-JavaASTContext::GetTypeQualifiers(lldb::opaque_compiler_type_t type)
-{
- return 0;
+unsigned JavaASTContext::GetTypeQualifiers(lldb::opaque_compiler_type_t type) {
+ return 0;
}
size_t
-JavaASTContext::ConvertStringToFloatValue(lldb::opaque_compiler_type_t type, const char *s, uint8_t *dst,
- size_t dst_size)
-{
- assert(false && "Not implemented");
- return 0;
+JavaASTContext::ConvertStringToFloatValue(lldb::opaque_compiler_type_t type,
+ const char *s, uint8_t *dst,
+ size_t dst_size) {
+ assert(false && "Not implemented");
+ return 0;
}
size_t
-JavaASTContext::GetNumTemplateArguments(lldb::opaque_compiler_type_t type)
-{
- return 0;
+JavaASTContext::GetNumTemplateArguments(lldb::opaque_compiler_type_t type) {
+ return 0;
}
CompilerType
-JavaASTContext::GetTemplateArgument(lldb::opaque_compiler_type_t type, size_t idx, lldb::TemplateArgumentKind &kind)
-{
- return CompilerType();
+JavaASTContext::GetTemplateArgument(lldb::opaque_compiler_type_t type,
+ size_t idx,
+ lldb::TemplateArgumentKind &kind) {
+ return CompilerType();
}
-uint32_t
-JavaASTContext::GetNumFields(lldb::opaque_compiler_type_t type)
-{
- if (JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type)))
- {
- GetCompleteType(type);
- return obj->GetNumFields();
- }
- return 0;
-}
+uint32_t JavaASTContext::GetNumFields(lldb::opaque_compiler_type_t type) {
+ if (JavaObjectType *obj =
+ llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type))) {
+ GetCompleteType(type);
+ return obj->GetNumFields();
+ }
+ return 0;
+}
+
+CompilerType JavaASTContext::GetFieldAtIndex(lldb::opaque_compiler_type_t type,
+ size_t idx, std::string &name,
+ uint64_t *bit_offset_ptr,
+ uint32_t *bitfield_bit_size_ptr,
+ bool *is_bitfield_ptr) {
+ if (bit_offset_ptr)
+ *bit_offset_ptr = 0;
+ if (bitfield_bit_size_ptr)
+ *bitfield_bit_size_ptr = 0;
+ if (is_bitfield_ptr)
+ *is_bitfield_ptr = false;
-CompilerType
-JavaASTContext::GetFieldAtIndex(lldb::opaque_compiler_type_t type, size_t idx, std::string &name,
- uint64_t *bit_offset_ptr, uint32_t *bitfield_bit_size_ptr, bool *is_bitfield_ptr)
-{
+ if (JavaObjectType *obj =
+ llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type))) {
+ GetCompleteType(type);
+
+ JavaObjectType::Field *field = obj->GetFieldAtIndex(idx);
+ if (!field)
+ return CompilerType();
+ name = field->m_name.AsCString();
if (bit_offset_ptr)
- *bit_offset_ptr = 0;
- if (bitfield_bit_size_ptr)
- *bitfield_bit_size_ptr = 0;
- if (is_bitfield_ptr)
- *is_bitfield_ptr = false;
-
- if (JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type)))
- {
- GetCompleteType(type);
-
- JavaObjectType::Field *field = obj->GetFieldAtIndex(idx);
- if (!field)
- return CompilerType();
- name = field->m_name.AsCString();
- if (bit_offset_ptr)
- *bit_offset_ptr = field->m_offset * 8;
- return field->m_type;
- }
- return CompilerType();
+ *bit_offset_ptr = field->m_offset * 8;
+ return field->m_type;
+ }
+ return CompilerType();
}
-uint32_t
-JavaASTContext::GetNumChildren(lldb::opaque_compiler_type_t type, bool omit_empty_base_classes)
-{
- GetCompleteType(type);
+uint32_t JavaASTContext::GetNumChildren(lldb::opaque_compiler_type_t type,
+ bool omit_empty_base_classes) {
+ GetCompleteType(type);
- if (JavaReferenceType *ref = llvm::dyn_cast<JavaReferenceType>(static_cast<JavaType *>(type)))
- return ref->GetPointeeType().GetNumChildren(omit_empty_base_classes);
+ if (JavaReferenceType *ref =
+ llvm::dyn_cast<JavaReferenceType>(static_cast<JavaType *>(type)))
+ return ref->GetPointeeType().GetNumChildren(omit_empty_base_classes);
- if (llvm::isa<JavaObjectType>(static_cast<JavaType *>(type)))
- return GetNumFields(type) + GetNumDirectBaseClasses(type);
+ if (llvm::isa<JavaObjectType>(static_cast<JavaType *>(type)))
+ return GetNumFields(type) + GetNumDirectBaseClasses(type);
- return 0;
+ return 0;
}
uint32_t
-JavaASTContext::GetNumDirectBaseClasses(lldb::opaque_compiler_type_t type)
-{
- if (JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type)))
- {
- GetCompleteType(type);
- return obj->GetNumInterfaces() + (obj->GetBaseClass() ? 1 : 0);
- }
- return 0;
+JavaASTContext::GetNumDirectBaseClasses(lldb::opaque_compiler_type_t type) {
+ if (JavaObjectType *obj =
+ llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type))) {
+ GetCompleteType(type);
+ return obj->GetNumInterfaces() + (obj->GetBaseClass() ? 1 : 0);
+ }
+ return 0;
}
uint32_t
-JavaASTContext::GetNumVirtualBaseClasses(lldb::opaque_compiler_type_t type)
-{
- if (JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type)))
- {
- GetCompleteType(type);
- return obj->GetNumInterfaces();
- }
- return 0;
+JavaASTContext::GetNumVirtualBaseClasses(lldb::opaque_compiler_type_t type) {
+ if (JavaObjectType *obj =
+ llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type))) {
+ GetCompleteType(type);
+ return obj->GetNumInterfaces();
+ }
+ return 0;
}
-CompilerType
-JavaASTContext::GetDirectBaseClassAtIndex(lldb::opaque_compiler_type_t type, size_t idx, uint32_t *bit_offset_ptr)
-{
- if (JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type)))
- {
- GetCompleteType(type);
-
- if (CompilerType base_class = obj->GetBaseClass())
- {
- if (idx == 0)
- return base_class;
- else
- --idx;
- }
- return obj->GetInterfaceAtIndex(idx);
- }
- return CompilerType();
+CompilerType JavaASTContext::GetDirectBaseClassAtIndex(
+ lldb::opaque_compiler_type_t type, size_t idx, uint32_t *bit_offset_ptr) {
+ if (JavaObjectType *obj =
+ llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type))) {
+ GetCompleteType(type);
+
+ if (CompilerType base_class = obj->GetBaseClass()) {
+ if (idx == 0)
+ return base_class;
+ else
+ --idx;
+ }
+ return obj->GetInterfaceAtIndex(idx);
+ }
+ return CompilerType();
}
-CompilerType
-JavaASTContext::GetVirtualBaseClassAtIndex(lldb::opaque_compiler_type_t type, size_t idx, uint32_t *bit_offset_ptr)
-{
- if (JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type)))
- {
- GetCompleteType(type);
- return obj->GetInterfaceAtIndex(idx);
- }
- return CompilerType();
+CompilerType JavaASTContext::GetVirtualBaseClassAtIndex(
+ lldb::opaque_compiler_type_t type, size_t idx, uint32_t *bit_offset_ptr) {
+ if (JavaObjectType *obj =
+ llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type))) {
+ GetCompleteType(type);
+ return obj->GetInterfaceAtIndex(idx);
+ }
+ return CompilerType();
}
-void
-JavaASTContext::DumpValue(lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx, Stream *s, lldb::Format format,
- const DataExtractor &data, lldb::offset_t data_offset, size_t data_byte_size,
- uint32_t bitfield_bit_size, uint32_t bitfield_bit_offset, bool show_types, bool show_summary,
- bool verbose, uint32_t depth)
-{
- assert(false && "Not implemented");
-}
-
-bool
-JavaASTContext::DumpTypeValue(lldb::opaque_compiler_type_t type, Stream *s, lldb::Format format,
- const DataExtractor &data, lldb::offset_t data_offset, size_t data_byte_size,
- uint32_t bitfield_bit_size, uint32_t bitfield_bit_offset,
- ExecutionContextScope *exe_scope)
-{
- if (IsScalarType(type))
- {
- return data.Dump(s, data_offset, format, data_byte_size,
- 1, // count
- UINT32_MAX, LLDB_INVALID_ADDRESS, bitfield_bit_size, bitfield_bit_offset, exe_scope);
- }
- return false;
+void JavaASTContext::DumpValue(
+ lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx, Stream *s,
+ lldb::Format format, const DataExtractor &data, lldb::offset_t data_offset,
+ size_t data_byte_size, uint32_t bitfield_bit_size,
+ uint32_t bitfield_bit_offset, bool show_types, bool show_summary,
+ bool verbose, uint32_t depth) {
+ assert(false && "Not implemented");
}
-void
-JavaASTContext::DumpTypeDescription(lldb::opaque_compiler_type_t type)
-{
- StreamFile s(stdout, false);
- DumpTypeDescription(type, &s);
+bool JavaASTContext::DumpTypeValue(
+ lldb::opaque_compiler_type_t type, Stream *s, lldb::Format format,
+ const DataExtractor &data, lldb::offset_t data_offset,
+ size_t data_byte_size, uint32_t bitfield_bit_size,
+ uint32_t bitfield_bit_offset, ExecutionContextScope *exe_scope) {
+ if (IsScalarType(type)) {
+ return data.Dump(s, data_offset, format, data_byte_size,
+ 1, // count
+ UINT32_MAX, LLDB_INVALID_ADDRESS, bitfield_bit_size,
+ bitfield_bit_offset, exe_scope);
+ }
+ return false;
}
-void
-JavaASTContext::DumpTypeDescription(lldb::opaque_compiler_type_t type, Stream *s)
-{
- static_cast<JavaType *>(type)->Dump(s);
+void JavaASTContext::DumpTypeDescription(lldb::opaque_compiler_type_t type) {
+ StreamFile s(stdout, false);
+ DumpTypeDescription(type, &s);
}
-void
-JavaASTContext::DumpSummary(lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx, Stream *s,
- const DataExtractor &data, lldb::offset_t data_offset, size_t data_byte_size)
-{
- assert(false && "Not implemented");
+void JavaASTContext::DumpTypeDescription(lldb::opaque_compiler_type_t type,
+ Stream *s) {
+ static_cast<JavaType *>(type)->Dump(s);
}
-int
-JavaASTContext::GetFunctionArgumentCount(lldb::opaque_compiler_type_t type)
-{
- return 0;
+void JavaASTContext::DumpSummary(lldb::opaque_compiler_type_t type,
+ ExecutionContext *exe_ctx, Stream *s,
+ const DataExtractor &data,
+ lldb::offset_t data_offset,
+ size_t data_byte_size) {
+ assert(false && "Not implemented");
}
-CompilerType
-JavaASTContext::GetFunctionArgumentTypeAtIndex(lldb::opaque_compiler_type_t type, size_t idx)
-{
- return CompilerType();
+int JavaASTContext::GetFunctionArgumentCount(
+ lldb::opaque_compiler_type_t type) {
+ return 0;
+}
+
+CompilerType JavaASTContext::GetFunctionArgumentTypeAtIndex(
+ lldb::opaque_compiler_type_t type, size_t idx) {
+ return CompilerType();
}
CompilerType
-JavaASTContext::GetFunctionReturnType(lldb::opaque_compiler_type_t type)
-{
- return CompilerType();
+JavaASTContext::GetFunctionReturnType(lldb::opaque_compiler_type_t type) {
+ return CompilerType();
}
size_t
-JavaASTContext::GetNumMemberFunctions(lldb::opaque_compiler_type_t type)
-{
- return 0;
+JavaASTContext::GetNumMemberFunctions(lldb::opaque_compiler_type_t type) {
+ return 0;
}
TypeMemberFunctionImpl
-JavaASTContext::GetMemberFunctionAtIndex(lldb::opaque_compiler_type_t type, size_t idx)
-{
- return TypeMemberFunctionImpl();
-}
+JavaASTContext::GetMemberFunctionAtIndex(lldb::opaque_compiler_type_t type,
+ size_t idx) {
+ return TypeMemberFunctionImpl();
+}
+
+CompilerType JavaASTContext::GetChildCompilerTypeAtIndex(
+ lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx, size_t idx,
+ bool transparent_pointers, bool omit_empty_base_classes,
+ bool ignore_array_bounds, std::string &child_name,
+ uint32_t &child_byte_size, int32_t &child_byte_offset,
+ uint32_t &child_bitfield_bit_size, uint32_t &child_bitfield_bit_offset,
+ bool &child_is_base_class, bool &child_is_deref_of_parent,
+ ValueObject *valobj, uint64_t &language_flags) {
+ child_name.clear();
+ child_byte_size = 0;
+ child_byte_offset = 0;
+ child_bitfield_bit_size = 0;
+ child_bitfield_bit_offset = 0;
+ child_is_base_class = false;
+ child_is_deref_of_parent = false;
+ language_flags = 0;
-CompilerType
-JavaASTContext::GetChildCompilerTypeAtIndex(lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx, size_t idx,
- bool transparent_pointers, bool omit_empty_base_classes,
- bool ignore_array_bounds, std::string &child_name,
- uint32_t &child_byte_size, int32_t &child_byte_offset,
- uint32_t &child_bitfield_bit_size, uint32_t &child_bitfield_bit_offset,
- bool &child_is_base_class, bool &child_is_deref_of_parent,
- ValueObject *valobj, uint64_t &language_flags)
-{
- child_name.clear();
- child_byte_size = 0;
- child_byte_offset = 0;
- child_bitfield_bit_size = 0;
- child_bitfield_bit_offset = 0;
- child_is_base_class = false;
- child_is_deref_of_parent = false;
- language_flags = 0;
-
- ExecutionContextScope *exec_ctx_scope = exe_ctx ? exe_ctx->GetBestExecutionContextScope() : nullptr;
-
- if (JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type)))
- {
- GetCompleteType(type);
-
- if (CompilerType base_class = obj->GetBaseClass())
- {
- if (idx == 0)
- {
- JavaType *base_class_type = static_cast<JavaType *>(base_class.GetOpaqueQualType());
- child_name = base_class_type->GetName().GetCString();
- child_byte_size = base_class.GetByteSize(exe_ctx ? exe_ctx->GetBestExecutionContextScope() : nullptr);
- child_byte_offset = obj->GetBaseClassOffset();
- child_is_base_class = true;
- return base_class;
- }
- idx -= 1;
- }
-
- JavaObjectType::Field *field = obj->GetFieldAtIndex(idx);
- if (!field)
- return CompilerType();
-
- child_name = field->m_name.AsCString();
- child_byte_size = field->m_type.GetByteSize(exec_ctx_scope);
- child_byte_offset = field->m_offset;
- return field->m_type;
- }
- else if (JavaReferenceType *ref = llvm::dyn_cast<JavaReferenceType>(static_cast<JavaType *>(type)))
- {
- CompilerType pointee_type = ref->GetPointeeType();
-
- if (transparent_pointers)
- return pointee_type.GetChildCompilerTypeAtIndex(
- exe_ctx, idx, transparent_pointers, omit_empty_base_classes, ignore_array_bounds, child_name,
- child_byte_size, child_byte_offset, child_bitfield_bit_size, child_bitfield_bit_offset,
- child_is_base_class, child_is_deref_of_parent, valobj, language_flags);
-
- if (idx != 0)
- return CompilerType();
-
- if (valobj && valobj->GetName())
- child_name = valobj->GetName().GetCString();
- child_is_deref_of_parent = true;
- child_byte_offset = 0;
- child_byte_size = pointee_type.GetByteSize(exec_ctx_scope);
- return pointee_type;
- }
- return CompilerType();
-}
+ ExecutionContextScope *exec_ctx_scope =
+ exe_ctx ? exe_ctx->GetBestExecutionContextScope() : nullptr;
-uint32_t
-JavaASTContext::GetIndexOfChildWithName(lldb::opaque_compiler_type_t type, const char *name,
- bool omit_empty_base_classes)
-{
- if (JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type)))
- {
- GetCompleteType(type);
-
- uint32_t index_offset = 0;
- if (CompilerType base_class = obj->GetBaseClass())
- {
- if (base_class.GetTypeName() == ConstString(name))
- return 0;
- index_offset = 1;
- }
- for (uint32_t i = 0; i < obj->GetNumFields(); ++i)
- {
- if (obj->GetFieldAtIndex(i)->m_name == ConstString(name))
- return i + index_offset;
- }
- }
- else if (JavaReferenceType *ref = llvm::dyn_cast<JavaReferenceType>(static_cast<JavaType *>(type)))
- {
- return GetIndexOfChildWithName(ref->GetPointeeType().GetOpaqueQualType(), name, omit_empty_base_classes);
- }
- return UINT_MAX;
-}
+ if (JavaObjectType *obj =
+ llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type))) {
+ GetCompleteType(type);
-size_t
-JavaASTContext::GetIndexOfChildMemberWithName(lldb::opaque_compiler_type_t type, const char *name,
- bool omit_empty_base_classes, std::vector<uint32_t> &child_indexes)
-{
- child_indexes.clear();
-
- if (JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type)))
- {
- GetCompleteType(type);
-
- uint32_t index_offset = 0;
- if (CompilerType base_class = obj->GetBaseClass())
- {
- if (GetIndexOfChildMemberWithName(base_class.GetOpaqueQualType(), name, omit_empty_base_classes,
- child_indexes) != 0)
- {
- child_indexes.insert(child_indexes.begin(), 0);
- return child_indexes.size();
- }
- index_offset = 1;
- }
-
- for (uint32_t i = 0; i < obj->GetNumFields(); ++i)
- {
- if (obj->GetFieldAtIndex(i)->m_name == ConstString(name))
- {
- child_indexes.push_back(i + index_offset);
- return child_indexes.size();
- }
- }
- }
- else if (JavaReferenceType *ref = llvm::dyn_cast<JavaReferenceType>(static_cast<JavaType *>(type)))
- {
- return GetIndexOfChildMemberWithName(ref->GetPointeeType().GetOpaqueQualType(), name, omit_empty_base_classes,
- child_indexes);
- }
- return 0;
+ if (CompilerType base_class = obj->GetBaseClass()) {
+ if (idx == 0) {
+ JavaType *base_class_type =
+ static_cast<JavaType *>(base_class.GetOpaqueQualType());
+ child_name = base_class_type->GetName().GetCString();
+ child_byte_size = base_class.GetByteSize(
+ exe_ctx ? exe_ctx->GetBestExecutionContextScope() : nullptr);
+ child_byte_offset = obj->GetBaseClassOffset();
+ child_is_base_class = true;
+ return base_class;
+ }
+ idx -= 1;
+ }
+
+ JavaObjectType::Field *field = obj->GetFieldAtIndex(idx);
+ if (!field)
+ return CompilerType();
+
+ child_name = field->m_name.AsCString();
+ child_byte_size = field->m_type.GetByteSize(exec_ctx_scope);
+ child_byte_offset = field->m_offset;
+ return field->m_type;
+ } else if (JavaReferenceType *ref = llvm::dyn_cast<JavaReferenceType>(
+ static_cast<JavaType *>(type))) {
+ CompilerType pointee_type = ref->GetPointeeType();
+
+ if (transparent_pointers)
+ return pointee_type.GetChildCompilerTypeAtIndex(
+ exe_ctx, idx, transparent_pointers, omit_empty_base_classes,
+ ignore_array_bounds, child_name, child_byte_size, child_byte_offset,
+ child_bitfield_bit_size, child_bitfield_bit_offset,
+ child_is_base_class, child_is_deref_of_parent, valobj,
+ language_flags);
+
+ if (idx != 0)
+ return CompilerType();
+
+ if (valobj && valobj->GetName())
+ child_name = valobj->GetName().GetCString();
+ child_is_deref_of_parent = true;
+ child_byte_offset = 0;
+ child_byte_size = pointee_type.GetByteSize(exec_ctx_scope);
+ return pointee_type;
+ }
+ return CompilerType();
}
-CompilerType
-JavaASTContext::GetLValueReferenceType(lldb::opaque_compiler_type_t type)
-{
- return CreateReferenceType(CompilerType(this, type));
-}
-
-ConstString
-JavaASTContext::DeclContextGetScopeQualifiedName(lldb::opaque_compiler_type_t opaque_decl_ctx)
-{
- return GetTypeName(opaque_decl_ctx);
-}
-
-static void
-AddPrimitiveType(JavaASTContext::JavaTypeMap &type_map, JavaPrimitiveType::TypeKind type_kind)
-{
- JavaPrimitiveType *type = new JavaPrimitiveType(type_kind);
- type_map.emplace(type->GetName(), std::unique_ptr<JavaASTContext::JavaType>(type));
-}
+uint32_t
+JavaASTContext::GetIndexOfChildWithName(lldb::opaque_compiler_type_t type,
+ const char *name,
+ bool omit_empty_base_classes) {
+ if (JavaObjectType *obj =
+ llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type))) {
+ GetCompleteType(type);
-CompilerType
-JavaASTContext::CreateBaseType(const ConstString &name)
-{
- if (m_base_type_map.empty())
- {
- AddPrimitiveType(m_base_type_map, JavaPrimitiveType::eTypeByte);
- AddPrimitiveType(m_base_type_map, JavaPrimitiveType::eTypeShort);
- AddPrimitiveType(m_base_type_map, JavaPrimitiveType::eTypeInt);
- AddPrimitiveType(m_base_type_map, JavaPrimitiveType::eTypeLong);
- AddPrimitiveType(m_base_type_map, JavaPrimitiveType::eTypeFloat);
- AddPrimitiveType(m_base_type_map, JavaPrimitiveType::eTypeDouble);
- AddPrimitiveType(m_base_type_map, JavaPrimitiveType::eTypeBoolean);
- AddPrimitiveType(m_base_type_map, JavaPrimitiveType::eTypeChar);
+ uint32_t index_offset = 0;
+ if (CompilerType base_class = obj->GetBaseClass()) {
+ if (base_class.GetTypeName() == ConstString(name))
+ return 0;
+ index_offset = 1;
}
- auto it = m_base_type_map.find(name);
- if (it != m_base_type_map.end())
- return CompilerType(this, it->second.get());
- return CompilerType();
-}
+ for (uint32_t i = 0; i < obj->GetNumFields(); ++i) {
+ if (obj->GetFieldAtIndex(i)->m_name == ConstString(name))
+ return i + index_offset;
+ }
+ } else if (JavaReferenceType *ref = llvm::dyn_cast<JavaReferenceType>(
+ static_cast<JavaType *>(type))) {
+ return GetIndexOfChildWithName(ref->GetPointeeType().GetOpaqueQualType(),
+ name, omit_empty_base_classes);
+ }
+ return UINT_MAX;
+}
+
+size_t JavaASTContext::GetIndexOfChildMemberWithName(
+ lldb::opaque_compiler_type_t type, const char *name,
+ bool omit_empty_base_classes, std::vector<uint32_t> &child_indexes) {
+ child_indexes.clear();
-CompilerType
-JavaASTContext::CreateObjectType(const ConstString &name, const ConstString &linkage_name, uint32_t byte_size)
-{
- auto it = m_object_type_map.find(name);
- if (it == m_object_type_map.end())
- {
- std::unique_ptr<JavaType> object_type(new JavaObjectType(name, linkage_name, byte_size));
- it = m_object_type_map.emplace(name, std::move(object_type)).first;
- }
- return CompilerType(this, it->second.get());
-}
+ if (JavaObjectType *obj =
+ llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type))) {
+ GetCompleteType(type);
-CompilerType
-JavaASTContext::CreateArrayType(const ConstString &linkage_name, const CompilerType &element_type,
- const DWARFExpression &length_expression, const lldb::addr_t data_offset)
-{
- ConstString name = element_type.GetTypeName();
- auto it = m_array_type_map.find(name);
- if (it == m_array_type_map.end())
- {
- std::unique_ptr<JavaType> array_type(new JavaArrayType(linkage_name, element_type, length_expression,
- data_offset));
- it = m_array_type_map.emplace(name, std::move(array_type)).first;
- }
- return CompilerType(this, it->second.get());
+ uint32_t index_offset = 0;
+ if (CompilerType base_class = obj->GetBaseClass()) {
+ if (GetIndexOfChildMemberWithName(base_class.GetOpaqueQualType(), name,
+ omit_empty_base_classes,
+ child_indexes) != 0) {
+ child_indexes.insert(child_indexes.begin(), 0);
+ return child_indexes.size();
+ }
+ index_offset = 1;
+ }
+
+ for (uint32_t i = 0; i < obj->GetNumFields(); ++i) {
+ if (obj->GetFieldAtIndex(i)->m_name == ConstString(name)) {
+ child_indexes.push_back(i + index_offset);
+ return child_indexes.size();
+ }
+ }
+ } else if (JavaReferenceType *ref = llvm::dyn_cast<JavaReferenceType>(
+ static_cast<JavaType *>(type))) {
+ return GetIndexOfChildMemberWithName(
+ ref->GetPointeeType().GetOpaqueQualType(), name,
+ omit_empty_base_classes, child_indexes);
+ }
+ return 0;
}
CompilerType
-JavaASTContext::CreateReferenceType(const CompilerType &pointee_type)
-{
- ConstString name = pointee_type.GetTypeName();
- auto it = m_reference_type_map.find(name);
- if (it == m_reference_type_map.end())
- it = m_reference_type_map.emplace(name, std::unique_ptr<JavaType>(new JavaReferenceType(pointee_type))).first;
+JavaASTContext::GetLValueReferenceType(lldb::opaque_compiler_type_t type) {
+ return CreateReferenceType(CompilerType(this, type));
+}
+
+ConstString JavaASTContext::DeclContextGetScopeQualifiedName(
+ lldb::opaque_compiler_type_t opaque_decl_ctx) {
+ return GetTypeName(opaque_decl_ctx);
+}
+
+static void AddPrimitiveType(JavaASTContext::JavaTypeMap &type_map,
+ JavaPrimitiveType::TypeKind type_kind) {
+ JavaPrimitiveType *type = new JavaPrimitiveType(type_kind);
+ type_map.emplace(type->GetName(),
+ std::unique_ptr<JavaASTContext::JavaType>(type));
+}
+
+CompilerType JavaASTContext::CreateBaseType(const ConstString &name) {
+ if (m_base_type_map.empty()) {
+ AddPrimitiveType(m_base_type_map, JavaPrimitiveType::eTypeByte);
+ AddPrimitiveType(m_base_type_map, JavaPrimitiveType::eTypeShort);
+ AddPrimitiveType(m_base_type_map, JavaPrimitiveType::eTypeInt);
+ AddPrimitiveType(m_base_type_map, JavaPrimitiveType::eTypeLong);
+ AddPrimitiveType(m_base_type_map, JavaPrimitiveType::eTypeFloat);
+ AddPrimitiveType(m_base_type_map, JavaPrimitiveType::eTypeDouble);
+ AddPrimitiveType(m_base_type_map, JavaPrimitiveType::eTypeBoolean);
+ AddPrimitiveType(m_base_type_map, JavaPrimitiveType::eTypeChar);
+ }
+ auto it = m_base_type_map.find(name);
+ if (it != m_base_type_map.end())
return CompilerType(this, it->second.get());
+ return CompilerType();
}
-void
-JavaASTContext::CompleteObjectType(const CompilerType &object_type)
-{
- JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(object_type.GetOpaqueQualType()));
- assert(obj && "JavaASTContext::CompleteObjectType called with not a JavaObjectType");
- obj->SetCompleteType(true);
-}
-
-void
-JavaASTContext::AddBaseClassToObject(const CompilerType &object_type, const CompilerType &member_type,
- uint32_t member_offset)
-{
- JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(object_type.GetOpaqueQualType()));
- assert(obj && "JavaASTContext::AddMemberToObject called with not a JavaObjectType");
- obj->AddBaseClass(member_type, member_offset);
-}
-
-void
-JavaASTContext::AddMemberToObject(const CompilerType &object_type, const ConstString &name,
- const CompilerType &member_type, uint32_t member_offset)
-{
- JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(object_type.GetOpaqueQualType()));
- assert(obj && "JavaASTContext::AddMemberToObject called with not a JavaObjectType");
- obj->AddField(name, member_type, member_offset);
-}
-
-void
-JavaASTContext::SetDynamicTypeId(const CompilerType &type, const DWARFExpression &type_id)
-{
- JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type.GetOpaqueQualType()));
- assert(obj && "JavaASTContext::SetDynamicTypeId called with not a JavaObjectType");
- obj->SetDynamicTypeId(type_id);
-}
-
-uint64_t
-JavaASTContext::CalculateDynamicTypeId(ExecutionContext *exe_ctx, const CompilerType &type, ValueObject &in_value)
-{
- if (JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type.GetOpaqueQualType())))
- return obj->CalculateDynamicTypeId(exe_ctx, in_value);
- if (JavaArrayType *arr = llvm::dyn_cast<JavaArrayType>(static_cast<JavaType *>(type.GetOpaqueQualType())))
- return arr->CalculateDynamicTypeId(exe_ctx, in_value);
- return UINT64_MAX;
-}
-
-uint32_t
-JavaASTContext::CalculateArraySize(const CompilerType &type, ValueObject &in_value)
-{
- if (JavaArrayType *arr = llvm::dyn_cast<JavaArrayType>(static_cast<JavaType *>(type.GetOpaqueQualType())))
- return arr->GetNumElements(&in_value);
- return UINT32_MAX;
-}
-
-uint64_t
-JavaASTContext::CalculateArrayElementOffset(const CompilerType &type, size_t index)
-{
- if (JavaArrayType *arr = llvm::dyn_cast<JavaArrayType>(static_cast<JavaType *>(type.GetOpaqueQualType())))
- return arr->GetElementOffset(index);
- return UINT64_MAX;
-}
-
-ConstString
-JavaASTContext::GetLinkageName(const CompilerType &type)
-{
- if (JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(static_cast<JavaType *>(type.GetOpaqueQualType())))
- return obj->GetLinkageName();
- return ConstString();
+CompilerType JavaASTContext::CreateObjectType(const ConstString &name,
+ const ConstString &linkage_name,
+ uint32_t byte_size) {
+ auto it = m_object_type_map.find(name);
+ if (it == m_object_type_map.end()) {
+ std::unique_ptr<JavaType> object_type(
+ new JavaObjectType(name, linkage_name, byte_size));
+ it = m_object_type_map.emplace(name, std::move(object_type)).first;
+ }
+ return CompilerType(this, it->second.get());
+}
+
+CompilerType JavaASTContext::CreateArrayType(
+ const ConstString &linkage_name, const CompilerType &element_type,
+ const DWARFExpression &length_expression, const lldb::addr_t data_offset) {
+ ConstString name = element_type.GetTypeName();
+ auto it = m_array_type_map.find(name);
+ if (it == m_array_type_map.end()) {
+ std::unique_ptr<JavaType> array_type(new JavaArrayType(
+ linkage_name, element_type, length_expression, data_offset));
+ it = m_array_type_map.emplace(name, std::move(array_type)).first;
+ }
+ return CompilerType(this, it->second.get());
+}
+
+CompilerType
+JavaASTContext::CreateReferenceType(const CompilerType &pointee_type) {
+ ConstString name = pointee_type.GetTypeName();
+ auto it = m_reference_type_map.find(name);
+ if (it == m_reference_type_map.end())
+ it = m_reference_type_map
+ .emplace(name, std::unique_ptr<JavaType>(
+ new JavaReferenceType(pointee_type)))
+ .first;
+ return CompilerType(this, it->second.get());
+}
+
+void JavaASTContext::CompleteObjectType(const CompilerType &object_type) {
+ JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(
+ static_cast<JavaType *>(object_type.GetOpaqueQualType()));
+ assert(obj &&
+ "JavaASTContext::CompleteObjectType called with not a JavaObjectType");
+ obj->SetCompleteType(true);
+}
+
+void JavaASTContext::AddBaseClassToObject(const CompilerType &object_type,
+ const CompilerType &member_type,
+ uint32_t member_offset) {
+ JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(
+ static_cast<JavaType *>(object_type.GetOpaqueQualType()));
+ assert(obj &&
+ "JavaASTContext::AddMemberToObject called with not a JavaObjectType");
+ obj->AddBaseClass(member_type, member_offset);
+}
+
+void JavaASTContext::AddMemberToObject(const CompilerType &object_type,
+ const ConstString &name,
+ const CompilerType &member_type,
+ uint32_t member_offset) {
+ JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(
+ static_cast<JavaType *>(object_type.GetOpaqueQualType()));
+ assert(obj &&
+ "JavaASTContext::AddMemberToObject called with not a JavaObjectType");
+ obj->AddField(name, member_type, member_offset);
+}
+
+void JavaASTContext::SetDynamicTypeId(const CompilerType &type,
+ const DWARFExpression &type_id) {
+ JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(
+ static_cast<JavaType *>(type.GetOpaqueQualType()));
+ assert(obj &&
+ "JavaASTContext::SetDynamicTypeId called with not a JavaObjectType");
+ obj->SetDynamicTypeId(type_id);
+}
+
+uint64_t JavaASTContext::CalculateDynamicTypeId(ExecutionContext *exe_ctx,
+ const CompilerType &type,
+ ValueObject &in_value) {
+ if (JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(
+ static_cast<JavaType *>(type.GetOpaqueQualType())))
+ return obj->CalculateDynamicTypeId(exe_ctx, in_value);
+ if (JavaArrayType *arr = llvm::dyn_cast<JavaArrayType>(
+ static_cast<JavaType *>(type.GetOpaqueQualType())))
+ return arr->CalculateDynamicTypeId(exe_ctx, in_value);
+ return UINT64_MAX;
+}
+
+uint32_t JavaASTContext::CalculateArraySize(const CompilerType &type,
+ ValueObject &in_value) {
+ if (JavaArrayType *arr = llvm::dyn_cast<JavaArrayType>(
+ static_cast<JavaType *>(type.GetOpaqueQualType())))
+ return arr->GetNumElements(&in_value);
+ return UINT32_MAX;
+}
+
+uint64_t JavaASTContext::CalculateArrayElementOffset(const CompilerType &type,
+ size_t index) {
+ if (JavaArrayType *arr = llvm::dyn_cast<JavaArrayType>(
+ static_cast<JavaType *>(type.GetOpaqueQualType())))
+ return arr->GetElementOffset(index);
+ return UINT64_MAX;
+}
+
+ConstString JavaASTContext::GetLinkageName(const CompilerType &type) {
+ if (JavaObjectType *obj = llvm::dyn_cast<JavaObjectType>(
+ static_cast<JavaType *>(type.GetOpaqueQualType())))
+ return obj->GetLinkageName();
+ return ConstString();
}
Modified: lldb/trunk/source/Symbol/LineEntry.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/LineEntry.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/LineEntry.cpp (original)
+++ lldb/trunk/source/Symbol/LineEntry.cpp Tue Sep 6 15:57:50 2016
@@ -14,286 +14,229 @@
using namespace lldb_private;
-LineEntry::LineEntry() :
- range(),
- file(),
- line(LLDB_INVALID_LINE_NUMBER),
- column(0),
- is_start_of_statement(0),
- is_start_of_basic_block(0),
- is_prologue_end(0),
- is_epilogue_begin(0),
- is_terminal_entry(0)
-{
-}
-
-LineEntry::LineEntry
-(
- const lldb::SectionSP §ion_sp,
- lldb::addr_t section_offset,
- lldb::addr_t byte_size,
- const FileSpec &_file,
- uint32_t _line,
- uint16_t _column,
- bool _is_start_of_statement,
- bool _is_start_of_basic_block,
- bool _is_prologue_end,
- bool _is_epilogue_begin,
- bool _is_terminal_entry
-) :
- range(section_sp, section_offset, byte_size),
- file(_file),
- original_file(_file),
- line(_line),
- column(_column),
- is_start_of_statement(_is_start_of_statement),
- is_start_of_basic_block(_is_start_of_basic_block),
- is_prologue_end(_is_prologue_end),
- is_epilogue_begin(_is_epilogue_begin),
- is_terminal_entry(_is_terminal_entry)
-{
-}
-
-void
-LineEntry::Clear()
-{
- range.Clear();
- file.Clear();
- original_file.Clear();
- line = LLDB_INVALID_LINE_NUMBER;
- column = 0;
- is_start_of_statement = 0;
- is_start_of_basic_block = 0;
- is_prologue_end = 0;
- is_epilogue_begin = 0;
- is_terminal_entry = 0;
-}
-
-
-bool
-LineEntry::IsValid() const
-{
- return range.GetBaseAddress().IsValid() && line != LLDB_INVALID_LINE_NUMBER;
-}
-
-bool
-LineEntry::DumpStopContext(Stream *s, bool show_fullpaths) const
-{
- bool result = false;
- if (file)
- {
- if (show_fullpaths)
- file.Dump (s);
- else
- file.GetFilename().Dump (s);
-
- if (line)
- s->PutChar(':');
- result = true;
- }
- if (line)
- s->Printf ("%u", line);
+LineEntry::LineEntry()
+ : range(), file(), line(LLDB_INVALID_LINE_NUMBER), column(0),
+ is_start_of_statement(0), is_start_of_basic_block(0), is_prologue_end(0),
+ is_epilogue_begin(0), is_terminal_entry(0) {}
+
+LineEntry::LineEntry(const lldb::SectionSP §ion_sp,
+ lldb::addr_t section_offset, lldb::addr_t byte_size,
+ const FileSpec &_file, uint32_t _line, uint16_t _column,
+ bool _is_start_of_statement, bool _is_start_of_basic_block,
+ bool _is_prologue_end, bool _is_epilogue_begin,
+ bool _is_terminal_entry)
+ : range(section_sp, section_offset, byte_size), file(_file),
+ original_file(_file), line(_line), column(_column),
+ is_start_of_statement(_is_start_of_statement),
+ is_start_of_basic_block(_is_start_of_basic_block),
+ is_prologue_end(_is_prologue_end), is_epilogue_begin(_is_epilogue_begin),
+ is_terminal_entry(_is_terminal_entry) {}
+
+void LineEntry::Clear() {
+ range.Clear();
+ file.Clear();
+ original_file.Clear();
+ line = LLDB_INVALID_LINE_NUMBER;
+ column = 0;
+ is_start_of_statement = 0;
+ is_start_of_basic_block = 0;
+ is_prologue_end = 0;
+ is_epilogue_begin = 0;
+ is_terminal_entry = 0;
+}
+
+bool LineEntry::IsValid() const {
+ return range.GetBaseAddress().IsValid() && line != LLDB_INVALID_LINE_NUMBER;
+}
+
+bool LineEntry::DumpStopContext(Stream *s, bool show_fullpaths) const {
+ bool result = false;
+ if (file) {
+ if (show_fullpaths)
+ file.Dump(s);
else
- result = false;
+ file.GetFilename().Dump(s);
- return result;
-}
-
-bool
-LineEntry::Dump
-(
- Stream *s,
- Target *target,
- bool show_file,
- Address::DumpStyle style,
- Address::DumpStyle fallback_style,
- bool show_range
-) const
-{
- if (show_range)
- {
- // Show address range
- if (!range.Dump(s, target, style, fallback_style))
- return false;
- }
- else
- {
- // Show address only
- if (!range.GetBaseAddress().Dump(s,
- target,
- style,
- fallback_style))
- return false;
- }
- if (show_file)
- *s << ", file = " << file;
if (line)
- s->Printf(", line = %u", line);
- if (column)
- s->Printf(", column = %u", column);
- if (is_start_of_statement)
+ s->PutChar(':');
+ result = true;
+ }
+ if (line)
+ s->Printf("%u", line);
+ else
+ result = false;
+
+ return result;
+}
+
+bool LineEntry::Dump(Stream *s, Target *target, bool show_file,
+ Address::DumpStyle style,
+ Address::DumpStyle fallback_style, bool show_range) const {
+ if (show_range) {
+ // Show address range
+ if (!range.Dump(s, target, style, fallback_style))
+ return false;
+ } else {
+ // Show address only
+ if (!range.GetBaseAddress().Dump(s, target, style, fallback_style))
+ return false;
+ }
+ if (show_file)
+ *s << ", file = " << file;
+ if (line)
+ s->Printf(", line = %u", line);
+ if (column)
+ s->Printf(", column = %u", column);
+ if (is_start_of_statement)
+ *s << ", is_start_of_statement = TRUE";
+
+ if (is_start_of_basic_block)
+ *s << ", is_start_of_basic_block = TRUE";
+
+ if (is_prologue_end)
+ *s << ", is_prologue_end = TRUE";
+
+ if (is_epilogue_begin)
+ *s << ", is_epilogue_begin = TRUE";
+
+ if (is_terminal_entry)
+ *s << ", is_terminal_entry = TRUE";
+ return true;
+}
+
+bool LineEntry::GetDescription(Stream *s, lldb::DescriptionLevel level,
+ CompileUnit *cu, Target *target,
+ bool show_address_only) const {
+
+ if (level == lldb::eDescriptionLevelBrief ||
+ level == lldb::eDescriptionLevelFull) {
+ if (show_address_only) {
+ range.GetBaseAddress().Dump(s, target, Address::DumpStyleLoadAddress,
+ Address::DumpStyleFileAddress);
+ } else {
+ range.Dump(s, target, Address::DumpStyleLoadAddress,
+ Address::DumpStyleFileAddress);
+ }
+
+ *s << ": " << file;
+
+ if (line) {
+ s->Printf(":%u", line);
+ if (column)
+ s->Printf(":%u", column);
+ }
+
+ if (level == lldb::eDescriptionLevelFull) {
+ if (is_start_of_statement)
*s << ", is_start_of_statement = TRUE";
- if (is_start_of_basic_block)
+ if (is_start_of_basic_block)
*s << ", is_start_of_basic_block = TRUE";
- if (is_prologue_end)
+ if (is_prologue_end)
*s << ", is_prologue_end = TRUE";
- if (is_epilogue_begin)
+ if (is_epilogue_begin)
*s << ", is_epilogue_begin = TRUE";
- if (is_terminal_entry)
+ if (is_terminal_entry)
*s << ", is_terminal_entry = TRUE";
- return true;
-}
-
-bool
-LineEntry::GetDescription (Stream *s, lldb::DescriptionLevel level, CompileUnit* cu, Target *target, bool show_address_only) const
-{
-
- if (level == lldb::eDescriptionLevelBrief || level == lldb::eDescriptionLevelFull)
- {
- if (show_address_only)
- {
- range.GetBaseAddress().Dump(s, target, Address::DumpStyleLoadAddress, Address::DumpStyleFileAddress);
- }
- else
- {
- range.Dump(s, target, Address::DumpStyleLoadAddress, Address::DumpStyleFileAddress);
- }
-
- *s << ": " << file;
-
- if (line)
- {
- s->Printf(":%u", line);
- if (column)
- s->Printf(":%u", column);
- }
-
-
- if (level == lldb::eDescriptionLevelFull)
- {
- if (is_start_of_statement)
- *s << ", is_start_of_statement = TRUE";
-
- if (is_start_of_basic_block)
- *s << ", is_start_of_basic_block = TRUE";
-
- if (is_prologue_end)
- *s << ", is_prologue_end = TRUE";
-
- if (is_epilogue_begin)
- *s << ", is_epilogue_begin = TRUE";
-
- if (is_terminal_entry)
- *s << ", is_terminal_entry = TRUE";
- }
- else
- {
- if (is_terminal_entry)
- s->EOL();
- }
- }
- else
- {
- return Dump (s, target, true, Address::DumpStyleLoadAddress, Address::DumpStyleModuleWithFileAddress, true);
+ } else {
+ if (is_terminal_entry)
+ s->EOL();
}
- return true;
+ } else {
+ return Dump(s, target, true, Address::DumpStyleLoadAddress,
+ Address::DumpStyleModuleWithFileAddress, true);
+ }
+ return true;
}
-
-bool
-lldb_private::operator< (const LineEntry& a, const LineEntry& b)
-{
- return LineEntry::Compare (a, b) < 0;
+bool lldb_private::operator<(const LineEntry &a, const LineEntry &b) {
+ return LineEntry::Compare(a, b) < 0;
}
-int
-LineEntry::Compare (const LineEntry& a, const LineEntry& b)
-{
- int result = Address::CompareFileAddress (a.range.GetBaseAddress(), b.range.GetBaseAddress());
- if (result != 0)
- return result;
-
- const lldb::addr_t a_byte_size = a.range.GetByteSize();
- const lldb::addr_t b_byte_size = b.range.GetByteSize();
-
- if (a_byte_size < b_byte_size)
- return -1;
- if (a_byte_size > b_byte_size)
- return +1;
-
- // Check for an end sequence entry mismatch after we have determined
- // that the address values are equal. If one of the items is an end
- // sequence, we don't care about the line, file, or column info.
- if (a.is_terminal_entry > b.is_terminal_entry)
- return -1;
- if (a.is_terminal_entry < b.is_terminal_entry)
- return +1;
-
- if (a.line < b.line)
- return -1;
- if (a.line > b.line)
- return +1;
-
- if (a.column < b.column)
- return -1;
- if (a.column > b.column)
- return +1;
+int LineEntry::Compare(const LineEntry &a, const LineEntry &b) {
+ int result = Address::CompareFileAddress(a.range.GetBaseAddress(),
+ b.range.GetBaseAddress());
+ if (result != 0)
+ return result;
- return FileSpec::Compare (a.file, b.file, true);
-}
+ const lldb::addr_t a_byte_size = a.range.GetByteSize();
+ const lldb::addr_t b_byte_size = b.range.GetByteSize();
-AddressRange
-LineEntry::GetSameLineContiguousAddressRange () const
-{
- // Add each LineEntry's range to complete_line_range until we find
- // a different file / line number.
- AddressRange complete_line_range = range;
-
- while (true)
- {
- SymbolContext next_line_sc;
- Address range_end (complete_line_range.GetBaseAddress());
- range_end.Slide (complete_line_range.GetByteSize());
- range_end.CalculateSymbolContext (&next_line_sc, lldb::eSymbolContextLineEntry);
-
- if (next_line_sc.line_entry.IsValid()
- && next_line_sc.line_entry.range.GetByteSize() > 0
- && original_file == next_line_sc.line_entry.original_file)
- {
- // Include any line 0 entries - they indicate that this is compiler-generated code
- // that does not correspond to user source code.
- if (next_line_sc.line_entry.line == 0)
- {
- complete_line_range.SetByteSize (complete_line_range.GetByteSize() + next_line_sc.line_entry.range.GetByteSize());
- continue;
- }
-
- if (line == next_line_sc.line_entry.line)
- {
- // next_line_sc is the same file & line as this LineEntry, so extend our
- // AddressRange by its size and continue to see if there are more LineEntries
- // that we can combine.
- complete_line_range.SetByteSize (complete_line_range.GetByteSize() + next_line_sc.line_entry.range.GetByteSize());
- continue;
- }
- }
- break;
- }
- return complete_line_range;
-}
-
-void
-LineEntry::ApplyFileMappings(lldb::TargetSP target_sp)
-{
- if (target_sp)
- {
- // Apply any file remappings to our file
- FileSpec new_file_spec;
- if (target_sp->GetSourcePathMap().FindFile(original_file, new_file_spec))
- file = new_file_spec;
- }
+ if (a_byte_size < b_byte_size)
+ return -1;
+ if (a_byte_size > b_byte_size)
+ return +1;
+
+ // Check for an end sequence entry mismatch after we have determined
+ // that the address values are equal. If one of the items is an end
+ // sequence, we don't care about the line, file, or column info.
+ if (a.is_terminal_entry > b.is_terminal_entry)
+ return -1;
+ if (a.is_terminal_entry < b.is_terminal_entry)
+ return +1;
+
+ if (a.line < b.line)
+ return -1;
+ if (a.line > b.line)
+ return +1;
+
+ if (a.column < b.column)
+ return -1;
+ if (a.column > b.column)
+ return +1;
+
+ return FileSpec::Compare(a.file, b.file, true);
+}
+
+AddressRange LineEntry::GetSameLineContiguousAddressRange() const {
+ // Add each LineEntry's range to complete_line_range until we find
+ // a different file / line number.
+ AddressRange complete_line_range = range;
+
+ while (true) {
+ SymbolContext next_line_sc;
+ Address range_end(complete_line_range.GetBaseAddress());
+ range_end.Slide(complete_line_range.GetByteSize());
+ range_end.CalculateSymbolContext(&next_line_sc,
+ lldb::eSymbolContextLineEntry);
+
+ if (next_line_sc.line_entry.IsValid() &&
+ next_line_sc.line_entry.range.GetByteSize() > 0 &&
+ original_file == next_line_sc.line_entry.original_file) {
+ // Include any line 0 entries - they indicate that this is
+ // compiler-generated code
+ // that does not correspond to user source code.
+ if (next_line_sc.line_entry.line == 0) {
+ complete_line_range.SetByteSize(
+ complete_line_range.GetByteSize() +
+ next_line_sc.line_entry.range.GetByteSize());
+ continue;
+ }
+
+ if (line == next_line_sc.line_entry.line) {
+ // next_line_sc is the same file & line as this LineEntry, so extend our
+ // AddressRange by its size and continue to see if there are more
+ // LineEntries
+ // that we can combine.
+ complete_line_range.SetByteSize(
+ complete_line_range.GetByteSize() +
+ next_line_sc.line_entry.range.GetByteSize());
+ continue;
+ }
+ }
+ break;
+ }
+ return complete_line_range;
+}
+
+void LineEntry::ApplyFileMappings(lldb::TargetSP target_sp) {
+ if (target_sp) {
+ // Apply any file remappings to our file
+ FileSpec new_file_spec;
+ if (target_sp->GetSourcePathMap().FindFile(original_file, new_file_spec))
+ file = new_file_spec;
+ }
}
Modified: lldb/trunk/source/Symbol/LineTable.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/LineTable.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/LineTable.cpp (original)
+++ lldb/trunk/source/Symbol/LineTable.cpp Tue Sep 6 15:57:50 2016
@@ -7,12 +7,12 @@
//
//===----------------------------------------------------------------------===//
+#include "lldb/Symbol/LineTable.h"
#include "lldb/Core/Address.h"
#include "lldb/Core/Module.h"
#include "lldb/Core/Section.h"
#include "lldb/Core/Stream.h"
#include "lldb/Symbol/CompileUnit.h"
-#include "lldb/Symbol/LineTable.h"
#include <algorithm>
using namespace lldb;
@@ -21,594 +21,522 @@ using namespace lldb_private;
//----------------------------------------------------------------------
// LineTable constructor
//----------------------------------------------------------------------
-LineTable::LineTable(CompileUnit* comp_unit) :
- m_comp_unit(comp_unit),
- m_entries()
-{
-}
+LineTable::LineTable(CompileUnit *comp_unit)
+ : m_comp_unit(comp_unit), m_entries() {}
//----------------------------------------------------------------------
// Destructor
//----------------------------------------------------------------------
-LineTable::~LineTable()
-{
-}
+LineTable::~LineTable() {}
-void
-LineTable::InsertLineEntry
-(
- lldb::addr_t file_addr,
- uint32_t line,
- uint16_t column,
- uint16_t file_idx,
- bool is_start_of_statement,
- bool is_start_of_basic_block,
- bool is_prologue_end,
- bool is_epilogue_begin,
- bool is_terminal_entry
-)
-{
- Entry entry(file_addr, line, column, file_idx, is_start_of_statement, is_start_of_basic_block, is_prologue_end, is_epilogue_begin, is_terminal_entry);
-
- entry_collection::iterator begin_pos = m_entries.begin();
- entry_collection::iterator end_pos = m_entries.end();
- LineTable::Entry::LessThanBinaryPredicate less_than_bp(this);
- entry_collection::iterator pos = upper_bound(begin_pos, end_pos, entry, less_than_bp);
-
-// Stream s(stdout);
-// s << "\n\nBefore:\n";
-// Dump (&s, Address::DumpStyleFileAddress);
- m_entries.insert(pos, entry);
-// s << "After:\n";
-// Dump (&s, Address::DumpStyleFileAddress);
-}
-
-LineSequence::LineSequence()
-{
-}
-
-void
-LineTable::LineSequenceImpl::Clear()
-{
- m_entries.clear();
-}
-
-LineSequence* LineTable::CreateLineSequenceContainer ()
-{
- return new LineTable::LineSequenceImpl();
-}
-
-void
-LineTable::AppendLineEntryToSequence
-(
- LineSequence* sequence,
- lldb::addr_t file_addr,
- uint32_t line,
- uint16_t column,
- uint16_t file_idx,
- bool is_start_of_statement,
- bool is_start_of_basic_block,
- bool is_prologue_end,
- bool is_epilogue_begin,
- bool is_terminal_entry
-)
-{
- assert(sequence != nullptr);
- LineSequenceImpl* seq = reinterpret_cast<LineSequenceImpl*>(sequence);
- Entry entry(file_addr, line, column, file_idx, is_start_of_statement, is_start_of_basic_block, is_prologue_end, is_epilogue_begin, is_terminal_entry);
- entry_collection &entries = seq->m_entries;
- // Replace the last entry if the address is the same, otherwise append it. If we have multiple
- // line entries at the same address, this indicates illegal DWARF so this "fixes" the line table
- // to be correct. If not fixed this can cause a line entry's address that when resolved back to
- // a symbol context, could resolve to a different line entry. We really want a 1 to 1 mapping
- // here to avoid these kinds of inconsistencies. We will need tor revisit this if the DWARF line
- // tables are updated to allow multiple entries at the same address legally.
- if (!entries.empty() && entries.back().file_addr == file_addr)
- {
- // GCC don't use the is_prologue_end flag to mark the first instruction after the prologue.
- // Instead of it it is issuing a line table entry for the first instruction of the prologue
- // and one for the first instruction after the prologue. If the size of the prologue is 0
- // instruction then the 2 line entry will have the same file address. Removing it will remove
- // our ability to properly detect the location of the end of prologe so we set the prologue_end
- // flag to preserve this information (setting the prologue_end flag for an entry what is after
- // the prologue end don't have any effect)
- entry.is_prologue_end = entry.file_idx == entries.back().file_idx;
- entries.back() = entry;
- }
- else
- entries.push_back (entry);
-}
-
-void
-LineTable::InsertSequence (LineSequence* sequence)
-{
- assert(sequence != nullptr);
- LineSequenceImpl* seq = reinterpret_cast<LineSequenceImpl*>(sequence);
- if (seq->m_entries.empty())
- return;
- Entry& entry = seq->m_entries.front();
-
- // If the first entry address in this sequence is greater than or equal to
- // the address of the last item in our entry collection, just append.
- if (m_entries.empty() || !Entry::EntryAddressLessThan(entry, m_entries.back()))
- {
- m_entries.insert(m_entries.end(),
- seq->m_entries.begin(),
- seq->m_entries.end());
- return;
- }
-
- // Otherwise, find where this belongs in the collection
- entry_collection::iterator begin_pos = m_entries.begin();
- entry_collection::iterator end_pos = m_entries.end();
- LineTable::Entry::LessThanBinaryPredicate less_than_bp(this);
- entry_collection::iterator pos = upper_bound(begin_pos, end_pos, entry, less_than_bp);
-
- // We should never insert a sequence in the middle of another sequence
- if (pos != begin_pos) {
- while (pos < end_pos && !((pos - 1)->is_terminal_entry))
- pos++;
- }
+void LineTable::InsertLineEntry(lldb::addr_t file_addr, uint32_t line,
+ uint16_t column, uint16_t file_idx,
+ bool is_start_of_statement,
+ bool is_start_of_basic_block,
+ bool is_prologue_end, bool is_epilogue_begin,
+ bool is_terminal_entry) {
+ Entry entry(file_addr, line, column, file_idx, is_start_of_statement,
+ is_start_of_basic_block, is_prologue_end, is_epilogue_begin,
+ is_terminal_entry);
+
+ entry_collection::iterator begin_pos = m_entries.begin();
+ entry_collection::iterator end_pos = m_entries.end();
+ LineTable::Entry::LessThanBinaryPredicate less_than_bp(this);
+ entry_collection::iterator pos =
+ upper_bound(begin_pos, end_pos, entry, less_than_bp);
+
+ // Stream s(stdout);
+ // s << "\n\nBefore:\n";
+ // Dump (&s, Address::DumpStyleFileAddress);
+ m_entries.insert(pos, entry);
+ // s << "After:\n";
+ // Dump (&s, Address::DumpStyleFileAddress);
+}
+
+LineSequence::LineSequence() {}
+
+void LineTable::LineSequenceImpl::Clear() { m_entries.clear(); }
+
+LineSequence *LineTable::CreateLineSequenceContainer() {
+ return new LineTable::LineSequenceImpl();
+}
+
+void LineTable::AppendLineEntryToSequence(
+ LineSequence *sequence, lldb::addr_t file_addr, uint32_t line,
+ uint16_t column, uint16_t file_idx, bool is_start_of_statement,
+ bool is_start_of_basic_block, bool is_prologue_end, bool is_epilogue_begin,
+ bool is_terminal_entry) {
+ assert(sequence != nullptr);
+ LineSequenceImpl *seq = reinterpret_cast<LineSequenceImpl *>(sequence);
+ Entry entry(file_addr, line, column, file_idx, is_start_of_statement,
+ is_start_of_basic_block, is_prologue_end, is_epilogue_begin,
+ is_terminal_entry);
+ entry_collection &entries = seq->m_entries;
+ // Replace the last entry if the address is the same, otherwise append it. If
+ // we have multiple
+ // line entries at the same address, this indicates illegal DWARF so this
+ // "fixes" the line table
+ // to be correct. If not fixed this can cause a line entry's address that when
+ // resolved back to
+ // a symbol context, could resolve to a different line entry. We really want a
+ // 1 to 1 mapping
+ // here to avoid these kinds of inconsistencies. We will need tor revisit this
+ // if the DWARF line
+ // tables are updated to allow multiple entries at the same address legally.
+ if (!entries.empty() && entries.back().file_addr == file_addr) {
+ // GCC don't use the is_prologue_end flag to mark the first instruction
+ // after the prologue.
+ // Instead of it it is issuing a line table entry for the first instruction
+ // of the prologue
+ // and one for the first instruction after the prologue. If the size of the
+ // prologue is 0
+ // instruction then the 2 line entry will have the same file address.
+ // Removing it will remove
+ // our ability to properly detect the location of the end of prologe so we
+ // set the prologue_end
+ // flag to preserve this information (setting the prologue_end flag for an
+ // entry what is after
+ // the prologue end don't have any effect)
+ entry.is_prologue_end = entry.file_idx == entries.back().file_idx;
+ entries.back() = entry;
+ } else
+ entries.push_back(entry);
+}
+
+void LineTable::InsertSequence(LineSequence *sequence) {
+ assert(sequence != nullptr);
+ LineSequenceImpl *seq = reinterpret_cast<LineSequenceImpl *>(sequence);
+ if (seq->m_entries.empty())
+ return;
+ Entry &entry = seq->m_entries.front();
+
+ // If the first entry address in this sequence is greater than or equal to
+ // the address of the last item in our entry collection, just append.
+ if (m_entries.empty() ||
+ !Entry::EntryAddressLessThan(entry, m_entries.back())) {
+ m_entries.insert(m_entries.end(), seq->m_entries.begin(),
+ seq->m_entries.end());
+ return;
+ }
+
+ // Otherwise, find where this belongs in the collection
+ entry_collection::iterator begin_pos = m_entries.begin();
+ entry_collection::iterator end_pos = m_entries.end();
+ LineTable::Entry::LessThanBinaryPredicate less_than_bp(this);
+ entry_collection::iterator pos =
+ upper_bound(begin_pos, end_pos, entry, less_than_bp);
+
+ // We should never insert a sequence in the middle of another sequence
+ if (pos != begin_pos) {
+ while (pos < end_pos && !((pos - 1)->is_terminal_entry))
+ pos++;
+ }
#ifdef LLDB_CONFIGURATION_DEBUG
- // If we aren't inserting at the beginning, the previous entry should
- // terminate a sequence.
- if (pos != begin_pos)
- {
- entry_collection::iterator prev_pos = pos - 1;
- assert(prev_pos->is_terminal_entry);
- }
+ // If we aren't inserting at the beginning, the previous entry should
+ // terminate a sequence.
+ if (pos != begin_pos) {
+ entry_collection::iterator prev_pos = pos - 1;
+ assert(prev_pos->is_terminal_entry);
+ }
#endif
- m_entries.insert(pos, seq->m_entries.begin(), seq->m_entries.end());
+ m_entries.insert(pos, seq->m_entries.begin(), seq->m_entries.end());
}
//----------------------------------------------------------------------
-LineTable::Entry::LessThanBinaryPredicate::LessThanBinaryPredicate(LineTable *line_table) :
- m_line_table (line_table)
-{
-}
-
-bool
-LineTable::Entry::LessThanBinaryPredicate::operator() (const LineTable::Entry& a, const LineTable::Entry& b) const
-{
- #define LT_COMPARE(a,b) if (a != b) return a < b
- LT_COMPARE (a.file_addr, b.file_addr);
- // b and a reversed on purpose below.
- LT_COMPARE (b.is_terminal_entry, a.is_terminal_entry);
- LT_COMPARE (a.line, b.line);
- LT_COMPARE (a.column, b.column);
- LT_COMPARE (a.is_start_of_statement, b.is_start_of_statement);
- LT_COMPARE (a.is_start_of_basic_block, b.is_start_of_basic_block);
- // b and a reversed on purpose below.
- LT_COMPARE (b.is_prologue_end, a.is_prologue_end);
- LT_COMPARE (a.is_epilogue_begin, b.is_epilogue_begin);
- LT_COMPARE (a.file_idx, b.file_idx);
- return false;
- #undef LT_COMPARE
-}
-
-
-
-uint32_t
-LineTable::GetSize() const
-{
- return m_entries.size();
-}
-
-bool
-LineTable::GetLineEntryAtIndex(uint32_t idx, LineEntry& line_entry)
-{
- if (idx < m_entries.size())
- {
- ConvertEntryAtIndexToLineEntry (idx, line_entry);
- return true;
- }
- line_entry.Clear();
- return false;
-}
-
-bool
-LineTable::FindLineEntryByAddress (const Address &so_addr, LineEntry& line_entry, uint32_t *index_ptr)
-{
- if (index_ptr != nullptr )
- *index_ptr = UINT32_MAX;
-
- bool success = false;
-
- if (so_addr.GetModule().get() == m_comp_unit->GetModule().get())
- {
- Entry search_entry;
- search_entry.file_addr = so_addr.GetFileAddress();
- if (search_entry.file_addr != LLDB_INVALID_ADDRESS)
- {
- entry_collection::const_iterator begin_pos = m_entries.begin();
- entry_collection::const_iterator end_pos = m_entries.end();
- entry_collection::const_iterator pos = lower_bound(begin_pos, end_pos, search_entry, Entry::EntryAddressLessThan);
- if (pos != end_pos)
- {
- if (pos != begin_pos)
- {
- if (pos->file_addr != search_entry.file_addr)
- --pos;
- else if (pos->file_addr == search_entry.file_addr)
- {
- // If this is a termination entry, it shouldn't match since
- // entries with the "is_terminal_entry" member set to true
- // are termination entries that define the range for the
- // previous entry.
- if (pos->is_terminal_entry)
- {
- // The matching entry is a terminal entry, so we skip
- // ahead to the next entry to see if there is another
- // entry following this one whose section/offset matches.
- ++pos;
- if (pos != end_pos)
- {
- if (pos->file_addr != search_entry.file_addr)
- pos = end_pos;
- }
- }
-
- if (pos != end_pos)
- {
- // While in the same section/offset backup to find the first
- // line entry that matches the address in case there are
- // multiple
- while (pos != begin_pos)
- {
- entry_collection::const_iterator prev_pos = pos - 1;
- if (prev_pos->file_addr == search_entry.file_addr &&
- prev_pos->is_terminal_entry == false)
- --pos;
- else
- break;
- }
- }
- }
-
- }
-
- // Make sure we have a valid match and that the match isn't a terminating
- // entry for a previous line...
- if (pos != end_pos && pos->is_terminal_entry == false)
- {
- uint32_t match_idx = std::distance (begin_pos, pos);
- success = ConvertEntryAtIndexToLineEntry(match_idx, line_entry);
- if (index_ptr != nullptr && success)
- *index_ptr = match_idx;
- }
+LineTable::Entry::LessThanBinaryPredicate::LessThanBinaryPredicate(
+ LineTable *line_table)
+ : m_line_table(line_table) {}
+
+bool LineTable::Entry::LessThanBinaryPredicate::
+operator()(const LineTable::Entry &a, const LineTable::Entry &b) const {
+#define LT_COMPARE(a, b) \
+ if (a != b) \
+ return a < b
+ LT_COMPARE(a.file_addr, b.file_addr);
+ // b and a reversed on purpose below.
+ LT_COMPARE(b.is_terminal_entry, a.is_terminal_entry);
+ LT_COMPARE(a.line, b.line);
+ LT_COMPARE(a.column, b.column);
+ LT_COMPARE(a.is_start_of_statement, b.is_start_of_statement);
+ LT_COMPARE(a.is_start_of_basic_block, b.is_start_of_basic_block);
+ // b and a reversed on purpose below.
+ LT_COMPARE(b.is_prologue_end, a.is_prologue_end);
+ LT_COMPARE(a.is_epilogue_begin, b.is_epilogue_begin);
+ LT_COMPARE(a.file_idx, b.file_idx);
+ return false;
+#undef LT_COMPARE
+}
+
+uint32_t LineTable::GetSize() const { return m_entries.size(); }
+
+bool LineTable::GetLineEntryAtIndex(uint32_t idx, LineEntry &line_entry) {
+ if (idx < m_entries.size()) {
+ ConvertEntryAtIndexToLineEntry(idx, line_entry);
+ return true;
+ }
+ line_entry.Clear();
+ return false;
+}
+
+bool LineTable::FindLineEntryByAddress(const Address &so_addr,
+ LineEntry &line_entry,
+ uint32_t *index_ptr) {
+ if (index_ptr != nullptr)
+ *index_ptr = UINT32_MAX;
+
+ bool success = false;
+
+ if (so_addr.GetModule().get() == m_comp_unit->GetModule().get()) {
+ Entry search_entry;
+ search_entry.file_addr = so_addr.GetFileAddress();
+ if (search_entry.file_addr != LLDB_INVALID_ADDRESS) {
+ entry_collection::const_iterator begin_pos = m_entries.begin();
+ entry_collection::const_iterator end_pos = m_entries.end();
+ entry_collection::const_iterator pos = lower_bound(
+ begin_pos, end_pos, search_entry, Entry::EntryAddressLessThan);
+ if (pos != end_pos) {
+ if (pos != begin_pos) {
+ if (pos->file_addr != search_entry.file_addr)
+ --pos;
+ else if (pos->file_addr == search_entry.file_addr) {
+ // If this is a termination entry, it shouldn't match since
+ // entries with the "is_terminal_entry" member set to true
+ // are termination entries that define the range for the
+ // previous entry.
+ if (pos->is_terminal_entry) {
+ // The matching entry is a terminal entry, so we skip
+ // ahead to the next entry to see if there is another
+ // entry following this one whose section/offset matches.
+ ++pos;
+ if (pos != end_pos) {
+ if (pos->file_addr != search_entry.file_addr)
+ pos = end_pos;
+ }
}
- }
- }
- return success;
-}
-
-bool
-LineTable::ConvertEntryAtIndexToLineEntry (uint32_t idx, LineEntry &line_entry)
-{
- if (idx < m_entries.size())
- {
- const Entry& entry = m_entries[idx];
- ModuleSP module_sp (m_comp_unit->GetModule());
- if (module_sp && module_sp->ResolveFileAddress(entry.file_addr, line_entry.range.GetBaseAddress()))
- {
- if (!entry.is_terminal_entry && idx + 1 < m_entries.size())
- line_entry.range.SetByteSize(m_entries[idx+1].file_addr - entry.file_addr);
- else
- line_entry.range.SetByteSize(0);
-
- line_entry.file = m_comp_unit->GetSupportFiles().GetFileSpecAtIndex (entry.file_idx);
- line_entry.original_file = m_comp_unit->GetSupportFiles().GetFileSpecAtIndex(entry.file_idx);
- line_entry.line = entry.line;
- line_entry.column = entry.column;
- line_entry.is_start_of_statement = entry.is_start_of_statement;
- line_entry.is_start_of_basic_block = entry.is_start_of_basic_block;
- line_entry.is_prologue_end = entry.is_prologue_end;
- line_entry.is_epilogue_begin = entry.is_epilogue_begin;
- line_entry.is_terminal_entry = entry.is_terminal_entry;
- return true;
- }
- }
- return false;
-}
-
-uint32_t
-LineTable::FindLineEntryIndexByFileIndex
-(
- uint32_t start_idx,
- const std::vector<uint32_t> &file_indexes,
- uint32_t line,
- bool exact,
- LineEntry* line_entry_ptr
-)
-{
-
- const size_t count = m_entries.size();
- std::vector<uint32_t>::const_iterator begin_pos = file_indexes.begin();
- std::vector<uint32_t>::const_iterator end_pos = file_indexes.end();
- size_t best_match = UINT32_MAX;
-
- for (size_t idx = start_idx; idx < count; ++idx)
- {
- // Skip line table rows that terminate the previous row (is_terminal_entry is non-zero)
- if (m_entries[idx].is_terminal_entry)
- continue;
-
- if (find (begin_pos, end_pos, m_entries[idx].file_idx) == end_pos)
- continue;
-
- // Exact match always wins. Otherwise try to find the closest line > the desired
- // line.
- // FIXME: Maybe want to find the line closest before and the line closest after and
- // if they're not in the same function, don't return a match.
-
- if (m_entries[idx].line < line)
- {
- continue;
- }
- else if (m_entries[idx].line == line)
- {
- if (line_entry_ptr)
- ConvertEntryAtIndexToLineEntry (idx, *line_entry_ptr);
- return idx;
- }
- else if (!exact)
- {
- if (best_match == UINT32_MAX)
- best_match = idx;
- else if (m_entries[idx].line < m_entries[best_match].line)
- best_match = idx;
- }
- }
-
- if (best_match != UINT32_MAX)
- {
- if (line_entry_ptr)
- ConvertEntryAtIndexToLineEntry (best_match, *line_entry_ptr);
- return best_match;
- }
- return UINT32_MAX;
-}
-
-uint32_t
-LineTable::FindLineEntryIndexByFileIndex (uint32_t start_idx, uint32_t file_idx, uint32_t line, bool exact, LineEntry* line_entry_ptr)
-{
- const size_t count = m_entries.size();
- size_t best_match = UINT32_MAX;
-
- for (size_t idx = start_idx; idx < count; ++idx)
- {
- // Skip line table rows that terminate the previous row (is_terminal_entry is non-zero)
- if (m_entries[idx].is_terminal_entry)
- continue;
-
- if (m_entries[idx].file_idx != file_idx)
- continue;
-
- // Exact match always wins. Otherwise try to find the closest line > the desired
- // line.
- // FIXME: Maybe want to find the line closest before and the line closest after and
- // if they're not in the same function, don't return a match.
-
- if (m_entries[idx].line < line)
- {
- continue;
- }
- else if (m_entries[idx].line == line)
- {
- if (line_entry_ptr)
- ConvertEntryAtIndexToLineEntry (idx, *line_entry_ptr);
- return idx;
- }
- else if (!exact)
- {
- if (best_match == UINT32_MAX)
- best_match = idx;
- else if (m_entries[idx].line < m_entries[best_match].line)
- best_match = idx;
- }
- }
-
- if (best_match != UINT32_MAX)
- {
- if (line_entry_ptr)
- ConvertEntryAtIndexToLineEntry (best_match, *line_entry_ptr);
- return best_match;
- }
- return UINT32_MAX;
-}
-
-size_t
-LineTable::FineLineEntriesForFileIndex (uint32_t file_idx,
- bool append,
- SymbolContextList &sc_list)
-{
-
- if (!append)
- sc_list.Clear();
-
- size_t num_added = 0;
- const size_t count = m_entries.size();
- if (count > 0)
- {
- SymbolContext sc (m_comp_unit);
-
- for (size_t idx = 0; idx < count; ++idx)
- {
- // Skip line table rows that terminate the previous row (is_terminal_entry is non-zero)
- if (m_entries[idx].is_terminal_entry)
- continue;
-
- if (m_entries[idx].file_idx == file_idx)
- {
- if (ConvertEntryAtIndexToLineEntry (idx, sc.line_entry))
- {
- ++num_added;
- sc_list.Append(sc);
- }
+ if (pos != end_pos) {
+ // While in the same section/offset backup to find the first
+ // line entry that matches the address in case there are
+ // multiple
+ while (pos != begin_pos) {
+ entry_collection::const_iterator prev_pos = pos - 1;
+ if (prev_pos->file_addr == search_entry.file_addr &&
+ prev_pos->is_terminal_entry == false)
+ --pos;
+ else
+ break;
+ }
}
+ }
}
- }
- return num_added;
-}
-
-void
-LineTable::Dump (Stream *s, Target *target, Address::DumpStyle style, Address::DumpStyle fallback_style, bool show_line_ranges)
-{
- const size_t count = m_entries.size();
- LineEntry line_entry;
- FileSpec prev_file;
- for (size_t idx = 0; idx < count; ++idx)
- {
- ConvertEntryAtIndexToLineEntry (idx, line_entry);
- line_entry.Dump (s, target, prev_file != line_entry.original_file, style, fallback_style, show_line_ranges);
- s->EOL();
- prev_file = line_entry.original_file;
- }
+ // Make sure we have a valid match and that the match isn't a
+ // terminating
+ // entry for a previous line...
+ if (pos != end_pos && pos->is_terminal_entry == false) {
+ uint32_t match_idx = std::distance(begin_pos, pos);
+ success = ConvertEntryAtIndexToLineEntry(match_idx, line_entry);
+ if (index_ptr != nullptr && success)
+ *index_ptr = match_idx;
+ }
+ }
+ }
+ }
+ return success;
+}
+
+bool LineTable::ConvertEntryAtIndexToLineEntry(uint32_t idx,
+ LineEntry &line_entry) {
+ if (idx < m_entries.size()) {
+ const Entry &entry = m_entries[idx];
+ ModuleSP module_sp(m_comp_unit->GetModule());
+ if (module_sp &&
+ module_sp->ResolveFileAddress(entry.file_addr,
+ line_entry.range.GetBaseAddress())) {
+ if (!entry.is_terminal_entry && idx + 1 < m_entries.size())
+ line_entry.range.SetByteSize(m_entries[idx + 1].file_addr -
+ entry.file_addr);
+ else
+ line_entry.range.SetByteSize(0);
+
+ line_entry.file =
+ m_comp_unit->GetSupportFiles().GetFileSpecAtIndex(entry.file_idx);
+ line_entry.original_file =
+ m_comp_unit->GetSupportFiles().GetFileSpecAtIndex(entry.file_idx);
+ line_entry.line = entry.line;
+ line_entry.column = entry.column;
+ line_entry.is_start_of_statement = entry.is_start_of_statement;
+ line_entry.is_start_of_basic_block = entry.is_start_of_basic_block;
+ line_entry.is_prologue_end = entry.is_prologue_end;
+ line_entry.is_epilogue_begin = entry.is_epilogue_begin;
+ line_entry.is_terminal_entry = entry.is_terminal_entry;
+ return true;
+ }
+ }
+ return false;
+}
+
+uint32_t LineTable::FindLineEntryIndexByFileIndex(
+ uint32_t start_idx, const std::vector<uint32_t> &file_indexes,
+ uint32_t line, bool exact, LineEntry *line_entry_ptr) {
+
+ const size_t count = m_entries.size();
+ std::vector<uint32_t>::const_iterator begin_pos = file_indexes.begin();
+ std::vector<uint32_t>::const_iterator end_pos = file_indexes.end();
+ size_t best_match = UINT32_MAX;
+
+ for (size_t idx = start_idx; idx < count; ++idx) {
+ // Skip line table rows that terminate the previous row (is_terminal_entry
+ // is non-zero)
+ if (m_entries[idx].is_terminal_entry)
+ continue;
+
+ if (find(begin_pos, end_pos, m_entries[idx].file_idx) == end_pos)
+ continue;
+
+ // Exact match always wins. Otherwise try to find the closest line > the
+ // desired
+ // line.
+ // FIXME: Maybe want to find the line closest before and the line closest
+ // after and
+ // if they're not in the same function, don't return a match.
+
+ if (m_entries[idx].line < line) {
+ continue;
+ } else if (m_entries[idx].line == line) {
+ if (line_entry_ptr)
+ ConvertEntryAtIndexToLineEntry(idx, *line_entry_ptr);
+ return idx;
+ } else if (!exact) {
+ if (best_match == UINT32_MAX)
+ best_match = idx;
+ else if (m_entries[idx].line < m_entries[best_match].line)
+ best_match = idx;
+ }
+ }
+
+ if (best_match != UINT32_MAX) {
+ if (line_entry_ptr)
+ ConvertEntryAtIndexToLineEntry(best_match, *line_entry_ptr);
+ return best_match;
+ }
+ return UINT32_MAX;
+}
+
+uint32_t LineTable::FindLineEntryIndexByFileIndex(uint32_t start_idx,
+ uint32_t file_idx,
+ uint32_t line, bool exact,
+ LineEntry *line_entry_ptr) {
+ const size_t count = m_entries.size();
+ size_t best_match = UINT32_MAX;
+
+ for (size_t idx = start_idx; idx < count; ++idx) {
+ // Skip line table rows that terminate the previous row (is_terminal_entry
+ // is non-zero)
+ if (m_entries[idx].is_terminal_entry)
+ continue;
+
+ if (m_entries[idx].file_idx != file_idx)
+ continue;
+
+ // Exact match always wins. Otherwise try to find the closest line > the
+ // desired
+ // line.
+ // FIXME: Maybe want to find the line closest before and the line closest
+ // after and
+ // if they're not in the same function, don't return a match.
+
+ if (m_entries[idx].line < line) {
+ continue;
+ } else if (m_entries[idx].line == line) {
+ if (line_entry_ptr)
+ ConvertEntryAtIndexToLineEntry(idx, *line_entry_ptr);
+ return idx;
+ } else if (!exact) {
+ if (best_match == UINT32_MAX)
+ best_match = idx;
+ else if (m_entries[idx].line < m_entries[best_match].line)
+ best_match = idx;
+ }
+ }
+
+ if (best_match != UINT32_MAX) {
+ if (line_entry_ptr)
+ ConvertEntryAtIndexToLineEntry(best_match, *line_entry_ptr);
+ return best_match;
+ }
+ return UINT32_MAX;
+}
+
+size_t LineTable::FineLineEntriesForFileIndex(uint32_t file_idx, bool append,
+ SymbolContextList &sc_list) {
+
+ if (!append)
+ sc_list.Clear();
+
+ size_t num_added = 0;
+ const size_t count = m_entries.size();
+ if (count > 0) {
+ SymbolContext sc(m_comp_unit);
+
+ for (size_t idx = 0; idx < count; ++idx) {
+ // Skip line table rows that terminate the previous row (is_terminal_entry
+ // is non-zero)
+ if (m_entries[idx].is_terminal_entry)
+ continue;
+
+ if (m_entries[idx].file_idx == file_idx) {
+ if (ConvertEntryAtIndexToLineEntry(idx, sc.line_entry)) {
+ ++num_added;
+ sc_list.Append(sc);
+ }
+ }
+ }
+ }
+ return num_added;
+}
+
+void LineTable::Dump(Stream *s, Target *target, Address::DumpStyle style,
+ Address::DumpStyle fallback_style, bool show_line_ranges) {
+ const size_t count = m_entries.size();
+ LineEntry line_entry;
+ FileSpec prev_file;
+ for (size_t idx = 0; idx < count; ++idx) {
+ ConvertEntryAtIndexToLineEntry(idx, line_entry);
+ line_entry.Dump(s, target, prev_file != line_entry.original_file, style,
+ fallback_style, show_line_ranges);
+ s->EOL();
+ prev_file = line_entry.original_file;
+ }
+}
+
+void LineTable::GetDescription(Stream *s, Target *target,
+ DescriptionLevel level) {
+ const size_t count = m_entries.size();
+ LineEntry line_entry;
+ for (size_t idx = 0; idx < count; ++idx) {
+ ConvertEntryAtIndexToLineEntry(idx, line_entry);
+ line_entry.GetDescription(s, level, m_comp_unit, target, true);
+ s->EOL();
+ }
+}
+
+size_t LineTable::GetContiguousFileAddressRanges(FileAddressRanges &file_ranges,
+ bool append) {
+ if (!append)
+ file_ranges.Clear();
+ const size_t initial_count = file_ranges.GetSize();
+
+ const size_t count = m_entries.size();
+ LineEntry line_entry;
+ FileAddressRanges::Entry range(LLDB_INVALID_ADDRESS, 0);
+ for (size_t idx = 0; idx < count; ++idx) {
+ const Entry &entry = m_entries[idx];
+
+ if (entry.is_terminal_entry) {
+ if (range.GetRangeBase() != LLDB_INVALID_ADDRESS) {
+ range.SetRangeEnd(entry.file_addr);
+ file_ranges.Append(range);
+ range.Clear(LLDB_INVALID_ADDRESS);
+ }
+ } else if (range.GetRangeBase() == LLDB_INVALID_ADDRESS) {
+ range.SetRangeBase(entry.file_addr);
+ }
+ }
+ return file_ranges.GetSize() - initial_count;
+}
+
+LineTable *LineTable::LinkLineTable(const FileRangeMap &file_range_map) {
+ std::unique_ptr<LineTable> line_table_ap(new LineTable(m_comp_unit));
+ LineSequenceImpl sequence;
+ const size_t count = m_entries.size();
+ LineEntry line_entry;
+ const FileRangeMap::Entry *file_range_entry = nullptr;
+ const FileRangeMap::Entry *prev_file_range_entry = nullptr;
+ lldb::addr_t prev_file_addr = LLDB_INVALID_ADDRESS;
+ bool prev_entry_was_linked = false;
+ bool range_changed = false;
+ for (size_t idx = 0; idx < count; ++idx) {
+ const Entry &entry = m_entries[idx];
+
+ const bool end_sequence = entry.is_terminal_entry;
+ const lldb::addr_t lookup_file_addr =
+ entry.file_addr - (end_sequence ? 1 : 0);
+ if (file_range_entry == nullptr ||
+ !file_range_entry->Contains(lookup_file_addr)) {
+ prev_file_range_entry = file_range_entry;
+ file_range_entry = file_range_map.FindEntryThatContains(lookup_file_addr);
+ range_changed = true;
+ }
+
+ lldb::addr_t prev_end_entry_linked_file_addr = LLDB_INVALID_ADDRESS;
+ lldb::addr_t entry_linked_file_addr = LLDB_INVALID_ADDRESS;
+
+ bool terminate_previous_entry = false;
+ if (file_range_entry) {
+ entry_linked_file_addr = entry.file_addr -
+ file_range_entry->GetRangeBase() +
+ file_range_entry->data;
+ // Determine if we need to terminate the previous entry when the previous
+ // entry was not contiguous with this one after being linked.
+ if (range_changed && prev_file_range_entry) {
+ prev_end_entry_linked_file_addr =
+ std::min<lldb::addr_t>(entry.file_addr,
+ prev_file_range_entry->GetRangeEnd()) -
+ prev_file_range_entry->GetRangeBase() + prev_file_range_entry->data;
+ if (prev_end_entry_linked_file_addr != entry_linked_file_addr)
+ terminate_previous_entry = prev_entry_was_linked;
+ }
+ } else if (prev_entry_was_linked) {
+ // This entry doesn't have a remapping and it needs to be removed.
+ // Watch out in case we need to terminate a previous entry needs to
+ // be terminated now that one line entry in a sequence is not longer
+ // valid.
+ if (!sequence.m_entries.empty() &&
+ !sequence.m_entries.back().is_terminal_entry) {
+ terminate_previous_entry = true;
+ }
+ }
+
+ if (terminate_previous_entry && !sequence.m_entries.empty()) {
+ assert(prev_file_addr != LLDB_INVALID_ADDRESS);
+ sequence.m_entries.push_back(sequence.m_entries.back());
+ if (prev_end_entry_linked_file_addr == LLDB_INVALID_ADDRESS)
+ prev_end_entry_linked_file_addr =
+ std::min<lldb::addr_t>(entry.file_addr,
+ prev_file_range_entry->GetRangeEnd()) -
+ prev_file_range_entry->GetRangeBase() + prev_file_range_entry->data;
+ sequence.m_entries.back().file_addr = prev_end_entry_linked_file_addr;
+ sequence.m_entries.back().is_terminal_entry = true;
+
+ // Append the sequence since we just terminated the previous one
+ line_table_ap->InsertSequence(&sequence);
+ sequence.Clear();
+ }
+
+ // Now link the current entry
+ if (file_range_entry) {
+ // This entry has an address remapping and it needs to have its address
+ // relinked
+ sequence.m_entries.push_back(entry);
+ sequence.m_entries.back().file_addr = entry_linked_file_addr;
+ }
+
+ // If we have items in the sequence and the last entry is a terminal entry,
+ // insert this sequence into our new line table.
+ if (!sequence.m_entries.empty() &&
+ sequence.m_entries.back().is_terminal_entry) {
+ line_table_ap->InsertSequence(&sequence);
+ sequence.Clear();
+ prev_entry_was_linked = false;
+ } else {
+ prev_entry_was_linked = file_range_entry != nullptr;
+ }
+ prev_file_addr = entry.file_addr;
+ range_changed = false;
+ }
+ if (line_table_ap->m_entries.empty())
+ return nullptr;
+ return line_table_ap.release();
}
-
-
-void
-LineTable::GetDescription (Stream *s, Target *target, DescriptionLevel level)
-{
- const size_t count = m_entries.size();
- LineEntry line_entry;
- for (size_t idx = 0; idx < count; ++idx)
- {
- ConvertEntryAtIndexToLineEntry (idx, line_entry);
- line_entry.GetDescription (s, level, m_comp_unit, target, true);
- s->EOL();
- }
-}
-
-size_t
-LineTable::GetContiguousFileAddressRanges (FileAddressRanges &file_ranges, bool append)
-{
- if (!append)
- file_ranges.Clear();
- const size_t initial_count = file_ranges.GetSize();
-
- const size_t count = m_entries.size();
- LineEntry line_entry;
- FileAddressRanges::Entry range (LLDB_INVALID_ADDRESS, 0);
- for (size_t idx = 0; idx < count; ++idx)
- {
- const Entry& entry = m_entries[idx];
-
- if (entry.is_terminal_entry)
- {
- if (range.GetRangeBase() != LLDB_INVALID_ADDRESS)
- {
- range.SetRangeEnd(entry.file_addr);
- file_ranges.Append(range);
- range.Clear(LLDB_INVALID_ADDRESS);
- }
- }
- else if (range.GetRangeBase() == LLDB_INVALID_ADDRESS)
- {
- range.SetRangeBase(entry.file_addr);
- }
- }
- return file_ranges.GetSize() - initial_count;
-}
-
-LineTable *
-LineTable::LinkLineTable (const FileRangeMap &file_range_map)
-{
- std::unique_ptr<LineTable> line_table_ap (new LineTable (m_comp_unit));
- LineSequenceImpl sequence;
- const size_t count = m_entries.size();
- LineEntry line_entry;
- const FileRangeMap::Entry *file_range_entry = nullptr;
- const FileRangeMap::Entry *prev_file_range_entry = nullptr;
- lldb::addr_t prev_file_addr = LLDB_INVALID_ADDRESS;
- bool prev_entry_was_linked = false;
- bool range_changed = false;
- for (size_t idx = 0; idx < count; ++idx)
- {
- const Entry& entry = m_entries[idx];
-
- const bool end_sequence = entry.is_terminal_entry;
- const lldb::addr_t lookup_file_addr = entry.file_addr - (end_sequence ? 1 : 0);
- if (file_range_entry == nullptr || !file_range_entry->Contains(lookup_file_addr))
- {
- prev_file_range_entry = file_range_entry;
- file_range_entry = file_range_map.FindEntryThatContains(lookup_file_addr);
- range_changed = true;
- }
-
- lldb::addr_t prev_end_entry_linked_file_addr = LLDB_INVALID_ADDRESS;
- lldb::addr_t entry_linked_file_addr = LLDB_INVALID_ADDRESS;
-
- bool terminate_previous_entry = false;
- if (file_range_entry)
- {
- entry_linked_file_addr = entry.file_addr - file_range_entry->GetRangeBase() + file_range_entry->data;
- // Determine if we need to terminate the previous entry when the previous
- // entry was not contiguous with this one after being linked.
- if (range_changed && prev_file_range_entry)
- {
- prev_end_entry_linked_file_addr = std::min<lldb::addr_t>(entry.file_addr, prev_file_range_entry->GetRangeEnd()) - prev_file_range_entry->GetRangeBase() + prev_file_range_entry->data;
- if (prev_end_entry_linked_file_addr != entry_linked_file_addr)
- terminate_previous_entry = prev_entry_was_linked;
- }
- }
- else if (prev_entry_was_linked)
- {
- // This entry doesn't have a remapping and it needs to be removed.
- // Watch out in case we need to terminate a previous entry needs to
- // be terminated now that one line entry in a sequence is not longer valid.
- if (!sequence.m_entries.empty() &&
- !sequence.m_entries.back().is_terminal_entry)
- {
- terminate_previous_entry = true;
- }
- }
-
- if (terminate_previous_entry && !sequence.m_entries.empty())
- {
- assert (prev_file_addr != LLDB_INVALID_ADDRESS);
- sequence.m_entries.push_back(sequence.m_entries.back());
- if (prev_end_entry_linked_file_addr == LLDB_INVALID_ADDRESS)
- prev_end_entry_linked_file_addr = std::min<lldb::addr_t>(entry.file_addr,prev_file_range_entry->GetRangeEnd()) - prev_file_range_entry->GetRangeBase() + prev_file_range_entry->data;
- sequence.m_entries.back().file_addr = prev_end_entry_linked_file_addr;
- sequence.m_entries.back().is_terminal_entry = true;
-
- // Append the sequence since we just terminated the previous one
- line_table_ap->InsertSequence (&sequence);
- sequence.Clear();
- }
-
- // Now link the current entry
- if (file_range_entry)
- {
- // This entry has an address remapping and it needs to have its address relinked
- sequence.m_entries.push_back(entry);
- sequence.m_entries.back().file_addr = entry_linked_file_addr;
- }
-
- // If we have items in the sequence and the last entry is a terminal entry,
- // insert this sequence into our new line table.
- if (!sequence.m_entries.empty() && sequence.m_entries.back().is_terminal_entry)
- {
- line_table_ap->InsertSequence (&sequence);
- sequence.Clear();
- prev_entry_was_linked = false;
- }
- else
- {
- prev_entry_was_linked = file_range_entry != nullptr;
- }
- prev_file_addr = entry.file_addr;
- range_changed = false;
- }
- if (line_table_ap->m_entries.empty())
- return nullptr;
- return line_table_ap.release();
-}
-
-
-
-
Modified: lldb/trunk/source/Symbol/OCamlASTContext.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/OCamlASTContext.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/OCamlASTContext.cpp (original)
+++ lldb/trunk/source/Symbol/OCamlASTContext.cpp Tue Sep 6 15:57:50 2016
@@ -1,4 +1,5 @@
-//===-- OCamlASTContext.cpp ----------------------------------------*- C++ -*-===//
+//===-- OCamlASTContext.cpp ----------------------------------------*- C++
+//-*-===//
//
// The LLVM Compiler Infrastructure
//
@@ -7,6 +8,7 @@
//
//===----------------------------------------------------------------------===//
+#include "lldb/Symbol/OCamlASTContext.h"
#include "lldb/Core/Log.h"
#include "lldb/Core/Module.h"
#include "lldb/Core/PluginManager.h"
@@ -14,7 +16,6 @@
#include "lldb/Core/ValueObject.h"
#include "lldb/Symbol/ObjectFile.h"
#include "lldb/Symbol/SymbolFile.h"
-#include "lldb/Symbol/OCamlASTContext.h"
#include "lldb/Symbol/Type.h"
#include "lldb/Target/ExecutionContext.h"
#include "lldb/Target/Target.h"
@@ -24,471 +25,371 @@
using namespace lldb;
using namespace lldb_private;
-namespace lldb_private
-{
- class OCamlASTContext::OCamlType
- {
- public:
- enum LLVMCastKind
- {
- eKindPrimitive,
- eKindObject,
- eKindReference,
- eKindArray,
- kNumKinds
- };
-
- OCamlType(LLVMCastKind kind) : m_kind(kind) {}
-
- virtual ~OCamlType() = default;
-
- virtual ConstString
- GetName() = 0;
-
- virtual void
- Dump(Stream *s) = 0;
-
- virtual bool
- IsCompleteType() = 0;
-
- LLVMCastKind
- getKind() const
- {
- return m_kind;
- }
-
- private:
- LLVMCastKind m_kind;
- };
+namespace lldb_private {
+class OCamlASTContext::OCamlType {
+public:
+ enum LLVMCastKind {
+ eKindPrimitive,
+ eKindObject,
+ eKindReference,
+ eKindArray,
+ kNumKinds
+ };
+
+ OCamlType(LLVMCastKind kind) : m_kind(kind) {}
+
+ virtual ~OCamlType() = default;
+
+ virtual ConstString GetName() = 0;
+
+ virtual void Dump(Stream *s) = 0;
+
+ virtual bool IsCompleteType() = 0;
+
+ LLVMCastKind getKind() const { return m_kind; }
+
+private:
+ LLVMCastKind m_kind;
+};
} // end of namespace lldb_private
-namespace
-{
+namespace {
+
+class OCamlPrimitiveType : public OCamlASTContext::OCamlType {
+public:
+ enum TypeKind {
+ eTypeInt,
+ };
+
+ OCamlPrimitiveType(TypeKind type_kind, uint32_t byte_size)
+ : OCamlType(OCamlType::eKindPrimitive), m_type_kind(type_kind),
+ m_type(ConstString()), m_byte_size(byte_size) {}
+
+ OCamlPrimitiveType(TypeKind type_kind, ConstString s, uint32_t byte_size)
+ : OCamlType(OCamlType::eKindPrimitive), m_type_kind(type_kind), m_type(s),
+ m_byte_size(byte_size) {}
+
+ ConstString GetName() override {
+ switch (m_type_kind) {
+ case eTypeInt:
+ return m_type;
+ }
+ return ConstString();
+ }
+
+ TypeKind GetTypeKind() { return m_type_kind; }
+
+ void Dump(Stream *s) override { s->Printf("%s\n", GetName().GetCString()); }
- class OCamlPrimitiveType : public OCamlASTContext::OCamlType
- {
- public:
- enum TypeKind
- {
- eTypeInt,
- };
-
- OCamlPrimitiveType(TypeKind type_kind, uint32_t byte_size) : OCamlType(OCamlType::eKindPrimitive), m_type_kind(type_kind), m_type(ConstString()), m_byte_size(byte_size) {}
-
- OCamlPrimitiveType(TypeKind type_kind, ConstString s, uint32_t byte_size) : OCamlType(OCamlType::eKindPrimitive), m_type_kind(type_kind), m_type(s), m_byte_size(byte_size) {}
-
- ConstString
- GetName() override
- {
- switch (m_type_kind)
- {
- case eTypeInt:
- return m_type;
- }
- return ConstString();
- }
-
- TypeKind
- GetTypeKind()
- {
- return m_type_kind;
- }
-
- void
- Dump(Stream *s) override
- {
- s->Printf("%s\n", GetName().GetCString());
- }
-
- bool
- IsCompleteType() override
- {
- return true;
- }
-
- static bool
- classof(const OCamlType *ot)
- {
- return ot->getKind() == OCamlType::eKindPrimitive;
- }
-
- uint64_t
- GetByteSize() const
- {
- return m_byte_size;
- }
-
- private:
- const TypeKind m_type_kind;
- const ConstString m_type;
- uint64_t m_byte_size;
- };
+ bool IsCompleteType() override { return true; }
+
+ static bool classof(const OCamlType *ot) {
+ return ot->getKind() == OCamlType::eKindPrimitive;
+ }
+
+ uint64_t GetByteSize() const { return m_byte_size; }
+
+private:
+ const TypeKind m_type_kind;
+ const ConstString m_type;
+ uint64_t m_byte_size;
+};
}
OCamlASTContext::OCamlASTContext()
- : TypeSystem(eKindOCaml),
- m_pointer_byte_size(0)
-{
-}
+ : TypeSystem(eKindOCaml), m_pointer_byte_size(0) {}
-OCamlASTContext::~OCamlASTContext()
-{
-}
+OCamlASTContext::~OCamlASTContext() {}
-ConstString
-OCamlASTContext::GetPluginNameStatic()
-{
- return ConstString("ocaml");
+ConstString OCamlASTContext::GetPluginNameStatic() {
+ return ConstString("ocaml");
}
-ConstString
-OCamlASTContext::GetPluginName()
-{
- return OCamlASTContext::GetPluginNameStatic();
+ConstString OCamlASTContext::GetPluginName() {
+ return OCamlASTContext::GetPluginNameStatic();
}
-uint32_t
-OCamlASTContext::GetPluginVersion()
-{
- return 1;
-}
-
-lldb::TypeSystemSP
-OCamlASTContext::CreateInstance (lldb::LanguageType language, Module *module, Target *target)
-{
- Log *log(lldb_private::GetLogIfAnyCategoriesSet (LIBLLDB_LOG_LANGUAGE));
-
- if (language == lldb::eLanguageTypeOCaml)
- {
- std::shared_ptr<OCamlASTContext> ocaml_ast_sp;
- ArchSpec arch;
-
- if (module)
- {
- arch = module->GetArchitecture();
-
- ObjectFile *objfile = module->GetObjectFile();
- ArchSpec object_arch;
-
- if (!objfile || !objfile->GetArchitecture(object_arch))
- return lldb::TypeSystemSP();
-
- ocaml_ast_sp = std::shared_ptr<OCamlASTContext>(new OCamlASTContext);
-
- if (log) {
- log->Printf ("((Module*)%p) [%s]->GetOCamlASTContext() = %p",
- (void *)module,
- module->GetFileSpec().GetFilename().AsCString("<anonymous>"),
- (void *)ocaml_ast_sp.get());
- }
-
- } else if (target) {
- arch = target->GetArchitecture();
- ocaml_ast_sp = std::shared_ptr<OCamlASTContextForExpr>(new OCamlASTContextForExpr(target->shared_from_this()));
-
- if (log)
- {
- log->Printf ("((Target*)%p)->GetOCamlASTContext() = %p",
- (void *)target,
- (void *)ocaml_ast_sp.get());
- }
- }
-
- if (arch.IsValid()) {
- ocaml_ast_sp->SetAddressByteSize(arch.GetAddressByteSize());
- return ocaml_ast_sp;
- }
+uint32_t OCamlASTContext::GetPluginVersion() { return 1; }
+
+lldb::TypeSystemSP OCamlASTContext::CreateInstance(lldb::LanguageType language,
+ Module *module,
+ Target *target) {
+ Log *log(lldb_private::GetLogIfAnyCategoriesSet(LIBLLDB_LOG_LANGUAGE));
+
+ if (language == lldb::eLanguageTypeOCaml) {
+ std::shared_ptr<OCamlASTContext> ocaml_ast_sp;
+ ArchSpec arch;
+
+ if (module) {
+ arch = module->GetArchitecture();
+
+ ObjectFile *objfile = module->GetObjectFile();
+ ArchSpec object_arch;
+
+ if (!objfile || !objfile->GetArchitecture(object_arch))
+ return lldb::TypeSystemSP();
+
+ ocaml_ast_sp = std::shared_ptr<OCamlASTContext>(new OCamlASTContext);
+
+ if (log) {
+ log->Printf(
+ "((Module*)%p) [%s]->GetOCamlASTContext() = %p", (void *)module,
+ module->GetFileSpec().GetFilename().AsCString("<anonymous>"),
+ (void *)ocaml_ast_sp.get());
+ }
+
+ } else if (target) {
+ arch = target->GetArchitecture();
+ ocaml_ast_sp = std::shared_ptr<OCamlASTContextForExpr>(
+ new OCamlASTContextForExpr(target->shared_from_this()));
+
+ if (log) {
+ log->Printf("((Target*)%p)->GetOCamlASTContext() = %p", (void *)target,
+ (void *)ocaml_ast_sp.get());
+ }
+ }
+
+ if (arch.IsValid()) {
+ ocaml_ast_sp->SetAddressByteSize(arch.GetAddressByteSize());
+ return ocaml_ast_sp;
}
+ }
- return lldb::TypeSystemSP();
+ return lldb::TypeSystemSP();
}
-void
-OCamlASTContext::EnumerateSupportedLanguages
-(std::set<lldb::LanguageType> &languages_for_types,
- std::set<lldb::LanguageType> &languages_for_expressions)
-{
- static std::vector<lldb::LanguageType> s_supported_languages_for_types({lldb::eLanguageTypeOCaml});
- static std::vector<lldb::LanguageType> s_supported_languages_for_expressions({});
+void OCamlASTContext::EnumerateSupportedLanguages(
+ std::set<lldb::LanguageType> &languages_for_types,
+ std::set<lldb::LanguageType> &languages_for_expressions) {
+ static std::vector<lldb::LanguageType> s_supported_languages_for_types(
+ {lldb::eLanguageTypeOCaml});
+ static std::vector<lldb::LanguageType> s_supported_languages_for_expressions(
+ {});
- languages_for_types.insert(s_supported_languages_for_types.begin(), s_supported_languages_for_types.end());
- languages_for_expressions.insert(s_supported_languages_for_expressions.begin(), s_supported_languages_for_expressions.end());
+ languages_for_types.insert(s_supported_languages_for_types.begin(),
+ s_supported_languages_for_types.end());
+ languages_for_expressions.insert(
+ s_supported_languages_for_expressions.begin(),
+ s_supported_languages_for_expressions.end());
}
-void
-OCamlASTContext::Initialize()
-{
- PluginManager::RegisterPlugin (GetPluginNameStatic(),
- "OCaml AST context plug-in",
- CreateInstance,
- EnumerateSupportedLanguages);
+void OCamlASTContext::Initialize() {
+ PluginManager::RegisterPlugin(GetPluginNameStatic(),
+ "OCaml AST context plug-in", CreateInstance,
+ EnumerateSupportedLanguages);
}
-void
-OCamlASTContext::Terminate()
-{
- PluginManager::UnregisterPlugin (CreateInstance);
+void OCamlASTContext::Terminate() {
+ PluginManager::UnregisterPlugin(CreateInstance);
}
-DWARFASTParser *
-OCamlASTContext::GetDWARFParser()
-{
- if (!m_dwarf_ast_parser_ap) {
- m_dwarf_ast_parser_ap.reset(new DWARFASTParserOCaml(*this));
- }
+DWARFASTParser *OCamlASTContext::GetDWARFParser() {
+ if (!m_dwarf_ast_parser_ap) {
+ m_dwarf_ast_parser_ap.reset(new DWARFASTParserOCaml(*this));
+ }
- return m_dwarf_ast_parser_ap.get();
+ return m_dwarf_ast_parser_ap.get();
}
-bool
-OCamlASTContext::IsArrayType(lldb::opaque_compiler_type_t type,
- CompilerType *element_type, uint64_t *size,
- bool *is_incomplete)
-{
- return false;
+bool OCamlASTContext::IsArrayType(lldb::opaque_compiler_type_t type,
+ CompilerType *element_type, uint64_t *size,
+ bool *is_incomplete) {
+ return false;
}
-bool
-OCamlASTContext::IsVectorType(lldb::opaque_compiler_type_t type, CompilerType *element_type, uint64_t *size)
-{
- return false;
+bool OCamlASTContext::IsVectorType(lldb::opaque_compiler_type_t type,
+ CompilerType *element_type, uint64_t *size) {
+ return false;
}
-bool
-OCamlASTContext::IsAggregateType(lldb::opaque_compiler_type_t type)
-{
- return false;
+bool OCamlASTContext::IsAggregateType(lldb::opaque_compiler_type_t type) {
+ return false;
}
-bool
-OCamlASTContext::IsBeingDefined(lldb::opaque_compiler_type_t type)
-{
- return false;
+bool OCamlASTContext::IsBeingDefined(lldb::opaque_compiler_type_t type) {
+ return false;
}
-bool
-OCamlASTContext::IsCharType(lldb::opaque_compiler_type_t type)
-{
- return false;
+bool OCamlASTContext::IsCharType(lldb::opaque_compiler_type_t type) {
+ return false;
}
-bool
-OCamlASTContext::IsCompleteType(lldb::opaque_compiler_type_t type)
-{
- return static_cast<OCamlPrimitiveType *>(type)->IsCompleteType();
+bool OCamlASTContext::IsCompleteType(lldb::opaque_compiler_type_t type) {
+ return static_cast<OCamlPrimitiveType *>(type)->IsCompleteType();
}
-bool
-OCamlASTContext::IsConst(lldb::opaque_compiler_type_t type)
-{
- return false;
+bool OCamlASTContext::IsConst(lldb::opaque_compiler_type_t type) {
+ return false;
}
-bool
-OCamlASTContext::IsCStringType(lldb::opaque_compiler_type_t type, uint32_t &length)
-{
- return false;
+bool OCamlASTContext::IsCStringType(lldb::opaque_compiler_type_t type,
+ uint32_t &length) {
+ return false;
}
-bool
-OCamlASTContext::IsDefined(lldb::opaque_compiler_type_t type)
-{
- return type != nullptr;
+bool OCamlASTContext::IsDefined(lldb::opaque_compiler_type_t type) {
+ return type != nullptr;
}
-bool
-OCamlASTContext::IsFloatingPointType(lldb::opaque_compiler_type_t type, uint32_t &count, bool &is_complex)
-{
- return false;
+bool OCamlASTContext::IsFloatingPointType(lldb::opaque_compiler_type_t type,
+ uint32_t &count, bool &is_complex) {
+ return false;
}
-bool
-OCamlASTContext::IsFunctionType(lldb::opaque_compiler_type_t type, bool *is_variadic_ptr)
-{
- return false;
+bool OCamlASTContext::IsFunctionType(lldb::opaque_compiler_type_t type,
+ bool *is_variadic_ptr) {
+ return false;
}
uint32_t
-OCamlASTContext::IsHomogeneousAggregate(lldb::opaque_compiler_type_t type, CompilerType *base_type_ptr)
-{
- return false;
+OCamlASTContext::IsHomogeneousAggregate(lldb::opaque_compiler_type_t type,
+ CompilerType *base_type_ptr) {
+ return false;
}
-size_t
-OCamlASTContext::GetNumberOfFunctionArguments(lldb::opaque_compiler_type_t type)
-{
- return 0;
+size_t OCamlASTContext::GetNumberOfFunctionArguments(
+ lldb::opaque_compiler_type_t type) {
+ return 0;
}
CompilerType
-OCamlASTContext::GetFunctionArgumentAtIndex(lldb::opaque_compiler_type_t type, const size_t index)
-{
- return CompilerType();
+OCamlASTContext::GetFunctionArgumentAtIndex(lldb::opaque_compiler_type_t type,
+ const size_t index) {
+ return CompilerType();
}
-bool
-OCamlASTContext::IsFunctionPointerType(lldb::opaque_compiler_type_t type)
-{
- return IsFunctionType(type);
+bool OCamlASTContext::IsFunctionPointerType(lldb::opaque_compiler_type_t type) {
+ return IsFunctionType(type);
}
-bool
-OCamlASTContext::IsBlockPointerType (lldb::opaque_compiler_type_t type, CompilerType *function_pointer_type_ptr)
-{
- return false;
+bool OCamlASTContext::IsBlockPointerType(
+ lldb::opaque_compiler_type_t type,
+ CompilerType *function_pointer_type_ptr) {
+ return false;
}
-bool
-OCamlASTContext::IsIntegerType(lldb::opaque_compiler_type_t type, bool &is_signed)
-{
- if (OCamlPrimitiveType *ptype = llvm::dyn_cast<OCamlPrimitiveType>(static_cast<OCamlType *>(type)))
- {
- switch (ptype->GetTypeKind())
- {
- case OCamlPrimitiveType::eTypeInt:
- is_signed = true;
- return true;
- }
+bool OCamlASTContext::IsIntegerType(lldb::opaque_compiler_type_t type,
+ bool &is_signed) {
+ if (OCamlPrimitiveType *ptype =
+ llvm::dyn_cast<OCamlPrimitiveType>(static_cast<OCamlType *>(type))) {
+ switch (ptype->GetTypeKind()) {
+ case OCamlPrimitiveType::eTypeInt:
+ is_signed = true;
+ return true;
}
+ }
- is_signed = false;
- return false;
+ is_signed = false;
+ return false;
}
-bool
-OCamlASTContext::IsPolymorphicClass(lldb::opaque_compiler_type_t type)
-{
- return false;
+bool OCamlASTContext::IsPolymorphicClass(lldb::opaque_compiler_type_t type) {
+ return false;
}
-bool
-OCamlASTContext::IsPossibleDynamicType(lldb::opaque_compiler_type_t type,
- CompilerType *target_type,
- bool check_cplusplus, bool check_objc)
-{
- return false;
+bool OCamlASTContext::IsPossibleDynamicType(lldb::opaque_compiler_type_t type,
+ CompilerType *target_type,
+ bool check_cplusplus,
+ bool check_objc) {
+ return false;
}
-bool
-OCamlASTContext::IsRuntimeGeneratedType(lldb::opaque_compiler_type_t type)
-{
- return false;
+bool OCamlASTContext::IsRuntimeGeneratedType(
+ lldb::opaque_compiler_type_t type) {
+ return false;
}
-bool
-OCamlASTContext::IsPointerType(lldb::opaque_compiler_type_t type, CompilerType *pointee_type)
-{
- if (pointee_type)
- pointee_type->Clear();
- return false;
+bool OCamlASTContext::IsPointerType(lldb::opaque_compiler_type_t type,
+ CompilerType *pointee_type) {
+ if (pointee_type)
+ pointee_type->Clear();
+ return false;
}
-bool
-OCamlASTContext::IsPointerOrReferenceType(lldb::opaque_compiler_type_t type, CompilerType *pointee_type)
-{
- return IsPointerType(type, pointee_type);
+bool OCamlASTContext::IsPointerOrReferenceType(
+ lldb::opaque_compiler_type_t type, CompilerType *pointee_type) {
+ return IsPointerType(type, pointee_type);
}
-bool
-OCamlASTContext::IsReferenceType(lldb::opaque_compiler_type_t type, CompilerType *pointee_type, bool *is_rvalue)
-{
- return false;
+bool OCamlASTContext::IsReferenceType(lldb::opaque_compiler_type_t type,
+ CompilerType *pointee_type,
+ bool *is_rvalue) {
+ return false;
}
-bool
-OCamlASTContext::IsScalarType(lldb::opaque_compiler_type_t type)
-{
- return llvm::isa<OCamlPrimitiveType>(static_cast<OCamlType *>(type));
+bool OCamlASTContext::IsScalarType(lldb::opaque_compiler_type_t type) {
+ return llvm::isa<OCamlPrimitiveType>(static_cast<OCamlType *>(type));
}
-bool
-OCamlASTContext::IsTypedefType(lldb::opaque_compiler_type_t type)
-{
- return false;
+bool OCamlASTContext::IsTypedefType(lldb::opaque_compiler_type_t type) {
+ return false;
}
-bool
-OCamlASTContext::IsVoidType(lldb::opaque_compiler_type_t type)
-{
- return false;
+bool OCamlASTContext::IsVoidType(lldb::opaque_compiler_type_t type) {
+ return false;
}
-bool
-OCamlASTContext::SupportsLanguage (lldb::LanguageType language)
-{
- return language == lldb::eLanguageTypeOCaml;
+bool OCamlASTContext::SupportsLanguage(lldb::LanguageType language) {
+ return language == lldb::eLanguageTypeOCaml;
}
-bool
-OCamlASTContext::GetCompleteType(lldb::opaque_compiler_type_t type)
-{
- if (IsCompleteType(type))
- return true;
+bool OCamlASTContext::GetCompleteType(lldb::opaque_compiler_type_t type) {
+ if (IsCompleteType(type))
+ return true;
- return false;
+ return false;
}
-uint32_t
-OCamlASTContext::GetPointerByteSize()
-{
- return m_pointer_byte_size;
-}
+uint32_t OCamlASTContext::GetPointerByteSize() { return m_pointer_byte_size; }
-ConstString
-OCamlASTContext::GetTypeName(lldb::opaque_compiler_type_t type)
-{
- if (type)
- return static_cast<OCamlPrimitiveType *>(type)->GetName();
+ConstString OCamlASTContext::GetTypeName(lldb::opaque_compiler_type_t type) {
+ if (type)
+ return static_cast<OCamlPrimitiveType *>(type)->GetName();
- return ConstString();
+ return ConstString();
}
uint32_t
-OCamlASTContext::GetTypeInfo(lldb::opaque_compiler_type_t type, CompilerType *pointee_or_element_compiler_type)
-{
- if (pointee_or_element_compiler_type)
- pointee_or_element_compiler_type->Clear();
- if (!type)
- return 0;
-
- if (OCamlPrimitiveType *ptype = llvm::dyn_cast<OCamlPrimitiveType>(static_cast<OCamlType *>(type)))
- {
- switch (ptype->GetTypeKind())
- {
- case OCamlPrimitiveType::eTypeInt:
- return eTypeHasValue | eTypeIsBuiltIn | eTypeIsScalar | eTypeIsInteger | eTypeIsSigned;
- }
+OCamlASTContext::GetTypeInfo(lldb::opaque_compiler_type_t type,
+ CompilerType *pointee_or_element_compiler_type) {
+ if (pointee_or_element_compiler_type)
+ pointee_or_element_compiler_type->Clear();
+ if (!type)
+ return 0;
+
+ if (OCamlPrimitiveType *ptype =
+ llvm::dyn_cast<OCamlPrimitiveType>(static_cast<OCamlType *>(type))) {
+ switch (ptype->GetTypeKind()) {
+ case OCamlPrimitiveType::eTypeInt:
+ return eTypeHasValue | eTypeIsBuiltIn | eTypeIsScalar | eTypeIsInteger |
+ eTypeIsSigned;
}
+ }
- return 0;
+ return 0;
}
lldb::TypeClass
-OCamlASTContext::GetTypeClass(lldb::opaque_compiler_type_t type)
-{
- if (llvm::isa<OCamlPrimitiveType>(static_cast<OCamlType *>(type)))
- return eTypeClassBuiltin;
+OCamlASTContext::GetTypeClass(lldb::opaque_compiler_type_t type) {
+ if (llvm::isa<OCamlPrimitiveType>(static_cast<OCamlType *>(type)))
+ return eTypeClassBuiltin;
- return lldb::eTypeClassInvalid;
+ return lldb::eTypeClassInvalid;
}
lldb::BasicType
-OCamlASTContext::GetBasicTypeEnumeration(lldb::opaque_compiler_type_t type)
-{
- return lldb::eBasicTypeInvalid;
+OCamlASTContext::GetBasicTypeEnumeration(lldb::opaque_compiler_type_t type) {
+ return lldb::eBasicTypeInvalid;
}
lldb::LanguageType
-OCamlASTContext::GetMinimumLanguage(lldb::opaque_compiler_type_t type)
-{
- return lldb::eLanguageTypeOCaml;
+OCamlASTContext::GetMinimumLanguage(lldb::opaque_compiler_type_t type) {
+ return lldb::eLanguageTypeOCaml;
}
-unsigned
-OCamlASTContext::GetTypeQualifiers(lldb::opaque_compiler_type_t type)
-{
- return 0;
+unsigned OCamlASTContext::GetTypeQualifiers(lldb::opaque_compiler_type_t type) {
+ return 0;
}
//----------------------------------------------------------------------
@@ -496,300 +397,273 @@ OCamlASTContext::GetTypeQualifiers(lldb:
//----------------------------------------------------------------------
CompilerType
-OCamlASTContext::GetArrayElementType(lldb::opaque_compiler_type_t type, uint64_t *stride)
-{
- return CompilerType();
+OCamlASTContext::GetArrayElementType(lldb::opaque_compiler_type_t type,
+ uint64_t *stride) {
+ return CompilerType();
}
CompilerType
-OCamlASTContext::GetCanonicalType(lldb::opaque_compiler_type_t type)
-{
- return CompilerType(this, type);
+OCamlASTContext::GetCanonicalType(lldb::opaque_compiler_type_t type) {
+ return CompilerType(this, type);
}
CompilerType
-OCamlASTContext::GetFullyUnqualifiedType(lldb::opaque_compiler_type_t type)
-{
- return CompilerType(this, type);
+OCamlASTContext::GetFullyUnqualifiedType(lldb::opaque_compiler_type_t type) {
+ return CompilerType(this, type);
}
-int
-OCamlASTContext::GetFunctionArgumentCount(lldb::opaque_compiler_type_t type)
-{
- return GetNumberOfFunctionArguments(type);
+int OCamlASTContext::GetFunctionArgumentCount(
+ lldb::opaque_compiler_type_t type) {
+ return GetNumberOfFunctionArguments(type);
}
-CompilerType
-OCamlASTContext::GetFunctionArgumentTypeAtIndex(lldb::opaque_compiler_type_t type, size_t idx)
-{
- return GetFunctionArgumentAtIndex(type, idx);
+CompilerType OCamlASTContext::GetFunctionArgumentTypeAtIndex(
+ lldb::opaque_compiler_type_t type, size_t idx) {
+ return GetFunctionArgumentAtIndex(type, idx);
}
CompilerType
-OCamlASTContext::GetFunctionReturnType(lldb::opaque_compiler_type_t type)
-{
- return CompilerType();
+OCamlASTContext::GetFunctionReturnType(lldb::opaque_compiler_type_t type) {
+ return CompilerType();
}
size_t
-OCamlASTContext::GetNumMemberFunctions(lldb::opaque_compiler_type_t type)
-{
- return 0;
+OCamlASTContext::GetNumMemberFunctions(lldb::opaque_compiler_type_t type) {
+ return 0;
}
TypeMemberFunctionImpl
-OCamlASTContext::GetMemberFunctionAtIndex(lldb::opaque_compiler_type_t type, size_t idx)
-{
- return TypeMemberFunctionImpl();
+OCamlASTContext::GetMemberFunctionAtIndex(lldb::opaque_compiler_type_t type,
+ size_t idx) {
+ return TypeMemberFunctionImpl();
}
CompilerType
-OCamlASTContext::GetNonReferenceType(lldb::opaque_compiler_type_t type)
-{
- return CompilerType(this, type);
+OCamlASTContext::GetNonReferenceType(lldb::opaque_compiler_type_t type) {
+ return CompilerType(this, type);
}
CompilerType
-OCamlASTContext::GetPointeeType(lldb::opaque_compiler_type_t type)
-{
- return CompilerType();
+OCamlASTContext::GetPointeeType(lldb::opaque_compiler_type_t type) {
+ return CompilerType();
}
CompilerType
-OCamlASTContext::GetPointerType(lldb::opaque_compiler_type_t type)
-{
- return CompilerType();
+OCamlASTContext::GetPointerType(lldb::opaque_compiler_type_t type) {
+ return CompilerType();
}
CompilerType
-OCamlASTContext::GetTypedefedType(lldb::opaque_compiler_type_t type)
-{
- return CompilerType();
+OCamlASTContext::GetTypedefedType(lldb::opaque_compiler_type_t type) {
+ return CompilerType();
}
-CompilerType
-OCamlASTContext::GetBasicTypeFromAST(lldb::BasicType basic_type)
-{
- return CompilerType();
+CompilerType OCamlASTContext::GetBasicTypeFromAST(lldb::BasicType basic_type) {
+ return CompilerType();
}
CompilerType
-OCamlASTContext::GetBuiltinTypeForEncodingAndBitSize (lldb::Encoding encoding,
- size_t bit_size)
-{
- return CompilerType();
+OCamlASTContext::GetBuiltinTypeForEncodingAndBitSize(lldb::Encoding encoding,
+ size_t bit_size) {
+ return CompilerType();
}
-uint64_t
-OCamlASTContext::GetBitSize(lldb::opaque_compiler_type_t type, ExecutionContextScope *exe_scope)
-{
- if (OCamlPrimitiveType *ptype = llvm::dyn_cast<OCamlPrimitiveType>(static_cast<OCamlType *>(type)))
- {
- switch (ptype->GetTypeKind())
- {
- case OCamlPrimitiveType::eTypeInt:
- return ptype->GetByteSize() * 8;
- }
+uint64_t OCamlASTContext::GetBitSize(lldb::opaque_compiler_type_t type,
+ ExecutionContextScope *exe_scope) {
+ if (OCamlPrimitiveType *ptype =
+ llvm::dyn_cast<OCamlPrimitiveType>(static_cast<OCamlType *>(type))) {
+ switch (ptype->GetTypeKind()) {
+ case OCamlPrimitiveType::eTypeInt:
+ return ptype->GetByteSize() * 8;
}
- return 0;
+ }
+ return 0;
}
-lldb::Encoding
-OCamlASTContext::GetEncoding(lldb::opaque_compiler_type_t type, uint64_t &count)
-{
- count = 1;
- bool is_signed;
- if (IsIntegerType(type, is_signed))
- return is_signed ? lldb::eEncodingSint : lldb::eEncodingUint;
- bool is_complex;
- uint32_t complex_count;
- if (IsFloatingPointType(type, complex_count, is_complex))
- {
- count = complex_count;
- return lldb::eEncodingIEEE754;
- }
- if (IsPointerType(type))
- return lldb::eEncodingUint;
- return lldb::eEncodingInvalid;
+lldb::Encoding OCamlASTContext::GetEncoding(lldb::opaque_compiler_type_t type,
+ uint64_t &count) {
+ count = 1;
+ bool is_signed;
+ if (IsIntegerType(type, is_signed))
+ return is_signed ? lldb::eEncodingSint : lldb::eEncodingUint;
+ bool is_complex;
+ uint32_t complex_count;
+ if (IsFloatingPointType(type, complex_count, is_complex)) {
+ count = complex_count;
+ return lldb::eEncodingIEEE754;
+ }
+ if (IsPointerType(type))
+ return lldb::eEncodingUint;
+ return lldb::eEncodingInvalid;
}
-lldb::Format
-OCamlASTContext::GetFormat(lldb::opaque_compiler_type_t type)
-{
- if (!type)
- return lldb::eFormatDefault;
- return lldb::eFormatBytes;
+lldb::Format OCamlASTContext::GetFormat(lldb::opaque_compiler_type_t type) {
+ if (!type)
+ return lldb::eFormatDefault;
+ return lldb::eFormatBytes;
}
-size_t
-OCamlASTContext::GetTypeBitAlign(lldb::opaque_compiler_type_t type)
-{
- return 0;
+size_t OCamlASTContext::GetTypeBitAlign(lldb::opaque_compiler_type_t type) {
+ return 0;
}
-uint32_t
-OCamlASTContext::GetNumChildren(lldb::opaque_compiler_type_t type, bool omit_empty_base_classes)
-{
- if (!type || !GetCompleteType(type))
- return 0;
+uint32_t OCamlASTContext::GetNumChildren(lldb::opaque_compiler_type_t type,
+ bool omit_empty_base_classes) {
+ if (!type || !GetCompleteType(type))
+ return 0;
- return GetNumFields(type);
+ return GetNumFields(type);
}
-uint32_t
-OCamlASTContext::GetNumFields(lldb::opaque_compiler_type_t type)
-{
- if (!type || !GetCompleteType(type))
- return 0;
+uint32_t OCamlASTContext::GetNumFields(lldb::opaque_compiler_type_t type) {
+ if (!type || !GetCompleteType(type))
return 0;
+ return 0;
}
-CompilerType
-OCamlASTContext::GetFieldAtIndex(lldb::opaque_compiler_type_t type, size_t idx,
- std::string &name, uint64_t *bit_offset_ptr,
- uint32_t *bitfield_bit_size_ptr, bool *is_bitfield_ptr)
-{
- if (bit_offset_ptr)
- *bit_offset_ptr = 0;
- if (bitfield_bit_size_ptr)
- *bitfield_bit_size_ptr = 0;
- if (is_bitfield_ptr)
- *is_bitfield_ptr = false;
-
- if (!type || !GetCompleteType(type))
- return CompilerType();
+CompilerType OCamlASTContext::GetFieldAtIndex(lldb::opaque_compiler_type_t type,
+ size_t idx, std::string &name,
+ uint64_t *bit_offset_ptr,
+ uint32_t *bitfield_bit_size_ptr,
+ bool *is_bitfield_ptr) {
+ if (bit_offset_ptr)
+ *bit_offset_ptr = 0;
+ if (bitfield_bit_size_ptr)
+ *bitfield_bit_size_ptr = 0;
+ if (is_bitfield_ptr)
+ *is_bitfield_ptr = false;
+ if (!type || !GetCompleteType(type))
return CompilerType();
-}
-CompilerType
-OCamlASTContext::GetChildCompilerTypeAtIndex(lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx, size_t idx,
- bool transparent_pointers, bool omit_empty_base_classes,
- bool ignore_array_bounds, std::string &child_name,
- uint32_t &child_byte_size, int32_t &child_byte_offset,
- uint32_t &child_bitfield_bit_size, uint32_t &child_bitfield_bit_offset,
- bool &child_is_base_class, bool &child_is_deref_of_parent, ValueObject *valobj,
- uint64_t &language_flags)
-{
- child_name.clear();
- child_byte_size = 0;
- child_byte_offset = 0;
- child_bitfield_bit_size = 0;
- child_bitfield_bit_offset = 0;
- child_is_base_class = false;
- child_is_deref_of_parent = false;
- language_flags = 0;
+ return CompilerType();
+}
- if (!type || !GetCompleteType(type))
- return CompilerType();
+CompilerType OCamlASTContext::GetChildCompilerTypeAtIndex(
+ lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx, size_t idx,
+ bool transparent_pointers, bool omit_empty_base_classes,
+ bool ignore_array_bounds, std::string &child_name,
+ uint32_t &child_byte_size, int32_t &child_byte_offset,
+ uint32_t &child_bitfield_bit_size, uint32_t &child_bitfield_bit_offset,
+ bool &child_is_base_class, bool &child_is_deref_of_parent,
+ ValueObject *valobj, uint64_t &language_flags) {
+ child_name.clear();
+ child_byte_size = 0;
+ child_byte_offset = 0;
+ child_bitfield_bit_size = 0;
+ child_bitfield_bit_offset = 0;
+ child_is_base_class = false;
+ child_is_deref_of_parent = false;
+ language_flags = 0;
+ if (!type || !GetCompleteType(type))
return CompilerType();
+
+ return CompilerType();
}
uint32_t
-OCamlASTContext::GetIndexOfChildWithName(lldb::opaque_compiler_type_t type, const char *name, bool omit_empty_base_classes)
-{
- if (!type || !GetCompleteType(type))
- return UINT_MAX;
-
+OCamlASTContext::GetIndexOfChildWithName(lldb::opaque_compiler_type_t type,
+ const char *name,
+ bool omit_empty_base_classes) {
+ if (!type || !GetCompleteType(type))
return UINT_MAX;
+
+ return UINT_MAX;
}
-size_t
-OCamlASTContext::GetIndexOfChildMemberWithName(lldb::opaque_compiler_type_t type, const char *name,
- bool omit_empty_base_classes, std::vector<uint32_t> &child_indexes)
-{
- uint32_t index = GetIndexOfChildWithName(type, name, omit_empty_base_classes);
- if (index == UINT_MAX)
- return 0;
- child_indexes.push_back(index);
- return 1;
+size_t OCamlASTContext::GetIndexOfChildMemberWithName(
+ lldb::opaque_compiler_type_t type, const char *name,
+ bool omit_empty_base_classes, std::vector<uint32_t> &child_indexes) {
+ uint32_t index = GetIndexOfChildWithName(type, name, omit_empty_base_classes);
+ if (index == UINT_MAX)
+ return 0;
+ child_indexes.push_back(index);
+ return 1;
}
size_t
-OCamlASTContext::ConvertStringToFloatValue(lldb::opaque_compiler_type_t type, const char *s, uint8_t *dst, size_t dst_size)
-{
- assert(false);
- return 0;
+OCamlASTContext::ConvertStringToFloatValue(lldb::opaque_compiler_type_t type,
+ const char *s, uint8_t *dst,
+ size_t dst_size) {
+ assert(false);
+ return 0;
}
//----------------------------------------------------------------------
// Dumping types
//----------------------------------------------------------------------
-void
-OCamlASTContext::DumpValue(lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx, Stream *s, lldb::Format format,
- const DataExtractor &data, lldb::offset_t data_byte_offset, size_t data_byte_size,
- uint32_t bitfield_bit_size, uint32_t bitfield_bit_offset, bool show_types, bool show_summary,
- bool verbose, uint32_t depth)
-{
- if (!type) {
- s->Printf("no type\n");
- return;
- }
-
- s->Printf("no value\n");
+void OCamlASTContext::DumpValue(
+ lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx, Stream *s,
+ lldb::Format format, const DataExtractor &data,
+ lldb::offset_t data_byte_offset, size_t data_byte_size,
+ uint32_t bitfield_bit_size, uint32_t bitfield_bit_offset, bool show_types,
+ bool show_summary, bool verbose, uint32_t depth) {
+ if (!type) {
+ s->Printf("no type\n");
+ return;
+ }
+
+ s->Printf("no value\n");
+
+ if (show_summary)
+ DumpSummary(type, exe_ctx, s, data, data_byte_offset, data_byte_size);
+}
+
+bool OCamlASTContext::DumpTypeValue(
+ lldb::opaque_compiler_type_t type, Stream *s, lldb::Format format,
+ const DataExtractor &data, lldb::offset_t byte_offset, size_t byte_size,
+ uint32_t bitfield_bit_size, uint32_t bitfield_bit_offset,
+ ExecutionContextScope *exe_scope) {
+ if (!type) {
+ s->Printf("no type value\n");
+ return false;
+ }
+
+ if (IsScalarType(type)) {
+ return data.Dump(s, byte_offset, format, byte_size, 1, UINT64_MAX,
+ LLDB_INVALID_ADDRESS, bitfield_bit_size,
+ bitfield_bit_offset, exe_scope);
+ }
+
+ return false;
+}
+
+void OCamlASTContext::DumpSummary(lldb::opaque_compiler_type_t type,
+ ExecutionContext *exe_ctx, Stream *s,
+ const DataExtractor &data,
+ lldb::offset_t data_offset,
+ size_t data_byte_size) {
+ s->Printf("no summary\n");
+}
+
+void OCamlASTContext::DumpTypeDescription(lldb::opaque_compiler_type_t type) {
+ StreamFile s(stdout, false);
+ DumpTypeDescription(type, &s);
+}
+
+void OCamlASTContext::DumpTypeDescription(lldb::opaque_compiler_type_t type,
+ Stream *s) {
+ static_cast<OCamlType *>(type)->Dump(s);
+}
+
+CompilerType OCamlASTContext::CreateBaseType(const ConstString &name,
+ uint64_t byte_size) {
+ if (m_base_type_map.empty()) {
+ OCamlPrimitiveType *type = new OCamlPrimitiveType(
+ OCamlPrimitiveType::eTypeInt, ConstString("ocaml_int"), byte_size);
+ m_base_type_map.emplace(type->GetName(),
+ std::unique_ptr<OCamlASTContext::OCamlType>(type));
+ }
+
+ auto it = m_base_type_map.find(name);
+ if (it == m_base_type_map.end()) {
+ OCamlPrimitiveType *type =
+ new OCamlPrimitiveType(OCamlPrimitiveType::eTypeInt, name, byte_size);
+ it = m_base_type_map
+ .emplace(name, std::unique_ptr<OCamlASTContext::OCamlType>(type))
+ .first;
+ }
- if (show_summary)
- DumpSummary (type, exe_ctx, s, data, data_byte_offset, data_byte_size);
+ return CompilerType(this, it->second.get());
}
-
-bool
-OCamlASTContext::DumpTypeValue(lldb::opaque_compiler_type_t type, Stream *s,
- lldb::Format format, const DataExtractor &data,
- lldb::offset_t byte_offset, size_t byte_size, uint32_t bitfield_bit_size,
- uint32_t bitfield_bit_offset, ExecutionContextScope *exe_scope)
-{
- if (!type) {
- s->Printf("no type value\n");
- return false;
- }
-
- if (IsScalarType(type))
- {
- return
- data.Dump(s, byte_offset, format, byte_size, 1, UINT64_MAX,
- LLDB_INVALID_ADDRESS, bitfield_bit_size, bitfield_bit_offset, exe_scope);
- }
-
- return false;
-}
-
-void
-OCamlASTContext::DumpSummary(lldb::opaque_compiler_type_t type, ExecutionContext *exe_ctx, Stream *s,
- const DataExtractor &data, lldb::offset_t data_offset, size_t data_byte_size)
-{
- s->Printf("no summary\n");
-}
-
-void
-OCamlASTContext::DumpTypeDescription(lldb::opaque_compiler_type_t type)
-{
- StreamFile s(stdout, false);
- DumpTypeDescription(type, &s);
-}
-
-void
-OCamlASTContext::DumpTypeDescription(lldb::opaque_compiler_type_t type, Stream *s)
-{
- static_cast<OCamlType *>(type)->Dump(s);
-}
-
-CompilerType
-OCamlASTContext::CreateBaseType(const ConstString &name, uint64_t byte_size)
-{
- if (m_base_type_map.empty())
- {
- OCamlPrimitiveType *type = new OCamlPrimitiveType(OCamlPrimitiveType::eTypeInt, ConstString("ocaml_int"), byte_size);
- m_base_type_map.emplace(type->GetName(), std::unique_ptr<OCamlASTContext::OCamlType>(type));
- }
-
- auto it = m_base_type_map.find(name);
- if (it == m_base_type_map.end())
- {
- OCamlPrimitiveType *type = new OCamlPrimitiveType(OCamlPrimitiveType::eTypeInt, name, byte_size);
- it = m_base_type_map.emplace(name, std::unique_ptr<OCamlASTContext::OCamlType>(type)).first;
- }
-
- return CompilerType(this, it->second.get());
-}
-
Modified: lldb/trunk/source/Symbol/ObjectFile.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/ObjectFile.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/ObjectFile.cpp (original)
+++ lldb/trunk/source/Symbol/ObjectFile.cpp Tue Sep 6 15:57:50 2016
@@ -7,7 +7,8 @@
//
//===----------------------------------------------------------------------===//
-#include "lldb/lldb-private.h"
+#include "lldb/Symbol/ObjectFile.h"
+#include "Plugins/ObjectContainer/BSD-Archive/ObjectContainerBSDArchive.h"
#include "lldb/Core/DataBuffer.h"
#include "lldb/Core/DataBufferHeap.h"
#include "lldb/Core/Log.h"
@@ -17,653 +18,632 @@
#include "lldb/Core/RegularExpression.h"
#include "lldb/Core/Section.h"
#include "lldb/Core/Timer.h"
-#include "lldb/Symbol/ObjectFile.h"
#include "lldb/Symbol/ObjectContainer.h"
#include "lldb/Symbol/SymbolFile.h"
#include "lldb/Target/Process.h"
-#include "Plugins/ObjectContainer/BSD-Archive/ObjectContainerBSDArchive.h"
+#include "lldb/lldb-private.h"
using namespace lldb;
using namespace lldb_private;
ObjectFileSP
-ObjectFile::FindPlugin (const lldb::ModuleSP &module_sp,
- const FileSpec* file,
- lldb::offset_t file_offset,
- lldb::offset_t file_size,
- DataBufferSP &data_sp,
- lldb::offset_t &data_offset)
-{
- ObjectFileSP object_file_sp;
-
- if (module_sp)
- {
- Timer scoped_timer (LLVM_PRETTY_FUNCTION,
- "ObjectFile::FindPlugin (module = %s, file = %p, file_offset = 0x%8.8" PRIx64 ", file_size = 0x%8.8" PRIx64 ")",
- module_sp->GetFileSpec().GetPath().c_str(),
- static_cast<const void*>(file),
- static_cast<uint64_t>(file_offset),
- static_cast<uint64_t>(file_size));
- if (file)
- {
- FileSpec archive_file;
- ObjectContainerCreateInstance create_object_container_callback;
-
- const bool file_exists = file->Exists();
- if (!data_sp)
- {
- // We have an object name which most likely means we have
- // a .o file in a static archive (.a file). Try and see if
- // we have a cached archive first without reading any data
- // first
- if (file_exists && module_sp->GetObjectName())
- {
- for (uint32_t idx = 0; (create_object_container_callback = PluginManager::GetObjectContainerCreateCallbackAtIndex(idx)) != nullptr; ++idx)
- {
- std::unique_ptr<ObjectContainer> object_container_ap(create_object_container_callback(module_sp, data_sp, data_offset, file, file_offset, file_size));
-
- if (object_container_ap.get())
- object_file_sp = object_container_ap->GetObjectFile(file);
-
- if (object_file_sp.get())
- return object_file_sp;
- }
- }
- // Ok, we didn't find any containers that have a named object, now
- // lets read the first 512 bytes from the file so the object file
- // and object container plug-ins can use these bytes to see if they
- // can parse this file.
- if (file_size > 0)
- {
- data_sp = file->ReadFileContents(file_offset, std::min<size_t>(512, file_size));
- data_offset = 0;
- }
- }
+ObjectFile::FindPlugin(const lldb::ModuleSP &module_sp, const FileSpec *file,
+ lldb::offset_t file_offset, lldb::offset_t file_size,
+ DataBufferSP &data_sp, lldb::offset_t &data_offset) {
+ ObjectFileSP object_file_sp;
+
+ if (module_sp) {
+ Timer scoped_timer(
+ LLVM_PRETTY_FUNCTION,
+ "ObjectFile::FindPlugin (module = %s, file = %p, file_offset = "
+ "0x%8.8" PRIx64 ", file_size = 0x%8.8" PRIx64 ")",
+ module_sp->GetFileSpec().GetPath().c_str(),
+ static_cast<const void *>(file), static_cast<uint64_t>(file_offset),
+ static_cast<uint64_t>(file_size));
+ if (file) {
+ FileSpec archive_file;
+ ObjectContainerCreateInstance create_object_container_callback;
+
+ const bool file_exists = file->Exists();
+ if (!data_sp) {
+ // We have an object name which most likely means we have
+ // a .o file in a static archive (.a file). Try and see if
+ // we have a cached archive first without reading any data
+ // first
+ if (file_exists && module_sp->GetObjectName()) {
+ for (uint32_t idx = 0;
+ (create_object_container_callback =
+ PluginManager::GetObjectContainerCreateCallbackAtIndex(
+ idx)) != nullptr;
+ ++idx) {
+ std::unique_ptr<ObjectContainer> object_container_ap(
+ create_object_container_callback(module_sp, data_sp,
+ data_offset, file, file_offset,
+ file_size));
- if (!data_sp || data_sp->GetByteSize() == 0)
- {
- // Check for archive file with format "/path/to/archive.a(object.o)"
- char path_with_object[PATH_MAX*2];
- module_sp->GetFileSpec().GetPath(path_with_object, sizeof(path_with_object));
-
- ConstString archive_object;
- const bool must_exist = true;
- if (ObjectFile::SplitArchivePathWithObject (path_with_object, archive_file, archive_object, must_exist))
- {
- file_size = archive_file.GetByteSize();
- if (file_size > 0)
- {
- file = &archive_file;
- module_sp->SetFileSpecAndObjectName (archive_file, archive_object);
- // Check if this is a object container by iterating through all object
- // container plugin instances and then trying to get an object file
- // from the container plugins since we had a name. Also, don't read
- // ANY data in case there is data cached in the container plug-ins
- // (like BSD archives caching the contained objects within an file).
- for (uint32_t idx = 0; (create_object_container_callback = PluginManager::GetObjectContainerCreateCallbackAtIndex(idx)) != nullptr; ++idx)
- {
- std::unique_ptr<ObjectContainer> object_container_ap(create_object_container_callback(module_sp, data_sp, data_offset, file, file_offset, file_size));
-
- if (object_container_ap.get())
- object_file_sp = object_container_ap->GetObjectFile(file);
-
- if (object_file_sp.get())
- return object_file_sp;
- }
- // We failed to find any cached object files in the container
- // plug-ins, so lets read the first 512 bytes and try again below...
- data_sp = archive_file.ReadFileContents(file_offset, 512);
- }
- }
- }
+ if (object_container_ap.get())
+ object_file_sp = object_container_ap->GetObjectFile(file);
- if (data_sp && data_sp->GetByteSize() > 0)
- {
- // Check if this is a normal object file by iterating through
- // all object file plugin instances.
- ObjectFileCreateInstance create_object_file_callback;
- for (uint32_t idx = 0; (create_object_file_callback = PluginManager::GetObjectFileCreateCallbackAtIndex(idx)) != nullptr; ++idx)
- {
- object_file_sp.reset (create_object_file_callback(module_sp, data_sp, data_offset, file, file_offset, file_size));
- if (object_file_sp.get())
- return object_file_sp;
- }
-
- // Check if this is a object container by iterating through
- // all object container plugin instances and then trying to get
- // an object file from the container.
- for (uint32_t idx = 0; (create_object_container_callback = PluginManager::GetObjectContainerCreateCallbackAtIndex(idx)) != nullptr; ++idx)
- {
- std::unique_ptr<ObjectContainer> object_container_ap(create_object_container_callback(module_sp, data_sp, data_offset, file, file_offset, file_size));
-
- if (object_container_ap.get())
- object_file_sp = object_container_ap->GetObjectFile(file);
-
- if (object_file_sp.get())
- return object_file_sp;
- }
- }
- }
- }
- // We didn't find it, so clear our shared pointer in case it
- // contains anything and return an empty shared pointer
- object_file_sp.reset();
- return object_file_sp;
-}
-
-ObjectFileSP
-ObjectFile::FindPlugin (const lldb::ModuleSP &module_sp,
- const ProcessSP &process_sp,
- lldb::addr_t header_addr,
- DataBufferSP &data_sp)
-{
- ObjectFileSP object_file_sp;
-
- if (module_sp)
- {
- Timer scoped_timer (LLVM_PRETTY_FUNCTION,
- "ObjectFile::FindPlugin (module = %s, process = %p, header_addr = 0x%" PRIx64 ")",
- module_sp->GetFileSpec().GetPath().c_str(),
- static_cast<void*>(process_sp.get()), header_addr);
- uint32_t idx;
-
- // Check if this is a normal object file by iterating through
- // all object file plugin instances.
- ObjectFileCreateMemoryInstance create_callback;
- for (idx = 0; (create_callback = PluginManager::GetObjectFileCreateMemoryCallbackAtIndex(idx)) != nullptr; ++idx)
- {
- object_file_sp.reset (create_callback(module_sp, data_sp, process_sp, header_addr));
if (object_file_sp.get())
- return object_file_sp;
+ return object_file_sp;
+ }
}
- }
-
- // We didn't find it, so clear our shared pointer in case it
- // contains anything and return an empty shared pointer
- object_file_sp.reset();
- return object_file_sp;
-}
-
-size_t
-ObjectFile::GetModuleSpecifications (const FileSpec &file,
- lldb::offset_t file_offset,
- lldb::offset_t file_size,
- ModuleSpecList &specs)
-{
- DataBufferSP data_sp (file.ReadFileContents(file_offset, 512));
- if (data_sp)
- {
- if (file_size == 0)
- {
- const lldb::offset_t actual_file_size = file.GetByteSize();
- if (actual_file_size > file_offset)
- file_size = actual_file_size - file_offset;
- }
- return ObjectFile::GetModuleSpecifications (file, // file spec
- data_sp, // data bytes
- 0, // data offset
- file_offset,// file offset
- file_size, // file length
- specs);
- }
- return 0;
-}
-
-size_t
-ObjectFile::GetModuleSpecifications (const lldb_private::FileSpec& file,
- lldb::DataBufferSP& data_sp,
- lldb::offset_t data_offset,
- lldb::offset_t file_offset,
- lldb::offset_t file_size,
- lldb_private::ModuleSpecList &specs)
-{
- const size_t initial_count = specs.GetSize();
- ObjectFileGetModuleSpecifications callback;
- uint32_t i;
- // Try the ObjectFile plug-ins
- for (i = 0; (callback = PluginManager::GetObjectFileGetModuleSpecificationsCallbackAtIndex(i)) != nullptr; ++i)
- {
- if (callback (file, data_sp, data_offset, file_offset, file_size, specs) > 0)
- return specs.GetSize() - initial_count;
- }
-
- // Try the ObjectContainer plug-ins
- for (i = 0; (callback = PluginManager::GetObjectContainerGetModuleSpecificationsCallbackAtIndex(i)) != nullptr; ++i)
- {
- if (callback (file, data_sp, data_offset, file_offset, file_size, specs) > 0)
- return specs.GetSize() - initial_count;
- }
- return 0;
-}
-
-ObjectFile::ObjectFile (const lldb::ModuleSP &module_sp,
- const FileSpec *file_spec_ptr,
- lldb::offset_t file_offset,
- lldb::offset_t length,
- const lldb::DataBufferSP& data_sp,
- lldb::offset_t data_offset) :
- ModuleChild (module_sp),
- m_file (), // This file could be different from the original module's file
- m_type (eTypeInvalid),
- m_strata (eStrataInvalid),
- m_file_offset (file_offset),
- m_length (length),
- m_data (),
- m_unwind_table (*this),
- m_process_wp(),
- m_memory_addr (LLDB_INVALID_ADDRESS),
- m_sections_ap(),
- m_symtab_ap (),
- m_synthetic_symbol_idx (0)
-{
- if (file_spec_ptr)
- m_file = *file_spec_ptr;
- if (data_sp)
- m_data.SetData (data_sp, data_offset, length);
- Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_OBJECT));
- if (log)
- log->Printf ("%p ObjectFile::ObjectFile() module = %p (%s), file = %s, file_offset = 0x%8.8" PRIx64 ", size = %" PRIu64,
- static_cast<void*>(this),
- static_cast<void*>(module_sp.get()),
- module_sp->GetSpecificationDescription().c_str(),
- m_file ? m_file.GetPath().c_str() : "<NULL>",
- m_file_offset, m_length);
-}
+ // Ok, we didn't find any containers that have a named object, now
+ // lets read the first 512 bytes from the file so the object file
+ // and object container plug-ins can use these bytes to see if they
+ // can parse this file.
+ if (file_size > 0) {
+ data_sp = file->ReadFileContents(file_offset,
+ std::min<size_t>(512, file_size));
+ data_offset = 0;
+ }
+ }
+
+ if (!data_sp || data_sp->GetByteSize() == 0) {
+ // Check for archive file with format "/path/to/archive.a(object.o)"
+ char path_with_object[PATH_MAX * 2];
+ module_sp->GetFileSpec().GetPath(path_with_object,
+ sizeof(path_with_object));
+
+ ConstString archive_object;
+ const bool must_exist = true;
+ if (ObjectFile::SplitArchivePathWithObject(
+ path_with_object, archive_file, archive_object, must_exist)) {
+ file_size = archive_file.GetByteSize();
+ if (file_size > 0) {
+ file = &archive_file;
+ module_sp->SetFileSpecAndObjectName(archive_file, archive_object);
+ // Check if this is a object container by iterating through all
+ // object
+ // container plugin instances and then trying to get an object file
+ // from the container plugins since we had a name. Also, don't read
+ // ANY data in case there is data cached in the container plug-ins
+ // (like BSD archives caching the contained objects within an file).
+ for (uint32_t idx = 0;
+ (create_object_container_callback =
+ PluginManager::GetObjectContainerCreateCallbackAtIndex(
+ idx)) != nullptr;
+ ++idx) {
+ std::unique_ptr<ObjectContainer> object_container_ap(
+ create_object_container_callback(module_sp, data_sp,
+ data_offset, file,
+ file_offset, file_size));
+ if (object_container_ap.get())
+ object_file_sp = object_container_ap->GetObjectFile(file);
-ObjectFile::ObjectFile (const lldb::ModuleSP &module_sp,
- const ProcessSP &process_sp,
- lldb::addr_t header_addr,
- DataBufferSP& header_data_sp) :
- ModuleChild (module_sp),
- m_file (),
- m_type (eTypeInvalid),
- m_strata (eStrataInvalid),
- m_file_offset (0),
- m_length (0),
- m_data (),
- m_unwind_table (*this),
- m_process_wp (process_sp),
- m_memory_addr (header_addr),
- m_sections_ap(),
- m_symtab_ap (),
- m_synthetic_symbol_idx (0)
-{
- if (header_data_sp)
- m_data.SetData (header_data_sp, 0, header_data_sp->GetByteSize());
- Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_OBJECT));
- if (log)
- log->Printf ("%p ObjectFile::ObjectFile() module = %p (%s), process = %p, header_addr = 0x%" PRIx64,
- static_cast<void*>(this),
- static_cast<void*>(module_sp.get()),
- module_sp->GetSpecificationDescription().c_str(),
- static_cast<void*>(process_sp.get()), m_memory_addr);
-}
-
-
-ObjectFile::~ObjectFile()
-{
- Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_OBJECT));
- if (log)
- log->Printf ("%p ObjectFile::~ObjectFile ()\n",
- static_cast<void*>(this));
-}
-
-bool
-ObjectFile::SetModulesArchitecture (const ArchSpec &new_arch)
-{
- ModuleSP module_sp (GetModule());
- if (module_sp)
- return module_sp->SetArchitecture (new_arch);
- return false;
-}
-
-AddressClass
-ObjectFile::GetAddressClass (addr_t file_addr)
-{
- Symtab *symtab = GetSymtab();
- if (symtab)
- {
- Symbol *symbol = symtab->FindSymbolContainingFileAddress(file_addr);
- if (symbol)
- {
- if (symbol->ValueIsAddress())
- {
- const SectionSP section_sp (symbol->GetAddressRef().GetSection());
- if (section_sp)
- {
- const SectionType section_type = section_sp->GetType();
- switch (section_type)
- {
- case eSectionTypeInvalid:
- return eAddressClassUnknown;
- case eSectionTypeCode:
- return eAddressClassCode;
- case eSectionTypeContainer:
- return eAddressClassUnknown;
- case eSectionTypeData:
- case eSectionTypeDataCString:
- case eSectionTypeDataCStringPointers:
- case eSectionTypeDataSymbolAddress:
- case eSectionTypeData4:
- case eSectionTypeData8:
- case eSectionTypeData16:
- case eSectionTypeDataPointers:
- case eSectionTypeZeroFill:
- case eSectionTypeDataObjCMessageRefs:
- case eSectionTypeDataObjCCFStrings:
- case eSectionTypeGoSymtab:
- return eAddressClassData;
- case eSectionTypeDebug:
- case eSectionTypeDWARFDebugAbbrev:
- case eSectionTypeDWARFDebugAddr:
- case eSectionTypeDWARFDebugAranges:
- case eSectionTypeDWARFDebugFrame:
- case eSectionTypeDWARFDebugInfo:
- case eSectionTypeDWARFDebugLine:
- case eSectionTypeDWARFDebugLoc:
- case eSectionTypeDWARFDebugMacInfo:
- case eSectionTypeDWARFDebugMacro:
- case eSectionTypeDWARFDebugPubNames:
- case eSectionTypeDWARFDebugPubTypes:
- case eSectionTypeDWARFDebugRanges:
- case eSectionTypeDWARFDebugStr:
- case eSectionTypeDWARFDebugStrOffsets:
- case eSectionTypeDWARFAppleNames:
- case eSectionTypeDWARFAppleTypes:
- case eSectionTypeDWARFAppleNamespaces:
- case eSectionTypeDWARFAppleObjC:
- return eAddressClassDebug;
- case eSectionTypeEHFrame:
- case eSectionTypeARMexidx:
- case eSectionTypeARMextab:
- case eSectionTypeCompactUnwind:
- return eAddressClassRuntime;
- case eSectionTypeELFSymbolTable:
- case eSectionTypeELFDynamicSymbols:
- case eSectionTypeELFRelocationEntries:
- case eSectionTypeELFDynamicLinkInfo:
- case eSectionTypeOther:
- return eAddressClassUnknown;
- case eSectionTypeAbsoluteAddress:
- // In case of absolute sections decide the address class based on the symbol
- // type because the section type isn't specify if it is a code or a data
- // section.
- break;
- }
- }
- }
-
- const SymbolType symbol_type = symbol->GetType();
- switch (symbol_type)
- {
- case eSymbolTypeAny: return eAddressClassUnknown;
- case eSymbolTypeAbsolute: return eAddressClassUnknown;
- case eSymbolTypeCode: return eAddressClassCode;
- case eSymbolTypeTrampoline: return eAddressClassCode;
- case eSymbolTypeResolver: return eAddressClassCode;
- case eSymbolTypeData: return eAddressClassData;
- case eSymbolTypeRuntime: return eAddressClassRuntime;
- case eSymbolTypeException: return eAddressClassRuntime;
- case eSymbolTypeSourceFile: return eAddressClassDebug;
- case eSymbolTypeHeaderFile: return eAddressClassDebug;
- case eSymbolTypeObjectFile: return eAddressClassDebug;
- case eSymbolTypeCommonBlock: return eAddressClassDebug;
- case eSymbolTypeBlock: return eAddressClassDebug;
- case eSymbolTypeLocal: return eAddressClassData;
- case eSymbolTypeParam: return eAddressClassData;
- case eSymbolTypeVariable: return eAddressClassData;
- case eSymbolTypeVariableType: return eAddressClassDebug;
- case eSymbolTypeLineEntry: return eAddressClassDebug;
- case eSymbolTypeLineHeader: return eAddressClassDebug;
- case eSymbolTypeScopeBegin: return eAddressClassDebug;
- case eSymbolTypeScopeEnd: return eAddressClassDebug;
- case eSymbolTypeAdditional: return eAddressClassUnknown;
- case eSymbolTypeCompiler: return eAddressClassDebug;
- case eSymbolTypeInstrumentation:return eAddressClassDebug;
- case eSymbolTypeUndefined: return eAddressClassUnknown;
- case eSymbolTypeObjCClass: return eAddressClassRuntime;
- case eSymbolTypeObjCMetaClass: return eAddressClassRuntime;
- case eSymbolTypeObjCIVar: return eAddressClassRuntime;
- case eSymbolTypeReExported: return eAddressClassRuntime;
+ if (object_file_sp.get())
+ return object_file_sp;
}
+ // We failed to find any cached object files in the container
+ // plug-ins, so lets read the first 512 bytes and try again below...
+ data_sp = archive_file.ReadFileContents(file_offset, 512);
+ }
}
- }
- return eAddressClassUnknown;
-}
-
-DataBufferSP
-ObjectFile::ReadMemory (const ProcessSP &process_sp, lldb::addr_t addr, size_t byte_size)
-{
- DataBufferSP data_sp;
- if (process_sp)
- {
- std::unique_ptr<DataBufferHeap> data_ap (new DataBufferHeap (byte_size, 0));
- Error error;
- const size_t bytes_read = process_sp->ReadMemory (addr,
- data_ap->GetBytes(),
- data_ap->GetByteSize(),
- error);
- if (bytes_read == byte_size)
- data_sp.reset (data_ap.release());
- }
- return data_sp;
-}
+ }
-size_t
-ObjectFile::GetData (lldb::offset_t offset, size_t length, DataExtractor &data) const
-{
- // The entire file has already been mmap'ed into m_data, so just copy from there
- // as the back mmap buffer will be shared with shared pointers.
- return data.SetData (m_data, offset, length);
-}
-
-size_t
-ObjectFile::CopyData (lldb::offset_t offset, size_t length, void *dst) const
-{
- // The entire file has already been mmap'ed into m_data, so just copy from there
- // Note that the data remains in target byte order.
- return m_data.CopyData (offset, length, dst);
-}
-
-
-size_t
-ObjectFile::ReadSectionData (const Section *section, lldb::offset_t section_offset, void *dst, size_t dst_len) const
-{
- assert(section);
- section_offset *= section->GetTargetByteSize();
-
- // If some other objectfile owns this data, pass this to them.
- if (section->GetObjectFile() != this)
- return section->GetObjectFile()->ReadSectionData (section, section_offset, dst, dst_len);
-
- if (IsInMemory())
- {
- ProcessSP process_sp (m_process_wp.lock());
- if (process_sp)
- {
- Error error;
- const addr_t base_load_addr = section->GetLoadBaseAddress (&process_sp->GetTarget());
- if (base_load_addr != LLDB_INVALID_ADDRESS)
- return process_sp->ReadMemory (base_load_addr + section_offset, dst, dst_len, error);
- }
- }
- else
- {
- const lldb::offset_t section_file_size = section->GetFileSize();
- if (section_offset < section_file_size)
- {
- const size_t section_bytes_left = section_file_size - section_offset;
- size_t section_dst_len = dst_len;
- if (section_dst_len > section_bytes_left)
- section_dst_len = section_bytes_left;
- return CopyData (section->GetFileOffset() + section_offset, section_dst_len, dst);
- }
- else
- {
- if (section->GetType() == eSectionTypeZeroFill)
- {
- const uint64_t section_size = section->GetByteSize();
- const uint64_t section_bytes_left = section_size - section_offset;
- uint64_t section_dst_len = dst_len;
- if (section_dst_len > section_bytes_left)
- section_dst_len = section_bytes_left;
- memset(dst, 0, section_dst_len);
- return section_dst_len;
- }
- }
+ if (data_sp && data_sp->GetByteSize() > 0) {
+ // Check if this is a normal object file by iterating through
+ // all object file plugin instances.
+ ObjectFileCreateInstance create_object_file_callback;
+ for (uint32_t idx = 0;
+ (create_object_file_callback =
+ PluginManager::GetObjectFileCreateCallbackAtIndex(idx)) !=
+ nullptr;
+ ++idx) {
+ object_file_sp.reset(create_object_file_callback(
+ module_sp, data_sp, data_offset, file, file_offset, file_size));
+ if (object_file_sp.get())
+ return object_file_sp;
+ }
+
+ // Check if this is a object container by iterating through
+ // all object container plugin instances and then trying to get
+ // an object file from the container.
+ for (uint32_t idx = 0;
+ (create_object_container_callback =
+ PluginManager::GetObjectContainerCreateCallbackAtIndex(
+ idx)) != nullptr;
+ ++idx) {
+ std::unique_ptr<ObjectContainer> object_container_ap(
+ create_object_container_callback(module_sp, data_sp, data_offset,
+ file, file_offset, file_size));
+
+ if (object_container_ap.get())
+ object_file_sp = object_container_ap->GetObjectFile(file);
+
+ if (object_file_sp.get())
+ return object_file_sp;
+ }
+ }
+ }
+ }
+ // We didn't find it, so clear our shared pointer in case it
+ // contains anything and return an empty shared pointer
+ object_file_sp.reset();
+ return object_file_sp;
+}
+
+ObjectFileSP ObjectFile::FindPlugin(const lldb::ModuleSP &module_sp,
+ const ProcessSP &process_sp,
+ lldb::addr_t header_addr,
+ DataBufferSP &data_sp) {
+ ObjectFileSP object_file_sp;
+
+ if (module_sp) {
+ Timer scoped_timer(LLVM_PRETTY_FUNCTION, "ObjectFile::FindPlugin (module = "
+ "%s, process = %p, header_addr = "
+ "0x%" PRIx64 ")",
+ module_sp->GetFileSpec().GetPath().c_str(),
+ static_cast<void *>(process_sp.get()), header_addr);
+ uint32_t idx;
+
+ // Check if this is a normal object file by iterating through
+ // all object file plugin instances.
+ ObjectFileCreateMemoryInstance create_callback;
+ for (idx = 0;
+ (create_callback =
+ PluginManager::GetObjectFileCreateMemoryCallbackAtIndex(idx)) !=
+ nullptr;
+ ++idx) {
+ object_file_sp.reset(
+ create_callback(module_sp, data_sp, process_sp, header_addr));
+ if (object_file_sp.get())
+ return object_file_sp;
+ }
+ }
+
+ // We didn't find it, so clear our shared pointer in case it
+ // contains anything and return an empty shared pointer
+ object_file_sp.reset();
+ return object_file_sp;
+}
+
+size_t ObjectFile::GetModuleSpecifications(const FileSpec &file,
+ lldb::offset_t file_offset,
+ lldb::offset_t file_size,
+ ModuleSpecList &specs) {
+ DataBufferSP data_sp(file.ReadFileContents(file_offset, 512));
+ if (data_sp) {
+ if (file_size == 0) {
+ const lldb::offset_t actual_file_size = file.GetByteSize();
+ if (actual_file_size > file_offset)
+ file_size = actual_file_size - file_offset;
+ }
+ return ObjectFile::GetModuleSpecifications(file, // file spec
+ data_sp, // data bytes
+ 0, // data offset
+ file_offset, // file offset
+ file_size, // file length
+ specs);
+ }
+ return 0;
+}
+
+size_t ObjectFile::GetModuleSpecifications(
+ const lldb_private::FileSpec &file, lldb::DataBufferSP &data_sp,
+ lldb::offset_t data_offset, lldb::offset_t file_offset,
+ lldb::offset_t file_size, lldb_private::ModuleSpecList &specs) {
+ const size_t initial_count = specs.GetSize();
+ ObjectFileGetModuleSpecifications callback;
+ uint32_t i;
+ // Try the ObjectFile plug-ins
+ for (i = 0;
+ (callback =
+ PluginManager::GetObjectFileGetModuleSpecificationsCallbackAtIndex(
+ i)) != nullptr;
+ ++i) {
+ if (callback(file, data_sp, data_offset, file_offset, file_size, specs) > 0)
+ return specs.GetSize() - initial_count;
+ }
+
+ // Try the ObjectContainer plug-ins
+ for (i = 0;
+ (callback = PluginManager::
+ GetObjectContainerGetModuleSpecificationsCallbackAtIndex(i)) !=
+ nullptr;
+ ++i) {
+ if (callback(file, data_sp, data_offset, file_offset, file_size, specs) > 0)
+ return specs.GetSize() - initial_count;
+ }
+ return 0;
+}
+
+ObjectFile::ObjectFile(const lldb::ModuleSP &module_sp,
+ const FileSpec *file_spec_ptr,
+ lldb::offset_t file_offset, lldb::offset_t length,
+ const lldb::DataBufferSP &data_sp,
+ lldb::offset_t data_offset)
+ : ModuleChild(module_sp),
+ m_file(), // This file could be different from the original module's file
+ m_type(eTypeInvalid), m_strata(eStrataInvalid),
+ m_file_offset(file_offset), m_length(length), m_data(),
+ m_unwind_table(*this), m_process_wp(),
+ m_memory_addr(LLDB_INVALID_ADDRESS), m_sections_ap(), m_symtab_ap(),
+ m_synthetic_symbol_idx(0) {
+ if (file_spec_ptr)
+ m_file = *file_spec_ptr;
+ if (data_sp)
+ m_data.SetData(data_sp, data_offset, length);
+ Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_OBJECT));
+ if (log)
+ log->Printf("%p ObjectFile::ObjectFile() module = %p (%s), file = %s, "
+ "file_offset = 0x%8.8" PRIx64 ", size = %" PRIu64,
+ static_cast<void *>(this), static_cast<void *>(module_sp.get()),
+ module_sp->GetSpecificationDescription().c_str(),
+ m_file ? m_file.GetPath().c_str() : "<NULL>", m_file_offset,
+ m_length);
+}
+
+ObjectFile::ObjectFile(const lldb::ModuleSP &module_sp,
+ const ProcessSP &process_sp, lldb::addr_t header_addr,
+ DataBufferSP &header_data_sp)
+ : ModuleChild(module_sp), m_file(), m_type(eTypeInvalid),
+ m_strata(eStrataInvalid), m_file_offset(0), m_length(0), m_data(),
+ m_unwind_table(*this), m_process_wp(process_sp),
+ m_memory_addr(header_addr), m_sections_ap(), m_symtab_ap(),
+ m_synthetic_symbol_idx(0) {
+ if (header_data_sp)
+ m_data.SetData(header_data_sp, 0, header_data_sp->GetByteSize());
+ Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_OBJECT));
+ if (log)
+ log->Printf("%p ObjectFile::ObjectFile() module = %p (%s), process = %p, "
+ "header_addr = 0x%" PRIx64,
+ static_cast<void *>(this), static_cast<void *>(module_sp.get()),
+ module_sp->GetSpecificationDescription().c_str(),
+ static_cast<void *>(process_sp.get()), m_memory_addr);
+}
+
+ObjectFile::~ObjectFile() {
+ Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_OBJECT));
+ if (log)
+ log->Printf("%p ObjectFile::~ObjectFile ()\n", static_cast<void *>(this));
+}
+
+bool ObjectFile::SetModulesArchitecture(const ArchSpec &new_arch) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp)
+ return module_sp->SetArchitecture(new_arch);
+ return false;
+}
+
+AddressClass ObjectFile::GetAddressClass(addr_t file_addr) {
+ Symtab *symtab = GetSymtab();
+ if (symtab) {
+ Symbol *symbol = symtab->FindSymbolContainingFileAddress(file_addr);
+ if (symbol) {
+ if (symbol->ValueIsAddress()) {
+ const SectionSP section_sp(symbol->GetAddressRef().GetSection());
+ if (section_sp) {
+ const SectionType section_type = section_sp->GetType();
+ switch (section_type) {
+ case eSectionTypeInvalid:
+ return eAddressClassUnknown;
+ case eSectionTypeCode:
+ return eAddressClassCode;
+ case eSectionTypeContainer:
+ return eAddressClassUnknown;
+ case eSectionTypeData:
+ case eSectionTypeDataCString:
+ case eSectionTypeDataCStringPointers:
+ case eSectionTypeDataSymbolAddress:
+ case eSectionTypeData4:
+ case eSectionTypeData8:
+ case eSectionTypeData16:
+ case eSectionTypeDataPointers:
+ case eSectionTypeZeroFill:
+ case eSectionTypeDataObjCMessageRefs:
+ case eSectionTypeDataObjCCFStrings:
+ case eSectionTypeGoSymtab:
+ return eAddressClassData;
+ case eSectionTypeDebug:
+ case eSectionTypeDWARFDebugAbbrev:
+ case eSectionTypeDWARFDebugAddr:
+ case eSectionTypeDWARFDebugAranges:
+ case eSectionTypeDWARFDebugFrame:
+ case eSectionTypeDWARFDebugInfo:
+ case eSectionTypeDWARFDebugLine:
+ case eSectionTypeDWARFDebugLoc:
+ case eSectionTypeDWARFDebugMacInfo:
+ case eSectionTypeDWARFDebugMacro:
+ case eSectionTypeDWARFDebugPubNames:
+ case eSectionTypeDWARFDebugPubTypes:
+ case eSectionTypeDWARFDebugRanges:
+ case eSectionTypeDWARFDebugStr:
+ case eSectionTypeDWARFDebugStrOffsets:
+ case eSectionTypeDWARFAppleNames:
+ case eSectionTypeDWARFAppleTypes:
+ case eSectionTypeDWARFAppleNamespaces:
+ case eSectionTypeDWARFAppleObjC:
+ return eAddressClassDebug;
+ case eSectionTypeEHFrame:
+ case eSectionTypeARMexidx:
+ case eSectionTypeARMextab:
+ case eSectionTypeCompactUnwind:
+ return eAddressClassRuntime;
+ case eSectionTypeELFSymbolTable:
+ case eSectionTypeELFDynamicSymbols:
+ case eSectionTypeELFRelocationEntries:
+ case eSectionTypeELFDynamicLinkInfo:
+ case eSectionTypeOther:
+ return eAddressClassUnknown;
+ case eSectionTypeAbsoluteAddress:
+ // In case of absolute sections decide the address class based on
+ // the symbol
+ // type because the section type isn't specify if it is a code or a
+ // data
+ // section.
+ break;
+ }
+ }
+ }
+
+ const SymbolType symbol_type = symbol->GetType();
+ switch (symbol_type) {
+ case eSymbolTypeAny:
+ return eAddressClassUnknown;
+ case eSymbolTypeAbsolute:
+ return eAddressClassUnknown;
+ case eSymbolTypeCode:
+ return eAddressClassCode;
+ case eSymbolTypeTrampoline:
+ return eAddressClassCode;
+ case eSymbolTypeResolver:
+ return eAddressClassCode;
+ case eSymbolTypeData:
+ return eAddressClassData;
+ case eSymbolTypeRuntime:
+ return eAddressClassRuntime;
+ case eSymbolTypeException:
+ return eAddressClassRuntime;
+ case eSymbolTypeSourceFile:
+ return eAddressClassDebug;
+ case eSymbolTypeHeaderFile:
+ return eAddressClassDebug;
+ case eSymbolTypeObjectFile:
+ return eAddressClassDebug;
+ case eSymbolTypeCommonBlock:
+ return eAddressClassDebug;
+ case eSymbolTypeBlock:
+ return eAddressClassDebug;
+ case eSymbolTypeLocal:
+ return eAddressClassData;
+ case eSymbolTypeParam:
+ return eAddressClassData;
+ case eSymbolTypeVariable:
+ return eAddressClassData;
+ case eSymbolTypeVariableType:
+ return eAddressClassDebug;
+ case eSymbolTypeLineEntry:
+ return eAddressClassDebug;
+ case eSymbolTypeLineHeader:
+ return eAddressClassDebug;
+ case eSymbolTypeScopeBegin:
+ return eAddressClassDebug;
+ case eSymbolTypeScopeEnd:
+ return eAddressClassDebug;
+ case eSymbolTypeAdditional:
+ return eAddressClassUnknown;
+ case eSymbolTypeCompiler:
+ return eAddressClassDebug;
+ case eSymbolTypeInstrumentation:
+ return eAddressClassDebug;
+ case eSymbolTypeUndefined:
+ return eAddressClassUnknown;
+ case eSymbolTypeObjCClass:
+ return eAddressClassRuntime;
+ case eSymbolTypeObjCMetaClass:
+ return eAddressClassRuntime;
+ case eSymbolTypeObjCIVar:
+ return eAddressClassRuntime;
+ case eSymbolTypeReExported:
+ return eAddressClassRuntime;
+ }
+ }
+ }
+ return eAddressClassUnknown;
+}
+
+DataBufferSP ObjectFile::ReadMemory(const ProcessSP &process_sp,
+ lldb::addr_t addr, size_t byte_size) {
+ DataBufferSP data_sp;
+ if (process_sp) {
+ std::unique_ptr<DataBufferHeap> data_ap(new DataBufferHeap(byte_size, 0));
+ Error error;
+ const size_t bytes_read = process_sp->ReadMemory(
+ addr, data_ap->GetBytes(), data_ap->GetByteSize(), error);
+ if (bytes_read == byte_size)
+ data_sp.reset(data_ap.release());
+ }
+ return data_sp;
+}
+
+size_t ObjectFile::GetData(lldb::offset_t offset, size_t length,
+ DataExtractor &data) const {
+ // The entire file has already been mmap'ed into m_data, so just copy from
+ // there
+ // as the back mmap buffer will be shared with shared pointers.
+ return data.SetData(m_data, offset, length);
+}
+
+size_t ObjectFile::CopyData(lldb::offset_t offset, size_t length,
+ void *dst) const {
+ // The entire file has already been mmap'ed into m_data, so just copy from
+ // there
+ // Note that the data remains in target byte order.
+ return m_data.CopyData(offset, length, dst);
+}
+
+size_t ObjectFile::ReadSectionData(const Section *section,
+ lldb::offset_t section_offset, void *dst,
+ size_t dst_len) const {
+ assert(section);
+ section_offset *= section->GetTargetByteSize();
+
+ // If some other objectfile owns this data, pass this to them.
+ if (section->GetObjectFile() != this)
+ return section->GetObjectFile()->ReadSectionData(section, section_offset,
+ dst, dst_len);
+
+ if (IsInMemory()) {
+ ProcessSP process_sp(m_process_wp.lock());
+ if (process_sp) {
+ Error error;
+ const addr_t base_load_addr =
+ section->GetLoadBaseAddress(&process_sp->GetTarget());
+ if (base_load_addr != LLDB_INVALID_ADDRESS)
+ return process_sp->ReadMemory(base_load_addr + section_offset, dst,
+ dst_len, error);
+ }
+ } else {
+ const lldb::offset_t section_file_size = section->GetFileSize();
+ if (section_offset < section_file_size) {
+ const size_t section_bytes_left = section_file_size - section_offset;
+ size_t section_dst_len = dst_len;
+ if (section_dst_len > section_bytes_left)
+ section_dst_len = section_bytes_left;
+ return CopyData(section->GetFileOffset() + section_offset,
+ section_dst_len, dst);
+ } else {
+ if (section->GetType() == eSectionTypeZeroFill) {
+ const uint64_t section_size = section->GetByteSize();
+ const uint64_t section_bytes_left = section_size - section_offset;
+ uint64_t section_dst_len = dst_len;
+ if (section_dst_len > section_bytes_left)
+ section_dst_len = section_bytes_left;
+ memset(dst, 0, section_dst_len);
+ return section_dst_len;
+ }
}
- return 0;
+ }
+ return 0;
}
//----------------------------------------------------------------------
// Get the section data the file on disk
//----------------------------------------------------------------------
-size_t
-ObjectFile::ReadSectionData (const Section *section, DataExtractor& section_data) const
-{
- // If some other objectfile owns this data, pass this to them.
- if (section->GetObjectFile() != this)
- return section->GetObjectFile()->ReadSectionData (section, section_data);
-
- if (IsInMemory())
- {
- ProcessSP process_sp (m_process_wp.lock());
- if (process_sp)
- {
- const addr_t base_load_addr = section->GetLoadBaseAddress (&process_sp->GetTarget());
- if (base_load_addr != LLDB_INVALID_ADDRESS)
- {
- DataBufferSP data_sp (ReadMemory (process_sp, base_load_addr, section->GetByteSize()));
- if (data_sp)
- {
- section_data.SetData (data_sp, 0, data_sp->GetByteSize());
- section_data.SetByteOrder (process_sp->GetByteOrder());
- section_data.SetAddressByteSize (process_sp->GetAddressByteSize());
- return section_data.GetByteSize();
- }
- }
- }
- return GetData(section->GetFileOffset(), section->GetFileSize(), section_data);
- }
- else
- {
- // The object file now contains a full mmap'ed copy of the object file data, so just use this
- return MemoryMapSectionData (section, section_data);
- }
-}
-
-size_t
-ObjectFile::MemoryMapSectionData (const Section *section, DataExtractor& section_data) const
-{
- // If some other objectfile owns this data, pass this to them.
- if (section->GetObjectFile() != this)
- return section->GetObjectFile()->MemoryMapSectionData (section, section_data);
-
- if (IsInMemory())
- {
- return ReadSectionData (section, section_data);
- }
- else
- {
- // The object file now contains a full mmap'ed copy of the object file data, so just use this
- return GetData(section->GetFileOffset(), section->GetFileSize(), section_data);
- }
-}
-
-
-bool
-ObjectFile::SplitArchivePathWithObject (const char *path_with_object, FileSpec &archive_file, ConstString &archive_object, bool must_exist)
-{
- RegularExpression g_object_regex("(.*)\\(([^\\)]+)\\)$");
- RegularExpression::Match regex_match(2);
- if (g_object_regex.Execute (path_with_object, ®ex_match))
- {
- std::string path;
- std::string obj;
- if (regex_match.GetMatchAtIndex (path_with_object, 1, path) &&
- regex_match.GetMatchAtIndex (path_with_object, 2, obj))
- {
- archive_file.SetFile (path.c_str(), false);
- archive_object.SetCString(obj.c_str());
- if (must_exist && !archive_file.Exists())
- return false;
- return true;
- }
- }
- return false;
+size_t ObjectFile::ReadSectionData(const Section *section,
+ DataExtractor §ion_data) const {
+ // If some other objectfile owns this data, pass this to them.
+ if (section->GetObjectFile() != this)
+ return section->GetObjectFile()->ReadSectionData(section, section_data);
+
+ if (IsInMemory()) {
+ ProcessSP process_sp(m_process_wp.lock());
+ if (process_sp) {
+ const addr_t base_load_addr =
+ section->GetLoadBaseAddress(&process_sp->GetTarget());
+ if (base_load_addr != LLDB_INVALID_ADDRESS) {
+ DataBufferSP data_sp(
+ ReadMemory(process_sp, base_load_addr, section->GetByteSize()));
+ if (data_sp) {
+ section_data.SetData(data_sp, 0, data_sp->GetByteSize());
+ section_data.SetByteOrder(process_sp->GetByteOrder());
+ section_data.SetAddressByteSize(process_sp->GetAddressByteSize());
+ return section_data.GetByteSize();
+ }
+ }
+ }
+ return GetData(section->GetFileOffset(), section->GetFileSize(),
+ section_data);
+ } else {
+ // The object file now contains a full mmap'ed copy of the object file data,
+ // so just use this
+ return MemoryMapSectionData(section, section_data);
+ }
+}
+
+size_t ObjectFile::MemoryMapSectionData(const Section *section,
+ DataExtractor §ion_data) const {
+ // If some other objectfile owns this data, pass this to them.
+ if (section->GetObjectFile() != this)
+ return section->GetObjectFile()->MemoryMapSectionData(section,
+ section_data);
+
+ if (IsInMemory()) {
+ return ReadSectionData(section, section_data);
+ } else {
+ // The object file now contains a full mmap'ed copy of the object file data,
+ // so just use this
+ return GetData(section->GetFileOffset(), section->GetFileSize(),
+ section_data);
+ }
+}
+
+bool ObjectFile::SplitArchivePathWithObject(const char *path_with_object,
+ FileSpec &archive_file,
+ ConstString &archive_object,
+ bool must_exist) {
+ RegularExpression g_object_regex("(.*)\\(([^\\)]+)\\)$");
+ RegularExpression::Match regex_match(2);
+ if (g_object_regex.Execute(path_with_object, ®ex_match)) {
+ std::string path;
+ std::string obj;
+ if (regex_match.GetMatchAtIndex(path_with_object, 1, path) &&
+ regex_match.GetMatchAtIndex(path_with_object, 2, obj)) {
+ archive_file.SetFile(path.c_str(), false);
+ archive_object.SetCString(obj.c_str());
+ if (must_exist && !archive_file.Exists())
+ return false;
+ return true;
+ }
+ }
+ return false;
+}
+
+void ObjectFile::ClearSymtab() {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_OBJECT));
+ if (log)
+ log->Printf("%p ObjectFile::ClearSymtab () symtab = %p",
+ static_cast<void *>(this),
+ static_cast<void *>(m_symtab_ap.get()));
+ m_symtab_ap.reset();
+ }
}
-void
-ObjectFile::ClearSymtab ()
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
+SectionList *ObjectFile::GetSectionList(bool update_module_section_list) {
+ if (m_sections_ap.get() == nullptr) {
+ if (update_module_section_list) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_OBJECT));
- if (log)
- log->Printf ("%p ObjectFile::ClearSymtab () symtab = %p",
- static_cast<void*>(this),
- static_cast<void*>(m_symtab_ap.get()));
- m_symtab_ap.reset();
- }
-}
-
-SectionList *
-ObjectFile::GetSectionList(bool update_module_section_list)
-{
- if (m_sections_ap.get() == nullptr)
- {
- if (update_module_section_list)
- {
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- CreateSections(*module_sp->GetUnifiedSectionList());
- }
- }
- else
- {
- SectionList unified_section_list;
- CreateSections(unified_section_list);
- }
+ CreateSections(*module_sp->GetUnifiedSectionList());
+ }
+ } else {
+ SectionList unified_section_list;
+ CreateSections(unified_section_list);
}
- return m_sections_ap.get();
+ }
+ return m_sections_ap.get();
}
lldb::SymbolType
-ObjectFile::GetSymbolTypeFromName (llvm::StringRef name,
- lldb::SymbolType symbol_type_hint)
-{
- if (!name.empty())
- {
- if (name.startswith("_OBJC_"))
- {
- // ObjC
- if (name.startswith("_OBJC_CLASS_$_"))
- return lldb::eSymbolTypeObjCClass;
- if (name.startswith("_OBJC_METACLASS_$_"))
- return lldb::eSymbolTypeObjCMetaClass;
- if (name.startswith("_OBJC_IVAR_$_"))
- return lldb::eSymbolTypeObjCIVar;
- }
- else if (name.startswith(".objc_class_name_"))
- {
- // ObjC v1
- return lldb::eSymbolTypeObjCClass;
- }
- }
- return symbol_type_hint;
+ObjectFile::GetSymbolTypeFromName(llvm::StringRef name,
+ lldb::SymbolType symbol_type_hint) {
+ if (!name.empty()) {
+ if (name.startswith("_OBJC_")) {
+ // ObjC
+ if (name.startswith("_OBJC_CLASS_$_"))
+ return lldb::eSymbolTypeObjCClass;
+ if (name.startswith("_OBJC_METACLASS_$_"))
+ return lldb::eSymbolTypeObjCMetaClass;
+ if (name.startswith("_OBJC_IVAR_$_"))
+ return lldb::eSymbolTypeObjCIVar;
+ } else if (name.startswith(".objc_class_name_")) {
+ // ObjC v1
+ return lldb::eSymbolTypeObjCClass;
+ }
+ }
+ return symbol_type_hint;
+}
+
+ConstString ObjectFile::GetNextSyntheticSymbolName() {
+ StreamString ss;
+ ConstString file_name = GetModule()->GetFileSpec().GetFilename();
+ ss.Printf("___lldb_unnamed_symbol%u$$%s", ++m_synthetic_symbol_idx,
+ file_name.GetCString());
+ return ConstString(ss.GetData());
}
-
-ConstString
-ObjectFile::GetNextSyntheticSymbolName()
-{
- StreamString ss;
- ConstString file_name = GetModule()->GetFileSpec().GetFilename();
- ss.Printf("___lldb_unnamed_symbol%u$$%s", ++m_synthetic_symbol_idx, file_name.GetCString());
- return ConstString(ss.GetData());
-}
-
Modified: lldb/trunk/source/Symbol/Symbol.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/Symbol.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/Symbol.cpp (original)
+++ lldb/trunk/source/Symbol/Symbol.cpp Tue Sep 6 15:57:50 2016
@@ -13,453 +13,338 @@
#include "lldb/Core/ModuleSpec.h"
#include "lldb/Core/Section.h"
#include "lldb/Core/Stream.h"
+#include "lldb/Symbol/Function.h"
#include "lldb/Symbol/ObjectFile.h"
+#include "lldb/Symbol/SymbolVendor.h"
#include "lldb/Symbol/Symtab.h"
-#include "lldb/Symbol/Function.h"
#include "lldb/Target/Process.h"
#include "lldb/Target/Target.h"
-#include "lldb/Symbol/SymbolVendor.h"
using namespace lldb;
using namespace lldb_private;
-
-Symbol::Symbol() :
- SymbolContextScope (),
- m_uid (UINT32_MAX),
- m_type_data (0),
- m_type_data_resolved (false),
- m_is_synthetic (false),
- m_is_debug (false),
- m_is_external (false),
- m_size_is_sibling (false),
- m_size_is_synthesized (false),
- m_size_is_valid (false),
- m_demangled_is_synthesized (false),
- m_contains_linker_annotations (false),
- m_type (eSymbolTypeInvalid),
- m_mangled (),
- m_addr_range (),
- m_flags ()
-{
-}
-
-Symbol::Symbol
-(
- uint32_t symID,
- const char *name,
- bool name_is_mangled,
- SymbolType type,
- bool external,
- bool is_debug,
- bool is_trampoline,
- bool is_artificial,
- const lldb::SectionSP §ion_sp,
- addr_t offset,
- addr_t size,
- bool size_is_valid,
- bool contains_linker_annotations,
- uint32_t flags
-) :
- SymbolContextScope (),
- m_uid (symID),
- m_type_data (0),
- m_type_data_resolved (false),
- m_is_synthetic (is_artificial),
- m_is_debug (is_debug),
- m_is_external (external),
- m_size_is_sibling (false),
- m_size_is_synthesized (false),
- m_size_is_valid (size_is_valid || size > 0),
- m_demangled_is_synthesized (false),
- m_contains_linker_annotations (contains_linker_annotations),
- m_type (type),
- m_mangled (ConstString(name), name_is_mangled),
- m_addr_range (section_sp, offset, size),
- m_flags (flags)
-{
-}
-
-Symbol::Symbol
-(
- uint32_t symID,
- const Mangled &mangled,
- SymbolType type,
- bool external,
- bool is_debug,
- bool is_trampoline,
- bool is_artificial,
- const AddressRange &range,
- bool size_is_valid,
- bool contains_linker_annotations,
- uint32_t flags
-) :
- SymbolContextScope (),
- m_uid (symID),
- m_type_data (0),
- m_type_data_resolved (false),
- m_is_synthetic (is_artificial),
- m_is_debug (is_debug),
- m_is_external (external),
- m_size_is_sibling (false),
- m_size_is_synthesized (false),
- m_size_is_valid (size_is_valid || range.GetByteSize() > 0),
- m_demangled_is_synthesized (false),
- m_contains_linker_annotations (contains_linker_annotations),
- m_type (type),
- m_mangled (mangled),
- m_addr_range (range),
- m_flags (flags)
-{
-}
-
-Symbol::Symbol(const Symbol& rhs):
- SymbolContextScope (rhs),
- m_uid (rhs.m_uid),
- m_type_data (rhs.m_type_data),
- m_type_data_resolved (rhs.m_type_data_resolved),
- m_is_synthetic (rhs.m_is_synthetic),
- m_is_debug (rhs.m_is_debug),
- m_is_external (rhs.m_is_external),
- m_size_is_sibling (rhs.m_size_is_sibling),
- m_size_is_synthesized (false),
- m_size_is_valid (rhs.m_size_is_valid),
- m_demangled_is_synthesized (rhs.m_demangled_is_synthesized),
- m_contains_linker_annotations (rhs.m_contains_linker_annotations),
- m_type (rhs.m_type),
- m_mangled (rhs.m_mangled),
- m_addr_range (rhs.m_addr_range),
- m_flags (rhs.m_flags)
-{
-}
-
-const Symbol&
-Symbol::operator= (const Symbol& rhs)
-{
- if (this != &rhs)
- {
- SymbolContextScope::operator= (rhs);
- m_uid = rhs.m_uid;
- m_type_data = rhs.m_type_data;
- m_type_data_resolved = rhs.m_type_data_resolved;
- m_is_synthetic = rhs.m_is_synthetic;
- m_is_debug = rhs.m_is_debug;
- m_is_external = rhs.m_is_external;
- m_size_is_sibling = rhs.m_size_is_sibling;
- m_size_is_synthesized = rhs.m_size_is_sibling;
- m_size_is_valid = rhs.m_size_is_valid;
- m_demangled_is_synthesized = rhs.m_demangled_is_synthesized;
- m_contains_linker_annotations = rhs.m_contains_linker_annotations;
- m_type = rhs.m_type;
- m_mangled = rhs.m_mangled;
- m_addr_range = rhs.m_addr_range;
- m_flags = rhs.m_flags;
- }
- return *this;
+Symbol::Symbol()
+ : SymbolContextScope(), m_uid(UINT32_MAX), m_type_data(0),
+ m_type_data_resolved(false), m_is_synthetic(false), m_is_debug(false),
+ m_is_external(false), m_size_is_sibling(false),
+ m_size_is_synthesized(false), m_size_is_valid(false),
+ m_demangled_is_synthesized(false), m_contains_linker_annotations(false),
+ m_type(eSymbolTypeInvalid), m_mangled(), m_addr_range(), m_flags() {}
+
+Symbol::Symbol(uint32_t symID, const char *name, bool name_is_mangled,
+ SymbolType type, bool external, bool is_debug,
+ bool is_trampoline, bool is_artificial,
+ const lldb::SectionSP §ion_sp, addr_t offset, addr_t size,
+ bool size_is_valid, bool contains_linker_annotations,
+ uint32_t flags)
+ : SymbolContextScope(), m_uid(symID), m_type_data(0),
+ m_type_data_resolved(false), m_is_synthetic(is_artificial),
+ m_is_debug(is_debug), m_is_external(external), m_size_is_sibling(false),
+ m_size_is_synthesized(false), m_size_is_valid(size_is_valid || size > 0),
+ m_demangled_is_synthesized(false),
+ m_contains_linker_annotations(contains_linker_annotations), m_type(type),
+ m_mangled(ConstString(name), name_is_mangled),
+ m_addr_range(section_sp, offset, size), m_flags(flags) {}
+
+Symbol::Symbol(uint32_t symID, const Mangled &mangled, SymbolType type,
+ bool external, bool is_debug, bool is_trampoline,
+ bool is_artificial, const AddressRange &range,
+ bool size_is_valid, bool contains_linker_annotations,
+ uint32_t flags)
+ : SymbolContextScope(), m_uid(symID), m_type_data(0),
+ m_type_data_resolved(false), m_is_synthetic(is_artificial),
+ m_is_debug(is_debug), m_is_external(external), m_size_is_sibling(false),
+ m_size_is_synthesized(false),
+ m_size_is_valid(size_is_valid || range.GetByteSize() > 0),
+ m_demangled_is_synthesized(false),
+ m_contains_linker_annotations(contains_linker_annotations), m_type(type),
+ m_mangled(mangled), m_addr_range(range), m_flags(flags) {}
+
+Symbol::Symbol(const Symbol &rhs)
+ : SymbolContextScope(rhs), m_uid(rhs.m_uid), m_type_data(rhs.m_type_data),
+ m_type_data_resolved(rhs.m_type_data_resolved),
+ m_is_synthetic(rhs.m_is_synthetic), m_is_debug(rhs.m_is_debug),
+ m_is_external(rhs.m_is_external),
+ m_size_is_sibling(rhs.m_size_is_sibling), m_size_is_synthesized(false),
+ m_size_is_valid(rhs.m_size_is_valid),
+ m_demangled_is_synthesized(rhs.m_demangled_is_synthesized),
+ m_contains_linker_annotations(rhs.m_contains_linker_annotations),
+ m_type(rhs.m_type), m_mangled(rhs.m_mangled),
+ m_addr_range(rhs.m_addr_range), m_flags(rhs.m_flags) {}
+
+const Symbol &Symbol::operator=(const Symbol &rhs) {
+ if (this != &rhs) {
+ SymbolContextScope::operator=(rhs);
+ m_uid = rhs.m_uid;
+ m_type_data = rhs.m_type_data;
+ m_type_data_resolved = rhs.m_type_data_resolved;
+ m_is_synthetic = rhs.m_is_synthetic;
+ m_is_debug = rhs.m_is_debug;
+ m_is_external = rhs.m_is_external;
+ m_size_is_sibling = rhs.m_size_is_sibling;
+ m_size_is_synthesized = rhs.m_size_is_sibling;
+ m_size_is_valid = rhs.m_size_is_valid;
+ m_demangled_is_synthesized = rhs.m_demangled_is_synthesized;
+ m_contains_linker_annotations = rhs.m_contains_linker_annotations;
+ m_type = rhs.m_type;
+ m_mangled = rhs.m_mangled;
+ m_addr_range = rhs.m_addr_range;
+ m_flags = rhs.m_flags;
+ }
+ return *this;
+}
+
+void Symbol::Clear() {
+ m_uid = UINT32_MAX;
+ m_mangled.Clear();
+ m_type_data = 0;
+ m_type_data_resolved = false;
+ m_is_synthetic = false;
+ m_is_debug = false;
+ m_is_external = false;
+ m_size_is_sibling = false;
+ m_size_is_synthesized = false;
+ m_size_is_valid = false;
+ m_demangled_is_synthesized = false;
+ m_contains_linker_annotations = false;
+ m_type = eSymbolTypeInvalid;
+ m_flags = 0;
+ m_addr_range.Clear();
}
-void
-Symbol::Clear()
-{
- m_uid = UINT32_MAX;
- m_mangled.Clear();
- m_type_data = 0;
- m_type_data_resolved = false;
- m_is_synthetic = false;
- m_is_debug = false;
- m_is_external = false;
- m_size_is_sibling = false;
- m_size_is_synthesized = false;
- m_size_is_valid = false;
- m_demangled_is_synthesized = false;
- m_contains_linker_annotations = false;
- m_type = eSymbolTypeInvalid;
- m_flags = 0;
- m_addr_range.Clear();
-}
-
-bool
-Symbol::ValueIsAddress() const
-{
- return m_addr_range.GetBaseAddress().GetSection().get() != nullptr;
-}
-
-ConstString
-Symbol::GetDisplayName () const
-{
- if (!m_mangled)
- return ConstString();
- return m_mangled.GetDisplayDemangledName(GetLanguage());
-}
-
-ConstString
-Symbol::GetReExportedSymbolName() const
-{
- if (m_type == eSymbolTypeReExported)
- {
- // For eSymbolTypeReExported, the "const char *" from a ConstString
- // is used as the offset in the address range base address. We can
- // then make this back into a string that is the re-exported name.
- intptr_t str_ptr = m_addr_range.GetBaseAddress().GetOffset();
- if (str_ptr != 0)
- return ConstString((const char *)str_ptr);
- else
- return GetName();
- }
- return ConstString();
+bool Symbol::ValueIsAddress() const {
+ return m_addr_range.GetBaseAddress().GetSection().get() != nullptr;
}
-FileSpec
-Symbol::GetReExportedSymbolSharedLibrary() const
-{
- if (m_type == eSymbolTypeReExported)
- {
- // For eSymbolTypeReExported, the "const char *" from a ConstString
- // is used as the offset in the address range base address. We can
- // then make this back into a string that is the re-exported name.
- intptr_t str_ptr = m_addr_range.GetByteSize();
- if (str_ptr != 0)
- return FileSpec((const char *)str_ptr, false);
- }
- return FileSpec();
+ConstString Symbol::GetDisplayName() const {
+ if (!m_mangled)
+ return ConstString();
+ return m_mangled.GetDisplayDemangledName(GetLanguage());
}
-void
-Symbol::SetReExportedSymbolName(const ConstString &name)
-{
- SetType (eSymbolTypeReExported);
+ConstString Symbol::GetReExportedSymbolName() const {
+ if (m_type == eSymbolTypeReExported) {
// For eSymbolTypeReExported, the "const char *" from a ConstString
- // is used as the offset in the address range base address.
- m_addr_range.GetBaseAddress().SetOffset((uintptr_t)name.GetCString());
+ // is used as the offset in the address range base address. We can
+ // then make this back into a string that is the re-exported name.
+ intptr_t str_ptr = m_addr_range.GetBaseAddress().GetOffset();
+ if (str_ptr != 0)
+ return ConstString((const char *)str_ptr);
+ else
+ return GetName();
+ }
+ return ConstString();
}
-bool
-Symbol::SetReExportedSymbolSharedLibrary(const FileSpec &fspec)
-{
- if (m_type == eSymbolTypeReExported)
- {
- // For eSymbolTypeReExported, the "const char *" from a ConstString
- // is used as the offset in the address range base address.
- m_addr_range.SetByteSize((uintptr_t)ConstString(fspec.GetPath().c_str()).GetCString());
- return true;
- }
- return false;
-
+FileSpec Symbol::GetReExportedSymbolSharedLibrary() const {
+ if (m_type == eSymbolTypeReExported) {
+ // For eSymbolTypeReExported, the "const char *" from a ConstString
+ // is used as the offset in the address range base address. We can
+ // then make this back into a string that is the re-exported name.
+ intptr_t str_ptr = m_addr_range.GetByteSize();
+ if (str_ptr != 0)
+ return FileSpec((const char *)str_ptr, false);
+ }
+ return FileSpec();
+}
+
+void Symbol::SetReExportedSymbolName(const ConstString &name) {
+ SetType(eSymbolTypeReExported);
+ // For eSymbolTypeReExported, the "const char *" from a ConstString
+ // is used as the offset in the address range base address.
+ m_addr_range.GetBaseAddress().SetOffset((uintptr_t)name.GetCString());
}
-uint32_t
-Symbol::GetSiblingIndex() const
-{
- return m_size_is_sibling ? m_addr_range.GetByteSize() : UINT32_MAX;
-}
-
-bool
-Symbol::IsTrampoline () const
-{
- return m_type == eSymbolTypeTrampoline;
-}
-
-bool
-Symbol::IsIndirect () const
-{
- return m_type == eSymbolTypeResolver;
-}
-
-void
-Symbol::GetDescription (Stream *s, lldb::DescriptionLevel level, Target *target) const
-{
- s->Printf("id = {0x%8.8x}", m_uid);
-
- if (m_addr_range.GetBaseAddress().GetSection())
- {
- if (ValueIsAddress())
- {
- const lldb::addr_t byte_size = GetByteSize();
- if (byte_size > 0)
- {
- s->PutCString (", range = ");
- m_addr_range.Dump(s, target, Address::DumpStyleLoadAddress, Address::DumpStyleFileAddress);
- }
- else
- {
- s->PutCString (", address = ");
- m_addr_range.GetBaseAddress().Dump(s, target, Address::DumpStyleLoadAddress, Address::DumpStyleFileAddress);
- }
- }
- else
- s->Printf (", value = 0x%16.16" PRIx64, m_addr_range.GetBaseAddress().GetOffset());
- }
+bool Symbol::SetReExportedSymbolSharedLibrary(const FileSpec &fspec) {
+ if (m_type == eSymbolTypeReExported) {
+ // For eSymbolTypeReExported, the "const char *" from a ConstString
+ // is used as the offset in the address range base address.
+ m_addr_range.SetByteSize(
+ (uintptr_t)ConstString(fspec.GetPath().c_str()).GetCString());
+ return true;
+ }
+ return false;
+}
+
+uint32_t Symbol::GetSiblingIndex() const {
+ return m_size_is_sibling ? m_addr_range.GetByteSize() : UINT32_MAX;
+}
+
+bool Symbol::IsTrampoline() const { return m_type == eSymbolTypeTrampoline; }
+
+bool Symbol::IsIndirect() const { return m_type == eSymbolTypeResolver; }
+
+void Symbol::GetDescription(Stream *s, lldb::DescriptionLevel level,
+ Target *target) const {
+ s->Printf("id = {0x%8.8x}", m_uid);
+
+ if (m_addr_range.GetBaseAddress().GetSection()) {
+ if (ValueIsAddress()) {
+ const lldb::addr_t byte_size = GetByteSize();
+ if (byte_size > 0) {
+ s->PutCString(", range = ");
+ m_addr_range.Dump(s, target, Address::DumpStyleLoadAddress,
+ Address::DumpStyleFileAddress);
+ } else {
+ s->PutCString(", address = ");
+ m_addr_range.GetBaseAddress().Dump(s, target,
+ Address::DumpStyleLoadAddress,
+ Address::DumpStyleFileAddress);
+ }
+ } else
+ s->Printf(", value = 0x%16.16" PRIx64,
+ m_addr_range.GetBaseAddress().GetOffset());
+ } else {
+ if (m_size_is_sibling)
+ s->Printf(", sibling = %5" PRIu64,
+ m_addr_range.GetBaseAddress().GetOffset());
else
- {
- if (m_size_is_sibling)
- s->Printf (", sibling = %5" PRIu64, m_addr_range.GetBaseAddress().GetOffset());
- else
- s->Printf (", value = 0x%16.16" PRIx64, m_addr_range.GetBaseAddress().GetOffset());
- }
- ConstString demangled = m_mangled.GetDemangledName(GetLanguage());
- if (demangled)
- s->Printf(", name=\"%s\"", demangled.AsCString());
- if (m_mangled.GetMangledName())
- s->Printf(", mangled=\"%s\"", m_mangled.GetMangledName().AsCString());
-
-}
-
-void
-Symbol::Dump(Stream *s, Target *target, uint32_t index) const
-{
- s->Printf("[%5u] %6u %c%c%c %-15s ",
- index,
- GetID(),
- m_is_debug ? 'D' : ' ',
- m_is_synthetic ? 'S' : ' ',
- m_is_external ? 'X' : ' ',
- GetTypeAsString());
-
- // Make sure the size of the symbol is up to date before dumping
- GetByteSize();
-
- ConstString name = m_mangled.GetName(GetLanguage());
- if (ValueIsAddress())
- {
- if (!m_addr_range.GetBaseAddress().Dump(s, nullptr, Address::DumpStyleFileAddress))
- s->Printf("%*s", 18, "");
-
- s->PutChar(' ');
-
- if (!m_addr_range.GetBaseAddress().Dump(s, target, Address::DumpStyleLoadAddress))
- s->Printf("%*s", 18, "");
-
- const char *format = m_size_is_sibling ?
- " Sibling -> [%5llu] 0x%8.8x %s\n":
- " 0x%16.16" PRIx64 " 0x%8.8x %s\n";
- s->Printf( format,
- GetByteSize(),
- m_flags,
- name.AsCString(""));
- }
- else if (m_type == eSymbolTypeReExported)
- {
- s->Printf (" 0x%8.8x %s",
- m_flags,
- name.AsCString(""));
-
- ConstString reexport_name = GetReExportedSymbolName();
- intptr_t shlib = m_addr_range.GetByteSize();
- if (shlib)
- s->Printf(" -> %s`%s\n", (const char *)shlib, reexport_name.GetCString());
- else
- s->Printf(" -> %s\n", reexport_name.GetCString());
- }
+ s->Printf(", value = 0x%16.16" PRIx64,
+ m_addr_range.GetBaseAddress().GetOffset());
+ }
+ ConstString demangled = m_mangled.GetDemangledName(GetLanguage());
+ if (demangled)
+ s->Printf(", name=\"%s\"", demangled.AsCString());
+ if (m_mangled.GetMangledName())
+ s->Printf(", mangled=\"%s\"", m_mangled.GetMangledName().AsCString());
+}
+
+void Symbol::Dump(Stream *s, Target *target, uint32_t index) const {
+ s->Printf("[%5u] %6u %c%c%c %-15s ", index, GetID(), m_is_debug ? 'D' : ' ',
+ m_is_synthetic ? 'S' : ' ', m_is_external ? 'X' : ' ',
+ GetTypeAsString());
+
+ // Make sure the size of the symbol is up to date before dumping
+ GetByteSize();
+
+ ConstString name = m_mangled.GetName(GetLanguage());
+ if (ValueIsAddress()) {
+ if (!m_addr_range.GetBaseAddress().Dump(s, nullptr,
+ Address::DumpStyleFileAddress))
+ s->Printf("%*s", 18, "");
+
+ s->PutChar(' ');
+
+ if (!m_addr_range.GetBaseAddress().Dump(s, target,
+ Address::DumpStyleLoadAddress))
+ s->Printf("%*s", 18, "");
+
+ const char *format = m_size_is_sibling ? " Sibling -> [%5llu] 0x%8.8x %s\n"
+ : " 0x%16.16" PRIx64 " 0x%8.8x %s\n";
+ s->Printf(format, GetByteSize(), m_flags, name.AsCString(""));
+ } else if (m_type == eSymbolTypeReExported) {
+ s->Printf(
+ " 0x%8.8x %s",
+ m_flags, name.AsCString(""));
+
+ ConstString reexport_name = GetReExportedSymbolName();
+ intptr_t shlib = m_addr_range.GetByteSize();
+ if (shlib)
+ s->Printf(" -> %s`%s\n", (const char *)shlib, reexport_name.GetCString());
else
- {
- const char *format = m_size_is_sibling ?
- "0x%16.16" PRIx64 " Sibling -> [%5llu] 0x%8.8x %s\n":
- "0x%16.16" PRIx64 " 0x%16.16" PRIx64 " 0x%8.8x %s\n";
- s->Printf( format,
- m_addr_range.GetBaseAddress().GetOffset(),
- GetByteSize(),
- m_flags,
- name.AsCString(""));
- }
-}
-
-uint32_t
-Symbol::GetPrologueByteSize ()
-{
- if (m_type == eSymbolTypeCode || m_type == eSymbolTypeResolver)
- {
- if (!m_type_data_resolved)
- {
- m_type_data_resolved = true;
-
- const Address &base_address = m_addr_range.GetBaseAddress();
- Function *function = base_address.CalculateSymbolContextFunction();
- if (function)
- {
- // Functions have line entries which can also potentially have end of prologue information.
- // So if this symbol points to a function, use the prologue information from there.
- m_type_data = function->GetPrologueByteSize();
- }
- else
- {
- ModuleSP module_sp (base_address.GetModule());
- SymbolContext sc;
- if (module_sp)
- {
- uint32_t resolved_flags = module_sp->ResolveSymbolContextForAddress (base_address,
- eSymbolContextLineEntry,
- sc);
- if (resolved_flags & eSymbolContextLineEntry)
- {
- // Default to the end of the first line entry.
- m_type_data = sc.line_entry.range.GetByteSize();
-
- // Set address for next line.
- Address addr (base_address);
- addr.Slide (m_type_data);
-
- // Check the first few instructions and look for one that has a line number that is
- // different than the first entry. This is also done in Function::GetPrologueByteSize().
- uint16_t total_offset = m_type_data;
- for (int idx = 0; idx < 6; ++idx)
- {
- SymbolContext sc_temp;
- resolved_flags = module_sp->ResolveSymbolContextForAddress (addr, eSymbolContextLineEntry, sc_temp);
- // Make sure we got line number information...
- if (!(resolved_flags & eSymbolContextLineEntry))
- break;
-
- // If this line number is different than our first one, use it and we're done.
- if (sc_temp.line_entry.line != sc.line_entry.line)
- {
- m_type_data = total_offset;
- break;
- }
-
- // Slide addr up to the next line address.
- addr.Slide (sc_temp.line_entry.range.GetByteSize());
- total_offset += sc_temp.line_entry.range.GetByteSize();
- // If we've gone too far, bail out.
- if (total_offset >= m_addr_range.GetByteSize())
- break;
- }
-
- // Sanity check - this may be a function in the middle of code that has debug information, but
- // not for this symbol. So the line entries surrounding us won't lie inside our function.
- // In that case, the line entry will be bigger than we are, so we do that quick check and
- // if that is true, we just return 0.
- if (m_type_data >= m_addr_range.GetByteSize())
- m_type_data = 0;
- }
- else
- {
- // TODO: expose something in Process to figure out the
- // size of a function prologue.
- m_type_data = 0;
- }
- }
+ s->Printf(" -> %s\n", reexport_name.GetCString());
+ } else {
+ const char *format =
+ m_size_is_sibling
+ ? "0x%16.16" PRIx64
+ " Sibling -> [%5llu] 0x%8.8x %s\n"
+ : "0x%16.16" PRIx64 " 0x%16.16" PRIx64
+ " 0x%8.8x %s\n";
+ s->Printf(format, m_addr_range.GetBaseAddress().GetOffset(), GetByteSize(),
+ m_flags, name.AsCString(""));
+ }
+}
+
+uint32_t Symbol::GetPrologueByteSize() {
+ if (m_type == eSymbolTypeCode || m_type == eSymbolTypeResolver) {
+ if (!m_type_data_resolved) {
+ m_type_data_resolved = true;
+
+ const Address &base_address = m_addr_range.GetBaseAddress();
+ Function *function = base_address.CalculateSymbolContextFunction();
+ if (function) {
+ // Functions have line entries which can also potentially have end of
+ // prologue information.
+ // So if this symbol points to a function, use the prologue information
+ // from there.
+ m_type_data = function->GetPrologueByteSize();
+ } else {
+ ModuleSP module_sp(base_address.GetModule());
+ SymbolContext sc;
+ if (module_sp) {
+ uint32_t resolved_flags = module_sp->ResolveSymbolContextForAddress(
+ base_address, eSymbolContextLineEntry, sc);
+ if (resolved_flags & eSymbolContextLineEntry) {
+ // Default to the end of the first line entry.
+ m_type_data = sc.line_entry.range.GetByteSize();
+
+ // Set address for next line.
+ Address addr(base_address);
+ addr.Slide(m_type_data);
+
+ // Check the first few instructions and look for one that has a line
+ // number that is
+ // different than the first entry. This is also done in
+ // Function::GetPrologueByteSize().
+ uint16_t total_offset = m_type_data;
+ for (int idx = 0; idx < 6; ++idx) {
+ SymbolContext sc_temp;
+ resolved_flags = module_sp->ResolveSymbolContextForAddress(
+ addr, eSymbolContextLineEntry, sc_temp);
+ // Make sure we got line number information...
+ if (!(resolved_flags & eSymbolContextLineEntry))
+ break;
+
+ // If this line number is different than our first one, use it and
+ // we're done.
+ if (sc_temp.line_entry.line != sc.line_entry.line) {
+ m_type_data = total_offset;
+ break;
+ }
+
+ // Slide addr up to the next line address.
+ addr.Slide(sc_temp.line_entry.range.GetByteSize());
+ total_offset += sc_temp.line_entry.range.GetByteSize();
+ // If we've gone too far, bail out.
+ if (total_offset >= m_addr_range.GetByteSize())
+ break;
}
+
+ // Sanity check - this may be a function in the middle of code that
+ // has debug information, but
+ // not for this symbol. So the line entries surrounding us won't
+ // lie inside our function.
+ // In that case, the line entry will be bigger than we are, so we do
+ // that quick check and
+ // if that is true, we just return 0.
+ if (m_type_data >= m_addr_range.GetByteSize())
+ m_type_data = 0;
+ } else {
+ // TODO: expose something in Process to figure out the
+ // size of a function prologue.
+ m_type_data = 0;
+ }
}
- return m_type_data;
+ }
}
- return 0;
+ return m_type_data;
+ }
+ return 0;
}
-bool
-Symbol::Compare(const ConstString& name, SymbolType type) const
-{
- if (type == eSymbolTypeAny || m_type == type)
- return m_mangled.GetMangledName() == name || m_mangled.GetDemangledName(GetLanguage()) == name;
- return false;
+bool Symbol::Compare(const ConstString &name, SymbolType type) const {
+ if (type == eSymbolTypeAny || m_type == type)
+ return m_mangled.GetMangledName() == name ||
+ m_mangled.GetDemangledName(GetLanguage()) == name;
+ return false;
}
-#define ENUM_TO_CSTRING(x) case eSymbolType##x: return #x;
+#define ENUM_TO_CSTRING(x) \
+ case eSymbolType##x: \
+ return #x;
-const char *
-Symbol::GetTypeAsString() const
-{
- switch (m_type)
- {
+const char *Symbol::GetTypeAsString() const {
+ switch (m_type) {
ENUM_TO_CSTRING(Invalid);
ENUM_TO_CSTRING(Absolute);
ENUM_TO_CSTRING(Code);
@@ -489,258 +374,200 @@ Symbol::GetTypeAsString() const
ENUM_TO_CSTRING(ObjCMetaClass);
ENUM_TO_CSTRING(ObjCIVar);
ENUM_TO_CSTRING(ReExported);
- default:
- break;
- }
- return "<unknown SymbolType>";
-}
-
-void
-Symbol::CalculateSymbolContext (SymbolContext *sc)
-{
- // Symbols can reconstruct the symbol and the module in the symbol context
- sc->symbol = this;
- if (ValueIsAddress())
- sc->module_sp = GetAddressRef().GetModule();
- else
- sc->module_sp.reset();
-}
-
-ModuleSP
-Symbol::CalculateSymbolContextModule ()
-{
- if (ValueIsAddress())
- return GetAddressRef().GetModule();
- return ModuleSP();
-}
-
-Symbol *
-Symbol::CalculateSymbolContextSymbol ()
-{
- return this;
-}
-
-void
-Symbol::DumpSymbolContext (Stream *s)
-{
- bool dumped_module = false;
- if (ValueIsAddress())
- {
- ModuleSP module_sp (GetAddressRef().GetModule());
- if (module_sp)
- {
- dumped_module = true;
- module_sp->DumpSymbolContext(s);
- }
- }
- if (dumped_module)
- s->PutCString(", ");
-
- s->Printf("Symbol{0x%8.8x}", GetID());
-}
-
-lldb::addr_t
-Symbol::GetByteSize () const
-{
- return m_addr_range.GetByteSize();
-}
-
-
-Symbol *
-Symbol::ResolveReExportedSymbolInModuleSpec (Target &target,
- ConstString &reexport_name,
- ModuleSpec &module_spec,
- ModuleList &seen_modules) const
-{
- ModuleSP module_sp;
- if (module_spec.GetFileSpec())
- {
- // Try searching for the module file spec first using the full path
- module_sp = target.GetImages().FindFirstModule(module_spec);
- if (!module_sp)
- {
- // Next try and find the module by basename in case environment
- // variables or other runtime trickery causes shared libraries
- // to be loaded from alternate paths
- module_spec.GetFileSpec().GetDirectory().Clear();
- module_sp = target.GetImages().FindFirstModule(module_spec);
- }
- }
-
- if (module_sp)
- {
- // There should not be cycles in the reexport list, but we don't want to crash if there are so make sure
- // we haven't seen this before:
- if (!seen_modules.AppendIfNeeded(module_sp))
- return nullptr;
-
- lldb_private::SymbolContextList sc_list;
- module_sp->FindSymbolsWithNameAndType(reexport_name, eSymbolTypeAny, sc_list);
- const size_t num_scs = sc_list.GetSize();
- if (num_scs > 0)
- {
- for (size_t i=0; i<num_scs; ++i)
- {
- lldb_private::SymbolContext sc;
- if (sc_list.GetContextAtIndex(i, sc))
- {
- if (sc.symbol->IsExternal())
- return sc.symbol;
- }
- }
- }
- // If we didn't find the symbol in this module, it may be because this module re-exports some
- // whole other library. We have to search those as well:
- seen_modules.Append(module_sp);
-
- FileSpecList reexported_libraries = module_sp->GetObjectFile()->GetReExportedLibraries();
- size_t num_reexported_libraries = reexported_libraries.GetSize();
- for (size_t idx = 0; idx < num_reexported_libraries; idx++)
- {
- ModuleSpec reexported_module_spec;
- reexported_module_spec.GetFileSpec() = reexported_libraries.GetFileSpecAtIndex(idx);
- Symbol *result_symbol = ResolveReExportedSymbolInModuleSpec(target,
- reexport_name,
- reexported_module_spec,
- seen_modules);
- if (result_symbol)
- return result_symbol;
+ default:
+ break;
+ }
+ return "<unknown SymbolType>";
+}
+
+void Symbol::CalculateSymbolContext(SymbolContext *sc) {
+ // Symbols can reconstruct the symbol and the module in the symbol context
+ sc->symbol = this;
+ if (ValueIsAddress())
+ sc->module_sp = GetAddressRef().GetModule();
+ else
+ sc->module_sp.reset();
+}
+
+ModuleSP Symbol::CalculateSymbolContextModule() {
+ if (ValueIsAddress())
+ return GetAddressRef().GetModule();
+ return ModuleSP();
+}
+
+Symbol *Symbol::CalculateSymbolContextSymbol() { return this; }
+
+void Symbol::DumpSymbolContext(Stream *s) {
+ bool dumped_module = false;
+ if (ValueIsAddress()) {
+ ModuleSP module_sp(GetAddressRef().GetModule());
+ if (module_sp) {
+ dumped_module = true;
+ module_sp->DumpSymbolContext(s);
+ }
+ }
+ if (dumped_module)
+ s->PutCString(", ");
+
+ s->Printf("Symbol{0x%8.8x}", GetID());
+}
+
+lldb::addr_t Symbol::GetByteSize() const { return m_addr_range.GetByteSize(); }
+
+Symbol *Symbol::ResolveReExportedSymbolInModuleSpec(
+ Target &target, ConstString &reexport_name, ModuleSpec &module_spec,
+ ModuleList &seen_modules) const {
+ ModuleSP module_sp;
+ if (module_spec.GetFileSpec()) {
+ // Try searching for the module file spec first using the full path
+ module_sp = target.GetImages().FindFirstModule(module_spec);
+ if (!module_sp) {
+ // Next try and find the module by basename in case environment
+ // variables or other runtime trickery causes shared libraries
+ // to be loaded from alternate paths
+ module_spec.GetFileSpec().GetDirectory().Clear();
+ module_sp = target.GetImages().FindFirstModule(module_spec);
+ }
+ }
+
+ if (module_sp) {
+ // There should not be cycles in the reexport list, but we don't want to
+ // crash if there are so make sure
+ // we haven't seen this before:
+ if (!seen_modules.AppendIfNeeded(module_sp))
+ return nullptr;
+
+ lldb_private::SymbolContextList sc_list;
+ module_sp->FindSymbolsWithNameAndType(reexport_name, eSymbolTypeAny,
+ sc_list);
+ const size_t num_scs = sc_list.GetSize();
+ if (num_scs > 0) {
+ for (size_t i = 0; i < num_scs; ++i) {
+ lldb_private::SymbolContext sc;
+ if (sc_list.GetContextAtIndex(i, sc)) {
+ if (sc.symbol->IsExternal())
+ return sc.symbol;
}
+ }
}
- return nullptr;
+ // If we didn't find the symbol in this module, it may be because this
+ // module re-exports some
+ // whole other library. We have to search those as well:
+ seen_modules.Append(module_sp);
+
+ FileSpecList reexported_libraries =
+ module_sp->GetObjectFile()->GetReExportedLibraries();
+ size_t num_reexported_libraries = reexported_libraries.GetSize();
+ for (size_t idx = 0; idx < num_reexported_libraries; idx++) {
+ ModuleSpec reexported_module_spec;
+ reexported_module_spec.GetFileSpec() =
+ reexported_libraries.GetFileSpecAtIndex(idx);
+ Symbol *result_symbol = ResolveReExportedSymbolInModuleSpec(
+ target, reexport_name, reexported_module_spec, seen_modules);
+ if (result_symbol)
+ return result_symbol;
+ }
+ }
+ return nullptr;
+}
+
+Symbol *Symbol::ResolveReExportedSymbol(Target &target) const {
+ ConstString reexport_name(GetReExportedSymbolName());
+ if (reexport_name) {
+ ModuleSpec module_spec;
+ ModuleList seen_modules;
+ module_spec.GetFileSpec() = GetReExportedSymbolSharedLibrary();
+ if (module_spec.GetFileSpec()) {
+ return ResolveReExportedSymbolInModuleSpec(target, reexport_name,
+ module_spec, seen_modules);
+ }
+ }
+ return nullptr;
+}
+
+lldb::addr_t Symbol::GetFileAddress() const {
+ if (ValueIsAddress())
+ return GetAddressRef().GetFileAddress();
+ else
+ return LLDB_INVALID_ADDRESS;
}
-Symbol *
-Symbol::ResolveReExportedSymbol (Target &target) const
-{
- ConstString reexport_name (GetReExportedSymbolName());
- if (reexport_name)
- {
- ModuleSpec module_spec;
- ModuleList seen_modules;
- module_spec.GetFileSpec() = GetReExportedSymbolSharedLibrary();
- if (module_spec.GetFileSpec())
- {
- return ResolveReExportedSymbolInModuleSpec(target, reexport_name, module_spec, seen_modules);
- }
- }
- return nullptr;
+lldb::addr_t Symbol::GetLoadAddress(Target *target) const {
+ if (ValueIsAddress())
+ return GetAddressRef().GetLoadAddress(target);
+ else
+ return LLDB_INVALID_ADDRESS;
}
-lldb::addr_t
-Symbol::GetFileAddress () const
-{
- if (ValueIsAddress())
- return GetAddressRef().GetFileAddress();
- else
- return LLDB_INVALID_ADDRESS;
-}
+ConstString Symbol::GetName() const { return m_mangled.GetName(GetLanguage()); }
-lldb::addr_t
-Symbol::GetLoadAddress (Target *target) const
-{
- if (ValueIsAddress())
- return GetAddressRef().GetLoadAddress(target);
- else
- return LLDB_INVALID_ADDRESS;
+ConstString Symbol::GetNameNoArguments() const {
+ return m_mangled.GetName(GetLanguage(),
+ Mangled::ePreferDemangledWithoutArguments);
}
-ConstString
-Symbol::GetName () const
-{
- return m_mangled.GetName(GetLanguage());
-}
-
-ConstString
-Symbol::GetNameNoArguments () const
-{
- return m_mangled.GetName(GetLanguage(), Mangled::ePreferDemangledWithoutArguments);
-}
-
-
-lldb::addr_t
-Symbol::ResolveCallableAddress(Target &target) const
-{
- if (GetType() == lldb::eSymbolTypeUndefined)
- return LLDB_INVALID_ADDRESS;
-
- Address func_so_addr;
-
- bool is_indirect = IsIndirect();
- if (GetType() == eSymbolTypeReExported)
- {
- Symbol *reexported_symbol = ResolveReExportedSymbol(target);
- if (reexported_symbol)
- {
- func_so_addr = reexported_symbol->GetAddress();
- is_indirect = reexported_symbol->IsIndirect();
- }
- }
- else
- {
- func_so_addr = GetAddress();
- is_indirect = IsIndirect();
- }
-
- if (func_so_addr.IsValid())
- {
- if (!target.GetProcessSP() && is_indirect)
- {
- // can't resolve indirect symbols without calling a function...
- return LLDB_INVALID_ADDRESS;
- }
-
- lldb::addr_t load_addr = func_so_addr.GetCallableLoadAddress (&target, is_indirect);
-
- if (load_addr != LLDB_INVALID_ADDRESS)
- {
- return load_addr;
- }
- }
-
+lldb::addr_t Symbol::ResolveCallableAddress(Target &target) const {
+ if (GetType() == lldb::eSymbolTypeUndefined)
return LLDB_INVALID_ADDRESS;
-}
-
-lldb::DisassemblerSP
-Symbol::GetInstructions (const ExecutionContext &exe_ctx,
- const char *flavor,
- bool prefer_file_cache)
-{
- ModuleSP module_sp (m_addr_range.GetBaseAddress().GetModule());
- if (module_sp)
- {
- const bool prefer_file_cache = false;
- return Disassembler::DisassembleRange (module_sp->GetArchitecture(),
- nullptr,
- flavor,
- exe_ctx,
- m_addr_range,
- prefer_file_cache);
- }
- return lldb::DisassemblerSP();
-}
+ Address func_so_addr;
-bool
-Symbol::GetDisassembly (const ExecutionContext &exe_ctx,
- const char *flavor,
- bool prefer_file_cache,
- Stream &strm)
-{
- lldb::DisassemblerSP disassembler_sp = GetInstructions (exe_ctx, flavor, prefer_file_cache);
- if (disassembler_sp)
- {
- const bool show_address = true;
- const bool show_bytes = false;
- disassembler_sp->GetInstructionList().Dump (&strm, show_address, show_bytes, &exe_ctx);
- return true;
- }
- return false;
+ bool is_indirect = IsIndirect();
+ if (GetType() == eSymbolTypeReExported) {
+ Symbol *reexported_symbol = ResolveReExportedSymbol(target);
+ if (reexported_symbol) {
+ func_so_addr = reexported_symbol->GetAddress();
+ is_indirect = reexported_symbol->IsIndirect();
+ }
+ } else {
+ func_so_addr = GetAddress();
+ is_indirect = IsIndirect();
+ }
+
+ if (func_so_addr.IsValid()) {
+ if (!target.GetProcessSP() && is_indirect) {
+ // can't resolve indirect symbols without calling a function...
+ return LLDB_INVALID_ADDRESS;
+ }
+
+ lldb::addr_t load_addr =
+ func_so_addr.GetCallableLoadAddress(&target, is_indirect);
+
+ if (load_addr != LLDB_INVALID_ADDRESS) {
+ return load_addr;
+ }
+ }
+
+ return LLDB_INVALID_ADDRESS;
+}
+
+lldb::DisassemblerSP Symbol::GetInstructions(const ExecutionContext &exe_ctx,
+ const char *flavor,
+ bool prefer_file_cache) {
+ ModuleSP module_sp(m_addr_range.GetBaseAddress().GetModule());
+ if (module_sp) {
+ const bool prefer_file_cache = false;
+ return Disassembler::DisassembleRange(module_sp->GetArchitecture(), nullptr,
+ flavor, exe_ctx, m_addr_range,
+ prefer_file_cache);
+ }
+ return lldb::DisassemblerSP();
+}
+
+bool Symbol::GetDisassembly(const ExecutionContext &exe_ctx, const char *flavor,
+ bool prefer_file_cache, Stream &strm) {
+ lldb::DisassemblerSP disassembler_sp =
+ GetInstructions(exe_ctx, flavor, prefer_file_cache);
+ if (disassembler_sp) {
+ const bool show_address = true;
+ const bool show_bytes = false;
+ disassembler_sp->GetInstructionList().Dump(&strm, show_address, show_bytes,
+ &exe_ctx);
+ return true;
+ }
+ return false;
}
-bool
-Symbol::ContainsFileAddress (lldb::addr_t file_addr) const
-{
- return m_addr_range.ContainsFileAddress(file_addr);
+bool Symbol::ContainsFileAddress(lldb::addr_t file_addr) const {
+ return m_addr_range.ContainsFileAddress(file_addr);
}
-
Modified: lldb/trunk/source/Symbol/SymbolContext.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/SymbolContext.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/SymbolContext.cpp (original)
+++ lldb/trunk/source/Symbol/SymbolContext.cpp Tue Sep 6 15:57:50 2016
@@ -27,907 +27,777 @@
using namespace lldb;
using namespace lldb_private;
-SymbolContext::SymbolContext() :
- target_sp (),
- module_sp (),
- comp_unit (nullptr),
- function (nullptr),
- block (nullptr),
- line_entry (),
- symbol (nullptr),
- variable (nullptr)
-{
-}
-
-SymbolContext::SymbolContext(const ModuleSP& m, CompileUnit *cu, Function *f, Block *b, LineEntry *le, Symbol *s) :
- target_sp (),
- module_sp (m),
- comp_unit (cu),
- function (f),
- block (b),
- line_entry (),
- symbol (s),
- variable (nullptr)
-{
- if (le)
- line_entry = *le;
-}
-
-SymbolContext::SymbolContext(const TargetSP &t, const ModuleSP& m, CompileUnit *cu, Function *f, Block *b, LineEntry *le, Symbol *s) :
- target_sp (t),
- module_sp (m),
- comp_unit (cu),
- function (f),
- block (b),
- line_entry (),
- symbol (s),
- variable (nullptr)
-{
- if (le)
- line_entry = *le;
-}
-
-SymbolContext::SymbolContext(const SymbolContext& rhs) :
- target_sp (rhs.target_sp),
- module_sp (rhs.module_sp),
- comp_unit (rhs.comp_unit),
- function (rhs.function),
- block (rhs.block),
- line_entry (rhs.line_entry),
- symbol (rhs.symbol),
- variable (rhs.variable)
-{
-}
-
-
-SymbolContext::SymbolContext (SymbolContextScope *sc_scope) :
- target_sp (),
- module_sp (),
- comp_unit (nullptr),
- function (nullptr),
- block (nullptr),
- line_entry (),
- symbol (nullptr),
- variable (nullptr)
-{
- sc_scope->CalculateSymbolContext (this);
-}
-
-SymbolContext::~SymbolContext ()
-{
-}
-
-const SymbolContext&
-SymbolContext::operator= (const SymbolContext& rhs)
-{
- if (this != &rhs)
- {
- target_sp = rhs.target_sp;
- module_sp = rhs.module_sp;
- comp_unit = rhs.comp_unit;
- function = rhs.function;
- block = rhs.block;
- line_entry = rhs.line_entry;
- symbol = rhs.symbol;
- variable = rhs.variable;
+SymbolContext::SymbolContext()
+ : target_sp(), module_sp(), comp_unit(nullptr), function(nullptr),
+ block(nullptr), line_entry(), symbol(nullptr), variable(nullptr) {}
+
+SymbolContext::SymbolContext(const ModuleSP &m, CompileUnit *cu, Function *f,
+ Block *b, LineEntry *le, Symbol *s)
+ : target_sp(), module_sp(m), comp_unit(cu), function(f), block(b),
+ line_entry(), symbol(s), variable(nullptr) {
+ if (le)
+ line_entry = *le;
+}
+
+SymbolContext::SymbolContext(const TargetSP &t, const ModuleSP &m,
+ CompileUnit *cu, Function *f, Block *b,
+ LineEntry *le, Symbol *s)
+ : target_sp(t), module_sp(m), comp_unit(cu), function(f), block(b),
+ line_entry(), symbol(s), variable(nullptr) {
+ if (le)
+ line_entry = *le;
+}
+
+SymbolContext::SymbolContext(const SymbolContext &rhs)
+ : target_sp(rhs.target_sp), module_sp(rhs.module_sp),
+ comp_unit(rhs.comp_unit), function(rhs.function), block(rhs.block),
+ line_entry(rhs.line_entry), symbol(rhs.symbol), variable(rhs.variable) {}
+
+SymbolContext::SymbolContext(SymbolContextScope *sc_scope)
+ : target_sp(), module_sp(), comp_unit(nullptr), function(nullptr),
+ block(nullptr), line_entry(), symbol(nullptr), variable(nullptr) {
+ sc_scope->CalculateSymbolContext(this);
+}
+
+SymbolContext::~SymbolContext() {}
+
+const SymbolContext &SymbolContext::operator=(const SymbolContext &rhs) {
+ if (this != &rhs) {
+ target_sp = rhs.target_sp;
+ module_sp = rhs.module_sp;
+ comp_unit = rhs.comp_unit;
+ function = rhs.function;
+ block = rhs.block;
+ line_entry = rhs.line_entry;
+ symbol = rhs.symbol;
+ variable = rhs.variable;
+ }
+ return *this;
+}
+
+void SymbolContext::Clear(bool clear_target) {
+ if (clear_target)
+ target_sp.reset();
+ module_sp.reset();
+ comp_unit = nullptr;
+ function = nullptr;
+ block = nullptr;
+ line_entry.Clear();
+ symbol = nullptr;
+ variable = nullptr;
+}
+
+bool SymbolContext::DumpStopContext(Stream *s, ExecutionContextScope *exe_scope,
+ const Address &addr, bool show_fullpaths,
+ bool show_module, bool show_inlined_frames,
+ bool show_function_arguments,
+ bool show_function_name) const {
+ bool dumped_something = false;
+ if (show_module && module_sp) {
+ if (show_fullpaths)
+ *s << module_sp->GetFileSpec();
+ else
+ *s << module_sp->GetFileSpec().GetFilename();
+ s->PutChar('`');
+ dumped_something = true;
+ }
+
+ if (function != nullptr) {
+ SymbolContext inline_parent_sc;
+ Address inline_parent_addr;
+ if (show_function_name == false) {
+ s->Printf("<");
+ dumped_something = true;
+ } else {
+ ConstString name;
+ if (show_function_arguments == false)
+ name = function->GetNameNoArguments();
+ if (!name)
+ name = function->GetName();
+ if (name)
+ name.Dump(s);
+ }
+
+ if (addr.IsValid()) {
+ const addr_t function_offset =
+ addr.GetOffset() -
+ function->GetAddressRange().GetBaseAddress().GetOffset();
+ if (show_function_name == false) {
+ // Print +offset even if offset is 0
+ dumped_something = true;
+ s->Printf("+%" PRIu64 ">", function_offset);
+ } else if (function_offset) {
+ dumped_something = true;
+ s->Printf(" + %" PRIu64, function_offset);
+ }
}
- return *this;
-}
-void
-SymbolContext::Clear(bool clear_target)
-{
- if (clear_target)
- target_sp.reset();
- module_sp.reset();
- comp_unit = nullptr;
- function = nullptr;
- block = nullptr;
- line_entry.Clear();
- symbol = nullptr;
- variable = nullptr;
-}
-
-bool
-SymbolContext::DumpStopContext (
- Stream *s,
- ExecutionContextScope *exe_scope,
- const Address &addr,
- bool show_fullpaths,
- bool show_module,
- bool show_inlined_frames,
- bool show_function_arguments,
- bool show_function_name
-) const
-{
- bool dumped_something = false;
- if (show_module && module_sp)
- {
- if (show_fullpaths)
- *s << module_sp->GetFileSpec();
- else
- *s << module_sp->GetFileSpec().GetFilename();
- s->PutChar('`');
+ if (GetParentOfInlinedScope(addr, inline_parent_sc, inline_parent_addr)) {
+ dumped_something = true;
+ Block *inlined_block = block->GetContainingInlinedBlock();
+ const InlineFunctionInfo *inlined_block_info =
+ inlined_block->GetInlinedFunctionInfo();
+ s->Printf(
+ " [inlined] %s",
+ inlined_block_info->GetName(function->GetLanguage()).GetCString());
+
+ lldb_private::AddressRange block_range;
+ if (inlined_block->GetRangeContainingAddress(addr, block_range)) {
+ const addr_t inlined_function_offset =
+ addr.GetOffset() - block_range.GetBaseAddress().GetOffset();
+ if (inlined_function_offset) {
+ s->Printf(" + %" PRIu64, inlined_function_offset);
+ }
+ }
+ const Declaration &call_site = inlined_block_info->GetCallSite();
+ if (call_site.IsValid()) {
+ s->PutCString(" at ");
+ call_site.DumpStopContext(s, show_fullpaths);
+ }
+ if (show_inlined_frames) {
+ s->EOL();
+ s->Indent();
+ const bool show_function_name = true;
+ return inline_parent_sc.DumpStopContext(
+ s, exe_scope, inline_parent_addr, show_fullpaths, show_module,
+ show_inlined_frames, show_function_arguments, show_function_name);
+ }
+ } else {
+ if (line_entry.IsValid()) {
+ dumped_something = true;
+ s->PutCString(" at ");
+ if (line_entry.DumpStopContext(s, show_fullpaths))
+ dumped_something = true;
+ }
+ }
+ } else if (symbol != nullptr) {
+ if (show_function_name == false) {
+ s->Printf("<");
+ dumped_something = true;
+ } else if (symbol->GetName()) {
+ dumped_something = true;
+ if (symbol->GetType() == eSymbolTypeTrampoline)
+ s->PutCString("symbol stub for: ");
+ symbol->GetName().Dump(s);
+ }
+
+ if (addr.IsValid() && symbol->ValueIsAddress()) {
+ const addr_t symbol_offset =
+ addr.GetOffset() - symbol->GetAddressRef().GetOffset();
+ if (show_function_name == false) {
+ // Print +offset even if offset is 0
+ dumped_something = true;
+ s->Printf("+%" PRIu64 ">", symbol_offset);
+ } else if (symbol_offset) {
dumped_something = true;
+ s->Printf(" + %" PRIu64, symbol_offset);
+ }
}
+ } else if (addr.IsValid()) {
+ addr.Dump(s, exe_scope, Address::DumpStyleModuleWithFileAddress);
+ dumped_something = true;
+ }
+ return dumped_something;
+}
+
+void SymbolContext::GetDescription(Stream *s, lldb::DescriptionLevel level,
+ Target *target) const {
+ if (module_sp) {
+ s->Indent(" Module: file = \"");
+ module_sp->GetFileSpec().Dump(s);
+ *s << '"';
+ if (module_sp->GetArchitecture().IsValid())
+ s->Printf(", arch = \"%s\"",
+ module_sp->GetArchitecture().GetArchitectureName());
+ s->EOL();
+ }
- if (function != nullptr)
- {
- SymbolContext inline_parent_sc;
- Address inline_parent_addr;
- if (show_function_name == false)
- {
- s->Printf("<");
- dumped_something = true;
- }
- else
- {
- ConstString name;
- if (show_function_arguments == false)
- name = function->GetNameNoArguments();
- if (!name)
- name = function->GetName();
- if (name)
- name.Dump(s);
- }
-
- if (addr.IsValid())
- {
- const addr_t function_offset = addr.GetOffset() - function->GetAddressRange().GetBaseAddress().GetOffset();
- if (show_function_name == false)
- {
- // Print +offset even if offset is 0
- dumped_something = true;
- s->Printf("+%" PRIu64 ">", function_offset);
- }
- else if (function_offset)
- {
- dumped_something = true;
- s->Printf(" + %" PRIu64, function_offset);
- }
- }
-
- if (GetParentOfInlinedScope (addr, inline_parent_sc, inline_parent_addr))
- {
- dumped_something = true;
- Block *inlined_block = block->GetContainingInlinedBlock();
- const InlineFunctionInfo* inlined_block_info = inlined_block->GetInlinedFunctionInfo();
- s->Printf (" [inlined] %s", inlined_block_info->GetName(function->GetLanguage()).GetCString());
-
- lldb_private::AddressRange block_range;
- if (inlined_block->GetRangeContainingAddress(addr, block_range))
- {
- const addr_t inlined_function_offset = addr.GetOffset() - block_range.GetBaseAddress().GetOffset();
- if (inlined_function_offset)
- {
- s->Printf(" + %" PRIu64, inlined_function_offset);
- }
- }
- const Declaration &call_site = inlined_block_info->GetCallSite();
- if (call_site.IsValid())
- {
- s->PutCString(" at ");
- call_site.DumpStopContext (s, show_fullpaths);
- }
- if (show_inlined_frames)
- {
- s->EOL();
- s->Indent();
- const bool show_function_name = true;
- return inline_parent_sc.DumpStopContext (s, exe_scope, inline_parent_addr, show_fullpaths, show_module, show_inlined_frames, show_function_arguments, show_function_name);
- }
- }
- else
- {
- if (line_entry.IsValid())
- {
- dumped_something = true;
- s->PutCString(" at ");
- if (line_entry.DumpStopContext(s, show_fullpaths))
- dumped_something = true;
- }
- }
- }
- else if (symbol != nullptr)
- {
- if (show_function_name == false)
- {
- s->Printf("<");
- dumped_something = true;
- }
- else if (symbol->GetName())
- {
- dumped_something = true;
- if (symbol->GetType() == eSymbolTypeTrampoline)
- s->PutCString("symbol stub for: ");
- symbol->GetName().Dump(s);
- }
+ if (comp_unit != nullptr) {
+ s->Indent("CompileUnit: ");
+ comp_unit->GetDescription(s, level);
+ s->EOL();
+ }
- if (addr.IsValid() && symbol->ValueIsAddress())
- {
- const addr_t symbol_offset = addr.GetOffset() - symbol->GetAddressRef().GetOffset();
- if (show_function_name == false)
- {
- // Print +offset even if offset is 0
- dumped_something = true;
- s->Printf("+%" PRIu64 ">", symbol_offset);
- }
- else if (symbol_offset)
- {
- dumped_something = true;
- s->Printf(" + %" PRIu64, symbol_offset);
- }
- }
- }
- else if (addr.IsValid())
- {
- addr.Dump(s, exe_scope, Address::DumpStyleModuleWithFileAddress);
- dumped_something = true;
- }
- return dumped_something;
-}
+ if (function != nullptr) {
+ s->Indent(" Function: ");
+ function->GetDescription(s, level, target);
+ s->EOL();
-void
-SymbolContext::GetDescription(Stream *s, lldb::DescriptionLevel level, Target *target) const
-{
- if (module_sp)
- {
- s->Indent(" Module: file = \"");
- module_sp->GetFileSpec().Dump(s);
- *s << '"';
- if (module_sp->GetArchitecture().IsValid())
- s->Printf (", arch = \"%s\"", module_sp->GetArchitecture().GetArchitectureName());
- s->EOL();
- }
+ Type *func_type = function->GetType();
+ if (func_type) {
+ s->Indent(" FuncType: ");
+ func_type->GetDescription(s, level, false);
+ s->EOL();
+ }
+ }
+
+ if (block != nullptr) {
+ std::vector<Block *> blocks;
+ blocks.push_back(block);
+ Block *parent_block = block->GetParent();
+
+ while (parent_block) {
+ blocks.push_back(parent_block);
+ parent_block = parent_block->GetParent();
+ }
+ std::vector<Block *>::reverse_iterator pos;
+ std::vector<Block *>::reverse_iterator begin = blocks.rbegin();
+ std::vector<Block *>::reverse_iterator end = blocks.rend();
+ for (pos = begin; pos != end; ++pos) {
+ if (pos == begin)
+ s->Indent(" Blocks: ");
+ else
+ s->Indent(" ");
+ (*pos)->GetDescription(s, function, level, target);
+ s->EOL();
+ }
+ }
+
+ if (line_entry.IsValid()) {
+ s->Indent(" LineEntry: ");
+ line_entry.GetDescription(s, level, comp_unit, target, false);
+ s->EOL();
+ }
- if (comp_unit != nullptr)
- {
- s->Indent("CompileUnit: ");
- comp_unit->GetDescription (s, level);
- s->EOL();
- }
+ if (symbol != nullptr) {
+ s->Indent(" Symbol: ");
+ symbol->GetDescription(s, level, target);
+ s->EOL();
+ }
- if (function != nullptr)
- {
- s->Indent(" Function: ");
- function->GetDescription (s, level, target);
- s->EOL();
+ if (variable != nullptr) {
+ s->Indent(" Variable: ");
- Type *func_type = function->GetType();
- if (func_type)
- {
- s->Indent(" FuncType: ");
- func_type->GetDescription (s, level, false);
- s->EOL();
- }
- }
+ s->Printf("id = {0x%8.8" PRIx64 "}, ", variable->GetID());
- if (block != nullptr)
- {
- std::vector<Block *> blocks;
- blocks.push_back (block);
- Block *parent_block = block->GetParent();
-
- while (parent_block)
- {
- blocks.push_back (parent_block);
- parent_block = parent_block->GetParent();
- }
- std::vector<Block *>::reverse_iterator pos;
- std::vector<Block *>::reverse_iterator begin = blocks.rbegin();
- std::vector<Block *>::reverse_iterator end = blocks.rend();
- for (pos = begin; pos != end; ++pos)
- {
- if (pos == begin)
- s->Indent(" Blocks: ");
- else
- s->Indent(" ");
- (*pos)->GetDescription(s, function, level, target);
- s->EOL();
- }
- }
+ switch (variable->GetScope()) {
+ case eValueTypeVariableGlobal:
+ s->PutCString("kind = global, ");
+ break;
- if (line_entry.IsValid())
- {
- s->Indent(" LineEntry: ");
- line_entry.GetDescription (s, level, comp_unit, target, false);
- s->EOL();
- }
+ case eValueTypeVariableStatic:
+ s->PutCString("kind = static, ");
+ break;
- if (symbol != nullptr)
- {
- s->Indent(" Symbol: ");
- symbol->GetDescription(s, level, target);
- s->EOL();
- }
+ case eValueTypeVariableArgument:
+ s->PutCString("kind = argument, ");
+ break;
- if (variable != nullptr)
- {
- s->Indent(" Variable: ");
-
- s->Printf("id = {0x%8.8" PRIx64 "}, ", variable->GetID());
-
- switch (variable->GetScope())
- {
- case eValueTypeVariableGlobal:
- s->PutCString("kind = global, ");
- break;
-
- case eValueTypeVariableStatic:
- s->PutCString("kind = static, ");
- break;
-
- case eValueTypeVariableArgument:
- s->PutCString("kind = argument, ");
- break;
-
- case eValueTypeVariableLocal:
- s->PutCString("kind = local, ");
- break;
-
- case eValueTypeVariableThreadLocal:
- s->PutCString("kind = thread local, ");
- break;
+ case eValueTypeVariableLocal:
+ s->PutCString("kind = local, ");
+ break;
- default:
- break;
- }
+ case eValueTypeVariableThreadLocal:
+ s->PutCString("kind = thread local, ");
+ break;
- s->Printf ("name = \"%s\"\n", variable->GetName().GetCString());
+ default:
+ break;
}
-}
-uint32_t
-SymbolContext::GetResolvedMask () const
-{
- uint32_t resolved_mask = 0;
- if (target_sp) resolved_mask |= eSymbolContextTarget;
- if (module_sp) resolved_mask |= eSymbolContextModule;
- if (comp_unit) resolved_mask |= eSymbolContextCompUnit;
- if (function) resolved_mask |= eSymbolContextFunction;
- if (block) resolved_mask |= eSymbolContextBlock;
- if (line_entry.IsValid()) resolved_mask |= eSymbolContextLineEntry;
- if (symbol) resolved_mask |= eSymbolContextSymbol;
- if (variable) resolved_mask |= eSymbolContextVariable;
- return resolved_mask;
+ s->Printf("name = \"%s\"\n", variable->GetName().GetCString());
+ }
}
-void
-SymbolContext::Dump(Stream *s, Target *target) const
-{
- *s << this << ": ";
- s->Indent();
- s->PutCString("SymbolContext");
- s->IndentMore();
+uint32_t SymbolContext::GetResolvedMask() const {
+ uint32_t resolved_mask = 0;
+ if (target_sp)
+ resolved_mask |= eSymbolContextTarget;
+ if (module_sp)
+ resolved_mask |= eSymbolContextModule;
+ if (comp_unit)
+ resolved_mask |= eSymbolContextCompUnit;
+ if (function)
+ resolved_mask |= eSymbolContextFunction;
+ if (block)
+ resolved_mask |= eSymbolContextBlock;
+ if (line_entry.IsValid())
+ resolved_mask |= eSymbolContextLineEntry;
+ if (symbol)
+ resolved_mask |= eSymbolContextSymbol;
+ if (variable)
+ resolved_mask |= eSymbolContextVariable;
+ return resolved_mask;
+}
+
+void SymbolContext::Dump(Stream *s, Target *target) const {
+ *s << this << ": ";
+ s->Indent();
+ s->PutCString("SymbolContext");
+ s->IndentMore();
+ s->EOL();
+ s->IndentMore();
+ s->Indent();
+ *s << "Module = " << module_sp.get() << ' ';
+ if (module_sp)
+ module_sp->GetFileSpec().Dump(s);
+ s->EOL();
+ s->Indent();
+ *s << "CompileUnit = " << comp_unit;
+ if (comp_unit != nullptr)
+ *s << " {0x" << comp_unit->GetID() << "} "
+ << *(static_cast<FileSpec *>(comp_unit));
+ s->EOL();
+ s->Indent();
+ *s << "Function = " << function;
+ if (function != nullptr) {
+ *s << " {0x" << function->GetID() << "} " << function->GetType()->GetName()
+ << ", address-range = ";
+ function->GetAddressRange().Dump(s, target, Address::DumpStyleLoadAddress,
+ Address::DumpStyleModuleWithFileAddress);
s->EOL();
- s->IndentMore();
s->Indent();
- *s << "Module = " << module_sp.get() << ' ';
- if (module_sp)
- module_sp->GetFileSpec().Dump(s);
+ Type *func_type = function->GetType();
+ if (func_type) {
+ *s << " Type = ";
+ func_type->Dump(s, false);
+ }
+ }
+ s->EOL();
+ s->Indent();
+ *s << "Block = " << block;
+ if (block != nullptr)
+ *s << " {0x" << block->GetID() << '}';
+ // Dump the block and pass it a negative depth to we print all the parent
+ // blocks
+ // if (block != NULL)
+ // block->Dump(s, function->GetFileAddress(), INT_MIN);
+ s->EOL();
+ s->Indent();
+ *s << "LineEntry = ";
+ line_entry.Dump(s, target, true, Address::DumpStyleLoadAddress,
+ Address::DumpStyleModuleWithFileAddress, true);
+ s->EOL();
+ s->Indent();
+ *s << "Symbol = " << symbol;
+ if (symbol != nullptr && symbol->GetMangled())
+ *s << ' ' << symbol->GetName().AsCString();
+ s->EOL();
+ *s << "Variable = " << variable;
+ if (variable != nullptr) {
+ *s << " {0x" << variable->GetID() << "} " << variable->GetType()->GetName();
s->EOL();
- s->Indent();
- *s << "CompileUnit = " << comp_unit;
- if (comp_unit != nullptr)
- *s << " {0x" << comp_unit->GetID() << "} " << *(static_cast<FileSpec*> (comp_unit));
- s->EOL();
- s->Indent();
- *s << "Function = " << function;
- if (function != nullptr)
- {
- *s << " {0x" << function->GetID() << "} " << function->GetType()->GetName() << ", address-range = ";
- function->GetAddressRange().Dump(s, target, Address::DumpStyleLoadAddress, Address::DumpStyleModuleWithFileAddress);
- s->EOL();
- s->Indent();
- Type* func_type = function->GetType();
- if (func_type)
- {
- *s << " Type = ";
- func_type->Dump (s, false);
- }
- }
- s->EOL();
- s->Indent();
- *s << "Block = " << block;
- if (block != nullptr)
- *s << " {0x" << block->GetID() << '}';
- // Dump the block and pass it a negative depth to we print all the parent blocks
- //if (block != NULL)
- // block->Dump(s, function->GetFileAddress(), INT_MIN);
- s->EOL();
- s->Indent();
- *s << "LineEntry = ";
- line_entry.Dump (s, target, true, Address::DumpStyleLoadAddress, Address::DumpStyleModuleWithFileAddress, true);
- s->EOL();
- s->Indent();
- *s << "Symbol = " << symbol;
- if (symbol != nullptr && symbol->GetMangled())
- *s << ' ' << symbol->GetName().AsCString();
- s->EOL();
- *s << "Variable = " << variable;
- if (variable != nullptr)
- {
- *s << " {0x" << variable->GetID() << "} " << variable->GetType()->GetName();
- s->EOL();
- }
- s->IndentLess();
- s->IndentLess();
-}
-
-bool
-lldb_private::operator== (const SymbolContext& lhs, const SymbolContext& rhs)
-{
- return lhs.function == rhs.function
- && lhs.symbol == rhs.symbol
- && lhs.module_sp.get() == rhs.module_sp.get()
- && lhs.comp_unit == rhs.comp_unit
- && lhs.target_sp.get() == rhs.target_sp.get()
- && LineEntry::Compare(lhs.line_entry, rhs.line_entry) == 0
- && lhs.variable == rhs.variable;
-}
-
-bool
-lldb_private::operator!= (const SymbolContext& lhs, const SymbolContext& rhs)
-{
- return lhs.function != rhs.function
- || lhs.symbol != rhs.symbol
- || lhs.module_sp.get() != rhs.module_sp.get()
- || lhs.comp_unit != rhs.comp_unit
- || lhs.target_sp.get() != rhs.target_sp.get()
- || LineEntry::Compare(lhs.line_entry, rhs.line_entry) != 0
- || lhs.variable != rhs.variable;
-}
+ }
+ s->IndentLess();
+ s->IndentLess();
+}
+
+bool lldb_private::operator==(const SymbolContext &lhs,
+ const SymbolContext &rhs) {
+ return lhs.function == rhs.function && lhs.symbol == rhs.symbol &&
+ lhs.module_sp.get() == rhs.module_sp.get() &&
+ lhs.comp_unit == rhs.comp_unit &&
+ lhs.target_sp.get() == rhs.target_sp.get() &&
+ LineEntry::Compare(lhs.line_entry, rhs.line_entry) == 0 &&
+ lhs.variable == rhs.variable;
+}
+
+bool lldb_private::operator!=(const SymbolContext &lhs,
+ const SymbolContext &rhs) {
+ return lhs.function != rhs.function || lhs.symbol != rhs.symbol ||
+ lhs.module_sp.get() != rhs.module_sp.get() ||
+ lhs.comp_unit != rhs.comp_unit ||
+ lhs.target_sp.get() != rhs.target_sp.get() ||
+ LineEntry::Compare(lhs.line_entry, rhs.line_entry) != 0 ||
+ lhs.variable != rhs.variable;
+}
+
+bool SymbolContext::GetAddressRange(uint32_t scope, uint32_t range_idx,
+ bool use_inline_block_range,
+ AddressRange &range) const {
+ if ((scope & eSymbolContextLineEntry) && line_entry.IsValid()) {
+ range = line_entry.range;
+ return true;
+ }
-bool
-SymbolContext::GetAddressRange (uint32_t scope,
- uint32_t range_idx,
- bool use_inline_block_range,
- AddressRange &range) const
-{
- if ((scope & eSymbolContextLineEntry) && line_entry.IsValid())
- {
- range = line_entry.range;
+ if ((scope & eSymbolContextBlock) && (block != nullptr)) {
+ if (use_inline_block_range) {
+ Block *inline_block = block->GetContainingInlinedBlock();
+ if (inline_block)
+ return inline_block->GetRangeAtIndex(range_idx, range);
+ } else {
+ return block->GetRangeAtIndex(range_idx, range);
+ }
+ }
+
+ if ((scope & eSymbolContextFunction) && (function != nullptr)) {
+ if (range_idx == 0) {
+ range = function->GetAddressRange();
+ return true;
+ }
+ }
+
+ if ((scope & eSymbolContextSymbol) && (symbol != nullptr)) {
+ if (range_idx == 0) {
+ if (symbol->ValueIsAddress()) {
+ range.GetBaseAddress() = symbol->GetAddressRef();
+ range.SetByteSize(symbol->GetByteSize());
return true;
+ }
}
-
- if ((scope & eSymbolContextBlock) && (block != nullptr))
- {
- if (use_inline_block_range)
- {
- Block *inline_block = block->GetContainingInlinedBlock();
- if (inline_block)
- return inline_block->GetRangeAtIndex (range_idx, range);
- }
- else
- {
- return block->GetRangeAtIndex (range_idx, range);
- }
- }
+ }
+ range.Clear();
+ return false;
+}
+
+LanguageType SymbolContext::GetLanguage() const {
+ LanguageType lang;
+ if (function && (lang = function->GetLanguage()) != eLanguageTypeUnknown) {
+ return lang;
+ } else if (variable &&
+ (lang = variable->GetLanguage()) != eLanguageTypeUnknown) {
+ return lang;
+ } else if (symbol && (lang = symbol->GetLanguage()) != eLanguageTypeUnknown) {
+ return lang;
+ } else if (comp_unit &&
+ (lang = comp_unit->GetLanguage()) != eLanguageTypeUnknown) {
+ return lang;
+ } else if (symbol) {
+ // If all else fails, try to guess the language from the name.
+ return symbol->GetMangled().GuessLanguage();
+ }
+ return eLanguageTypeUnknown;
+}
+
+bool SymbolContext::GetParentOfInlinedScope(const Address &curr_frame_pc,
+ SymbolContext &next_frame_sc,
+ Address &next_frame_pc) const {
+ next_frame_sc.Clear(false);
+ next_frame_pc.Clear();
+
+ if (block) {
+ // const addr_t curr_frame_file_addr = curr_frame_pc.GetFileAddress();
+
+ // In order to get the parent of an inlined function we first need to
+ // see if we are in an inlined block as "this->block" could be an
+ // inlined block, or a parent of "block" could be. So lets check if
+ // this block or one of this blocks parents is an inlined function.
+ Block *curr_inlined_block = block->GetContainingInlinedBlock();
+ if (curr_inlined_block) {
+ // "this->block" is contained in an inline function block, so to
+ // get the scope above the inlined block, we get the parent of the
+ // inlined block itself
+ Block *next_frame_block = curr_inlined_block->GetParent();
+ // Now calculate the symbol context of the containing block
+ next_frame_block->CalculateSymbolContext(&next_frame_sc);
+
+ // If we get here we weren't able to find the return line entry using the
+ // nesting of the blocks and
+ // the line table. So just use the call site info from our inlined block.
+
+ AddressRange range;
+ if (curr_inlined_block->GetRangeContainingAddress(curr_frame_pc, range)) {
+ // To see there this new frame block it, we need to look at the
+ // call site information from
+ const InlineFunctionInfo *curr_inlined_block_inlined_info =
+ curr_inlined_block->GetInlinedFunctionInfo();
+ next_frame_pc = range.GetBaseAddress();
+ next_frame_sc.line_entry.range.GetBaseAddress() = next_frame_pc;
+ next_frame_sc.line_entry.file =
+ curr_inlined_block_inlined_info->GetCallSite().GetFile();
+ next_frame_sc.line_entry.original_file =
+ curr_inlined_block_inlined_info->GetCallSite().GetFile();
+ next_frame_sc.line_entry.line =
+ curr_inlined_block_inlined_info->GetCallSite().GetLine();
+ next_frame_sc.line_entry.column =
+ curr_inlined_block_inlined_info->GetCallSite().GetColumn();
+ return true;
+ } else {
+ Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_SYMBOLS));
- if ((scope & eSymbolContextFunction) && (function != nullptr))
- {
- if (range_idx == 0)
- {
- range = function->GetAddressRange();
- return true;
- }
- }
-
- if ((scope & eSymbolContextSymbol) && (symbol != nullptr))
- {
- if (range_idx == 0)
- {
- if (symbol->ValueIsAddress())
- {
- range.GetBaseAddress() = symbol->GetAddressRef();
- range.SetByteSize (symbol->GetByteSize());
- return true;
- }
+ if (log) {
+ log->Printf(
+ "warning: inlined block 0x%8.8" PRIx64
+ " doesn't have a range that contains file address 0x%" PRIx64,
+ curr_inlined_block->GetID(), curr_frame_pc.GetFileAddress());
}
- }
- range.Clear();
- return false;
-}
-
-LanguageType
-SymbolContext::GetLanguage () const
-{
- LanguageType lang;
- if (function &&
- (lang = function->GetLanguage()) != eLanguageTypeUnknown)
- {
- return lang;
- }
- else if (variable &&
- (lang = variable->GetLanguage()) != eLanguageTypeUnknown)
- {
- return lang;
- }
- else if (symbol &&
- (lang = symbol->GetLanguage()) != eLanguageTypeUnknown)
- {
- return lang;
- }
- else if (comp_unit &&
- (lang = comp_unit->GetLanguage()) != eLanguageTypeUnknown)
- {
- return lang;
- }
- else if (symbol)
- {
- // If all else fails, try to guess the language from the name.
- return symbol->GetMangled().GuessLanguage();
- }
- return eLanguageTypeUnknown;
-}
-
-bool
-SymbolContext::GetParentOfInlinedScope (const Address &curr_frame_pc,
- SymbolContext &next_frame_sc,
- Address &next_frame_pc) const
-{
- next_frame_sc.Clear(false);
- next_frame_pc.Clear();
-
- if (block)
- {
- //const addr_t curr_frame_file_addr = curr_frame_pc.GetFileAddress();
-
- // In order to get the parent of an inlined function we first need to
- // see if we are in an inlined block as "this->block" could be an
- // inlined block, or a parent of "block" could be. So lets check if
- // this block or one of this blocks parents is an inlined function.
- Block *curr_inlined_block = block->GetContainingInlinedBlock();
- if (curr_inlined_block)
- {
- // "this->block" is contained in an inline function block, so to
- // get the scope above the inlined block, we get the parent of the
- // inlined block itself
- Block *next_frame_block = curr_inlined_block->GetParent();
- // Now calculate the symbol context of the containing block
- next_frame_block->CalculateSymbolContext (&next_frame_sc);
-
- // If we get here we weren't able to find the return line entry using the nesting of the blocks and
- // the line table. So just use the call site info from our inlined block.
-
- AddressRange range;
- if (curr_inlined_block->GetRangeContainingAddress (curr_frame_pc, range))
- {
- // To see there this new frame block it, we need to look at the
- // call site information from
- const InlineFunctionInfo* curr_inlined_block_inlined_info = curr_inlined_block->GetInlinedFunctionInfo();
- next_frame_pc = range.GetBaseAddress();
- next_frame_sc.line_entry.range.GetBaseAddress() = next_frame_pc;
- next_frame_sc.line_entry.file = curr_inlined_block_inlined_info->GetCallSite().GetFile();
- next_frame_sc.line_entry.original_file = curr_inlined_block_inlined_info->GetCallSite().GetFile();
- next_frame_sc.line_entry.line = curr_inlined_block_inlined_info->GetCallSite().GetLine();
- next_frame_sc.line_entry.column = curr_inlined_block_inlined_info->GetCallSite().GetColumn();
- return true;
- }
- else
- {
- Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_SYMBOLS));
-
- if (log)
- {
- log->Printf ("warning: inlined block 0x%8.8" PRIx64 " doesn't have a range that contains file address 0x%" PRIx64,
- curr_inlined_block->GetID(), curr_frame_pc.GetFileAddress());
- }
#ifdef LLDB_CONFIGURATION_DEBUG
- else
- {
- ObjectFile *objfile = NULL;
- if (module_sp)
- {
- SymbolVendor *symbol_vendor = module_sp->GetSymbolVendor();
- if (symbol_vendor)
- {
- SymbolFile *symbol_file = symbol_vendor->GetSymbolFile();
- if (symbol_file)
- objfile = symbol_file->GetObjectFile();
- }
- }
- if (objfile)
- {
- Host::SystemLog (Host::eSystemLogWarning,
- "warning: inlined block 0x%8.8" PRIx64 " doesn't have a range that contains file address 0x%" PRIx64 " in %s\n",
- curr_inlined_block->GetID(),
- curr_frame_pc.GetFileAddress(),
- objfile->GetFileSpec().GetPath().c_str());
- }
- else
- {
- Host::SystemLog (Host::eSystemLogWarning,
- "warning: inlined block 0x%8.8" PRIx64 " doesn't have a range that contains file address 0x%" PRIx64 "\n",
- curr_inlined_block->GetID(),
- curr_frame_pc.GetFileAddress());
- }
- }
-#endif
- }
+ else {
+ ObjectFile *objfile = NULL;
+ if (module_sp) {
+ SymbolVendor *symbol_vendor = module_sp->GetSymbolVendor();
+ if (symbol_vendor) {
+ SymbolFile *symbol_file = symbol_vendor->GetSymbolFile();
+ if (symbol_file)
+ objfile = symbol_file->GetObjectFile();
+ }
+ }
+ if (objfile) {
+ Host::SystemLog(
+ Host::eSystemLogWarning,
+ "warning: inlined block 0x%8.8" PRIx64
+ " doesn't have a range that contains file address 0x%" PRIx64
+ " in %s\n",
+ curr_inlined_block->GetID(), curr_frame_pc.GetFileAddress(),
+ objfile->GetFileSpec().GetPath().c_str());
+ } else {
+ Host::SystemLog(
+ Host::eSystemLogWarning,
+ "warning: inlined block 0x%8.8" PRIx64
+ " doesn't have a range that contains file address 0x%" PRIx64
+ "\n",
+ curr_inlined_block->GetID(), curr_frame_pc.GetFileAddress());
+ }
}
+#endif
+ }
}
-
- return false;
-}
-
-Block *
-SymbolContext::GetFunctionBlock ()
-{
- if (function)
- {
- if (block)
- {
- // If this symbol context has a block, check to see if this block
- // is itself, or is contained within a block with inlined function
- // information. If so, then the inlined block is the block that
- // defines the function.
- Block *inlined_block = block->GetContainingInlinedBlock();
- if (inlined_block)
- return inlined_block;
-
- // The block in this symbol context is not inside an inlined
- // block, so the block that defines the function is the function's
- // top level block, which is returned below.
- }
-
- // There is no block information in this symbol context, so we must
- // assume that the block that is desired is the top level block of
- // the function itself.
- return &function->GetBlock(true);
- }
- return nullptr;
-}
-
-bool
-SymbolContext::GetFunctionMethodInfo (lldb::LanguageType &language,
- bool &is_instance_method,
- ConstString &language_object_name)
+ }
-
-{
- Block *function_block = GetFunctionBlock();
- if (function_block)
- {
- CompilerDeclContext decl_ctx = function_block->GetDeclContext();
- if (decl_ctx)
- return decl_ctx.IsClassMethod(&language, &is_instance_method, &language_object_name);
- }
- return false;
+ return false;
}
-void
-SymbolContext::SortTypeList(TypeMap &type_map, TypeList &type_list) const
-{
- Block * curr_block = block;
- bool isInlinedblock = false;
- if (curr_block != nullptr && curr_block->GetContainingInlinedBlock() != nullptr)
- isInlinedblock = true;
-
- //----------------------------------------------------------------------
- // Find all types that match the current block if we have one and put
- // them first in the list. Keep iterating up through all blocks.
- //----------------------------------------------------------------------
- while (curr_block != nullptr && !isInlinedblock)
- {
- type_map.ForEach([curr_block, &type_list](const lldb::TypeSP& type_sp) -> bool {
- SymbolContextScope *scs = type_sp->GetSymbolContextScope();
- if (scs && curr_block == scs->CalculateSymbolContextBlock())
- type_list.Insert(type_sp);
- return true; // Keep iterating
- });
-
- // Remove any entries that are now in "type_list" from "type_map"
- // since we can't remove from type_map while iterating
- type_list.ForEach([&type_map](const lldb::TypeSP& type_sp) -> bool {
- type_map.Remove(type_sp);
- return true; // Keep iterating
- });
- curr_block = curr_block->GetParent();
- }
- //----------------------------------------------------------------------
- // Find all types that match the current function, if we have onem, and
- // put them next in the list.
- //----------------------------------------------------------------------
- if (function != nullptr && !type_map.Empty())
- {
- const size_t old_type_list_size = type_list.GetSize();
- type_map.ForEach([this, &type_list](const lldb::TypeSP& type_sp) -> bool {
- SymbolContextScope *scs = type_sp->GetSymbolContextScope();
- if (scs && function == scs->CalculateSymbolContextFunction())
- type_list.Insert(type_sp);
- return true; // Keep iterating
- });
-
- // Remove any entries that are now in "type_list" from "type_map"
- // since we can't remove from type_map while iterating
- const size_t new_type_list_size = type_list.GetSize();
- if (new_type_list_size > old_type_list_size)
- {
- for (size_t i=old_type_list_size; i<new_type_list_size; ++i)
- type_map.Remove(type_list.GetTypeAtIndex(i));
- }
- }
- //----------------------------------------------------------------------
- // Find all types that match the current compile unit, if we have one,
- // and put them next in the list.
- //----------------------------------------------------------------------
- if (comp_unit != nullptr && !type_map.Empty())
- {
- const size_t old_type_list_size = type_list.GetSize();
-
- type_map.ForEach([this, &type_list](const lldb::TypeSP& type_sp) -> bool {
- SymbolContextScope *scs = type_sp->GetSymbolContextScope();
- if (scs && comp_unit == scs->CalculateSymbolContextCompileUnit())
- type_list.Insert(type_sp);
- return true; // Keep iterating
- });
-
- // Remove any entries that are now in "type_list" from "type_map"
- // since we can't remove from type_map while iterating
- const size_t new_type_list_size = type_list.GetSize();
- if (new_type_list_size > old_type_list_size)
- {
- for (size_t i=old_type_list_size; i<new_type_list_size; ++i)
- type_map.Remove(type_list.GetTypeAtIndex(i));
- }
- }
- //----------------------------------------------------------------------
- // Find all types that match the current module, if we have one, and put
- // them next in the list.
- //----------------------------------------------------------------------
- if (module_sp && !type_map.Empty())
- {
- const size_t old_type_list_size = type_list.GetSize();
- type_map.ForEach([this, &type_list](const lldb::TypeSP& type_sp) -> bool {
- SymbolContextScope *scs = type_sp->GetSymbolContextScope();
- if (scs && module_sp == scs->CalculateSymbolContextModule())
- type_list.Insert(type_sp);
- return true; // Keep iterating
- });
- // Remove any entries that are now in "type_list" from "type_map"
- // since we can't remove from type_map while iterating
- const size_t new_type_list_size = type_list.GetSize();
- if (new_type_list_size > old_type_list_size)
- {
- for (size_t i=old_type_list_size; i<new_type_list_size; ++i)
- type_map.Remove(type_list.GetTypeAtIndex(i));
- }
- }
- //----------------------------------------------------------------------
- // Any types that are left get copied into the list an any order.
- //----------------------------------------------------------------------
- if (!type_map.Empty())
- {
- type_map.ForEach([&type_list](const lldb::TypeSP& type_sp) -> bool {
+Block *SymbolContext::GetFunctionBlock() {
+ if (function) {
+ if (block) {
+ // If this symbol context has a block, check to see if this block
+ // is itself, or is contained within a block with inlined function
+ // information. If so, then the inlined block is the block that
+ // defines the function.
+ Block *inlined_block = block->GetContainingInlinedBlock();
+ if (inlined_block)
+ return inlined_block;
+
+ // The block in this symbol context is not inside an inlined
+ // block, so the block that defines the function is the function's
+ // top level block, which is returned below.
+ }
+
+ // There is no block information in this symbol context, so we must
+ // assume that the block that is desired is the top level block of
+ // the function itself.
+ return &function->GetBlock(true);
+ }
+ return nullptr;
+}
+
+bool SymbolContext::GetFunctionMethodInfo(lldb::LanguageType &language,
+ bool &is_instance_method,
+ ConstString &language_object_name)
+
+{
+ Block *function_block = GetFunctionBlock();
+ if (function_block) {
+ CompilerDeclContext decl_ctx = function_block->GetDeclContext();
+ if (decl_ctx)
+ return decl_ctx.IsClassMethod(&language, &is_instance_method,
+ &language_object_name);
+ }
+ return false;
+}
+
+void SymbolContext::SortTypeList(TypeMap &type_map, TypeList &type_list) const {
+ Block *curr_block = block;
+ bool isInlinedblock = false;
+ if (curr_block != nullptr &&
+ curr_block->GetContainingInlinedBlock() != nullptr)
+ isInlinedblock = true;
+
+ //----------------------------------------------------------------------
+ // Find all types that match the current block if we have one and put
+ // them first in the list. Keep iterating up through all blocks.
+ //----------------------------------------------------------------------
+ while (curr_block != nullptr && !isInlinedblock) {
+ type_map.ForEach(
+ [curr_block, &type_list](const lldb::TypeSP &type_sp) -> bool {
+ SymbolContextScope *scs = type_sp->GetSymbolContextScope();
+ if (scs && curr_block == scs->CalculateSymbolContextBlock())
type_list.Insert(type_sp);
- return true; // Keep iterating
+ return true; // Keep iterating
});
- }
-}
-ConstString
-SymbolContext::GetFunctionName (Mangled::NamePreference preference) const
-{
- if (function)
- {
- if (block)
- {
- Block *inlined_block = block->GetContainingInlinedBlock();
-
- if (inlined_block)
- {
- const InlineFunctionInfo *inline_info = inlined_block->GetInlinedFunctionInfo();
- if (inline_info)
- return inline_info->GetName(function->GetLanguage());
- }
- }
- return function->GetMangled().GetName(function->GetLanguage(), preference);
- }
- else if (symbol && symbol->ValueIsAddress())
- {
- return symbol->GetMangled().GetName(symbol->GetLanguage(), preference);
- }
- else
- {
- // No function, return an empty string.
- return ConstString();
- }
+ // Remove any entries that are now in "type_list" from "type_map"
+ // since we can't remove from type_map while iterating
+ type_list.ForEach([&type_map](const lldb::TypeSP &type_sp) -> bool {
+ type_map.Remove(type_sp);
+ return true; // Keep iterating
+ });
+ curr_block = curr_block->GetParent();
+ }
+ //----------------------------------------------------------------------
+ // Find all types that match the current function, if we have onem, and
+ // put them next in the list.
+ //----------------------------------------------------------------------
+ if (function != nullptr && !type_map.Empty()) {
+ const size_t old_type_list_size = type_list.GetSize();
+ type_map.ForEach([this, &type_list](const lldb::TypeSP &type_sp) -> bool {
+ SymbolContextScope *scs = type_sp->GetSymbolContextScope();
+ if (scs && function == scs->CalculateSymbolContextFunction())
+ type_list.Insert(type_sp);
+ return true; // Keep iterating
+ });
+
+ // Remove any entries that are now in "type_list" from "type_map"
+ // since we can't remove from type_map while iterating
+ const size_t new_type_list_size = type_list.GetSize();
+ if (new_type_list_size > old_type_list_size) {
+ for (size_t i = old_type_list_size; i < new_type_list_size; ++i)
+ type_map.Remove(type_list.GetTypeAtIndex(i));
+ }
+ }
+ //----------------------------------------------------------------------
+ // Find all types that match the current compile unit, if we have one,
+ // and put them next in the list.
+ //----------------------------------------------------------------------
+ if (comp_unit != nullptr && !type_map.Empty()) {
+ const size_t old_type_list_size = type_list.GetSize();
+
+ type_map.ForEach([this, &type_list](const lldb::TypeSP &type_sp) -> bool {
+ SymbolContextScope *scs = type_sp->GetSymbolContextScope();
+ if (scs && comp_unit == scs->CalculateSymbolContextCompileUnit())
+ type_list.Insert(type_sp);
+ return true; // Keep iterating
+ });
+
+ // Remove any entries that are now in "type_list" from "type_map"
+ // since we can't remove from type_map while iterating
+ const size_t new_type_list_size = type_list.GetSize();
+ if (new_type_list_size > old_type_list_size) {
+ for (size_t i = old_type_list_size; i < new_type_list_size; ++i)
+ type_map.Remove(type_list.GetTypeAtIndex(i));
+ }
+ }
+ //----------------------------------------------------------------------
+ // Find all types that match the current module, if we have one, and put
+ // them next in the list.
+ //----------------------------------------------------------------------
+ if (module_sp && !type_map.Empty()) {
+ const size_t old_type_list_size = type_list.GetSize();
+ type_map.ForEach([this, &type_list](const lldb::TypeSP &type_sp) -> bool {
+ SymbolContextScope *scs = type_sp->GetSymbolContextScope();
+ if (scs && module_sp == scs->CalculateSymbolContextModule())
+ type_list.Insert(type_sp);
+ return true; // Keep iterating
+ });
+ // Remove any entries that are now in "type_list" from "type_map"
+ // since we can't remove from type_map while iterating
+ const size_t new_type_list_size = type_list.GetSize();
+ if (new_type_list_size > old_type_list_size) {
+ for (size_t i = old_type_list_size; i < new_type_list_size; ++i)
+ type_map.Remove(type_list.GetTypeAtIndex(i));
+ }
+ }
+ //----------------------------------------------------------------------
+ // Any types that are left get copied into the list an any order.
+ //----------------------------------------------------------------------
+ if (!type_map.Empty()) {
+ type_map.ForEach([&type_list](const lldb::TypeSP &type_sp) -> bool {
+ type_list.Insert(type_sp);
+ return true; // Keep iterating
+ });
+ }
}
-LineEntry
-SymbolContext::GetFunctionStartLineEntry () const
-{
- LineEntry line_entry;
- Address start_addr;
- if (block)
- {
- Block *inlined_block = block->GetContainingInlinedBlock();
- if (inlined_block)
- {
- if (inlined_block->GetStartAddress (start_addr))
- {
- if (start_addr.CalculateSymbolContextLineEntry (line_entry))
- return line_entry;
- }
- return LineEntry();
- }
- }
-
- if (function)
- {
- if (function->GetAddressRange().GetBaseAddress().CalculateSymbolContextLineEntry(line_entry))
- return line_entry;
- }
- return LineEntry();
-}
+ConstString
+SymbolContext::GetFunctionName(Mangled::NamePreference preference) const {
+ if (function) {
+ if (block) {
+ Block *inlined_block = block->GetContainingInlinedBlock();
+
+ if (inlined_block) {
+ const InlineFunctionInfo *inline_info =
+ inlined_block->GetInlinedFunctionInfo();
+ if (inline_info)
+ return inline_info->GetName(function->GetLanguage());
+ }
+ }
+ return function->GetMangled().GetName(function->GetLanguage(), preference);
+ } else if (symbol && symbol->ValueIsAddress()) {
+ return symbol->GetMangled().GetName(symbol->GetLanguage(), preference);
+ } else {
+ // No function, return an empty string.
+ return ConstString();
+ }
+}
+
+LineEntry SymbolContext::GetFunctionStartLineEntry() const {
+ LineEntry line_entry;
+ Address start_addr;
+ if (block) {
+ Block *inlined_block = block->GetContainingInlinedBlock();
+ if (inlined_block) {
+ if (inlined_block->GetStartAddress(start_addr)) {
+ if (start_addr.CalculateSymbolContextLineEntry(line_entry))
+ return line_entry;
+ }
+ return LineEntry();
+ }
+ }
+
+ if (function) {
+ if (function->GetAddressRange()
+ .GetBaseAddress()
+ .CalculateSymbolContextLineEntry(line_entry))
+ return line_entry;
+ }
+ return LineEntry();
+}
+
+bool SymbolContext::GetAddressRangeFromHereToEndLine(uint32_t end_line,
+ AddressRange &range,
+ Error &error) {
+ if (!line_entry.IsValid()) {
+ error.SetErrorString("Symbol context has no line table.");
+ return false;
+ }
-bool
-SymbolContext::GetAddressRangeFromHereToEndLine(uint32_t end_line, AddressRange &range, Error &error)
-{
- if (!line_entry.IsValid())
- {
- error.SetErrorString("Symbol context has no line table.");
- return false;
- }
-
- range = line_entry.range;
- if (line_entry.line > end_line)
- {
- error.SetErrorStringWithFormat("end line option %d must be after the current line: %d",
- end_line,
- line_entry.line);
- return false;
- }
+ range = line_entry.range;
+ if (line_entry.line > end_line) {
+ error.SetErrorStringWithFormat(
+ "end line option %d must be after the current line: %d", end_line,
+ line_entry.line);
+ return false;
+ }
- uint32_t line_index = 0;
- bool found = false;
- while (1)
- {
- LineEntry this_line;
- line_index = comp_unit->FindLineEntry(line_index, line_entry.line, nullptr, false, &this_line);
- if (line_index == UINT32_MAX)
- break;
- if (LineEntry::Compare(this_line, line_entry) == 0)
- {
- found = true;
- break;
- }
- }
-
- LineEntry end_entry;
- if (!found)
- {
- // Can't find the index of the SymbolContext's line entry in the SymbolContext's CompUnit.
- error.SetErrorString("Can't find the current line entry in the CompUnit - can't process "
- "the end-line option");
- return false;
- }
-
- line_index = comp_unit->FindLineEntry(line_index, end_line, nullptr, false, &end_entry);
+ uint32_t line_index = 0;
+ bool found = false;
+ while (1) {
+ LineEntry this_line;
+ line_index = comp_unit->FindLineEntry(line_index, line_entry.line, nullptr,
+ false, &this_line);
if (line_index == UINT32_MAX)
- {
- error.SetErrorStringWithFormat("could not find a line table entry corresponding "
- "to end line number %d",
- end_line);
- return false;
- }
-
- Block *func_block = GetFunctionBlock();
- if (func_block && func_block->GetRangeIndexContainingAddress(end_entry.range.GetBaseAddress()) == UINT32_MAX)
- {
- error.SetErrorStringWithFormat("end line number %d is not contained within the current function.",
- end_line);
- return false;
- }
-
- lldb::addr_t range_size = end_entry.range.GetBaseAddress().GetFileAddress()
- - range.GetBaseAddress().GetFileAddress();
- range.SetByteSize(range_size);
- return true;
-}
+ break;
+ if (LineEntry::Compare(this_line, line_entry) == 0) {
+ found = true;
+ break;
+ }
+ }
+
+ LineEntry end_entry;
+ if (!found) {
+ // Can't find the index of the SymbolContext's line entry in the
+ // SymbolContext's CompUnit.
+ error.SetErrorString(
+ "Can't find the current line entry in the CompUnit - can't process "
+ "the end-line option");
+ return false;
+ }
+ line_index = comp_unit->FindLineEntry(line_index, end_line, nullptr, false,
+ &end_entry);
+ if (line_index == UINT32_MAX) {
+ error.SetErrorStringWithFormat(
+ "could not find a line table entry corresponding "
+ "to end line number %d",
+ end_line);
+ return false;
+ }
+
+ Block *func_block = GetFunctionBlock();
+ if (func_block &&
+ func_block->GetRangeIndexContainingAddress(
+ end_entry.range.GetBaseAddress()) == UINT32_MAX) {
+ error.SetErrorStringWithFormat(
+ "end line number %d is not contained within the current function.",
+ end_line);
+ return false;
+ }
+ lldb::addr_t range_size = end_entry.range.GetBaseAddress().GetFileAddress() -
+ range.GetBaseAddress().GetFileAddress();
+ range.SetByteSize(range_size);
+ return true;
+}
//----------------------------------------------------------------------
//
@@ -935,310 +805,263 @@ SymbolContext::GetAddressRangeFromHereTo
//
//----------------------------------------------------------------------
-SymbolContextSpecifier::SymbolContextSpecifier (const TargetSP &target_sp) :
- m_target_sp (target_sp),
- m_module_spec (),
- m_module_sp (),
- m_file_spec_ap (),
- m_start_line (0),
- m_end_line (0),
- m_function_spec (),
- m_class_name (),
- m_address_range_ap (),
- m_type (eNothingSpecified)
-{
-}
-
-SymbolContextSpecifier::~SymbolContextSpecifier()
-{
-}
+SymbolContextSpecifier::SymbolContextSpecifier(const TargetSP &target_sp)
+ : m_target_sp(target_sp), m_module_spec(), m_module_sp(), m_file_spec_ap(),
+ m_start_line(0), m_end_line(0), m_function_spec(), m_class_name(),
+ m_address_range_ap(), m_type(eNothingSpecified) {}
+
+SymbolContextSpecifier::~SymbolContextSpecifier() {}
+
+bool SymbolContextSpecifier::AddLineSpecification(uint32_t line_no,
+ SpecificationType type) {
+ bool return_value = true;
+ switch (type) {
+ case eNothingSpecified:
+ Clear();
+ break;
+ case eLineStartSpecified:
+ m_start_line = line_no;
+ m_type |= eLineStartSpecified;
+ break;
+ case eLineEndSpecified:
+ m_end_line = line_no;
+ m_type |= eLineEndSpecified;
+ break;
+ default:
+ return_value = false;
+ break;
+ }
+ return return_value;
+}
+
+bool SymbolContextSpecifier::AddSpecification(const char *spec_string,
+ SpecificationType type) {
+ bool return_value = true;
+ switch (type) {
+ case eNothingSpecified:
+ Clear();
+ break;
+ case eModuleSpecified: {
+ // See if we can find the Module, if so stick it in the SymbolContext.
+ FileSpec module_file_spec(spec_string, false);
+ ModuleSpec module_spec(module_file_spec);
+ lldb::ModuleSP module_sp(
+ m_target_sp->GetImages().FindFirstModule(module_spec));
+ m_type |= eModuleSpecified;
+ if (module_sp)
+ m_module_sp = module_sp;
+ else
+ m_module_spec.assign(spec_string);
+ } break;
+ case eFileSpecified:
+ // CompUnits can't necessarily be resolved here, since an inlined function
+ // might show up in
+ // a number of CompUnits. Instead we just convert to a FileSpec and store
+ // it away.
+ m_file_spec_ap.reset(new FileSpec(spec_string, false));
+ m_type |= eFileSpecified;
+ break;
+ case eLineStartSpecified:
+ m_start_line = StringConvert::ToSInt32(spec_string, 0, 0, &return_value);
+ if (return_value)
+ m_type |= eLineStartSpecified;
+ break;
+ case eLineEndSpecified:
+ m_end_line = StringConvert::ToSInt32(spec_string, 0, 0, &return_value);
+ if (return_value)
+ m_type |= eLineEndSpecified;
+ break;
+ case eFunctionSpecified:
+ m_function_spec.assign(spec_string);
+ m_type |= eFunctionSpecified;
+ break;
+ case eClassOrNamespaceSpecified:
+ Clear();
+ m_class_name.assign(spec_string);
+ m_type = eClassOrNamespaceSpecified;
+ break;
+ case eAddressRangeSpecified:
+ // Not specified yet...
+ break;
+ }
+
+ return return_value;
+}
+
+void SymbolContextSpecifier::Clear() {
+ m_module_spec.clear();
+ m_file_spec_ap.reset();
+ m_function_spec.clear();
+ m_class_name.clear();
+ m_start_line = 0;
+ m_end_line = 0;
+ m_address_range_ap.reset();
-bool
-SymbolContextSpecifier::AddLineSpecification (uint32_t line_no, SpecificationType type)
-{
- bool return_value = true;
- switch (type)
- {
- case eNothingSpecified:
- Clear();
- break;
- case eLineStartSpecified:
- m_start_line = line_no;
- m_type |= eLineStartSpecified;
- break;
- case eLineEndSpecified:
- m_end_line = line_no;
- m_type |= eLineEndSpecified;
- break;
- default:
- return_value = false;
- break;
- }
- return return_value;
+ m_type = eNothingSpecified;
}
-bool
-SymbolContextSpecifier::AddSpecification (const char *spec_string, SpecificationType type)
-{
- bool return_value = true;
- switch (type)
- {
- case eNothingSpecified:
- Clear();
- break;
- case eModuleSpecified:
- {
- // See if we can find the Module, if so stick it in the SymbolContext.
- FileSpec module_file_spec(spec_string, false);
- ModuleSpec module_spec (module_file_spec);
- lldb::ModuleSP module_sp (m_target_sp->GetImages().FindFirstModule (module_spec));
- m_type |= eModuleSpecified;
- if (module_sp)
- m_module_sp = module_sp;
- else
- m_module_spec.assign (spec_string);
- }
- break;
- case eFileSpecified:
- // CompUnits can't necessarily be resolved here, since an inlined function might show up in
- // a number of CompUnits. Instead we just convert to a FileSpec and store it away.
- m_file_spec_ap.reset (new FileSpec (spec_string, false));
- m_type |= eFileSpecified;
- break;
- case eLineStartSpecified:
- m_start_line = StringConvert::ToSInt32(spec_string, 0, 0, &return_value);
- if (return_value)
- m_type |= eLineStartSpecified;
- break;
- case eLineEndSpecified:
- m_end_line = StringConvert::ToSInt32(spec_string, 0, 0, &return_value);
- if (return_value)
- m_type |= eLineEndSpecified;
- break;
- case eFunctionSpecified:
- m_function_spec.assign(spec_string);
- m_type |= eFunctionSpecified;
- break;
- case eClassOrNamespaceSpecified:
- Clear();
- m_class_name.assign (spec_string);
- m_type = eClassOrNamespaceSpecified;
- break;
- case eAddressRangeSpecified:
- // Not specified yet...
- break;
- }
-
- return return_value;
-}
+bool SymbolContextSpecifier::SymbolContextMatches(SymbolContext &sc) {
+ if (m_type == eNothingSpecified)
+ return true;
-void
-SymbolContextSpecifier::Clear()
-{
- m_module_spec.clear();
- m_file_spec_ap.reset();
- m_function_spec.clear();
- m_class_name.clear();
- m_start_line = 0;
- m_end_line = 0;
- m_address_range_ap.reset();
-
- m_type = eNothingSpecified;
-}
+ if (m_target_sp.get() != sc.target_sp.get())
+ return false;
-bool
-SymbolContextSpecifier::SymbolContextMatches(SymbolContext &sc)
-{
- if (m_type == eNothingSpecified)
- return true;
-
- if (m_target_sp.get() != sc.target_sp.get())
+ if (m_type & eModuleSpecified) {
+ if (sc.module_sp) {
+ if (m_module_sp.get() != nullptr) {
+ if (m_module_sp.get() != sc.module_sp.get())
+ return false;
+ } else {
+ FileSpec module_file_spec(m_module_spec.c_str(), false);
+ if (!FileSpec::Equal(module_file_spec, sc.module_sp->GetFileSpec(),
+ false))
+ return false;
+ }
+ }
+ }
+ if (m_type & eFileSpecified) {
+ if (m_file_spec_ap.get()) {
+ // If we don't have a block or a comp_unit, then we aren't going to match
+ // a source file.
+ if (sc.block == nullptr && sc.comp_unit == nullptr)
return false;
-
- if (m_type & eModuleSpecified)
- {
- if (sc.module_sp)
- {
- if (m_module_sp.get() != nullptr)
- {
- if (m_module_sp.get() != sc.module_sp.get())
- return false;
- }
- else
- {
- FileSpec module_file_spec (m_module_spec.c_str(), false);
- if (!FileSpec::Equal (module_file_spec, sc.module_sp->GetFileSpec(), false))
- return false;
- }
- }
- }
- if (m_type & eFileSpecified)
- {
- if (m_file_spec_ap.get())
- {
- // If we don't have a block or a comp_unit, then we aren't going to match a source file.
- if (sc.block == nullptr && sc.comp_unit == nullptr)
- return false;
-
- // Check if the block is present, and if so is it inlined:
- bool was_inlined = false;
- if (sc.block != nullptr)
- {
- const InlineFunctionInfo *inline_info = sc.block->GetInlinedFunctionInfo();
- if (inline_info != nullptr)
- {
- was_inlined = true;
- if (!FileSpec::Equal (inline_info->GetDeclaration().GetFile(), *(m_file_spec_ap.get()), false))
- return false;
- }
- }
-
- // Next check the comp unit, but only if the SymbolContext was not inlined.
- if (!was_inlined && sc.comp_unit != nullptr)
- {
- if (!FileSpec::Equal (*(sc.comp_unit), *(m_file_spec_ap.get()), false))
- return false;
- }
- }
- }
- if (m_type & eLineStartSpecified
- || m_type & eLineEndSpecified)
- {
- if (sc.line_entry.line < m_start_line || sc.line_entry.line > m_end_line)
+
+ // Check if the block is present, and if so is it inlined:
+ bool was_inlined = false;
+ if (sc.block != nullptr) {
+ const InlineFunctionInfo *inline_info =
+ sc.block->GetInlinedFunctionInfo();
+ if (inline_info != nullptr) {
+ was_inlined = true;
+ if (!FileSpec::Equal(inline_info->GetDeclaration().GetFile(),
+ *(m_file_spec_ap.get()), false))
return false;
- }
-
- if (m_type & eFunctionSpecified)
- {
- // First check the current block, and if it is inlined, get the inlined function name:
- bool was_inlined = false;
- ConstString func_name(m_function_spec.c_str());
-
- if (sc.block != nullptr)
- {
- const InlineFunctionInfo *inline_info = sc.block->GetInlinedFunctionInfo();
- if (inline_info != nullptr)
- {
- was_inlined = true;
- const Mangled &name = inline_info->GetMangled();
- if (!name.NameMatches (func_name, sc.function->GetLanguage()))
- return false;
- }
}
- // If it wasn't inlined, check the name in the function or symbol:
- if (!was_inlined)
- {
- if (sc.function != nullptr)
- {
- if (!sc.function->GetMangled().NameMatches(func_name, sc.function->GetLanguage()))
- return false;
- }
- else if (sc.symbol != nullptr)
- {
- if (!sc.symbol->GetMangled().NameMatches(func_name, sc.symbol->GetLanguage()))
- return false;
- }
- }
-
-
- }
-
- return true;
-}
+ }
-bool
-SymbolContextSpecifier::AddressMatches(lldb::addr_t addr)
-{
- if (m_type & eAddressRangeSpecified)
- {
-
+ // Next check the comp unit, but only if the SymbolContext was not
+ // inlined.
+ if (!was_inlined && sc.comp_unit != nullptr) {
+ if (!FileSpec::Equal(*(sc.comp_unit), *(m_file_spec_ap.get()), false))
+ return false;
+ }
+ }
+ }
+ if (m_type & eLineStartSpecified || m_type & eLineEndSpecified) {
+ if (sc.line_entry.line < m_start_line || sc.line_entry.line > m_end_line)
+ return false;
+ }
+
+ if (m_type & eFunctionSpecified) {
+ // First check the current block, and if it is inlined, get the inlined
+ // function name:
+ bool was_inlined = false;
+ ConstString func_name(m_function_spec.c_str());
+
+ if (sc.block != nullptr) {
+ const InlineFunctionInfo *inline_info =
+ sc.block->GetInlinedFunctionInfo();
+ if (inline_info != nullptr) {
+ was_inlined = true;
+ const Mangled &name = inline_info->GetMangled();
+ if (!name.NameMatches(func_name, sc.function->GetLanguage()))
+ return false;
+ }
+ }
+ // If it wasn't inlined, check the name in the function or symbol:
+ if (!was_inlined) {
+ if (sc.function != nullptr) {
+ if (!sc.function->GetMangled().NameMatches(func_name,
+ sc.function->GetLanguage()))
+ return false;
+ } else if (sc.symbol != nullptr) {
+ if (!sc.symbol->GetMangled().NameMatches(func_name,
+ sc.symbol->GetLanguage()))
+ return false;
+ }
+ }
+ }
+
+ return true;
+}
+
+bool SymbolContextSpecifier::AddressMatches(lldb::addr_t addr) {
+ if (m_type & eAddressRangeSpecified) {
+
+ } else {
+ Address match_address(addr, nullptr);
+ SymbolContext sc;
+ m_target_sp->GetImages().ResolveSymbolContextForAddress(
+ match_address, eSymbolContextEverything, sc);
+ return SymbolContextMatches(sc);
+ }
+ return true;
+}
+
+void SymbolContextSpecifier::GetDescription(
+ Stream *s, lldb::DescriptionLevel level) const {
+ char path_str[PATH_MAX + 1];
+
+ if (m_type == eNothingSpecified) {
+ s->Printf("Nothing specified.\n");
+ }
+
+ if (m_type == eModuleSpecified) {
+ s->Indent();
+ if (m_module_sp) {
+ m_module_sp->GetFileSpec().GetPath(path_str, PATH_MAX);
+ s->Printf("Module: %s\n", path_str);
+ } else
+ s->Printf("Module: %s\n", m_module_spec.c_str());
+ }
+
+ if (m_type == eFileSpecified && m_file_spec_ap.get() != nullptr) {
+ m_file_spec_ap->GetPath(path_str, PATH_MAX);
+ s->Indent();
+ s->Printf("File: %s", path_str);
+ if (m_type == eLineStartSpecified) {
+ s->Printf(" from line %" PRIu64 "", (uint64_t)m_start_line);
+ if (m_type == eLineEndSpecified)
+ s->Printf("to line %" PRIu64 "", (uint64_t)m_end_line);
+ else
+ s->Printf("to end");
+ } else if (m_type == eLineEndSpecified) {
+ s->Printf(" from start to line %" PRIu64 "", (uint64_t)m_end_line);
}
+ s->Printf(".\n");
+ }
+
+ if (m_type == eLineStartSpecified) {
+ s->Indent();
+ s->Printf("From line %" PRIu64 "", (uint64_t)m_start_line);
+ if (m_type == eLineEndSpecified)
+ s->Printf("to line %" PRIu64 "", (uint64_t)m_end_line);
else
- {
- Address match_address (addr, nullptr);
- SymbolContext sc;
- m_target_sp->GetImages().ResolveSymbolContextForAddress(match_address, eSymbolContextEverything, sc);
- return SymbolContextMatches(sc);
- }
- return true;
-}
+ s->Printf("to end");
+ s->Printf(".\n");
+ } else if (m_type == eLineEndSpecified) {
+ s->Printf("From start to line %" PRIu64 ".\n", (uint64_t)m_end_line);
+ }
-void
-SymbolContextSpecifier::GetDescription (Stream *s, lldb::DescriptionLevel level) const
-{
- char path_str[PATH_MAX + 1];
+ if (m_type == eFunctionSpecified) {
+ s->Indent();
+ s->Printf("Function: %s.\n", m_function_spec.c_str());
+ }
- if (m_type == eNothingSpecified)
- {
- s->Printf ("Nothing specified.\n");
- }
-
- if (m_type == eModuleSpecified)
- {
- s->Indent();
- if (m_module_sp)
- {
- m_module_sp->GetFileSpec().GetPath (path_str, PATH_MAX);
- s->Printf ("Module: %s\n", path_str);
- }
- else
- s->Printf ("Module: %s\n", m_module_spec.c_str());
- }
-
- if (m_type == eFileSpecified && m_file_spec_ap.get() != nullptr)
- {
- m_file_spec_ap->GetPath (path_str, PATH_MAX);
- s->Indent();
- s->Printf ("File: %s", path_str);
- if (m_type == eLineStartSpecified)
- {
- s->Printf (" from line %" PRIu64 "", (uint64_t)m_start_line);
- if (m_type == eLineEndSpecified)
- s->Printf ("to line %" PRIu64 "", (uint64_t)m_end_line);
- else
- s->Printf ("to end");
- }
- else if (m_type == eLineEndSpecified)
- {
- s->Printf (" from start to line %" PRIu64 "", (uint64_t)m_end_line);
- }
- s->Printf (".\n");
- }
-
- if (m_type == eLineStartSpecified)
- {
- s->Indent();
- s->Printf ("From line %" PRIu64 "", (uint64_t)m_start_line);
- if (m_type == eLineEndSpecified)
- s->Printf ("to line %" PRIu64 "", (uint64_t)m_end_line);
- else
- s->Printf ("to end");
- s->Printf (".\n");
- }
- else if (m_type == eLineEndSpecified)
- {
- s->Printf ("From start to line %" PRIu64 ".\n", (uint64_t)m_end_line);
- }
-
- if (m_type == eFunctionSpecified)
- {
- s->Indent();
- s->Printf ("Function: %s.\n", m_function_spec.c_str());
- }
-
- if (m_type == eClassOrNamespaceSpecified)
- {
- s->Indent();
- s->Printf ("Class name: %s.\n", m_class_name.c_str());
- }
-
- if (m_type == eAddressRangeSpecified && m_address_range_ap.get() != nullptr)
- {
- s->Indent();
- s->PutCString ("Address range: ");
- m_address_range_ap->Dump (s, m_target_sp.get(), Address::DumpStyleLoadAddress, Address::DumpStyleFileAddress);
- s->PutCString ("\n");
- }
+ if (m_type == eClassOrNamespaceSpecified) {
+ s->Indent();
+ s->Printf("Class name: %s.\n", m_class_name.c_str());
+ }
+
+ if (m_type == eAddressRangeSpecified && m_address_range_ap.get() != nullptr) {
+ s->Indent();
+ s->PutCString("Address range: ");
+ m_address_range_ap->Dump(s, m_target_sp.get(),
+ Address::DumpStyleLoadAddress,
+ Address::DumpStyleFileAddress);
+ s->PutCString("\n");
+ }
}
//----------------------------------------------------------------------
@@ -1247,241 +1070,180 @@ SymbolContextSpecifier::GetDescription (
//
//----------------------------------------------------------------------
+SymbolContextList::SymbolContextList() : m_symbol_contexts() {}
-SymbolContextList::SymbolContextList() :
- m_symbol_contexts()
-{
-}
-
-SymbolContextList::~SymbolContextList()
-{
-}
-
-void
-SymbolContextList::Append(const SymbolContext& sc)
-{
- m_symbol_contexts.push_back(sc);
-}
-
-void
-SymbolContextList::Append (const SymbolContextList& sc_list)
-{
- collection::const_iterator pos, end = sc_list.m_symbol_contexts.end();
- for (pos = sc_list.m_symbol_contexts.begin(); pos != end; ++pos)
- m_symbol_contexts.push_back (*pos);
-}
-
+SymbolContextList::~SymbolContextList() {}
-uint32_t
-SymbolContextList::AppendIfUnique (const SymbolContextList& sc_list, bool merge_symbol_into_function)
-{
- uint32_t unique_sc_add_count = 0;
- collection::const_iterator pos, end = sc_list.m_symbol_contexts.end();
- for (pos = sc_list.m_symbol_contexts.begin(); pos != end; ++pos)
- {
- if (AppendIfUnique (*pos, merge_symbol_into_function))
- ++unique_sc_add_count;
- }
- return unique_sc_add_count;
+void SymbolContextList::Append(const SymbolContext &sc) {
+ m_symbol_contexts.push_back(sc);
}
-bool
-SymbolContextList::AppendIfUnique (const SymbolContext& sc, bool merge_symbol_into_function)
-{
- collection::iterator pos, end = m_symbol_contexts.end();
- for (pos = m_symbol_contexts.begin(); pos != end; ++pos)
- {
- if (*pos == sc)
- return false;
- }
- if (merge_symbol_into_function
- && sc.symbol != nullptr
- && sc.comp_unit == nullptr
- && sc.function == nullptr
- && sc.block == nullptr
- && sc.line_entry.IsValid() == false)
- {
- if (sc.symbol->ValueIsAddress())
- {
- for (pos = m_symbol_contexts.begin(); pos != end; ++pos)
- {
- // Don't merge symbols into inlined function symbol contexts
- if (pos->block && pos->block->GetContainingInlinedBlock())
- continue;
-
- if (pos->function)
- {
- if (pos->function->GetAddressRange().GetBaseAddress() == sc.symbol->GetAddressRef())
- {
- // Do we already have a function with this symbol?
- if (pos->symbol == sc.symbol)
- return false;
- if (pos->symbol == nullptr)
- {
- pos->symbol = sc.symbol;
- return false;
- }
- }
- }
- }
- }
- }
- m_symbol_contexts.push_back(sc);
+void SymbolContextList::Append(const SymbolContextList &sc_list) {
+ collection::const_iterator pos, end = sc_list.m_symbol_contexts.end();
+ for (pos = sc_list.m_symbol_contexts.begin(); pos != end; ++pos)
+ m_symbol_contexts.push_back(*pos);
+}
+
+uint32_t SymbolContextList::AppendIfUnique(const SymbolContextList &sc_list,
+ bool merge_symbol_into_function) {
+ uint32_t unique_sc_add_count = 0;
+ collection::const_iterator pos, end = sc_list.m_symbol_contexts.end();
+ for (pos = sc_list.m_symbol_contexts.begin(); pos != end; ++pos) {
+ if (AppendIfUnique(*pos, merge_symbol_into_function))
+ ++unique_sc_add_count;
+ }
+ return unique_sc_add_count;
+}
+
+bool SymbolContextList::AppendIfUnique(const SymbolContext &sc,
+ bool merge_symbol_into_function) {
+ collection::iterator pos, end = m_symbol_contexts.end();
+ for (pos = m_symbol_contexts.begin(); pos != end; ++pos) {
+ if (*pos == sc)
+ return false;
+ }
+ if (merge_symbol_into_function && sc.symbol != nullptr &&
+ sc.comp_unit == nullptr && sc.function == nullptr &&
+ sc.block == nullptr && sc.line_entry.IsValid() == false) {
+ if (sc.symbol->ValueIsAddress()) {
+ for (pos = m_symbol_contexts.begin(); pos != end; ++pos) {
+ // Don't merge symbols into inlined function symbol contexts
+ if (pos->block && pos->block->GetContainingInlinedBlock())
+ continue;
+
+ if (pos->function) {
+ if (pos->function->GetAddressRange().GetBaseAddress() ==
+ sc.symbol->GetAddressRef()) {
+ // Do we already have a function with this symbol?
+ if (pos->symbol == sc.symbol)
+ return false;
+ if (pos->symbol == nullptr) {
+ pos->symbol = sc.symbol;
+ return false;
+ }
+ }
+ }
+ }
+ }
+ }
+ m_symbol_contexts.push_back(sc);
+ return true;
+}
+
+bool SymbolContextList::MergeSymbolContextIntoFunctionContext(
+ const SymbolContext &symbol_sc, uint32_t start_idx, uint32_t stop_idx) {
+ if (symbol_sc.symbol != nullptr && symbol_sc.comp_unit == nullptr &&
+ symbol_sc.function == nullptr && symbol_sc.block == nullptr &&
+ symbol_sc.line_entry.IsValid() == false) {
+ if (symbol_sc.symbol->ValueIsAddress()) {
+ const size_t end = std::min<size_t>(m_symbol_contexts.size(), stop_idx);
+ for (size_t i = start_idx; i < end; ++i) {
+ const SymbolContext &function_sc = m_symbol_contexts[i];
+ // Don't merge symbols into inlined function symbol contexts
+ if (function_sc.block && function_sc.block->GetContainingInlinedBlock())
+ continue;
+
+ if (function_sc.function) {
+ if (function_sc.function->GetAddressRange().GetBaseAddress() ==
+ symbol_sc.symbol->GetAddressRef()) {
+ // Do we already have a function with this symbol?
+ if (function_sc.symbol == symbol_sc.symbol)
+ return true; // Already have a symbol context with this symbol,
+ // return true
+
+ if (function_sc.symbol == nullptr) {
+ // We successfully merged this symbol into an existing symbol
+ // context
+ m_symbol_contexts[i].symbol = symbol_sc.symbol;
+ return true;
+ }
+ }
+ }
+ }
+ }
+ }
+ return false;
+}
+
+void SymbolContextList::Clear() { m_symbol_contexts.clear(); }
+
+void SymbolContextList::Dump(Stream *s, Target *target) const {
+
+ *s << this << ": ";
+ s->Indent();
+ s->PutCString("SymbolContextList");
+ s->EOL();
+ s->IndentMore();
+
+ collection::const_iterator pos, end = m_symbol_contexts.end();
+ for (pos = m_symbol_contexts.begin(); pos != end; ++pos) {
+ // pos->Dump(s, target);
+ pos->GetDescription(s, eDescriptionLevelVerbose, target);
+ }
+ s->IndentLess();
+}
+
+bool SymbolContextList::GetContextAtIndex(size_t idx, SymbolContext &sc) const {
+ if (idx < m_symbol_contexts.size()) {
+ sc = m_symbol_contexts[idx];
return true;
+ }
+ return false;
}
-bool
-SymbolContextList::MergeSymbolContextIntoFunctionContext (const SymbolContext& symbol_sc,
- uint32_t start_idx,
- uint32_t stop_idx)
-{
- if (symbol_sc.symbol != nullptr
- && symbol_sc.comp_unit == nullptr
- && symbol_sc.function == nullptr
- && symbol_sc.block == nullptr
- && symbol_sc.line_entry.IsValid() == false)
- {
- if (symbol_sc.symbol->ValueIsAddress())
- {
- const size_t end = std::min<size_t>(m_symbol_contexts.size(), stop_idx);
- for (size_t i=start_idx; i<end; ++i)
- {
- const SymbolContext &function_sc = m_symbol_contexts[i];
- // Don't merge symbols into inlined function symbol contexts
- if (function_sc.block && function_sc.block->GetContainingInlinedBlock())
- continue;
-
- if (function_sc.function)
- {
- if (function_sc.function->GetAddressRange().GetBaseAddress() == symbol_sc.symbol->GetAddressRef())
- {
- // Do we already have a function with this symbol?
- if (function_sc.symbol == symbol_sc.symbol)
- return true; // Already have a symbol context with this symbol, return true
-
- if (function_sc.symbol == nullptr)
- {
- // We successfully merged this symbol into an existing symbol context
- m_symbol_contexts[i].symbol = symbol_sc.symbol;
- return true;
- }
- }
- }
- }
- }
- }
- return false;
+bool SymbolContextList::GetLastContext(SymbolContext &sc) const {
+ if (!m_symbol_contexts.empty()) {
+ sc = m_symbol_contexts.back();
+ return true;
+ }
+ return false;
}
-void
-SymbolContextList::Clear()
-{
- m_symbol_contexts.clear();
+bool SymbolContextList::RemoveContextAtIndex(size_t idx) {
+ if (idx < m_symbol_contexts.size()) {
+ m_symbol_contexts.erase(m_symbol_contexts.begin() + idx);
+ return true;
+ }
+ return false;
}
-void
-SymbolContextList::Dump(Stream *s, Target *target) const
-{
-
- *s << this << ": ";
- s->Indent();
- s->PutCString("SymbolContextList");
- s->EOL();
- s->IndentMore();
+uint32_t SymbolContextList::GetSize() const { return m_symbol_contexts.size(); }
- collection::const_iterator pos, end = m_symbol_contexts.end();
- for (pos = m_symbol_contexts.begin(); pos != end; ++pos)
- {
- //pos->Dump(s, target);
- pos->GetDescription(s, eDescriptionLevelVerbose, target);
- }
- s->IndentLess();
+uint32_t SymbolContextList::NumLineEntriesWithLine(uint32_t line) const {
+ uint32_t match_count = 0;
+ const size_t size = m_symbol_contexts.size();
+ for (size_t idx = 0; idx < size; ++idx) {
+ if (m_symbol_contexts[idx].line_entry.line == line)
+ ++match_count;
+ }
+ return match_count;
}
-bool
-SymbolContextList::GetContextAtIndex(size_t idx, SymbolContext& sc) const
-{
- if (idx < m_symbol_contexts.size())
- {
- sc = m_symbol_contexts[idx];
- return true;
- }
- return false;
+void SymbolContextList::GetDescription(Stream *s, lldb::DescriptionLevel level,
+ Target *target) const {
+ const size_t size = m_symbol_contexts.size();
+ for (size_t idx = 0; idx < size; ++idx)
+ m_symbol_contexts[idx].GetDescription(s, level, target);
}
-bool
-SymbolContextList::GetLastContext(SymbolContext& sc) const
-{
- if (!m_symbol_contexts.empty())
- {
- sc = m_symbol_contexts.back();
- return true;
- }
+bool lldb_private::operator==(const SymbolContextList &lhs,
+ const SymbolContextList &rhs) {
+ const uint32_t size = lhs.GetSize();
+ if (size != rhs.GetSize())
return false;
-}
-bool
-SymbolContextList::RemoveContextAtIndex (size_t idx)
-{
- if (idx < m_symbol_contexts.size())
- {
- m_symbol_contexts.erase(m_symbol_contexts.begin() + idx);
- return true;
- }
- return false;
-}
-
-uint32_t
-SymbolContextList::GetSize() const
-{
- return m_symbol_contexts.size();
-}
-
-uint32_t
-SymbolContextList::NumLineEntriesWithLine (uint32_t line) const
-{
- uint32_t match_count = 0;
- const size_t size = m_symbol_contexts.size();
- for (size_t idx = 0; idx<size; ++idx)
- {
- if (m_symbol_contexts[idx].line_entry.line == line)
- ++match_count;
- }
- return match_count;
+ SymbolContext lhs_sc;
+ SymbolContext rhs_sc;
+ for (uint32_t i = 0; i < size; ++i) {
+ lhs.GetContextAtIndex(i, lhs_sc);
+ rhs.GetContextAtIndex(i, rhs_sc);
+ if (lhs_sc != rhs_sc)
+ return false;
+ }
+ return true;
}
-void
-SymbolContextList::GetDescription(Stream *s,
- lldb::DescriptionLevel level,
- Target *target) const
-{
- const size_t size = m_symbol_contexts.size();
- for (size_t idx = 0; idx<size; ++idx)
- m_symbol_contexts[idx].GetDescription (s, level, target);
+bool lldb_private::operator!=(const SymbolContextList &lhs,
+ const SymbolContextList &rhs) {
+ return !(lhs == rhs);
}
-
-bool
-lldb_private::operator== (const SymbolContextList& lhs, const SymbolContextList& rhs)
-{
- const uint32_t size = lhs.GetSize();
- if (size != rhs.GetSize())
- return false;
-
- SymbolContext lhs_sc;
- SymbolContext rhs_sc;
- for (uint32_t i=0; i<size; ++i)
- {
- lhs.GetContextAtIndex(i, lhs_sc);
- rhs.GetContextAtIndex(i, rhs_sc);
- if (lhs_sc != rhs_sc)
- return false;
- }
- return true;
-}
-
-bool
-lldb_private::operator!= (const SymbolContextList& lhs, const SymbolContextList& rhs)
-{
- return !(lhs == rhs);
-}
-
Modified: lldb/trunk/source/Symbol/SymbolFile.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/SymbolFile.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/SymbolFile.cpp (original)
+++ lldb/trunk/source/Symbol/SymbolFile.cpp Tue Sep 6 15:57:50 2016
@@ -9,7 +9,6 @@
#include "lldb/Symbol/SymbolFile.h"
-#include "lldb/lldb-private.h"
#include "lldb/Core/Log.h"
#include "lldb/Core/Module.h"
#include "lldb/Core/PluginManager.h"
@@ -18,141 +17,136 @@
#include "lldb/Symbol/TypeMap.h"
#include "lldb/Symbol/TypeSystem.h"
#include "lldb/Symbol/VariableList.h"
+#include "lldb/lldb-private.h"
using namespace lldb_private;
-SymbolFile*
-SymbolFile::FindPlugin (ObjectFile* obj_file)
-{
- std::unique_ptr<SymbolFile> best_symfile_ap;
- if (obj_file != nullptr)
- {
-
- // We need to test the abilities of this section list. So create what it would
- // be with this new obj_file.
- lldb::ModuleSP module_sp(obj_file->GetModule());
- if (module_sp)
- {
- // Default to the main module section list.
- ObjectFile *module_obj_file = module_sp->GetObjectFile();
- if (module_obj_file != obj_file)
- {
- // Make sure the main object file's sections are created
- module_obj_file->GetSectionList();
- obj_file->CreateSections (*module_sp->GetUnifiedSectionList());
- }
- }
+SymbolFile *SymbolFile::FindPlugin(ObjectFile *obj_file) {
+ std::unique_ptr<SymbolFile> best_symfile_ap;
+ if (obj_file != nullptr) {
+
+ // We need to test the abilities of this section list. So create what it
+ // would
+ // be with this new obj_file.
+ lldb::ModuleSP module_sp(obj_file->GetModule());
+ if (module_sp) {
+ // Default to the main module section list.
+ ObjectFile *module_obj_file = module_sp->GetObjectFile();
+ if (module_obj_file != obj_file) {
+ // Make sure the main object file's sections are created
+ module_obj_file->GetSectionList();
+ obj_file->CreateSections(*module_sp->GetUnifiedSectionList());
+ }
+ }
- // TODO: Load any plug-ins in the appropriate plug-in search paths and
- // iterate over all of them to find the best one for the job.
+ // TODO: Load any plug-ins in the appropriate plug-in search paths and
+ // iterate over all of them to find the best one for the job.
- uint32_t best_symfile_abilities = 0;
+ uint32_t best_symfile_abilities = 0;
- SymbolFileCreateInstance create_callback;
- for (uint32_t idx = 0; (create_callback = PluginManager::GetSymbolFileCreateCallbackAtIndex(idx)) != nullptr; ++idx)
- {
- std::unique_ptr<SymbolFile> curr_symfile_ap(create_callback(obj_file));
-
- if (curr_symfile_ap.get())
- {
- const uint32_t sym_file_abilities = curr_symfile_ap->GetAbilities();
- if (sym_file_abilities > best_symfile_abilities)
- {
- best_symfile_abilities = sym_file_abilities;
- best_symfile_ap.reset (curr_symfile_ap.release());
- // If any symbol file parser has all of the abilities, then
- // we should just stop looking.
- if ((kAllAbilities & sym_file_abilities) == kAllAbilities)
- break;
- }
- }
- }
- if (best_symfile_ap.get())
- {
- // Let the winning symbol file parser initialize itself more
- // completely now that it has been chosen
- best_symfile_ap->InitializeObject();
+ SymbolFileCreateInstance create_callback;
+ for (uint32_t idx = 0;
+ (create_callback = PluginManager::GetSymbolFileCreateCallbackAtIndex(
+ idx)) != nullptr;
+ ++idx) {
+ std::unique_ptr<SymbolFile> curr_symfile_ap(create_callback(obj_file));
+
+ if (curr_symfile_ap.get()) {
+ const uint32_t sym_file_abilities = curr_symfile_ap->GetAbilities();
+ if (sym_file_abilities > best_symfile_abilities) {
+ best_symfile_abilities = sym_file_abilities;
+ best_symfile_ap.reset(curr_symfile_ap.release());
+ // If any symbol file parser has all of the abilities, then
+ // we should just stop looking.
+ if ((kAllAbilities & sym_file_abilities) == kAllAbilities)
+ break;
}
+ }
}
- return best_symfile_ap.release();
-}
-
-TypeList *
-SymbolFile::GetTypeList ()
-{
- if (m_obj_file)
- return m_obj_file->GetModule()->GetTypeList();
- return nullptr;
-}
-
-TypeSystem *
-SymbolFile::GetTypeSystemForLanguage (lldb::LanguageType language)
-{
- TypeSystem *type_system = m_obj_file->GetModule()->GetTypeSystemForLanguage(language);
- if (type_system)
- type_system->SetSymbolFile(this);
- return type_system;
-}
-
-uint32_t
-SymbolFile::ResolveSymbolContext (const FileSpec& file_spec, uint32_t line, bool check_inlines, uint32_t resolve_scope, SymbolContextList& sc_list)
-{
- return 0;
-}
-
-
-uint32_t
-SymbolFile::FindGlobalVariables (const ConstString &name, const CompilerDeclContext *parent_decl_ctx, bool append, uint32_t max_matches, VariableList& variables)
-{
- if (!append)
- variables.Clear();
- return 0;
-}
-
-
-uint32_t
-SymbolFile::FindGlobalVariables (const RegularExpression& regex, bool append, uint32_t max_matches, VariableList& variables)
-{
- if (!append)
- variables.Clear();
- return 0;
-}
-
-uint32_t
-SymbolFile::FindFunctions (const ConstString &name, const CompilerDeclContext *parent_decl_ctx, uint32_t name_type_mask, bool include_inlines, bool append, SymbolContextList& sc_list)
-{
- if (!append)
- sc_list.Clear();
- return 0;
-}
-
-uint32_t
-SymbolFile::FindFunctions (const RegularExpression& regex, bool include_inlines, bool append, SymbolContextList& sc_list)
-{
- if (!append)
- sc_list.Clear();
- return 0;
-}
-
-void
-SymbolFile::GetMangledNamesForFunction(const std::string &scope_qualified_name, std::vector<ConstString> &mangled_names)
-{
- return;
-}
-
-uint32_t
-SymbolFile::FindTypes (const SymbolContext& sc, const ConstString &name, const CompilerDeclContext *parent_decl_ctx, bool append, uint32_t max_matches, llvm::DenseSet<lldb_private::SymbolFile *> &searched_symbol_files, TypeMap& types)
-{
- if (!append)
- types.Clear();
- return 0;
+ if (best_symfile_ap.get()) {
+ // Let the winning symbol file parser initialize itself more
+ // completely now that it has been chosen
+ best_symfile_ap->InitializeObject();
+ }
+ }
+ return best_symfile_ap.release();
}
-
-size_t
-SymbolFile::FindTypes (const std::vector<CompilerContext> &context, bool append, TypeMap& types)
-{
- if (!append)
- types.Clear();
- return 0;
+TypeList *SymbolFile::GetTypeList() {
+ if (m_obj_file)
+ return m_obj_file->GetModule()->GetTypeList();
+ return nullptr;
+}
+
+TypeSystem *SymbolFile::GetTypeSystemForLanguage(lldb::LanguageType language) {
+ TypeSystem *type_system =
+ m_obj_file->GetModule()->GetTypeSystemForLanguage(language);
+ if (type_system)
+ type_system->SetSymbolFile(this);
+ return type_system;
+}
+
+uint32_t SymbolFile::ResolveSymbolContext(const FileSpec &file_spec,
+ uint32_t line, bool check_inlines,
+ uint32_t resolve_scope,
+ SymbolContextList &sc_list) {
+ return 0;
+}
+
+uint32_t SymbolFile::FindGlobalVariables(
+ const ConstString &name, const CompilerDeclContext *parent_decl_ctx,
+ bool append, uint32_t max_matches, VariableList &variables) {
+ if (!append)
+ variables.Clear();
+ return 0;
+}
+
+uint32_t SymbolFile::FindGlobalVariables(const RegularExpression ®ex,
+ bool append, uint32_t max_matches,
+ VariableList &variables) {
+ if (!append)
+ variables.Clear();
+ return 0;
+}
+
+uint32_t SymbolFile::FindFunctions(const ConstString &name,
+ const CompilerDeclContext *parent_decl_ctx,
+ uint32_t name_type_mask,
+ bool include_inlines, bool append,
+ SymbolContextList &sc_list) {
+ if (!append)
+ sc_list.Clear();
+ return 0;
+}
+
+uint32_t SymbolFile::FindFunctions(const RegularExpression ®ex,
+ bool include_inlines, bool append,
+ SymbolContextList &sc_list) {
+ if (!append)
+ sc_list.Clear();
+ return 0;
+}
+
+void SymbolFile::GetMangledNamesForFunction(
+ const std::string &scope_qualified_name,
+ std::vector<ConstString> &mangled_names) {
+ return;
+}
+
+uint32_t SymbolFile::FindTypes(
+ const SymbolContext &sc, const ConstString &name,
+ const CompilerDeclContext *parent_decl_ctx, bool append,
+ uint32_t max_matches,
+ llvm::DenseSet<lldb_private::SymbolFile *> &searched_symbol_files,
+ TypeMap &types) {
+ if (!append)
+ types.Clear();
+ return 0;
+}
+
+size_t SymbolFile::FindTypes(const std::vector<CompilerContext> &context,
+ bool append, TypeMap &types) {
+ if (!append)
+ types.Clear();
+ return 0;
}
Modified: lldb/trunk/source/Symbol/SymbolVendor.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/SymbolVendor.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/SymbolVendor.cpp (original)
+++ lldb/trunk/source/Symbol/SymbolVendor.cpp Tue Sep 6 15:57:50 2016
@@ -23,7 +23,6 @@
using namespace lldb;
using namespace lldb_private;
-
//----------------------------------------------------------------------
// FindPlugin
//
@@ -31,547 +30,455 @@ using namespace lldb_private;
// vendors to allow for complex debug information file setups, and to
// also allow for finding separate debug information files.
//----------------------------------------------------------------------
-SymbolVendor*
-SymbolVendor::FindPlugin (const lldb::ModuleSP &module_sp, lldb_private::Stream *feedback_strm)
-{
- std::unique_ptr<SymbolVendor> instance_ap;
- SymbolVendorCreateInstance create_callback;
-
- for (size_t idx = 0; (create_callback = PluginManager::GetSymbolVendorCreateCallbackAtIndex(idx)) != nullptr; ++idx)
- {
- instance_ap.reset(create_callback(module_sp, feedback_strm));
-
- if (instance_ap.get())
- {
- return instance_ap.release();
- }
- }
- // The default implementation just tries to create debug information using the
- // file representation for the module.
- instance_ap.reset(new SymbolVendor(module_sp));
- if (instance_ap.get())
- {
- ObjectFile *objfile = module_sp->GetObjectFile();
- if (objfile)
- instance_ap->AddSymbolFileRepresentation(objfile->shared_from_this());
- }
- return instance_ap.release();
+SymbolVendor *SymbolVendor::FindPlugin(const lldb::ModuleSP &module_sp,
+ lldb_private::Stream *feedback_strm) {
+ std::unique_ptr<SymbolVendor> instance_ap;
+ SymbolVendorCreateInstance create_callback;
+
+ for (size_t idx = 0;
+ (create_callback = PluginManager::GetSymbolVendorCreateCallbackAtIndex(
+ idx)) != nullptr;
+ ++idx) {
+ instance_ap.reset(create_callback(module_sp, feedback_strm));
+
+ if (instance_ap.get()) {
+ return instance_ap.release();
+ }
+ }
+ // The default implementation just tries to create debug information using the
+ // file representation for the module.
+ instance_ap.reset(new SymbolVendor(module_sp));
+ if (instance_ap.get()) {
+ ObjectFile *objfile = module_sp->GetObjectFile();
+ if (objfile)
+ instance_ap->AddSymbolFileRepresentation(objfile->shared_from_this());
+ }
+ return instance_ap.release();
}
//----------------------------------------------------------------------
// SymbolVendor constructor
//----------------------------------------------------------------------
-SymbolVendor::SymbolVendor(const lldb::ModuleSP &module_sp) :
- ModuleChild (module_sp),
- m_type_list(),
- m_compile_units(),
- m_sym_file_ap()
-{
-}
+SymbolVendor::SymbolVendor(const lldb::ModuleSP &module_sp)
+ : ModuleChild(module_sp), m_type_list(), m_compile_units(),
+ m_sym_file_ap() {}
//----------------------------------------------------------------------
// Destructor
//----------------------------------------------------------------------
-SymbolVendor::~SymbolVendor()
-{
-}
+SymbolVendor::~SymbolVendor() {}
//----------------------------------------------------------------------
// Add a representation given an object file.
//----------------------------------------------------------------------
-void
-SymbolVendor::AddSymbolFileRepresentation(const ObjectFileSP &objfile_sp)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (objfile_sp)
- {
- m_objfile_sp = objfile_sp;
- m_sym_file_ap.reset(SymbolFile::FindPlugin(objfile_sp.get()));
- }
+void SymbolVendor::AddSymbolFileRepresentation(const ObjectFileSP &objfile_sp) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (objfile_sp) {
+ m_objfile_sp = objfile_sp;
+ m_sym_file_ap.reset(SymbolFile::FindPlugin(objfile_sp.get()));
+ }
+ }
+}
+
+bool SymbolVendor::SetCompileUnitAtIndex(size_t idx, const CompUnitSP &cu_sp) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ const size_t num_compile_units = GetNumCompileUnits();
+ if (idx < num_compile_units) {
+ // Fire off an assertion if this compile unit already exists for now.
+ // The partial parsing should take care of only setting the compile
+ // unit once, so if this assertion fails, we need to make sure that
+ // we don't have a race condition, or have a second parse of the same
+ // compile unit.
+ assert(m_compile_units[idx].get() == nullptr);
+ m_compile_units[idx] = cu_sp;
+ return true;
+ } else {
+ // This should NOT happen, and if it does, we want to crash and know
+ // about it
+ assert(idx < num_compile_units);
+ }
+ }
+ return false;
+}
+
+size_t SymbolVendor::GetNumCompileUnits() {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_compile_units.empty()) {
+ if (m_sym_file_ap.get()) {
+ // Resize our array of compile unit shared pointers -- which will
+ // each remain NULL until someone asks for the actual compile unit
+ // information. When this happens, the symbol file will be asked
+ // to parse this compile unit information.
+ m_compile_units.resize(m_sym_file_ap->GetNumCompileUnits());
+ }
}
+ }
+ return m_compile_units.size();
}
-bool
-SymbolVendor::SetCompileUnitAtIndex (size_t idx, const CompUnitSP &cu_sp)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- const size_t num_compile_units = GetNumCompileUnits();
- if (idx < num_compile_units)
- {
- // Fire off an assertion if this compile unit already exists for now.
- // The partial parsing should take care of only setting the compile
- // unit once, so if this assertion fails, we need to make sure that
- // we don't have a race condition, or have a second parse of the same
- // compile unit.
- assert(m_compile_units[idx].get() == nullptr);
- m_compile_units[idx] = cu_sp;
- return true;
- }
- else
- {
- // This should NOT happen, and if it does, we want to crash and know
- // about it
- assert (idx < num_compile_units);
- }
- }
- return false;
+lldb::LanguageType
+SymbolVendor::ParseCompileUnitLanguage(const SymbolContext &sc) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->ParseCompileUnitLanguage(sc);
+ }
+ return eLanguageTypeUnknown;
}
-size_t
-SymbolVendor::GetNumCompileUnits()
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_compile_units.empty())
- {
- if (m_sym_file_ap.get())
- {
- // Resize our array of compile unit shared pointers -- which will
- // each remain NULL until someone asks for the actual compile unit
- // information. When this happens, the symbol file will be asked
- // to parse this compile unit information.
- m_compile_units.resize(m_sym_file_ap->GetNumCompileUnits());
- }
- }
- }
- return m_compile_units.size();
+size_t SymbolVendor::ParseCompileUnitFunctions(const SymbolContext &sc) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->ParseCompileUnitFunctions(sc);
+ }
+ return 0;
}
-lldb::LanguageType
-SymbolVendor::ParseCompileUnitLanguage (const SymbolContext& sc)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->ParseCompileUnitLanguage(sc);
- }
- return eLanguageTypeUnknown;
-}
-
-
-size_t
-SymbolVendor::ParseCompileUnitFunctions (const SymbolContext &sc)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->ParseCompileUnitFunctions(sc);
- }
- return 0;
-}
-
-bool
-SymbolVendor::ParseCompileUnitLineTable (const SymbolContext &sc)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->ParseCompileUnitLineTable(sc);
- }
- return false;
-}
-
-bool
-SymbolVendor::ParseCompileUnitDebugMacros (const SymbolContext &sc)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->ParseCompileUnitDebugMacros(sc);
- }
- return false;
-}
-bool
-SymbolVendor::ParseCompileUnitSupportFiles (const SymbolContext& sc, FileSpecList& support_files)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->ParseCompileUnitSupportFiles(sc, support_files);
- }
- return false;
-}
-
-bool
-SymbolVendor::ParseCompileUnitIsOptimized(const SymbolContext &sc)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->ParseCompileUnitIsOptimized(sc);
- }
- return false;
-}
-
-bool
-SymbolVendor::ParseImportedModules(const SymbolContext &sc, std::vector<ConstString> &imported_modules)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->ParseImportedModules(sc, imported_modules);
- }
- return false;
-
-}
-
-size_t
-SymbolVendor::ParseFunctionBlocks (const SymbolContext &sc)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->ParseFunctionBlocks(sc);
- }
- return 0;
-}
-
-size_t
-SymbolVendor::ParseTypes (const SymbolContext &sc)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->ParseTypes(sc);
- }
- return 0;
-}
-
-size_t
-SymbolVendor::ParseVariablesForContext (const SymbolContext& sc)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->ParseVariablesForContext(sc);
- }
- return 0;
-}
-
-Type*
-SymbolVendor::ResolveTypeUID(lldb::user_id_t type_uid)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->ResolveTypeUID(type_uid);
- }
- return nullptr;
-}
-
-
-uint32_t
-SymbolVendor::ResolveSymbolContext (const Address& so_addr, uint32_t resolve_scope, SymbolContext& sc)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->ResolveSymbolContext(so_addr, resolve_scope, sc);
- }
- return 0;
-}
-
-uint32_t
-SymbolVendor::ResolveSymbolContext (const FileSpec& file_spec, uint32_t line, bool check_inlines, uint32_t resolve_scope, SymbolContextList& sc_list)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->ResolveSymbolContext(file_spec, line, check_inlines, resolve_scope, sc_list);
- }
- return 0;
-}
-
-size_t
-SymbolVendor::FindGlobalVariables (const ConstString &name, const CompilerDeclContext *parent_decl_ctx, bool append, size_t max_matches, VariableList& variables)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->FindGlobalVariables(name, parent_decl_ctx, append, max_matches, variables);
- }
- return 0;
-}
-
-size_t
-SymbolVendor::FindGlobalVariables (const RegularExpression& regex, bool append, size_t max_matches, VariableList& variables)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->FindGlobalVariables(regex, append, max_matches, variables);
- }
- return 0;
-}
-
-size_t
-SymbolVendor::FindFunctions(const ConstString &name, const CompilerDeclContext *parent_decl_ctx, uint32_t name_type_mask, bool include_inlines, bool append, SymbolContextList& sc_list)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->FindFunctions(name, parent_decl_ctx, name_type_mask, include_inlines, append, sc_list);
- }
- return 0;
-}
-
-size_t
-SymbolVendor::FindFunctions(const RegularExpression& regex, bool include_inlines, bool append, SymbolContextList& sc_list)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->FindFunctions(regex, include_inlines, append, sc_list);
- }
- return 0;
-}
-
-
-size_t
-SymbolVendor::FindTypes (const SymbolContext& sc, const ConstString &name, const CompilerDeclContext *parent_decl_ctx, bool append, size_t max_matches, llvm::DenseSet<lldb_private::SymbolFile *> &searched_symbol_files, TypeMap& types)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->FindTypes(sc, name, parent_decl_ctx, append, max_matches, searched_symbol_files, types);
- }
- if (!append)
- types.Clear();
- return 0;
-}
-
-size_t
-SymbolVendor::FindTypes (const std::vector<CompilerContext> &context, bool append, TypeMap& types)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->FindTypes(context, append, types);
- }
- if (!append)
- types.Clear();
- return 0;
-}
-
-size_t
-SymbolVendor::GetTypes (SymbolContextScope *sc_scope,
- uint32_t type_mask,
- lldb_private::TypeList &type_list)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- return m_sym_file_ap->GetTypes (sc_scope, type_mask, type_list);
- }
- return 0;
+bool SymbolVendor::ParseCompileUnitLineTable(const SymbolContext &sc) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->ParseCompileUnitLineTable(sc);
+ }
+ return false;
}
-CompilerDeclContext
-SymbolVendor::FindNamespace(const SymbolContext& sc, const ConstString &name, const CompilerDeclContext *parent_decl_ctx)
-{
- CompilerDeclContext namespace_decl_ctx;
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- if (m_sym_file_ap.get())
- namespace_decl_ctx = m_sym_file_ap->FindNamespace (sc, name, parent_decl_ctx);
- }
- return namespace_decl_ctx;
-}
-
-void
-SymbolVendor::Dump(Stream *s)
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
-
- bool show_context = false;
-
- s->Printf("%p: ", static_cast<void*>(this));
- s->Indent();
- s->PutCString("SymbolVendor");
- if (m_sym_file_ap.get())
- {
- ObjectFile *objfile = m_sym_file_ap->GetObjectFile();
- if (objfile)
- {
- const FileSpec &objfile_file_spec = objfile->GetFileSpec();
- if (objfile_file_spec)
- {
- s->PutCString(" (");
- objfile_file_spec.Dump(s);
- s->PutChar(')');
- }
- }
- }
- s->EOL();
- s->IndentMore();
- m_type_list.Dump(s, show_context);
-
- CompileUnitConstIter cu_pos, cu_end;
- cu_end = m_compile_units.end();
- for (cu_pos = m_compile_units.begin(); cu_pos != cu_end; ++cu_pos)
- {
- // We currently only dump the compile units that have been parsed
- if (cu_pos->get())
- (*cu_pos)->Dump(s, show_context);
- }
+bool SymbolVendor::ParseCompileUnitDebugMacros(const SymbolContext &sc) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->ParseCompileUnitDebugMacros(sc);
+ }
+ return false;
+}
+bool SymbolVendor::ParseCompileUnitSupportFiles(const SymbolContext &sc,
+ FileSpecList &support_files) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->ParseCompileUnitSupportFiles(sc, support_files);
+ }
+ return false;
+}
- s->IndentLess();
- }
+bool SymbolVendor::ParseCompileUnitIsOptimized(const SymbolContext &sc) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->ParseCompileUnitIsOptimized(sc);
+ }
+ return false;
}
-CompUnitSP
-SymbolVendor::GetCompileUnitAtIndex(size_t idx)
-{
- CompUnitSP cu_sp;
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
- const size_t num_compile_units = GetNumCompileUnits();
- if (idx < num_compile_units)
- {
- cu_sp = m_compile_units[idx];
- if (cu_sp.get() == nullptr)
- {
- m_compile_units[idx] = m_sym_file_ap->ParseCompileUnitAtIndex(idx);
- cu_sp = m_compile_units[idx];
- }
- }
- }
- return cu_sp;
+bool SymbolVendor::ParseImportedModules(
+ const SymbolContext &sc, std::vector<ConstString> &imported_modules) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->ParseImportedModules(sc, imported_modules);
+ }
+ return false;
}
-FileSpec
-SymbolVendor::GetMainFileSpec() const
-{
+size_t SymbolVendor::ParseFunctionBlocks(const SymbolContext &sc) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
if (m_sym_file_ap.get())
- {
- const ObjectFile *symfile_objfile = m_sym_file_ap->GetObjectFile();
- if (symfile_objfile)
- return symfile_objfile->GetFileSpec();
- }
+ return m_sym_file_ap->ParseFunctionBlocks(sc);
+ }
+ return 0;
+}
- return FileSpec();
+size_t SymbolVendor::ParseTypes(const SymbolContext &sc) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->ParseTypes(sc);
+ }
+ return 0;
}
-Symtab *
-SymbolVendor::GetSymtab ()
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- ObjectFile *objfile = module_sp->GetObjectFile();
- if (objfile)
- {
- // Get symbol table from unified section list.
- return objfile->GetSymtab ();
- }
- }
- return nullptr;
+size_t SymbolVendor::ParseVariablesForContext(const SymbolContext &sc) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->ParseVariablesForContext(sc);
+ }
+ return 0;
}
-void
-SymbolVendor::ClearSymtab()
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- ObjectFile *objfile = module_sp->GetObjectFile();
- if (objfile)
- {
- // Clear symbol table from unified section list.
- objfile->ClearSymtab ();
- }
- }
+Type *SymbolVendor::ResolveTypeUID(lldb::user_id_t type_uid) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->ResolveTypeUID(type_uid);
+ }
+ return nullptr;
}
-void
-SymbolVendor::SectionFileAddressesChanged ()
-{
- ModuleSP module_sp(GetModule());
- if (module_sp)
- {
- ObjectFile *module_objfile = module_sp->GetObjectFile ();
- if (m_sym_file_ap.get())
- {
- ObjectFile *symfile_objfile = m_sym_file_ap->GetObjectFile ();
- if (symfile_objfile != module_objfile)
- symfile_objfile->SectionFileAddressesChanged ();
- }
- Symtab *symtab = GetSymtab ();
- if (symtab)
- {
- symtab->SectionFileAddressesChanged ();
- }
+uint32_t SymbolVendor::ResolveSymbolContext(const Address &so_addr,
+ uint32_t resolve_scope,
+ SymbolContext &sc) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->ResolveSymbolContext(so_addr, resolve_scope, sc);
+ }
+ return 0;
+}
+
+uint32_t SymbolVendor::ResolveSymbolContext(const FileSpec &file_spec,
+ uint32_t line, bool check_inlines,
+ uint32_t resolve_scope,
+ SymbolContextList &sc_list) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->ResolveSymbolContext(file_spec, line, check_inlines,
+ resolve_scope, sc_list);
+ }
+ return 0;
+}
+
+size_t SymbolVendor::FindGlobalVariables(
+ const ConstString &name, const CompilerDeclContext *parent_decl_ctx,
+ bool append, size_t max_matches, VariableList &variables) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->FindGlobalVariables(name, parent_decl_ctx, append,
+ max_matches, variables);
+ }
+ return 0;
+}
+
+size_t SymbolVendor::FindGlobalVariables(const RegularExpression ®ex,
+ bool append, size_t max_matches,
+ VariableList &variables) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->FindGlobalVariables(regex, append, max_matches,
+ variables);
+ }
+ return 0;
+}
+
+size_t SymbolVendor::FindFunctions(const ConstString &name,
+ const CompilerDeclContext *parent_decl_ctx,
+ uint32_t name_type_mask,
+ bool include_inlines, bool append,
+ SymbolContextList &sc_list) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->FindFunctions(name, parent_decl_ctx, name_type_mask,
+ include_inlines, append, sc_list);
+ }
+ return 0;
+}
+
+size_t SymbolVendor::FindFunctions(const RegularExpression ®ex,
+ bool include_inlines, bool append,
+ SymbolContextList &sc_list) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->FindFunctions(regex, include_inlines, append,
+ sc_list);
+ }
+ return 0;
+}
+
+size_t SymbolVendor::FindTypes(
+ const SymbolContext &sc, const ConstString &name,
+ const CompilerDeclContext *parent_decl_ctx, bool append, size_t max_matches,
+ llvm::DenseSet<lldb_private::SymbolFile *> &searched_symbol_files,
+ TypeMap &types) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->FindTypes(sc, name, parent_decl_ctx, append,
+ max_matches, searched_symbol_files,
+ types);
+ }
+ if (!append)
+ types.Clear();
+ return 0;
+}
+
+size_t SymbolVendor::FindTypes(const std::vector<CompilerContext> &context,
+ bool append, TypeMap &types) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->FindTypes(context, append, types);
+ }
+ if (!append)
+ types.Clear();
+ return 0;
+}
+
+size_t SymbolVendor::GetTypes(SymbolContextScope *sc_scope, uint32_t type_mask,
+ lldb_private::TypeList &type_list) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ return m_sym_file_ap->GetTypes(sc_scope, type_mask, type_list);
+ }
+ return 0;
+}
+
+CompilerDeclContext
+SymbolVendor::FindNamespace(const SymbolContext &sc, const ConstString &name,
+ const CompilerDeclContext *parent_decl_ctx) {
+ CompilerDeclContext namespace_decl_ctx;
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ if (m_sym_file_ap.get())
+ namespace_decl_ctx =
+ m_sym_file_ap->FindNamespace(sc, name, parent_decl_ctx);
+ }
+ return namespace_decl_ctx;
+}
+
+void SymbolVendor::Dump(Stream *s) {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+
+ bool show_context = false;
+
+ s->Printf("%p: ", static_cast<void *>(this));
+ s->Indent();
+ s->PutCString("SymbolVendor");
+ if (m_sym_file_ap.get()) {
+ ObjectFile *objfile = m_sym_file_ap->GetObjectFile();
+ if (objfile) {
+ const FileSpec &objfile_file_spec = objfile->GetFileSpec();
+ if (objfile_file_spec) {
+ s->PutCString(" (");
+ objfile_file_spec.Dump(s);
+ s->PutChar(')');
+ }
+ }
+ }
+ s->EOL();
+ s->IndentMore();
+ m_type_list.Dump(s, show_context);
+
+ CompileUnitConstIter cu_pos, cu_end;
+ cu_end = m_compile_units.end();
+ for (cu_pos = m_compile_units.begin(); cu_pos != cu_end; ++cu_pos) {
+ // We currently only dump the compile units that have been parsed
+ if (cu_pos->get())
+ (*cu_pos)->Dump(s, show_context);
+ }
+
+ s->IndentLess();
+ }
+}
+
+CompUnitSP SymbolVendor::GetCompileUnitAtIndex(size_t idx) {
+ CompUnitSP cu_sp;
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ std::lock_guard<std::recursive_mutex> guard(module_sp->GetMutex());
+ const size_t num_compile_units = GetNumCompileUnits();
+ if (idx < num_compile_units) {
+ cu_sp = m_compile_units[idx];
+ if (cu_sp.get() == nullptr) {
+ m_compile_units[idx] = m_sym_file_ap->ParseCompileUnitAtIndex(idx);
+ cu_sp = m_compile_units[idx];
+ }
+ }
+ }
+ return cu_sp;
+}
+
+FileSpec SymbolVendor::GetMainFileSpec() const {
+ if (m_sym_file_ap.get()) {
+ const ObjectFile *symfile_objfile = m_sym_file_ap->GetObjectFile();
+ if (symfile_objfile)
+ return symfile_objfile->GetFileSpec();
+ }
+
+ return FileSpec();
+}
+
+Symtab *SymbolVendor::GetSymtab() {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ ObjectFile *objfile = module_sp->GetObjectFile();
+ if (objfile) {
+ // Get symbol table from unified section list.
+ return objfile->GetSymtab();
+ }
+ }
+ return nullptr;
+}
+
+void SymbolVendor::ClearSymtab() {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ ObjectFile *objfile = module_sp->GetObjectFile();
+ if (objfile) {
+ // Clear symbol table from unified section list.
+ objfile->ClearSymtab();
+ }
+ }
+}
+
+void SymbolVendor::SectionFileAddressesChanged() {
+ ModuleSP module_sp(GetModule());
+ if (module_sp) {
+ ObjectFile *module_objfile = module_sp->GetObjectFile();
+ if (m_sym_file_ap.get()) {
+ ObjectFile *symfile_objfile = m_sym_file_ap->GetObjectFile();
+ if (symfile_objfile != module_objfile)
+ symfile_objfile->SectionFileAddressesChanged();
+ }
+ Symtab *symtab = GetSymtab();
+ if (symtab) {
+ symtab->SectionFileAddressesChanged();
}
+ }
}
//------------------------------------------------------------------
// PluginInterface protocol
//------------------------------------------------------------------
-lldb_private::ConstString
-SymbolVendor::GetPluginName()
-{
- static ConstString g_name("vendor-default");
- return g_name;
-}
-
-uint32_t
-SymbolVendor::GetPluginVersion()
-{
- return 1;
+lldb_private::ConstString SymbolVendor::GetPluginName() {
+ static ConstString g_name("vendor-default");
+ return g_name;
}
+uint32_t SymbolVendor::GetPluginVersion() { return 1; }
Modified: lldb/trunk/source/Symbol/Symtab.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/Symtab.cpp?rev=280751&r1=280750&r2=280751&view=diff
==============================================================================
--- lldb/trunk/source/Symbol/Symtab.cpp (original)
+++ lldb/trunk/source/Symbol/Symtab.cpp Tue Sep 6 15:57:50 2016
@@ -10,6 +10,8 @@
#include <map>
#include <set>
+#include "Plugins/Language/CPlusPlus/CPlusPlusLanguage.h"
+#include "Plugins/Language/ObjC/ObjCLanguage.h"
#include "lldb/Core/Module.h"
#include "lldb/Core/RegularExpression.h"
#include "lldb/Core/Section.h"
@@ -19,1244 +21,1147 @@
#include "lldb/Symbol/Symbol.h"
#include "lldb/Symbol/SymbolContext.h"
#include "lldb/Symbol/Symtab.h"
-#include "Plugins/Language/ObjC/ObjCLanguage.h"
-#include "Plugins/Language/CPlusPlus/CPlusPlusLanguage.h"
using namespace lldb;
using namespace lldb_private;
Symtab::Symtab(ObjectFile *objfile)
- : m_objfile(objfile),
- m_symbols(),
- m_file_addr_to_index(),
- m_name_to_index(),
- m_mutex(),
- m_file_addr_to_index_computed(false),
- m_name_indexes_computed(false)
-{
-}
-
-Symtab::~Symtab()
-{
-}
-
-void
-Symtab::Reserve(size_t count)
-{
- // Clients should grab the mutex from this symbol table and lock it manually
- // when calling this function to avoid performance issues.
- m_symbols.reserve (count);
-}
-
-Symbol *
-Symtab::Resize(size_t count)
-{
- // Clients should grab the mutex from this symbol table and lock it manually
- // when calling this function to avoid performance issues.
- m_symbols.resize (count);
- return m_symbols.empty() ? nullptr : &m_symbols[0];
-}
-
-uint32_t
-Symtab::AddSymbol(const Symbol& symbol)
-{
- // Clients should grab the mutex from this symbol table and lock it manually
- // when calling this function to avoid performance issues.
- uint32_t symbol_idx = m_symbols.size();
- m_name_to_index.Clear();
- m_file_addr_to_index.Clear();
- m_symbols.push_back(symbol);
- m_file_addr_to_index_computed = false;
- m_name_indexes_computed = false;
- return symbol_idx;
-}
-
-size_t
-Symtab::GetNumSymbols() const
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
- return m_symbols.size();
-}
-
-void
-Symtab::SectionFileAddressesChanged ()
-{
- m_name_to_index.Clear();
- m_file_addr_to_index_computed = false;
-}
-
-void
-Symtab::Dump (Stream *s, Target *target, SortOrder sort_order)
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- // s->Printf("%.*p: ", (int)sizeof(void*) * 2, this);
- s->Indent();
- const FileSpec &file_spec = m_objfile->GetFileSpec();
- const char * object_name = nullptr;
- if (m_objfile->GetModule())
- object_name = m_objfile->GetModule()->GetObjectName().GetCString();
-
- if (file_spec)
- s->Printf("Symtab, file = %s%s%s%s, num_symbols = %" PRIu64,
- file_spec.GetPath().c_str(),
- object_name ? "(" : "",
- object_name ? object_name : "",
- object_name ? ")" : "",
- (uint64_t)m_symbols.size());
- else
- s->Printf("Symtab, num_symbols = %" PRIu64 "", (uint64_t)m_symbols.size());
-
- if (!m_symbols.empty())
- {
- switch (sort_order)
- {
- case eSortOrderNone:
- {
- s->PutCString (":\n");
- DumpSymbolHeader (s);
- const_iterator begin = m_symbols.begin();
- const_iterator end = m_symbols.end();
- for (const_iterator pos = m_symbols.begin(); pos != end; ++pos)
- {
- s->Indent();
- pos->Dump(s, target, std::distance(begin, pos));
- }
- }
- break;
-
- case eSortOrderByName:
- {
- // Although we maintain a lookup by exact name map, the table
- // isn't sorted by name. So we must make the ordered symbol list
- // up ourselves.
- s->PutCString (" (sorted by name):\n");
- DumpSymbolHeader (s);
- typedef std::multimap<const char*, const Symbol *, CStringCompareFunctionObject> CStringToSymbol;
- CStringToSymbol name_map;
- for (const_iterator pos = m_symbols.begin(), end = m_symbols.end(); pos != end; ++pos)
- {
- const char *name = pos->GetName().AsCString();
- if (name && name[0])
- name_map.insert (std::make_pair(name, &(*pos)));
- }
-
- for (CStringToSymbol::const_iterator pos = name_map.begin(), end = name_map.end(); pos != end; ++pos)
- {
- s->Indent();
- pos->second->Dump (s, target, pos->second - &m_symbols[0]);
- }
- }
- break;
-
- case eSortOrderByAddress:
- s->PutCString (" (sorted by address):\n");
- DumpSymbolHeader (s);
- if (!m_file_addr_to_index_computed)
- InitAddressIndexes();
- const size_t num_entries = m_file_addr_to_index.GetSize();
- for (size_t i=0; i<num_entries; ++i)
- {
- s->Indent();
- const uint32_t symbol_idx = m_file_addr_to_index.GetEntryRef(i).data;
- m_symbols[symbol_idx].Dump(s, target, symbol_idx);
- }
- break;
- }
- }
-}
-
-void
-Symtab::Dump(Stream *s, Target *target, std::vector<uint32_t>& indexes) const
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- const size_t num_symbols = GetNumSymbols();
- //s->Printf("%.*p: ", (int)sizeof(void*) * 2, this);
- s->Indent();
- s->Printf("Symtab %" PRIu64 " symbol indexes (%" PRIu64 " symbols total):\n", (uint64_t)indexes.size(), (uint64_t)m_symbols.size());
- s->IndentMore();
-
- if (!indexes.empty())
- {
- std::vector<uint32_t>::const_iterator pos;
- std::vector<uint32_t>::const_iterator end = indexes.end();
- DumpSymbolHeader (s);
- for (pos = indexes.begin(); pos != end; ++pos)
- {
- size_t idx = *pos;
- if (idx < num_symbols)
- {
- s->Indent();
- m_symbols[idx].Dump(s, target, idx);
- }
- }
- }
- s->IndentLess ();
-}
-
-void
-Symtab::DumpSymbolHeader (Stream *s)
-{
- s->Indent(" Debug symbol\n");
- s->Indent(" |Synthetic symbol\n");
- s->Indent(" ||Externally Visible\n");
- s->Indent(" |||\n");
- s->Indent("Index UserID DSX Type File Address/Value Load Address Size Flags Name\n");
- s->Indent("------- ------ --- --------------- ------------------ ------------------ ------------------ ---------- ----------------------------------\n");
-}
-
-
-static int
-CompareSymbolID (const void *key, const void *p)
-{
- const user_id_t match_uid = *(const user_id_t*) key;
- const user_id_t symbol_uid = ((const Symbol *)p)->GetID();
- if (match_uid < symbol_uid)
- return -1;
- if (match_uid > symbol_uid)
- return 1;
- return 0;
-}
-
-Symbol *
-Symtab::FindSymbolByID (lldb::user_id_t symbol_uid) const
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- Symbol *symbol = (Symbol*)::bsearch (&symbol_uid,
- &m_symbols[0],
- m_symbols.size(),
- sizeof(m_symbols[0]),
- CompareSymbolID);
- return symbol;
-}
-
-
-Symbol *
-Symtab::SymbolAtIndex(size_t idx)
-{
- // Clients should grab the mutex from this symbol table and lock it manually
- // when calling this function to avoid performance issues.
- if (idx < m_symbols.size())
- return &m_symbols[idx];
- return nullptr;
-}
-
-
-const Symbol *
-Symtab::SymbolAtIndex(size_t idx) const
-{
- // Clients should grab the mutex from this symbol table and lock it manually
- // when calling this function to avoid performance issues.
- if (idx < m_symbols.size())
- return &m_symbols[idx];
- return nullptr;
+ : m_objfile(objfile), m_symbols(), m_file_addr_to_index(),
+ m_name_to_index(), m_mutex(), m_file_addr_to_index_computed(false),
+ m_name_indexes_computed(false) {}
+
+Symtab::~Symtab() {}
+
+void Symtab::Reserve(size_t count) {
+ // Clients should grab the mutex from this symbol table and lock it manually
+ // when calling this function to avoid performance issues.
+ m_symbols.reserve(count);
+}
+
+Symbol *Symtab::Resize(size_t count) {
+ // Clients should grab the mutex from this symbol table and lock it manually
+ // when calling this function to avoid performance issues.
+ m_symbols.resize(count);
+ return m_symbols.empty() ? nullptr : &m_symbols[0];
+}
+
+uint32_t Symtab::AddSymbol(const Symbol &symbol) {
+ // Clients should grab the mutex from this symbol table and lock it manually
+ // when calling this function to avoid performance issues.
+ uint32_t symbol_idx = m_symbols.size();
+ m_name_to_index.Clear();
+ m_file_addr_to_index.Clear();
+ m_symbols.push_back(symbol);
+ m_file_addr_to_index_computed = false;
+ m_name_indexes_computed = false;
+ return symbol_idx;
+}
+
+size_t Symtab::GetNumSymbols() const {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+ return m_symbols.size();
+}
+
+void Symtab::SectionFileAddressesChanged() {
+ m_name_to_index.Clear();
+ m_file_addr_to_index_computed = false;
+}
+
+void Symtab::Dump(Stream *s, Target *target, SortOrder sort_order) {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ // s->Printf("%.*p: ", (int)sizeof(void*) * 2, this);
+ s->Indent();
+ const FileSpec &file_spec = m_objfile->GetFileSpec();
+ const char *object_name = nullptr;
+ if (m_objfile->GetModule())
+ object_name = m_objfile->GetModule()->GetObjectName().GetCString();
+
+ if (file_spec)
+ s->Printf("Symtab, file = %s%s%s%s, num_symbols = %" PRIu64,
+ file_spec.GetPath().c_str(), object_name ? "(" : "",
+ object_name ? object_name : "", object_name ? ")" : "",
+ (uint64_t)m_symbols.size());
+ else
+ s->Printf("Symtab, num_symbols = %" PRIu64 "", (uint64_t)m_symbols.size());
+
+ if (!m_symbols.empty()) {
+ switch (sort_order) {
+ case eSortOrderNone: {
+ s->PutCString(":\n");
+ DumpSymbolHeader(s);
+ const_iterator begin = m_symbols.begin();
+ const_iterator end = m_symbols.end();
+ for (const_iterator pos = m_symbols.begin(); pos != end; ++pos) {
+ s->Indent();
+ pos->Dump(s, target, std::distance(begin, pos));
+ }
+ } break;
+
+ case eSortOrderByName: {
+ // Although we maintain a lookup by exact name map, the table
+ // isn't sorted by name. So we must make the ordered symbol list
+ // up ourselves.
+ s->PutCString(" (sorted by name):\n");
+ DumpSymbolHeader(s);
+ typedef std::multimap<const char *, const Symbol *,
+ CStringCompareFunctionObject>
+ CStringToSymbol;
+ CStringToSymbol name_map;
+ for (const_iterator pos = m_symbols.begin(), end = m_symbols.end();
+ pos != end; ++pos) {
+ const char *name = pos->GetName().AsCString();
+ if (name && name[0])
+ name_map.insert(std::make_pair(name, &(*pos)));
+ }
+
+ for (CStringToSymbol::const_iterator pos = name_map.begin(),
+ end = name_map.end();
+ pos != end; ++pos) {
+ s->Indent();
+ pos->second->Dump(s, target, pos->second - &m_symbols[0]);
+ }
+ } break;
+
+ case eSortOrderByAddress:
+ s->PutCString(" (sorted by address):\n");
+ DumpSymbolHeader(s);
+ if (!m_file_addr_to_index_computed)
+ InitAddressIndexes();
+ const size_t num_entries = m_file_addr_to_index.GetSize();
+ for (size_t i = 0; i < num_entries; ++i) {
+ s->Indent();
+ const uint32_t symbol_idx = m_file_addr_to_index.GetEntryRef(i).data;
+ m_symbols[symbol_idx].Dump(s, target, symbol_idx);
+ }
+ break;
+ }
+ }
+}
+
+void Symtab::Dump(Stream *s, Target *target,
+ std::vector<uint32_t> &indexes) const {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ const size_t num_symbols = GetNumSymbols();
+ // s->Printf("%.*p: ", (int)sizeof(void*) * 2, this);
+ s->Indent();
+ s->Printf("Symtab %" PRIu64 " symbol indexes (%" PRIu64 " symbols total):\n",
+ (uint64_t)indexes.size(), (uint64_t)m_symbols.size());
+ s->IndentMore();
+
+ if (!indexes.empty()) {
+ std::vector<uint32_t>::const_iterator pos;
+ std::vector<uint32_t>::const_iterator end = indexes.end();
+ DumpSymbolHeader(s);
+ for (pos = indexes.begin(); pos != end; ++pos) {
+ size_t idx = *pos;
+ if (idx < num_symbols) {
+ s->Indent();
+ m_symbols[idx].Dump(s, target, idx);
+ }
+ }
+ }
+ s->IndentLess();
+}
+
+void Symtab::DumpSymbolHeader(Stream *s) {
+ s->Indent(" Debug symbol\n");
+ s->Indent(" |Synthetic symbol\n");
+ s->Indent(" ||Externally Visible\n");
+ s->Indent(" |||\n");
+ s->Indent("Index UserID DSX Type File Address/Value Load "
+ "Address Size Flags Name\n");
+ s->Indent("------- ------ --- --------------- ------------------ "
+ "------------------ ------------------ ---------- "
+ "----------------------------------\n");
+}
+
+static int CompareSymbolID(const void *key, const void *p) {
+ const user_id_t match_uid = *(const user_id_t *)key;
+ const user_id_t symbol_uid = ((const Symbol *)p)->GetID();
+ if (match_uid < symbol_uid)
+ return -1;
+ if (match_uid > symbol_uid)
+ return 1;
+ return 0;
+}
+
+Symbol *Symtab::FindSymbolByID(lldb::user_id_t symbol_uid) const {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ Symbol *symbol =
+ (Symbol *)::bsearch(&symbol_uid, &m_symbols[0], m_symbols.size(),
+ sizeof(m_symbols[0]), CompareSymbolID);
+ return symbol;
+}
+
+Symbol *Symtab::SymbolAtIndex(size_t idx) {
+ // Clients should grab the mutex from this symbol table and lock it manually
+ // when calling this function to avoid performance issues.
+ if (idx < m_symbols.size())
+ return &m_symbols[idx];
+ return nullptr;
+}
+
+const Symbol *Symtab::SymbolAtIndex(size_t idx) const {
+ // Clients should grab the mutex from this symbol table and lock it manually
+ // when calling this function to avoid performance issues.
+ if (idx < m_symbols.size())
+ return &m_symbols[idx];
+ return nullptr;
}
//----------------------------------------------------------------------
// InitNameIndexes
//----------------------------------------------------------------------
-void
-Symtab::InitNameIndexes()
-{
- // Protected function, no need to lock mutex...
- if (!m_name_indexes_computed)
- {
- m_name_indexes_computed = true;
- Timer scoped_timer (LLVM_PRETTY_FUNCTION, "%s", LLVM_PRETTY_FUNCTION);
- // Create the name index vector to be able to quickly search by name
- const size_t num_symbols = m_symbols.size();
+void Symtab::InitNameIndexes() {
+ // Protected function, no need to lock mutex...
+ if (!m_name_indexes_computed) {
+ m_name_indexes_computed = true;
+ Timer scoped_timer(LLVM_PRETTY_FUNCTION, "%s", LLVM_PRETTY_FUNCTION);
+ // Create the name index vector to be able to quickly search by name
+ const size_t num_symbols = m_symbols.size();
#if 1
- m_name_to_index.Reserve (num_symbols);
+ m_name_to_index.Reserve(num_symbols);
#else
- // TODO: benchmark this to see if we save any memory. Otherwise we
- // will always keep the memory reserved in the vector unless we pull
- // some STL swap magic and then recopy...
- uint32_t actual_count = 0;
- for (const_iterator pos = m_symbols.begin(), end = m_symbols.end();
- pos != end;
- ++pos)
- {
- const Mangled &mangled = pos->GetMangled();
- if (mangled.GetMangledName())
- ++actual_count;
-
- if (mangled.GetDemangledName())
- ++actual_count;
- }
+ // TODO: benchmark this to see if we save any memory. Otherwise we
+ // will always keep the memory reserved in the vector unless we pull
+ // some STL swap magic and then recopy...
+ uint32_t actual_count = 0;
+ for (const_iterator pos = m_symbols.begin(), end = m_symbols.end();
+ pos != end; ++pos) {
+ const Mangled &mangled = pos->GetMangled();
+ if (mangled.GetMangledName())
+ ++actual_count;
+
+ if (mangled.GetDemangledName())
+ ++actual_count;
+ }
- m_name_to_index.Reserve (actual_count);
+ m_name_to_index.Reserve(actual_count);
#endif
- NameToIndexMap::Entry entry;
+ NameToIndexMap::Entry entry;
- // The "const char *" in "class_contexts" must come from a ConstString::GetCString()
- std::set<const char *> class_contexts;
- UniqueCStringMap<uint32_t> mangled_name_to_index;
- std::vector<const char *> symbol_contexts(num_symbols, nullptr);
-
- for (entry.value = 0; entry.value<num_symbols; ++entry.value)
- {
- const Symbol *symbol = &m_symbols[entry.value];
-
- // Don't let trampolines get into the lookup by name map
- // If we ever need the trampoline symbols to be searchable by name
- // we can remove this and then possibly add a new bool to any of the
- // Symtab functions that lookup symbols by name to indicate if they
- // want trampolines.
- if (symbol->IsTrampoline())
- continue;
-
- const Mangled &mangled = symbol->GetMangled();
- entry.cstring = mangled.GetMangledName().GetCString();
- if (entry.cstring && entry.cstring[0])
- {
- m_name_to_index.Append (entry);
-
- if (symbol->ContainsLinkerAnnotations()) {
- // If the symbol has linker annotations, also add the version without the
- // annotations.
- entry.cstring = ConstString(m_objfile->StripLinkerSymbolAnnotations(entry.cstring)).GetCString();
- m_name_to_index.Append (entry);
- }
-
- const SymbolType symbol_type = symbol->GetType();
- if (symbol_type == eSymbolTypeCode || symbol_type == eSymbolTypeResolver)
- {
- if (entry.cstring[0] == '_' && entry.cstring[1] == 'Z' &&
- (entry.cstring[2] != 'T' && // avoid virtual table, VTT structure, typeinfo structure, and typeinfo name
- entry.cstring[2] != 'G' && // avoid guard variables
- entry.cstring[2] != 'Z')) // named local entities (if we eventually handle eSymbolTypeData, we will want this back)
- {
- CPlusPlusLanguage::MethodName cxx_method (mangled.GetDemangledName(lldb::eLanguageTypeC_plus_plus));
- entry.cstring = ConstString(cxx_method.GetBasename()).GetCString();
- if (entry.cstring && entry.cstring[0])
- {
- // ConstString objects permanently store the string in the pool so calling
- // GetCString() on the value gets us a const char * that will never go away
- const char *const_context = ConstString(cxx_method.GetContext()).GetCString();
-
- if (entry.cstring[0] == '~' || !cxx_method.GetQualifiers().empty())
- {
- // The first character of the demangled basename is '~' which
- // means we have a class destructor. We can use this information
- // to help us know what is a class and what isn't.
- if (class_contexts.find(const_context) == class_contexts.end())
- class_contexts.insert(const_context);
- m_method_to_index.Append (entry);
- }
- else
- {
- if (const_context && const_context[0])
- {
- if (class_contexts.find(const_context) != class_contexts.end())
- {
- // The current decl context is in our "class_contexts" which means
- // this is a method on a class
- m_method_to_index.Append (entry);
- }
- else
- {
- // We don't know if this is a function basename or a method,
- // so put it into a temporary collection so once we are done
- // we can look in class_contexts to see if each entry is a class
- // or just a function and will put any remaining items into
- // m_method_to_index or m_basename_to_index as needed
- mangled_name_to_index.Append (entry);
- symbol_contexts[entry.value] = const_context;
- }
- }
- else
- {
- // No context for this function so this has to be a basename
- m_basename_to_index.Append(entry);
- }
- }
- }
- }
- }
- }
-
- entry.cstring = mangled.GetDemangledName(symbol->GetLanguage()).GetCString();
+ // The "const char *" in "class_contexts" must come from a
+ // ConstString::GetCString()
+ std::set<const char *> class_contexts;
+ UniqueCStringMap<uint32_t> mangled_name_to_index;
+ std::vector<const char *> symbol_contexts(num_symbols, nullptr);
+
+ for (entry.value = 0; entry.value < num_symbols; ++entry.value) {
+ const Symbol *symbol = &m_symbols[entry.value];
+
+ // Don't let trampolines get into the lookup by name map
+ // If we ever need the trampoline symbols to be searchable by name
+ // we can remove this and then possibly add a new bool to any of the
+ // Symtab functions that lookup symbols by name to indicate if they
+ // want trampolines.
+ if (symbol->IsTrampoline())
+ continue;
+
+ const Mangled &mangled = symbol->GetMangled();
+ entry.cstring = mangled.GetMangledName().GetCString();
+ if (entry.cstring && entry.cstring[0]) {
+ m_name_to_index.Append(entry);
+
+ if (symbol->ContainsLinkerAnnotations()) {
+ // If the symbol has linker annotations, also add the version without
+ // the
+ // annotations.
+ entry.cstring = ConstString(m_objfile->StripLinkerSymbolAnnotations(
+ entry.cstring))
+ .GetCString();
+ m_name_to_index.Append(entry);
+ }
+
+ const SymbolType symbol_type = symbol->GetType();
+ if (symbol_type == eSymbolTypeCode ||
+ symbol_type == eSymbolTypeResolver) {
+ if (entry.cstring[0] == '_' && entry.cstring[1] == 'Z' &&
+ (entry.cstring[2] != 'T' && // avoid virtual table, VTT structure,
+ // typeinfo structure, and typeinfo
+ // name
+ entry.cstring[2] != 'G' && // avoid guard variables
+ entry.cstring[2] != 'Z')) // named local entities (if we
+ // eventually handle eSymbolTypeData,
+ // we will want this back)
+ {
+ CPlusPlusLanguage::MethodName cxx_method(
+ mangled.GetDemangledName(lldb::eLanguageTypeC_plus_plus));
+ entry.cstring = ConstString(cxx_method.GetBasename()).GetCString();
if (entry.cstring && entry.cstring[0]) {
- m_name_to_index.Append (entry);
-
- if (symbol->ContainsLinkerAnnotations()) {
- // If the symbol has linker annotations, also add the version without the
- // annotations.
- entry.cstring = ConstString(m_objfile->StripLinkerSymbolAnnotations(entry.cstring)).GetCString();
- m_name_to_index.Append (entry);
- }
- }
-
- // If the demangled name turns out to be an ObjC name, and
- // is a category name, add the version without categories to the index too.
- ObjCLanguage::MethodName objc_method (entry.cstring, true);
- if (objc_method.IsValid(true))
- {
- entry.cstring = objc_method.GetSelector().GetCString();
- m_selector_to_index.Append (entry);
-
- ConstString objc_method_no_category (objc_method.GetFullNameWithoutCategory(true));
- if (objc_method_no_category)
- {
- entry.cstring = objc_method_no_category.GetCString();
- m_name_to_index.Append (entry);
- }
- }
-
- }
-
- size_t count;
- if (!mangled_name_to_index.IsEmpty())
- {
- count = mangled_name_to_index.GetSize();
- for (size_t i=0; i<count; ++i)
- {
- if (mangled_name_to_index.GetValueAtIndex(i, entry.value))
- {
- entry.cstring = mangled_name_to_index.GetCStringAtIndex(i);
- if (symbol_contexts[entry.value] && class_contexts.find(symbol_contexts[entry.value]) != class_contexts.end())
- {
- m_method_to_index.Append (entry);
- }
- else
- {
- // If we got here, we have something that had a context (was inside a namespace or class)
- // yet we don't know if the entry
- m_method_to_index.Append (entry);
- m_basename_to_index.Append (entry);
- }
+ // ConstString objects permanently store the string in the pool so
+ // calling
+ // GetCString() on the value gets us a const char * that will
+ // never go away
+ const char *const_context =
+ ConstString(cxx_method.GetContext()).GetCString();
+
+ if (entry.cstring[0] == '~' ||
+ !cxx_method.GetQualifiers().empty()) {
+ // The first character of the demangled basename is '~' which
+ // means we have a class destructor. We can use this information
+ // to help us know what is a class and what isn't.
+ if (class_contexts.find(const_context) == class_contexts.end())
+ class_contexts.insert(const_context);
+ m_method_to_index.Append(entry);
+ } else {
+ if (const_context && const_context[0]) {
+ if (class_contexts.find(const_context) !=
+ class_contexts.end()) {
+ // The current decl context is in our "class_contexts" which
+ // means
+ // this is a method on a class
+ m_method_to_index.Append(entry);
+ } else {
+ // We don't know if this is a function basename or a method,
+ // so put it into a temporary collection so once we are done
+ // we can look in class_contexts to see if each entry is a
+ // class
+ // or just a function and will put any remaining items into
+ // m_method_to_index or m_basename_to_index as needed
+ mangled_name_to_index.Append(entry);
+ symbol_contexts[entry.value] = const_context;
+ }
+ } else {
+ // No context for this function so this has to be a basename
+ m_basename_to_index.Append(entry);
}
+ }
}
+ }
}
- m_name_to_index.Sort();
- m_name_to_index.SizeToFit();
- m_selector_to_index.Sort();
- m_selector_to_index.SizeToFit();
- m_basename_to_index.Sort();
- m_basename_to_index.SizeToFit();
- m_method_to_index.Sort();
- m_method_to_index.SizeToFit();
-
-// static StreamFile a ("/tmp/a.txt");
-//
-// count = m_basename_to_index.GetSize();
-// if (count)
-// {
-// for (size_t i=0; i<count; ++i)
-// {
-// if (m_basename_to_index.GetValueAtIndex(i, entry.value))
-// a.Printf ("%s BASENAME\n", m_symbols[entry.value].GetMangled().GetName().GetCString());
-// }
-// }
-// count = m_method_to_index.GetSize();
-// if (count)
-// {
-// for (size_t i=0; i<count; ++i)
-// {
-// if (m_method_to_index.GetValueAtIndex(i, entry.value))
-// a.Printf ("%s METHOD\n", m_symbols[entry.value].GetMangled().GetName().GetCString());
-// }
-// }
- }
-}
-
-void
-Symtab::AppendSymbolNamesToMap (const IndexCollection &indexes,
- bool add_demangled,
- bool add_mangled,
- NameToIndexMap &name_to_index_map) const
-{
- if (add_demangled || add_mangled)
- {
- Timer scoped_timer (LLVM_PRETTY_FUNCTION, "%s", LLVM_PRETTY_FUNCTION);
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- // Create the name index vector to be able to quickly search by name
- NameToIndexMap::Entry entry;
- const size_t num_indexes = indexes.size();
- for (size_t i=0; i<num_indexes; ++i)
- {
- entry.value = indexes[i];
- assert (i < m_symbols.size());
- const Symbol *symbol = &m_symbols[entry.value];
-
- const Mangled &mangled = symbol->GetMangled();
- if (add_demangled)
- {
- entry.cstring = mangled.GetDemangledName(symbol->GetLanguage()).GetCString();
- if (entry.cstring && entry.cstring[0])
- name_to_index_map.Append (entry);
- }
-
- if (add_mangled)
- {
- entry.cstring = mangled.GetMangledName().GetCString();
- if (entry.cstring && entry.cstring[0])
- name_to_index_map.Append (entry);
- }
- }
- }
-}
-
-uint32_t
-Symtab::AppendSymbolIndexesWithType (SymbolType symbol_type, std::vector<uint32_t>& indexes, uint32_t start_idx, uint32_t end_index) const
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- uint32_t prev_size = indexes.size();
-
- const uint32_t count = std::min<uint32_t> (m_symbols.size(), end_index);
-
- for (uint32_t i = start_idx; i < count; ++i)
- {
- if (symbol_type == eSymbolTypeAny || m_symbols[i].GetType() == symbol_type)
- indexes.push_back(i);
- }
-
- return indexes.size() - prev_size;
-}
-
-uint32_t
-Symtab::AppendSymbolIndexesWithTypeAndFlagsValue (SymbolType symbol_type, uint32_t flags_value, std::vector<uint32_t>& indexes, uint32_t start_idx, uint32_t end_index) const
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- uint32_t prev_size = indexes.size();
-
- const uint32_t count = std::min<uint32_t> (m_symbols.size(), end_index);
-
- for (uint32_t i = start_idx; i < count; ++i)
- {
- if ((symbol_type == eSymbolTypeAny || m_symbols[i].GetType() == symbol_type) && m_symbols[i].GetFlags() == flags_value)
- indexes.push_back(i);
- }
-
- return indexes.size() - prev_size;
-}
-
-uint32_t
-Symtab::AppendSymbolIndexesWithType (SymbolType symbol_type, Debug symbol_debug_type, Visibility symbol_visibility, std::vector<uint32_t>& indexes, uint32_t start_idx, uint32_t end_index) const
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- uint32_t prev_size = indexes.size();
-
- const uint32_t count = std::min<uint32_t> (m_symbols.size(), end_index);
-
- for (uint32_t i = start_idx; i < count; ++i)
- {
- if (symbol_type == eSymbolTypeAny || m_symbols[i].GetType() == symbol_type)
- {
- if (CheckSymbolAtIndex(i, symbol_debug_type, symbol_visibility))
- indexes.push_back(i);
- }
- }
-
- return indexes.size() - prev_size;
-}
-
-
-uint32_t
-Symtab::GetIndexForSymbol (const Symbol *symbol) const
-{
- if (!m_symbols.empty())
- {
- const Symbol *first_symbol = &m_symbols[0];
- if (symbol >= first_symbol && symbol < first_symbol + m_symbols.size())
- return symbol - first_symbol;
- }
- return UINT32_MAX;
-}
+ }
-struct SymbolSortInfo
-{
- const bool sort_by_load_addr;
- const Symbol *symbols;
+ entry.cstring =
+ mangled.GetDemangledName(symbol->GetLanguage()).GetCString();
+ if (entry.cstring && entry.cstring[0]) {
+ m_name_to_index.Append(entry);
+
+ if (symbol->ContainsLinkerAnnotations()) {
+ // If the symbol has linker annotations, also add the version without
+ // the
+ // annotations.
+ entry.cstring = ConstString(m_objfile->StripLinkerSymbolAnnotations(
+ entry.cstring))
+ .GetCString();
+ m_name_to_index.Append(entry);
+ }
+ }
+
+ // If the demangled name turns out to be an ObjC name, and
+ // is a category name, add the version without categories to the index
+ // too.
+ ObjCLanguage::MethodName objc_method(entry.cstring, true);
+ if (objc_method.IsValid(true)) {
+ entry.cstring = objc_method.GetSelector().GetCString();
+ m_selector_to_index.Append(entry);
+
+ ConstString objc_method_no_category(
+ objc_method.GetFullNameWithoutCategory(true));
+ if (objc_method_no_category) {
+ entry.cstring = objc_method_no_category.GetCString();
+ m_name_to_index.Append(entry);
+ }
+ }
+ }
+
+ size_t count;
+ if (!mangled_name_to_index.IsEmpty()) {
+ count = mangled_name_to_index.GetSize();
+ for (size_t i = 0; i < count; ++i) {
+ if (mangled_name_to_index.GetValueAtIndex(i, entry.value)) {
+ entry.cstring = mangled_name_to_index.GetCStringAtIndex(i);
+ if (symbol_contexts[entry.value] &&
+ class_contexts.find(symbol_contexts[entry.value]) !=
+ class_contexts.end()) {
+ m_method_to_index.Append(entry);
+ } else {
+ // If we got here, we have something that had a context (was inside
+ // a namespace or class)
+ // yet we don't know if the entry
+ m_method_to_index.Append(entry);
+ m_basename_to_index.Append(entry);
+ }
+ }
+ }
+ }
+ m_name_to_index.Sort();
+ m_name_to_index.SizeToFit();
+ m_selector_to_index.Sort();
+ m_selector_to_index.SizeToFit();
+ m_basename_to_index.Sort();
+ m_basename_to_index.SizeToFit();
+ m_method_to_index.Sort();
+ m_method_to_index.SizeToFit();
+
+ // static StreamFile a ("/tmp/a.txt");
+ //
+ // count = m_basename_to_index.GetSize();
+ // if (count)
+ // {
+ // for (size_t i=0; i<count; ++i)
+ // {
+ // if (m_basename_to_index.GetValueAtIndex(i, entry.value))
+ // a.Printf ("%s BASENAME\n",
+ // m_symbols[entry.value].GetMangled().GetName().GetCString());
+ // }
+ // }
+ // count = m_method_to_index.GetSize();
+ // if (count)
+ // {
+ // for (size_t i=0; i<count; ++i)
+ // {
+ // if (m_method_to_index.GetValueAtIndex(i, entry.value))
+ // a.Printf ("%s METHOD\n",
+ // m_symbols[entry.value].GetMangled().GetName().GetCString());
+ // }
+ // }
+ }
+}
+
+void Symtab::AppendSymbolNamesToMap(const IndexCollection &indexes,
+ bool add_demangled, bool add_mangled,
+ NameToIndexMap &name_to_index_map) const {
+ if (add_demangled || add_mangled) {
+ Timer scoped_timer(LLVM_PRETTY_FUNCTION, "%s", LLVM_PRETTY_FUNCTION);
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ // Create the name index vector to be able to quickly search by name
+ NameToIndexMap::Entry entry;
+ const size_t num_indexes = indexes.size();
+ for (size_t i = 0; i < num_indexes; ++i) {
+ entry.value = indexes[i];
+ assert(i < m_symbols.size());
+ const Symbol *symbol = &m_symbols[entry.value];
+
+ const Mangled &mangled = symbol->GetMangled();
+ if (add_demangled) {
+ entry.cstring =
+ mangled.GetDemangledName(symbol->GetLanguage()).GetCString();
+ if (entry.cstring && entry.cstring[0])
+ name_to_index_map.Append(entry);
+ }
+
+ if (add_mangled) {
+ entry.cstring = mangled.GetMangledName().GetCString();
+ if (entry.cstring && entry.cstring[0])
+ name_to_index_map.Append(entry);
+ }
+ }
+ }
+}
+
+uint32_t Symtab::AppendSymbolIndexesWithType(SymbolType symbol_type,
+ std::vector<uint32_t> &indexes,
+ uint32_t start_idx,
+ uint32_t end_index) const {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ uint32_t prev_size = indexes.size();
+
+ const uint32_t count = std::min<uint32_t>(m_symbols.size(), end_index);
+
+ for (uint32_t i = start_idx; i < count; ++i) {
+ if (symbol_type == eSymbolTypeAny || m_symbols[i].GetType() == symbol_type)
+ indexes.push_back(i);
+ }
+
+ return indexes.size() - prev_size;
+}
+
+uint32_t Symtab::AppendSymbolIndexesWithTypeAndFlagsValue(
+ SymbolType symbol_type, uint32_t flags_value,
+ std::vector<uint32_t> &indexes, uint32_t start_idx,
+ uint32_t end_index) const {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ uint32_t prev_size = indexes.size();
+
+ const uint32_t count = std::min<uint32_t>(m_symbols.size(), end_index);
+
+ for (uint32_t i = start_idx; i < count; ++i) {
+ if ((symbol_type == eSymbolTypeAny ||
+ m_symbols[i].GetType() == symbol_type) &&
+ m_symbols[i].GetFlags() == flags_value)
+ indexes.push_back(i);
+ }
+
+ return indexes.size() - prev_size;
+}
+
+uint32_t Symtab::AppendSymbolIndexesWithType(SymbolType symbol_type,
+ Debug symbol_debug_type,
+ Visibility symbol_visibility,
+ std::vector<uint32_t> &indexes,
+ uint32_t start_idx,
+ uint32_t end_index) const {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ uint32_t prev_size = indexes.size();
+
+ const uint32_t count = std::min<uint32_t>(m_symbols.size(), end_index);
+
+ for (uint32_t i = start_idx; i < count; ++i) {
+ if (symbol_type == eSymbolTypeAny ||
+ m_symbols[i].GetType() == symbol_type) {
+ if (CheckSymbolAtIndex(i, symbol_debug_type, symbol_visibility))
+ indexes.push_back(i);
+ }
+ }
+
+ return indexes.size() - prev_size;
+}
+
+uint32_t Symtab::GetIndexForSymbol(const Symbol *symbol) const {
+ if (!m_symbols.empty()) {
+ const Symbol *first_symbol = &m_symbols[0];
+ if (symbol >= first_symbol && symbol < first_symbol + m_symbols.size())
+ return symbol - first_symbol;
+ }
+ return UINT32_MAX;
+}
+
+struct SymbolSortInfo {
+ const bool sort_by_load_addr;
+ const Symbol *symbols;
};
namespace {
- struct SymbolIndexComparator {
- const std::vector<Symbol>& symbols;
- std::vector<lldb::addr_t> &addr_cache;
-
- // Getting from the symbol to the Address to the File Address involves some work.
- // Since there are potentially many symbols here, and we're using this for sorting so
- // we're going to be computing the address many times, cache that in addr_cache.
- // The array passed in has to be the same size as the symbols array passed into the
- // member variable symbols, and should be initialized with LLDB_INVALID_ADDRESS.
- // NOTE: You have to make addr_cache externally and pass it in because std::stable_sort
- // makes copies of the comparator it is initially passed in, and you end up spending
- // huge amounts of time copying this array...
-
- SymbolIndexComparator(const std::vector<Symbol>& s, std::vector<lldb::addr_t> &a) : symbols(s), addr_cache(a) {
- assert (symbols.size() == addr_cache.size());
- }
- bool operator()(uint32_t index_a, uint32_t index_b) {
- addr_t value_a = addr_cache[index_a];
- if (value_a == LLDB_INVALID_ADDRESS)
- {
- value_a = symbols[index_a].GetAddressRef().GetFileAddress();
- addr_cache[index_a] = value_a;
- }
-
- addr_t value_b = addr_cache[index_b];
- if (value_b == LLDB_INVALID_ADDRESS)
- {
- value_b = symbols[index_b].GetAddressRef().GetFileAddress();
- addr_cache[index_b] = value_b;
- }
-
-
- if (value_a == value_b) {
- // The if the values are equal, use the original symbol user ID
- lldb::user_id_t uid_a = symbols[index_a].GetID();
- lldb::user_id_t uid_b = symbols[index_b].GetID();
- if (uid_a < uid_b)
- return true;
- if (uid_a > uid_b)
- return false;
- return false;
- } else if (value_a < value_b)
- return true;
-
- return false;
- }
- };
-}
-
-void
-Symtab::SortSymbolIndexesByValue (std::vector<uint32_t>& indexes, bool remove_duplicates) const
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- Timer scoped_timer (LLVM_PRETTY_FUNCTION,LLVM_PRETTY_FUNCTION);
- // No need to sort if we have zero or one items...
- if (indexes.size() <= 1)
- return;
-
- // Sort the indexes in place using std::stable_sort.
- // NOTE: The use of std::stable_sort instead of std::sort here is strictly for performance,
- // not correctness. The indexes vector tends to be "close" to sorted, which the
- // stable sort handles better.
-
- std::vector<lldb::addr_t> addr_cache(m_symbols.size(), LLDB_INVALID_ADDRESS);
-
- SymbolIndexComparator comparator(m_symbols, addr_cache);
- std::stable_sort(indexes.begin(), indexes.end(), comparator);
-
- // Remove any duplicates if requested
- if (remove_duplicates)
- std::unique(indexes.begin(), indexes.end());
-}
-
-uint32_t
-Symtab::AppendSymbolIndexesWithName (const ConstString& symbol_name, std::vector<uint32_t>& indexes)
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- Timer scoped_timer (LLVM_PRETTY_FUNCTION, "%s", LLVM_PRETTY_FUNCTION);
- if (symbol_name)
- {
- const char *symbol_cstr = symbol_name.GetCString();
- if (!m_name_indexes_computed)
- InitNameIndexes();
-
- return m_name_to_index.GetValues (symbol_cstr, indexes);
- }
- return 0;
-}
-
-uint32_t
-Symtab::AppendSymbolIndexesWithName (const ConstString& symbol_name, Debug symbol_debug_type, Visibility symbol_visibility, std::vector<uint32_t>& indexes)
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- Timer scoped_timer (LLVM_PRETTY_FUNCTION, "%s", LLVM_PRETTY_FUNCTION);
- if (symbol_name)
- {
- const size_t old_size = indexes.size();
- if (!m_name_indexes_computed)
- InitNameIndexes();
-
- const char *symbol_cstr = symbol_name.GetCString();
-
- std::vector<uint32_t> all_name_indexes;
- const size_t name_match_count = m_name_to_index.GetValues (symbol_cstr, all_name_indexes);
- for (size_t i=0; i<name_match_count; ++i)
- {
- if (CheckSymbolAtIndex(all_name_indexes[i], symbol_debug_type, symbol_visibility))
- indexes.push_back (all_name_indexes[i]);
- }
- return indexes.size() - old_size;
- }
- return 0;
-}
+struct SymbolIndexComparator {
+ const std::vector<Symbol> &symbols;
+ std::vector<lldb::addr_t> &addr_cache;
+
+ // Getting from the symbol to the Address to the File Address involves some
+ // work.
+ // Since there are potentially many symbols here, and we're using this for
+ // sorting so
+ // we're going to be computing the address many times, cache that in
+ // addr_cache.
+ // The array passed in has to be the same size as the symbols array passed
+ // into the
+ // member variable symbols, and should be initialized with
+ // LLDB_INVALID_ADDRESS.
+ // NOTE: You have to make addr_cache externally and pass it in because
+ // std::stable_sort
+ // makes copies of the comparator it is initially passed in, and you end up
+ // spending
+ // huge amounts of time copying this array...
+
+ SymbolIndexComparator(const std::vector<Symbol> &s,
+ std::vector<lldb::addr_t> &a)
+ : symbols(s), addr_cache(a) {
+ assert(symbols.size() == addr_cache.size());
+ }
+ bool operator()(uint32_t index_a, uint32_t index_b) {
+ addr_t value_a = addr_cache[index_a];
+ if (value_a == LLDB_INVALID_ADDRESS) {
+ value_a = symbols[index_a].GetAddressRef().GetFileAddress();
+ addr_cache[index_a] = value_a;
+ }
+
+ addr_t value_b = addr_cache[index_b];
+ if (value_b == LLDB_INVALID_ADDRESS) {
+ value_b = symbols[index_b].GetAddressRef().GetFileAddress();
+ addr_cache[index_b] = value_b;
+ }
+
+ if (value_a == value_b) {
+ // The if the values are equal, use the original symbol user ID
+ lldb::user_id_t uid_a = symbols[index_a].GetID();
+ lldb::user_id_t uid_b = symbols[index_b].GetID();
+ if (uid_a < uid_b)
+ return true;
+ if (uid_a > uid_b)
+ return false;
+ return false;
+ } else if (value_a < value_b)
+ return true;
-uint32_t
-Symtab::AppendSymbolIndexesWithNameAndType (const ConstString& symbol_name, SymbolType symbol_type, std::vector<uint32_t>& indexes)
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- if (AppendSymbolIndexesWithName(symbol_name, indexes) > 0)
- {
- std::vector<uint32_t>::iterator pos = indexes.begin();
- while (pos != indexes.end())
- {
- if (symbol_type == eSymbolTypeAny || m_symbols[*pos].GetType() == symbol_type)
- ++pos;
- else
- pos = indexes.erase(pos);
- }
- }
- return indexes.size();
-}
-
-uint32_t
-Symtab::AppendSymbolIndexesWithNameAndType (const ConstString& symbol_name, SymbolType symbol_type, Debug symbol_debug_type, Visibility symbol_visibility, std::vector<uint32_t>& indexes)
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- if (AppendSymbolIndexesWithName(symbol_name, symbol_debug_type, symbol_visibility, indexes) > 0)
- {
- std::vector<uint32_t>::iterator pos = indexes.begin();
- while (pos != indexes.end())
- {
- if (symbol_type == eSymbolTypeAny || m_symbols[*pos].GetType() == symbol_type)
- ++pos;
- else
- pos = indexes.erase(pos);
- }
- }
- return indexes.size();
-}
-
-
-uint32_t
-Symtab::AppendSymbolIndexesMatchingRegExAndType (const RegularExpression ®exp, SymbolType symbol_type, std::vector<uint32_t>& indexes)
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- uint32_t prev_size = indexes.size();
- uint32_t sym_end = m_symbols.size();
-
- for (uint32_t i = 0; i < sym_end; i++)
- {
- if (symbol_type == eSymbolTypeAny || m_symbols[i].GetType() == symbol_type)
- {
- const char *name = m_symbols[i].GetName().AsCString();
- if (name)
- {
- if (regexp.Execute (name))
- indexes.push_back(i);
- }
- }
- }
- return indexes.size() - prev_size;
-
-}
-
-uint32_t
-Symtab::AppendSymbolIndexesMatchingRegExAndType (const RegularExpression ®exp, SymbolType symbol_type, Debug symbol_debug_type, Visibility symbol_visibility, std::vector<uint32_t>& indexes)
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- uint32_t prev_size = indexes.size();
- uint32_t sym_end = m_symbols.size();
-
- for (uint32_t i = 0; i < sym_end; i++)
- {
- if (symbol_type == eSymbolTypeAny || m_symbols[i].GetType() == symbol_type)
- {
- if (CheckSymbolAtIndex(i, symbol_debug_type, symbol_visibility) == false)
- continue;
-
- const char *name = m_symbols[i].GetName().AsCString();
- if (name)
- {
- if (regexp.Execute (name))
- indexes.push_back(i);
- }
- }
- }
- return indexes.size() - prev_size;
-
-}
-
-Symbol *
-Symtab::FindSymbolWithType (SymbolType symbol_type, Debug symbol_debug_type, Visibility symbol_visibility, uint32_t& start_idx)
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- const size_t count = m_symbols.size();
- for (size_t idx = start_idx; idx < count; ++idx)
- {
- if (symbol_type == eSymbolTypeAny || m_symbols[idx].GetType() == symbol_type)
- {
- if (CheckSymbolAtIndex(idx, symbol_debug_type, symbol_visibility))
- {
- start_idx = idx;
- return &m_symbols[idx];
- }
- }
- }
- return nullptr;
+ return false;
+ }
+};
}
-size_t
-Symtab::FindAllSymbolsWithNameAndType (const ConstString &name, SymbolType symbol_type, std::vector<uint32_t>& symbol_indexes)
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- Timer scoped_timer (LLVM_PRETTY_FUNCTION, "%s", LLVM_PRETTY_FUNCTION);
- // Initialize all of the lookup by name indexes before converting NAME
- // to a uniqued string NAME_STR below.
+void Symtab::SortSymbolIndexesByValue(std::vector<uint32_t> &indexes,
+ bool remove_duplicates) const {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ Timer scoped_timer(LLVM_PRETTY_FUNCTION, LLVM_PRETTY_FUNCTION);
+ // No need to sort if we have zero or one items...
+ if (indexes.size() <= 1)
+ return;
+
+ // Sort the indexes in place using std::stable_sort.
+ // NOTE: The use of std::stable_sort instead of std::sort here is strictly for
+ // performance,
+ // not correctness. The indexes vector tends to be "close" to sorted, which
+ // the
+ // stable sort handles better.
+
+ std::vector<lldb::addr_t> addr_cache(m_symbols.size(), LLDB_INVALID_ADDRESS);
+
+ SymbolIndexComparator comparator(m_symbols, addr_cache);
+ std::stable_sort(indexes.begin(), indexes.end(), comparator);
+
+ // Remove any duplicates if requested
+ if (remove_duplicates)
+ std::unique(indexes.begin(), indexes.end());
+}
+
+uint32_t Symtab::AppendSymbolIndexesWithName(const ConstString &symbol_name,
+ std::vector<uint32_t> &indexes) {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ Timer scoped_timer(LLVM_PRETTY_FUNCTION, "%s", LLVM_PRETTY_FUNCTION);
+ if (symbol_name) {
+ const char *symbol_cstr = symbol_name.GetCString();
if (!m_name_indexes_computed)
- InitNameIndexes();
-
- if (name)
- {
- // The string table did have a string that matched, but we need
- // to check the symbols and match the symbol_type if any was given.
- AppendSymbolIndexesWithNameAndType (name, symbol_type, symbol_indexes);
- }
- return symbol_indexes.size();
-}
-
-size_t
-Symtab::FindAllSymbolsWithNameAndType (const ConstString &name, SymbolType symbol_type, Debug symbol_debug_type, Visibility symbol_visibility, std::vector<uint32_t>& symbol_indexes)
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
+ InitNameIndexes();
- Timer scoped_timer (LLVM_PRETTY_FUNCTION, "%s", LLVM_PRETTY_FUNCTION);
- // Initialize all of the lookup by name indexes before converting NAME
- // to a uniqued string NAME_STR below.
+ return m_name_to_index.GetValues(symbol_cstr, indexes);
+ }
+ return 0;
+}
+
+uint32_t Symtab::AppendSymbolIndexesWithName(const ConstString &symbol_name,
+ Debug symbol_debug_type,
+ Visibility symbol_visibility,
+ std::vector<uint32_t> &indexes) {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ Timer scoped_timer(LLVM_PRETTY_FUNCTION, "%s", LLVM_PRETTY_FUNCTION);
+ if (symbol_name) {
+ const size_t old_size = indexes.size();
if (!m_name_indexes_computed)
- InitNameIndexes();
-
- if (name)
- {
- // The string table did have a string that matched, but we need
- // to check the symbols and match the symbol_type if any was given.
- AppendSymbolIndexesWithNameAndType (name, symbol_type, symbol_debug_type, symbol_visibility, symbol_indexes);
- }
- return symbol_indexes.size();
-}
+ InitNameIndexes();
-size_t
-Symtab::FindAllSymbolsMatchingRexExAndType (const RegularExpression ®ex, SymbolType symbol_type, Debug symbol_debug_type, Visibility symbol_visibility, std::vector<uint32_t>& symbol_indexes)
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
+ const char *symbol_cstr = symbol_name.GetCString();
- AppendSymbolIndexesMatchingRegExAndType(regex, symbol_type, symbol_debug_type, symbol_visibility, symbol_indexes);
- return symbol_indexes.size();
+ std::vector<uint32_t> all_name_indexes;
+ const size_t name_match_count =
+ m_name_to_index.GetValues(symbol_cstr, all_name_indexes);
+ for (size_t i = 0; i < name_match_count; ++i) {
+ if (CheckSymbolAtIndex(all_name_indexes[i], symbol_debug_type,
+ symbol_visibility))
+ indexes.push_back(all_name_indexes[i]);
+ }
+ return indexes.size() - old_size;
+ }
+ return 0;
}
-Symbol *
-Symtab::FindFirstSymbolWithNameAndType (const ConstString &name, SymbolType symbol_type, Debug symbol_debug_type, Visibility symbol_visibility)
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- Timer scoped_timer (LLVM_PRETTY_FUNCTION, "%s", LLVM_PRETTY_FUNCTION);
- if (!m_name_indexes_computed)
- InitNameIndexes();
-
- if (name)
- {
- std::vector<uint32_t> matching_indexes;
- // The string table did have a string that matched, but we need
- // to check the symbols and match the symbol_type if any was given.
- if (AppendSymbolIndexesWithNameAndType (name, symbol_type, symbol_debug_type, symbol_visibility, matching_indexes))
- {
- std::vector<uint32_t>::const_iterator pos, end = matching_indexes.end();
- for (pos = matching_indexes.begin(); pos != end; ++pos)
- {
- Symbol *symbol = SymbolAtIndex(*pos);
-
- if (symbol->Compare(name, symbol_type))
- return symbol;
- }
- }
+uint32_t
+Symtab::AppendSymbolIndexesWithNameAndType(const ConstString &symbol_name,
+ SymbolType symbol_type,
+ std::vector<uint32_t> &indexes) {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ if (AppendSymbolIndexesWithName(symbol_name, indexes) > 0) {
+ std::vector<uint32_t>::iterator pos = indexes.begin();
+ while (pos != indexes.end()) {
+ if (symbol_type == eSymbolTypeAny ||
+ m_symbols[*pos].GetType() == symbol_type)
+ ++pos;
+ else
+ pos = indexes.erase(pos);
+ }
+ }
+ return indexes.size();
+}
+
+uint32_t Symtab::AppendSymbolIndexesWithNameAndType(
+ const ConstString &symbol_name, SymbolType symbol_type,
+ Debug symbol_debug_type, Visibility symbol_visibility,
+ std::vector<uint32_t> &indexes) {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ if (AppendSymbolIndexesWithName(symbol_name, symbol_debug_type,
+ symbol_visibility, indexes) > 0) {
+ std::vector<uint32_t>::iterator pos = indexes.begin();
+ while (pos != indexes.end()) {
+ if (symbol_type == eSymbolTypeAny ||
+ m_symbols[*pos].GetType() == symbol_type)
+ ++pos;
+ else
+ pos = indexes.erase(pos);
+ }
+ }
+ return indexes.size();
+}
+
+uint32_t Symtab::AppendSymbolIndexesMatchingRegExAndType(
+ const RegularExpression ®exp, SymbolType symbol_type,
+ std::vector<uint32_t> &indexes) {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ uint32_t prev_size = indexes.size();
+ uint32_t sym_end = m_symbols.size();
+
+ for (uint32_t i = 0; i < sym_end; i++) {
+ if (symbol_type == eSymbolTypeAny ||
+ m_symbols[i].GetType() == symbol_type) {
+ const char *name = m_symbols[i].GetName().AsCString();
+ if (name) {
+ if (regexp.Execute(name))
+ indexes.push_back(i);
+ }
+ }
+ }
+ return indexes.size() - prev_size;
+}
+
+uint32_t Symtab::AppendSymbolIndexesMatchingRegExAndType(
+ const RegularExpression ®exp, SymbolType symbol_type,
+ Debug symbol_debug_type, Visibility symbol_visibility,
+ std::vector<uint32_t> &indexes) {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ uint32_t prev_size = indexes.size();
+ uint32_t sym_end = m_symbols.size();
+
+ for (uint32_t i = 0; i < sym_end; i++) {
+ if (symbol_type == eSymbolTypeAny ||
+ m_symbols[i].GetType() == symbol_type) {
+ if (CheckSymbolAtIndex(i, symbol_debug_type, symbol_visibility) == false)
+ continue;
+
+ const char *name = m_symbols[i].GetName().AsCString();
+ if (name) {
+ if (regexp.Execute(name))
+ indexes.push_back(i);
+ }
+ }
+ }
+ return indexes.size() - prev_size;
+}
+
+Symbol *Symtab::FindSymbolWithType(SymbolType symbol_type,
+ Debug symbol_debug_type,
+ Visibility symbol_visibility,
+ uint32_t &start_idx) {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ const size_t count = m_symbols.size();
+ for (size_t idx = start_idx; idx < count; ++idx) {
+ if (symbol_type == eSymbolTypeAny ||
+ m_symbols[idx].GetType() == symbol_type) {
+ if (CheckSymbolAtIndex(idx, symbol_debug_type, symbol_visibility)) {
+ start_idx = idx;
+ return &m_symbols[idx];
+ }
}
- return nullptr;
+ }
+ return nullptr;
}
-typedef struct
-{
- const Symtab *symtab;
- const addr_t file_addr;
- Symbol *match_symbol;
- const uint32_t *match_index_ptr;
- addr_t match_offset;
+size_t
+Symtab::FindAllSymbolsWithNameAndType(const ConstString &name,
+ SymbolType symbol_type,
+ std::vector<uint32_t> &symbol_indexes) {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ Timer scoped_timer(LLVM_PRETTY_FUNCTION, "%s", LLVM_PRETTY_FUNCTION);
+ // Initialize all of the lookup by name indexes before converting NAME
+ // to a uniqued string NAME_STR below.
+ if (!m_name_indexes_computed)
+ InitNameIndexes();
+
+ if (name) {
+ // The string table did have a string that matched, but we need
+ // to check the symbols and match the symbol_type if any was given.
+ AppendSymbolIndexesWithNameAndType(name, symbol_type, symbol_indexes);
+ }
+ return symbol_indexes.size();
+}
+
+size_t Symtab::FindAllSymbolsWithNameAndType(
+ const ConstString &name, SymbolType symbol_type, Debug symbol_debug_type,
+ Visibility symbol_visibility, std::vector<uint32_t> &symbol_indexes) {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ Timer scoped_timer(LLVM_PRETTY_FUNCTION, "%s", LLVM_PRETTY_FUNCTION);
+ // Initialize all of the lookup by name indexes before converting NAME
+ // to a uniqued string NAME_STR below.
+ if (!m_name_indexes_computed)
+ InitNameIndexes();
+
+ if (name) {
+ // The string table did have a string that matched, but we need
+ // to check the symbols and match the symbol_type if any was given.
+ AppendSymbolIndexesWithNameAndType(name, symbol_type, symbol_debug_type,
+ symbol_visibility, symbol_indexes);
+ }
+ return symbol_indexes.size();
+}
+
+size_t Symtab::FindAllSymbolsMatchingRexExAndType(
+ const RegularExpression ®ex, SymbolType symbol_type,
+ Debug symbol_debug_type, Visibility symbol_visibility,
+ std::vector<uint32_t> &symbol_indexes) {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ AppendSymbolIndexesMatchingRegExAndType(regex, symbol_type, symbol_debug_type,
+ symbol_visibility, symbol_indexes);
+ return symbol_indexes.size();
+}
+
+Symbol *Symtab::FindFirstSymbolWithNameAndType(const ConstString &name,
+ SymbolType symbol_type,
+ Debug symbol_debug_type,
+ Visibility symbol_visibility) {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ Timer scoped_timer(LLVM_PRETTY_FUNCTION, "%s", LLVM_PRETTY_FUNCTION);
+ if (!m_name_indexes_computed)
+ InitNameIndexes();
+
+ if (name) {
+ std::vector<uint32_t> matching_indexes;
+ // The string table did have a string that matched, but we need
+ // to check the symbols and match the symbol_type if any was given.
+ if (AppendSymbolIndexesWithNameAndType(name, symbol_type, symbol_debug_type,
+ symbol_visibility,
+ matching_indexes)) {
+ std::vector<uint32_t>::const_iterator pos, end = matching_indexes.end();
+ for (pos = matching_indexes.begin(); pos != end; ++pos) {
+ Symbol *symbol = SymbolAtIndex(*pos);
+
+ if (symbol->Compare(name, symbol_type))
+ return symbol;
+ }
+ }
+ }
+ return nullptr;
+}
+
+typedef struct {
+ const Symtab *symtab;
+ const addr_t file_addr;
+ Symbol *match_symbol;
+ const uint32_t *match_index_ptr;
+ addr_t match_offset;
} SymbolSearchInfo;
// Add all the section file start address & size to the RangeVector,
-// recusively adding any children sections.
-static void
-AddSectionsToRangeMap (SectionList *sectlist, RangeVector<addr_t, addr_t> §ion_ranges)
-{
- const int num_sections = sectlist->GetNumSections (0);
- for (int i = 0; i < num_sections; i++)
- {
- SectionSP sect_sp = sectlist->GetSectionAtIndex (i);
- if (sect_sp)
- {
- SectionList &child_sectlist = sect_sp->GetChildren();
-
- // If this section has children, add the children to the RangeVector.
- // Else add this section to the RangeVector.
- if (child_sectlist.GetNumSections (0) > 0)
- {
- AddSectionsToRangeMap (&child_sectlist, section_ranges);
- }
- else
- {
- size_t size = sect_sp->GetByteSize();
- if (size > 0)
- {
- addr_t base_addr = sect_sp->GetFileAddress();
- RangeVector<addr_t, addr_t>::Entry entry;
- entry.SetRangeBase (base_addr);
- entry.SetByteSize (size);
- section_ranges.Append (entry);
- }
- }
- }
- }
-}
-
-void
-Symtab::InitAddressIndexes()
-{
- // Protected function, no need to lock mutex...
- if (!m_file_addr_to_index_computed && !m_symbols.empty())
- {
- m_file_addr_to_index_computed = true;
-
- FileRangeToIndexMap::Entry entry;
- const_iterator begin = m_symbols.begin();
- const_iterator end = m_symbols.end();
- for (const_iterator pos = m_symbols.begin(); pos != end; ++pos)
- {
- if (pos->ValueIsAddress())
- {
- entry.SetRangeBase(pos->GetAddressRef().GetFileAddress());
- entry.SetByteSize(pos->GetByteSize());
- entry.data = std::distance(begin, pos);
- m_file_addr_to_index.Append(entry);
- }
- }
- const size_t num_entries = m_file_addr_to_index.GetSize();
- if (num_entries > 0)
- {
- m_file_addr_to_index.Sort();
-
- // Create a RangeVector with the start & size of all the sections for
- // this objfile. We'll need to check this for any FileRangeToIndexMap
- // entries with an uninitialized size, which could potentially be a
- // large number so reconstituting the weak pointer is busywork when it
- // is invariant information.
- SectionList *sectlist = m_objfile->GetSectionList();
- RangeVector<addr_t, addr_t> section_ranges;
- if (sectlist)
- {
- AddSectionsToRangeMap (sectlist, section_ranges);
- section_ranges.Sort();
- }
-
- // Iterate through the FileRangeToIndexMap and fill in the size for any
- // entries that didn't already have a size from the Symbol (e.g. if we
- // have a plain linker symbol with an address only, instead of debug info
- // where we get an address and a size and a type, etc.)
- for (size_t i = 0; i < num_entries; i++)
- {
- FileRangeToIndexMap::Entry *entry = m_file_addr_to_index.GetMutableEntryAtIndex (i);
- if (entry->GetByteSize() == 0)
- {
- addr_t curr_base_addr = entry->GetRangeBase();
- const RangeVector<addr_t, addr_t>::Entry *containing_section =
- section_ranges.FindEntryThatContains (curr_base_addr);
-
- // Use the end of the section as the default max size of the symbol
- addr_t sym_size = 0;
- if (containing_section)
- {
- sym_size = containing_section->GetByteSize() -
- (entry->GetRangeBase() - containing_section->GetRangeBase());
- }
-
- for (size_t j = i; j < num_entries; j++)
- {
- FileRangeToIndexMap::Entry *next_entry = m_file_addr_to_index.GetMutableEntryAtIndex (j);
- addr_t next_base_addr = next_entry->GetRangeBase();
- if (next_base_addr > curr_base_addr)
- {
- addr_t size_to_next_symbol = next_base_addr - curr_base_addr;
-
- // Take the difference between this symbol and the next one as its size,
- // if it is less than the size of the section.
- if (sym_size == 0 || size_to_next_symbol < sym_size)
- {
- sym_size = size_to_next_symbol;
- }
- break;
- }
- }
-
- if (sym_size > 0)
- {
- entry->SetByteSize (sym_size);
- Symbol &symbol = m_symbols[entry->data];
- symbol.SetByteSize (sym_size);
- symbol.SetSizeIsSynthesized (true);
- }
- }
- }
-
- // Sort again in case the range size changes the ordering
- m_file_addr_to_index.Sort();
- }
- }
-}
-
-void
-Symtab::CalculateSymbolSizes ()
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- if (!m_symbols.empty())
- {
- if (!m_file_addr_to_index_computed)
- InitAddressIndexes();
-
- const size_t num_entries = m_file_addr_to_index.GetSize();
-
- for (size_t i = 0; i < num_entries; ++i)
- {
- // The entries in the m_file_addr_to_index have calculated the sizes already
- // so we will use this size if we need to.
- const FileRangeToIndexMap::Entry &entry = m_file_addr_to_index.GetEntryRef(i);
-
- Symbol &symbol = m_symbols[entry.data];
-
- // If the symbol size is already valid, no need to do anything
- if (symbol.GetByteSizeIsValid())
- continue;
-
- const addr_t range_size = entry.GetByteSize();
- if (range_size > 0)
- {
- symbol.SetByteSize(range_size);
- symbol.SetSizeIsSynthesized(true);
- }
- }
+// recusively adding any children sections.
+static void AddSectionsToRangeMap(SectionList *sectlist,
+ RangeVector<addr_t, addr_t> §ion_ranges) {
+ const int num_sections = sectlist->GetNumSections(0);
+ for (int i = 0; i < num_sections; i++) {
+ SectionSP sect_sp = sectlist->GetSectionAtIndex(i);
+ if (sect_sp) {
+ SectionList &child_sectlist = sect_sp->GetChildren();
+
+ // If this section has children, add the children to the RangeVector.
+ // Else add this section to the RangeVector.
+ if (child_sectlist.GetNumSections(0) > 0) {
+ AddSectionsToRangeMap(&child_sectlist, section_ranges);
+ } else {
+ size_t size = sect_sp->GetByteSize();
+ if (size > 0) {
+ addr_t base_addr = sect_sp->GetFileAddress();
+ RangeVector<addr_t, addr_t>::Entry entry;
+ entry.SetRangeBase(base_addr);
+ entry.SetByteSize(size);
+ section_ranges.Append(entry);
+ }
+ }
+ }
+ }
+}
+
+void Symtab::InitAddressIndexes() {
+ // Protected function, no need to lock mutex...
+ if (!m_file_addr_to_index_computed && !m_symbols.empty()) {
+ m_file_addr_to_index_computed = true;
+
+ FileRangeToIndexMap::Entry entry;
+ const_iterator begin = m_symbols.begin();
+ const_iterator end = m_symbols.end();
+ for (const_iterator pos = m_symbols.begin(); pos != end; ++pos) {
+ if (pos->ValueIsAddress()) {
+ entry.SetRangeBase(pos->GetAddressRef().GetFileAddress());
+ entry.SetByteSize(pos->GetByteSize());
+ entry.data = std::distance(begin, pos);
+ m_file_addr_to_index.Append(entry);
+ }
+ }
+ const size_t num_entries = m_file_addr_to_index.GetSize();
+ if (num_entries > 0) {
+ m_file_addr_to_index.Sort();
+
+ // Create a RangeVector with the start & size of all the sections for
+ // this objfile. We'll need to check this for any FileRangeToIndexMap
+ // entries with an uninitialized size, which could potentially be a
+ // large number so reconstituting the weak pointer is busywork when it
+ // is invariant information.
+ SectionList *sectlist = m_objfile->GetSectionList();
+ RangeVector<addr_t, addr_t> section_ranges;
+ if (sectlist) {
+ AddSectionsToRangeMap(sectlist, section_ranges);
+ section_ranges.Sort();
+ }
+
+ // Iterate through the FileRangeToIndexMap and fill in the size for any
+ // entries that didn't already have a size from the Symbol (e.g. if we
+ // have a plain linker symbol with an address only, instead of debug info
+ // where we get an address and a size and a type, etc.)
+ for (size_t i = 0; i < num_entries; i++) {
+ FileRangeToIndexMap::Entry *entry =
+ m_file_addr_to_index.GetMutableEntryAtIndex(i);
+ if (entry->GetByteSize() == 0) {
+ addr_t curr_base_addr = entry->GetRangeBase();
+ const RangeVector<addr_t, addr_t>::Entry *containing_section =
+ section_ranges.FindEntryThatContains(curr_base_addr);
+
+ // Use the end of the section as the default max size of the symbol
+ addr_t sym_size = 0;
+ if (containing_section) {
+ sym_size =
+ containing_section->GetByteSize() -
+ (entry->GetRangeBase() - containing_section->GetRangeBase());
+ }
+
+ for (size_t j = i; j < num_entries; j++) {
+ FileRangeToIndexMap::Entry *next_entry =
+ m_file_addr_to_index.GetMutableEntryAtIndex(j);
+ addr_t next_base_addr = next_entry->GetRangeBase();
+ if (next_base_addr > curr_base_addr) {
+ addr_t size_to_next_symbol = next_base_addr - curr_base_addr;
+
+ // Take the difference between this symbol and the next one as its
+ // size,
+ // if it is less than the size of the section.
+ if (sym_size == 0 || size_to_next_symbol < sym_size) {
+ sym_size = size_to_next_symbol;
+ }
+ break;
+ }
+ }
+
+ if (sym_size > 0) {
+ entry->SetByteSize(sym_size);
+ Symbol &symbol = m_symbols[entry->data];
+ symbol.SetByteSize(sym_size);
+ symbol.SetSizeIsSynthesized(true);
+ }
+ }
+ }
+
+ // Sort again in case the range size changes the ordering
+ m_file_addr_to_index.Sort();
}
+ }
}
-Symbol *
-Symtab::FindSymbolAtFileAddress (addr_t file_addr)
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
- if (!m_file_addr_to_index_computed)
- InitAddressIndexes();
-
- const FileRangeToIndexMap::Entry *entry = m_file_addr_to_index.FindEntryStartsAt(file_addr);
- if (entry)
- {
- Symbol* symbol = SymbolAtIndex(entry->data);
- if (symbol->GetFileAddress() == file_addr)
- return symbol;
- }
- return nullptr;
-}
-
-Symbol *
-Symtab::FindSymbolContainingFileAddress (addr_t file_addr)
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
-
- if (!m_file_addr_to_index_computed)
- InitAddressIndexes();
-
- const FileRangeToIndexMap::Entry *entry = m_file_addr_to_index.FindEntryThatContains(file_addr);
- if (entry)
- {
- Symbol* symbol = SymbolAtIndex(entry->data);
- if (symbol->ContainsFileAddress(file_addr))
- return symbol;
- }
- return nullptr;
-}
-
-void
-Symtab::ForEachSymbolContainingFileAddress(addr_t file_addr, std::function<bool(Symbol *)> const &callback)
-{
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
+void Symtab::CalculateSymbolSizes() {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+ if (!m_symbols.empty()) {
if (!m_file_addr_to_index_computed)
- InitAddressIndexes();
-
- std::vector<uint32_t> all_addr_indexes;
+ InitAddressIndexes();
- // Get all symbols with file_addr
- const size_t addr_match_count = m_file_addr_to_index.FindEntryIndexesThatContain(file_addr, all_addr_indexes);
-
- for (size_t i = 0; i < addr_match_count; ++i)
- {
- Symbol* symbol = SymbolAtIndex(all_addr_indexes[i]);
- if (symbol->ContainsFileAddress(file_addr))
- {
- if (!callback(symbol))
- break;
- }
- }
-}
+ const size_t num_entries = m_file_addr_to_index.GetSize();
-void
-Symtab::SymbolIndicesToSymbolContextList (std::vector<uint32_t> &symbol_indexes, SymbolContextList &sc_list)
-{
- // No need to protect this call using m_mutex all other method calls are
- // already thread safe.
-
- const bool merge_symbol_into_function = true;
- size_t num_indices = symbol_indexes.size();
- if (num_indices > 0)
- {
- SymbolContext sc;
- sc.module_sp = m_objfile->GetModule();
- for (size_t i = 0; i < num_indices; i++)
- {
- sc.symbol = SymbolAtIndex (symbol_indexes[i]);
- if (sc.symbol)
- sc_list.AppendIfUnique(sc, merge_symbol_into_function);
+ for (size_t i = 0; i < num_entries; ++i) {
+ // The entries in the m_file_addr_to_index have calculated the sizes
+ // already
+ // so we will use this size if we need to.
+ const FileRangeToIndexMap::Entry &entry =
+ m_file_addr_to_index.GetEntryRef(i);
+
+ Symbol &symbol = m_symbols[entry.data];
+
+ // If the symbol size is already valid, no need to do anything
+ if (symbol.GetByteSizeIsValid())
+ continue;
+
+ const addr_t range_size = entry.GetByteSize();
+ if (range_size > 0) {
+ symbol.SetByteSize(range_size);
+ symbol.SetSizeIsSynthesized(true);
+ }
+ }
+ }
+}
+
+Symbol *Symtab::FindSymbolAtFileAddress(addr_t file_addr) {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+ if (!m_file_addr_to_index_computed)
+ InitAddressIndexes();
+
+ const FileRangeToIndexMap::Entry *entry =
+ m_file_addr_to_index.FindEntryStartsAt(file_addr);
+ if (entry) {
+ Symbol *symbol = SymbolAtIndex(entry->data);
+ if (symbol->GetFileAddress() == file_addr)
+ return symbol;
+ }
+ return nullptr;
+}
+
+Symbol *Symtab::FindSymbolContainingFileAddress(addr_t file_addr) {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ if (!m_file_addr_to_index_computed)
+ InitAddressIndexes();
+
+ const FileRangeToIndexMap::Entry *entry =
+ m_file_addr_to_index.FindEntryThatContains(file_addr);
+ if (entry) {
+ Symbol *symbol = SymbolAtIndex(entry->data);
+ if (symbol->ContainsFileAddress(file_addr))
+ return symbol;
+ }
+ return nullptr;
+}
+
+void Symtab::ForEachSymbolContainingFileAddress(
+ addr_t file_addr, std::function<bool(Symbol *)> const &callback) {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+
+ if (!m_file_addr_to_index_computed)
+ InitAddressIndexes();
+
+ std::vector<uint32_t> all_addr_indexes;
+
+ // Get all symbols with file_addr
+ const size_t addr_match_count =
+ m_file_addr_to_index.FindEntryIndexesThatContain(file_addr,
+ all_addr_indexes);
+
+ for (size_t i = 0; i < addr_match_count; ++i) {
+ Symbol *symbol = SymbolAtIndex(all_addr_indexes[i]);
+ if (symbol->ContainsFileAddress(file_addr)) {
+ if (!callback(symbol))
+ break;
+ }
+ }
+}
+
+void Symtab::SymbolIndicesToSymbolContextList(
+ std::vector<uint32_t> &symbol_indexes, SymbolContextList &sc_list) {
+ // No need to protect this call using m_mutex all other method calls are
+ // already thread safe.
+
+ const bool merge_symbol_into_function = true;
+ size_t num_indices = symbol_indexes.size();
+ if (num_indices > 0) {
+ SymbolContext sc;
+ sc.module_sp = m_objfile->GetModule();
+ for (size_t i = 0; i < num_indices; i++) {
+ sc.symbol = SymbolAtIndex(symbol_indexes[i]);
+ if (sc.symbol)
+ sc_list.AppendIfUnique(sc, merge_symbol_into_function);
+ }
+ }
+}
+
+size_t Symtab::FindFunctionSymbols(const ConstString &name,
+ uint32_t name_type_mask,
+ SymbolContextList &sc_list) {
+ size_t count = 0;
+ std::vector<uint32_t> symbol_indexes;
+
+ const char *name_cstr = name.GetCString();
+
+ // eFunctionNameTypeAuto should be pre-resolved by a call to
+ // Module::PrepareForFunctionNameLookup()
+ assert((name_type_mask & eFunctionNameTypeAuto) == 0);
+
+ if (name_type_mask & (eFunctionNameTypeBase | eFunctionNameTypeFull)) {
+ std::vector<uint32_t> temp_symbol_indexes;
+ FindAllSymbolsWithNameAndType(name, eSymbolTypeAny, temp_symbol_indexes);
+
+ unsigned temp_symbol_indexes_size = temp_symbol_indexes.size();
+ if (temp_symbol_indexes_size > 0) {
+ std::lock_guard<std::recursive_mutex> guard(m_mutex);
+ for (unsigned i = 0; i < temp_symbol_indexes_size; i++) {
+ SymbolContext sym_ctx;
+ sym_ctx.symbol = SymbolAtIndex(temp_symbol_indexes[i]);
+ if (sym_ctx.symbol) {
+ switch (sym_ctx.symbol->GetType()) {
+ case eSymbolTypeCode:
+ case eSymbolTypeResolver:
+ case eSymbolTypeReExported:
+ symbol_indexes.push_back(temp_symbol_indexes[i]);
+ break;
+ default:
+ break;
+ }
}
+ }
}
-}
+ }
+ if (name_type_mask & eFunctionNameTypeBase) {
+ // From mangled names we can't tell what is a basename and what
+ // is a method name, so we just treat them the same
+ if (!m_name_indexes_computed)
+ InitNameIndexes();
-size_t
-Symtab::FindFunctionSymbols (const ConstString &name,
- uint32_t name_type_mask,
- SymbolContextList& sc_list)
-{
- size_t count = 0;
- std::vector<uint32_t> symbol_indexes;
-
- const char *name_cstr = name.GetCString();
-
- // eFunctionNameTypeAuto should be pre-resolved by a call to Module::PrepareForFunctionNameLookup()
- assert ((name_type_mask & eFunctionNameTypeAuto) == 0);
-
- if (name_type_mask & (eFunctionNameTypeBase | eFunctionNameTypeFull))
- {
- std::vector<uint32_t> temp_symbol_indexes;
- FindAllSymbolsWithNameAndType (name, eSymbolTypeAny, temp_symbol_indexes);
-
- unsigned temp_symbol_indexes_size = temp_symbol_indexes.size();
- if (temp_symbol_indexes_size > 0)
- {
- std::lock_guard<std::recursive_mutex> guard(m_mutex);
- for (unsigned i = 0; i < temp_symbol_indexes_size; i++)
- {
- SymbolContext sym_ctx;
- sym_ctx.symbol = SymbolAtIndex (temp_symbol_indexes[i]);
- if (sym_ctx.symbol)
- {
- switch (sym_ctx.symbol->GetType())
- {
- case eSymbolTypeCode:
- case eSymbolTypeResolver:
- case eSymbolTypeReExported:
- symbol_indexes.push_back(temp_symbol_indexes[i]);
- break;
- default:
- break;
- }
- }
- }
- }
- }
-
- if (name_type_mask & eFunctionNameTypeBase)
- {
- // From mangled names we can't tell what is a basename and what
- // is a method name, so we just treat them the same
- if (!m_name_indexes_computed)
- InitNameIndexes();
-
- if (!m_basename_to_index.IsEmpty())
- {
- const UniqueCStringMap<uint32_t>::Entry *match;
- for (match = m_basename_to_index.FindFirstValueForName(name_cstr);
- match != nullptr;
- match = m_basename_to_index.FindNextValueForName(match))
- {
- symbol_indexes.push_back(match->value);
- }
- }
- }
-
- if (name_type_mask & eFunctionNameTypeMethod)
- {
- if (!m_name_indexes_computed)
- InitNameIndexes();
-
- if (!m_method_to_index.IsEmpty())
- {
- const UniqueCStringMap<uint32_t>::Entry *match;
- for (match = m_method_to_index.FindFirstValueForName(name_cstr);
- match != nullptr;
- match = m_method_to_index.FindNextValueForName(match))
- {
- symbol_indexes.push_back(match->value);
- }
- }
+ if (!m_basename_to_index.IsEmpty()) {
+ const UniqueCStringMap<uint32_t>::Entry *match;
+ for (match = m_basename_to_index.FindFirstValueForName(name_cstr);
+ match != nullptr;
+ match = m_basename_to_index.FindNextValueForName(match)) {
+ symbol_indexes.push_back(match->value);
+ }
}
+ }
- if (name_type_mask & eFunctionNameTypeSelector)
- {
- if (!m_name_indexes_computed)
- InitNameIndexes();
-
- if (!m_selector_to_index.IsEmpty())
- {
- const UniqueCStringMap<uint32_t>::Entry *match;
- for (match = m_selector_to_index.FindFirstValueForName(name_cstr);
- match != nullptr;
- match = m_selector_to_index.FindNextValueForName(match))
- {
- symbol_indexes.push_back(match->value);
- }
- }
- }
+ if (name_type_mask & eFunctionNameTypeMethod) {
+ if (!m_name_indexes_computed)
+ InitNameIndexes();
- if (!symbol_indexes.empty())
- {
- std::sort(symbol_indexes.begin(), symbol_indexes.end());
- symbol_indexes.erase(std::unique(symbol_indexes.begin(), symbol_indexes.end()), symbol_indexes.end());
- count = symbol_indexes.size();
- SymbolIndicesToSymbolContextList (symbol_indexes, sc_list);
- }
-
- return count;
-}
+ if (!m_method_to_index.IsEmpty()) {
+ const UniqueCStringMap<uint32_t>::Entry *match;
+ for (match = m_method_to_index.FindFirstValueForName(name_cstr);
+ match != nullptr;
+ match = m_method_to_index.FindNextValueForName(match)) {
+ symbol_indexes.push_back(match->value);
+ }
+ }
+ }
+ if (name_type_mask & eFunctionNameTypeSelector) {
+ if (!m_name_indexes_computed)
+ InitNameIndexes();
-const Symbol *
-Symtab::GetParent (Symbol *child_symbol) const
-{
- uint32_t child_idx = GetIndexForSymbol(child_symbol);
- if (child_idx != UINT32_MAX && child_idx > 0)
- {
- for (uint32_t idx = child_idx - 1; idx != UINT32_MAX; --idx)
- {
- const Symbol *symbol = SymbolAtIndex (idx);
- const uint32_t sibling_idx = symbol->GetSiblingIndex();
- if (sibling_idx != UINT32_MAX && sibling_idx > child_idx)
- return symbol;
- }
+ if (!m_selector_to_index.IsEmpty()) {
+ const UniqueCStringMap<uint32_t>::Entry *match;
+ for (match = m_selector_to_index.FindFirstValueForName(name_cstr);
+ match != nullptr;
+ match = m_selector_to_index.FindNextValueForName(match)) {
+ symbol_indexes.push_back(match->value);
+ }
+ }
+ }
+
+ if (!symbol_indexes.empty()) {
+ std::sort(symbol_indexes.begin(), symbol_indexes.end());
+ symbol_indexes.erase(
+ std::unique(symbol_indexes.begin(), symbol_indexes.end()),
+ symbol_indexes.end());
+ count = symbol_indexes.size();
+ SymbolIndicesToSymbolContextList(symbol_indexes, sc_list);
+ }
+
+ return count;
+}
+
+const Symbol *Symtab::GetParent(Symbol *child_symbol) const {
+ uint32_t child_idx = GetIndexForSymbol(child_symbol);
+ if (child_idx != UINT32_MAX && child_idx > 0) {
+ for (uint32_t idx = child_idx - 1; idx != UINT32_MAX; --idx) {
+ const Symbol *symbol = SymbolAtIndex(idx);
+ const uint32_t sibling_idx = symbol->GetSiblingIndex();
+ if (sibling_idx != UINT32_MAX && sibling_idx > child_idx)
+ return symbol;
}
- return NULL;
+ }
+ return NULL;
}
More information about the lldb-commits
mailing list