diff options
author | Dimitry Andric <dim@FreeBSD.org> | 2015-12-30 11:55:28 +0000 |
---|---|---|
committer | Dimitry Andric <dim@FreeBSD.org> | 2015-12-30 11:55:28 +0000 |
commit | e81d9d49145e432d917eea3a70d2ae74dcad1d89 (patch) | |
tree | 9ed5e1a91f242e2cb5911577356e487a55c01b78 /source/Plugins/UnwindAssembly | |
parent | 85d8ef8f1f0e0e063a8571944302be2d2026f823 (diff) |
Notes
Diffstat (limited to 'source/Plugins/UnwindAssembly')
3 files changed, 113 insertions, 94 deletions
diff --git a/source/Plugins/UnwindAssembly/InstEmulation/UnwindAssemblyInstEmulation.cpp b/source/Plugins/UnwindAssembly/InstEmulation/UnwindAssemblyInstEmulation.cpp index 8f5d92697501c..eb5fec34fc200 100644 --- a/source/Plugins/UnwindAssembly/InstEmulation/UnwindAssemblyInstEmulation.cpp +++ b/source/Plugins/UnwindAssembly/InstEmulation/UnwindAssemblyInstEmulation.cpp @@ -117,21 +117,13 @@ UnwindAssemblyInstEmulation::GetNonCallSiteUnwindPlanFromAssembly (AddressRange& // cache the pc register number (in whatever register numbering this UnwindPlan uses) for // quick reference during instruction parsing. - uint32_t pc_reg_num = LLDB_INVALID_REGNUM; RegisterInfo pc_reg_info; - if (m_inst_emulator_ap->GetRegisterInfo (eRegisterKindGeneric, LLDB_REGNUM_GENERIC_PC, pc_reg_info)) - pc_reg_num = pc_reg_info.kinds[unwind_plan.GetRegisterKind()]; - else - pc_reg_num = LLDB_INVALID_REGNUM; + m_inst_emulator_ap->GetRegisterInfo (eRegisterKindGeneric, LLDB_REGNUM_GENERIC_PC, pc_reg_info); // cache the return address register number (in whatever register numbering this UnwindPlan uses) for // quick reference during instruction parsing. - uint32_t ra_reg_num = LLDB_INVALID_REGNUM; RegisterInfo ra_reg_info; - if (m_inst_emulator_ap->GetRegisterInfo (eRegisterKindGeneric, LLDB_REGNUM_GENERIC_RA, ra_reg_info)) - ra_reg_num = ra_reg_info.kinds[unwind_plan.GetRegisterKind()]; - else - ra_reg_num = LLDB_INVALID_REGNUM; + m_inst_emulator_ap->GetRegisterInfo (eRegisterKindGeneric, LLDB_REGNUM_GENERIC_RA, ra_reg_info); for (size_t idx=0; idx<num_instructions; ++idx) { @@ -511,7 +503,8 @@ UnwindAssemblyInstEmulation::WriteRegister (EmulateInstruction *instruction, log->PutCString(strm.GetData()); } - SetRegisterValue (*reg_info, reg_value); + if (!instruction->IsInstructionConditional()) + SetRegisterValue (*reg_info, reg_value); switch (context.type) { @@ -573,18 +566,45 @@ UnwindAssemblyInstEmulation::WriteRegister (EmulateInstruction *instruction, case EmulateInstruction::eContextPopRegisterOffStack: { - const uint32_t reg_num = reg_info->kinds[m_unwind_plan_ptr->GetRegisterKind()]; - const uint32_t generic_regnum = reg_info->kinds[eRegisterKindGeneric]; - if (reg_num != LLDB_INVALID_REGNUM && generic_regnum != LLDB_REGNUM_GENERIC_SP) + if (!instruction->IsInstructionConditional()) { - m_curr_row->SetRegisterLocationToSame (reg_num, /*must_replace*/ false); - m_curr_row_modified = true; + const uint32_t reg_num = reg_info->kinds[m_unwind_plan_ptr->GetRegisterKind()]; + const uint32_t generic_regnum = reg_info->kinds[eRegisterKindGeneric]; + if (reg_num != LLDB_INVALID_REGNUM && generic_regnum != LLDB_REGNUM_GENERIC_SP) + { + switch (context.info_type) + { + case EmulateInstruction::eInfoTypeAddress: + if (m_pushed_regs.find(reg_num) != m_pushed_regs.end() && + context.info.address == m_pushed_regs[reg_num]) + { + m_curr_row->SetRegisterLocationToSame(reg_num, + false /*must_replace*/); + m_curr_row_modified = true; + } + break; + case EmulateInstruction::eInfoTypeISA: + assert((generic_regnum == LLDB_REGNUM_GENERIC_PC || + generic_regnum == LLDB_REGNUM_GENERIC_FLAGS) && + "eInfoTypeISA used for poping a register other the the PC/FLAGS"); + if (generic_regnum != LLDB_REGNUM_GENERIC_FLAGS) + { + m_curr_row->SetRegisterLocationToSame(reg_num, + false /*must_replace*/); + m_curr_row_modified = true; + } + break; + default: + assert(false && "unhandled case, add code to handle this!"); + break; + } + } } } break; case EmulateInstruction::eContextSetFramePointer: - if (!m_fp_is_cfa) + if (!m_fp_is_cfa && !instruction->IsInstructionConditional()) { m_fp_is_cfa = true; m_cfa_reg_info = *reg_info; @@ -599,7 +619,7 @@ UnwindAssemblyInstEmulation::WriteRegister (EmulateInstruction *instruction, case EmulateInstruction::eContextAdjustStackPointer: // If we have created a frame using the frame pointer, don't follow // subsequent adjustments to the stack pointer. - if (!m_fp_is_cfa) + if (!m_fp_is_cfa && !instruction->IsInstructionConditional()) { m_curr_row->GetCFAValue().SetIsRegisterPlusOffset( m_curr_row->GetCFAValue().GetRegisterNumber(), diff --git a/source/Plugins/UnwindAssembly/InstEmulation/UnwindAssemblyInstEmulation.h b/source/Plugins/UnwindAssembly/InstEmulation/UnwindAssemblyInstEmulation.h index bf6d017370cc2..61d3ece3f6c36 100644 --- a/source/Plugins/UnwindAssembly/InstEmulation/UnwindAssemblyInstEmulation.h +++ b/source/Plugins/UnwindAssembly/InstEmulation/UnwindAssemblyInstEmulation.h @@ -1,4 +1,4 @@ -//===-- UnwindAssemblyInstEmulation.h ----------------------------*- C++ -*-===// +//===-- UnwindAssemblyInstEmulation.h ---------------------------*- C++ -*-===// // // The LLVM Compiler Infrastructure // @@ -10,6 +10,10 @@ #ifndef liblldb_UnwindAssemblyInstEmulation_h_ #define liblldb_UnwindAssemblyInstEmulation_h_ +// C Includes +// C++ Includes +// Other libraries and framework includes +// Project includes #include "lldb/lldb-private.h" #include "lldb/Core/EmulateInstruction.h" #include "lldb/Core/RegisterValue.h" @@ -19,32 +23,28 @@ class UnwindAssemblyInstEmulation : public lldb_private::UnwindAssembly { public: + ~UnwindAssemblyInstEmulation() override = default; - virtual - ~UnwindAssemblyInstEmulation () - { - } - - virtual bool - GetNonCallSiteUnwindPlanFromAssembly (lldb_private::AddressRange& func, - lldb_private::Thread& thread, - lldb_private::UnwindPlan& unwind_plan); + bool + GetNonCallSiteUnwindPlanFromAssembly(lldb_private::AddressRange& func, + lldb_private::Thread& thread, + lldb_private::UnwindPlan& unwind_plan) override; - virtual bool - AugmentUnwindPlanFromCallSite (lldb_private::AddressRange& func, - lldb_private::Thread& thread, - lldb_private::UnwindPlan& unwind_plan); + bool + AugmentUnwindPlanFromCallSite(lldb_private::AddressRange& func, + lldb_private::Thread& thread, + lldb_private::UnwindPlan& unwind_plan) override; - virtual bool - GetFastUnwindPlan (lldb_private::AddressRange& func, - lldb_private::Thread& thread, - lldb_private::UnwindPlan &unwind_plan); + bool + GetFastUnwindPlan(lldb_private::AddressRange& func, + lldb_private::Thread& thread, + lldb_private::UnwindPlan &unwind_plan) override; // thread may be NULL in which case we only use the Target (e.g. if this is called pre-process-launch). - virtual bool - FirstNonPrologueInsn (lldb_private::AddressRange& func, - const lldb_private::ExecutionContext &exe_ctx, - lldb_private::Address& first_non_prologue_insn); + bool + FirstNonPrologueInsn(lldb_private::AddressRange& func, + const lldb_private::ExecutionContext &exe_ctx, + lldb_private::Address& first_non_prologue_insn) override; static lldb_private::UnwindAssembly * CreateInstance (const lldb_private::ArchSpec &arch); @@ -64,14 +64,36 @@ public: static const char * GetPluginDescriptionStatic(); - virtual lldb_private::ConstString - GetPluginName(); + lldb_private::ConstString + GetPluginName() override; - virtual uint32_t - GetPluginVersion(); + uint32_t + GetPluginVersion() override; private: - + // Call CreateInstance to get an instance of this class + UnwindAssemblyInstEmulation(const lldb_private::ArchSpec &arch, + lldb_private::EmulateInstruction *inst_emulator) : + UnwindAssembly (arch), + m_inst_emulator_ap (inst_emulator), + m_range_ptr (NULL), + m_thread_ptr (NULL), + m_unwind_plan_ptr (NULL), + m_curr_row (), + m_cfa_reg_info (), + m_fp_is_cfa (false), + m_register_values (), + m_pushed_regs(), + m_curr_row_modified (false), + m_forward_branch_offset (0) + { + if (m_inst_emulator_ap.get()) + { + m_inst_emulator_ap->SetBaton (this); + m_inst_emulator_ap->SetCallbacks (ReadMemory, WriteMemory, ReadRegister, WriteRegister); + } + } + static size_t ReadMemory (lldb_private::EmulateInstruction *instruction, void *baton, @@ -101,7 +123,6 @@ private: const lldb_private::RegisterInfo *reg_info, const lldb_private::RegisterValue ®_value); - // size_t // ReadMemory (lldb_private::EmulateInstruction *instruction, // const lldb_private::EmulateInstruction::Context &context, @@ -127,29 +148,6 @@ private: const lldb_private::RegisterInfo *reg_info, const lldb_private::RegisterValue ®_value); - // Call CreateInstance to get an instance of this class - UnwindAssemblyInstEmulation (const lldb_private::ArchSpec &arch, - lldb_private::EmulateInstruction *inst_emulator) : - UnwindAssembly (arch), - m_inst_emulator_ap (inst_emulator), - m_range_ptr (NULL), - m_thread_ptr (NULL), - m_unwind_plan_ptr (NULL), - m_curr_row (), - m_cfa_reg_info (), - m_fp_is_cfa (false), - m_register_values (), - m_pushed_regs(), - m_curr_row_modified (false), - m_forward_branch_offset (0) - { - if (m_inst_emulator_ap.get()) - { - m_inst_emulator_ap->SetBaton (this); - m_inst_emulator_ap->SetCallbacks (ReadMemory, WriteMemory, ReadRegister, WriteRegister); - } - } - static uint64_t MakeRegisterKindValuePair (const lldb_private::RegisterInfo ®_info); diff --git a/source/Plugins/UnwindAssembly/x86/UnwindAssembly-x86.h b/source/Plugins/UnwindAssembly/x86/UnwindAssembly-x86.h index 8a4fe7c09800c..4d43a6e02b731 100644 --- a/source/Plugins/UnwindAssembly/x86/UnwindAssembly-x86.h +++ b/source/Plugins/UnwindAssembly/x86/UnwindAssembly-x86.h @@ -1,4 +1,4 @@ -//===-- UnwindAssembly-x86.h -------------------------------------*- C++ -*-===// +//===-- UnwindAssembly-x86.h ------------------------------------*- C++ -*-===// // // The LLVM Compiler Infrastructure // @@ -10,42 +10,44 @@ #ifndef liblldb_UnwindAssembly_x86_h_ #define liblldb_UnwindAssembly_x86_h_ +// C Includes +// C++ Includes +// Other libraries and framework includes #include "llvm-c/Disassembler.h" +// Project includes #include "lldb/lldb-private.h" #include "lldb/Target/UnwindAssembly.h" class UnwindAssembly_x86 : public lldb_private::UnwindAssembly { public: + ~UnwindAssembly_x86() override; - ~UnwindAssembly_x86 (); + bool + GetNonCallSiteUnwindPlanFromAssembly(lldb_private::AddressRange& func, + lldb_private::Thread& thread, + lldb_private::UnwindPlan& unwind_plan) override; - virtual bool - GetNonCallSiteUnwindPlanFromAssembly (lldb_private::AddressRange& func, - lldb_private::Thread& thread, - lldb_private::UnwindPlan& unwind_plan); + bool + AugmentUnwindPlanFromCallSite(lldb_private::AddressRange& func, + lldb_private::Thread& thread, + lldb_private::UnwindPlan& unwind_plan) override; - virtual bool - AugmentUnwindPlanFromCallSite (lldb_private::AddressRange& func, - lldb_private::Thread& thread, - lldb_private::UnwindPlan& unwind_plan); - - virtual bool - GetFastUnwindPlan (lldb_private::AddressRange& func, - lldb_private::Thread& thread, - lldb_private::UnwindPlan &unwind_plan); + bool + GetFastUnwindPlan(lldb_private::AddressRange& func, + lldb_private::Thread& thread, + lldb_private::UnwindPlan &unwind_plan) override; // thread may be NULL in which case we only use the Target (e.g. if this is called pre-process-launch). - virtual bool - FirstNonPrologueInsn (lldb_private::AddressRange& func, - const lldb_private::ExecutionContext &exe_ctx, - lldb_private::Address& first_non_prologue_insn); + bool + FirstNonPrologueInsn(lldb_private::AddressRange& func, + const lldb_private::ExecutionContext &exe_ctx, + lldb_private::Address& first_non_prologue_insn) override; static lldb_private::UnwindAssembly * CreateInstance (const lldb_private::ArchSpec &arch); - //------------------------------------------------------------------ // PluginInterface protocol //------------------------------------------------------------------ @@ -61,11 +63,11 @@ public: static const char * GetPluginDescriptionStatic(); - virtual lldb_private::ConstString - GetPluginName(); + lldb_private::ConstString + GetPluginName() override; - virtual uint32_t - GetPluginVersion(); + uint32_t + GetPluginVersion() override; private: UnwindAssembly_x86 (const lldb_private::ArchSpec &arch, int cpu); @@ -74,5 +76,4 @@ private: lldb_private::ArchSpec m_arch; }; - #endif // liblldb_UnwindAssembly_x86_h_ |