diff options
41 files changed, 2456 insertions, 1435 deletions
diff --git a/lldb/include/lldb/Core/EmulateInstruction.h b/lldb/include/lldb/Core/EmulateInstruction.h index 3ea6bd9..ae2fbf0 100644 --- a/lldb/include/lldb/Core/EmulateInstruction.h +++ b/lldb/include/lldb/Core/EmulateInstruction.h @@ -113,6 +113,9 @@ public: // Add or subtract a value from the stack eContextAdjustStackPointer, + // Adjust the frame pointer for the current frame + eContextSetFramePointer, + // Add or subtract a value from a base address register (other than SP) eContextAdjustBaseRegister, @@ -234,6 +237,12 @@ public: } info; + Context () : + type (eContextInvalid), + info_type (eInfoTypeNoArgs) + { + } + void SetRegisterPlusOffset (RegisterInfo base_reg, int64_t signed_offset) @@ -347,7 +356,7 @@ public: } void - Dump (FILE *fh, + Dump (Stream &s, EmulateInstruction *instruction) const; }; diff --git a/lldb/include/lldb/Core/PluginManager.h b/lldb/include/lldb/Core/PluginManager.h index 6b66465..66e152d 100644 --- a/lldb/include/lldb/Core/PluginManager.h +++ b/lldb/include/lldb/Core/PluginManager.h @@ -270,40 +270,6 @@ public: static UnwindAssemblyCreateInstance GetUnwindAssemblyCreateCallbackForPluginName (const char *name); - //------------------------------------------------------------------ - // ArchDefaultUnwindPlan - //------------------------------------------------------------------ - static bool - RegisterPlugin (const char *name, - const char *description, - ArchDefaultUnwindPlanCreateInstance create_callback); - - static bool - UnregisterPlugin (ArchDefaultUnwindPlanCreateInstance create_callback); - - static ArchDefaultUnwindPlanCreateInstance - GetArchDefaultUnwindPlanCreateCallbackAtIndex (uint32_t idx); - - static ArchDefaultUnwindPlanCreateInstance - GetArchDefaultUnwindPlanCreateCallbackForPluginName (const char *name); - - //------------------------------------------------------------------ - // ArchVolatileRegs - //------------------------------------------------------------------ - static bool - RegisterPlugin (const char *name, - const char *description, - ArchVolatileRegsCreateInstance create_callback); - - static bool - UnregisterPlugin (ArchVolatileRegsCreateInstance create_callback); - - static ArchVolatileRegsCreateInstance - GetArchVolatileRegsCreateCallbackAtIndex (uint32_t idx); - - static ArchVolatileRegsCreateInstance - GetArchVolatileRegsCreateCallbackForPluginName (const char *name); - }; diff --git a/lldb/include/lldb/Symbol/UnwindPlan.h b/lldb/include/lldb/Symbol/UnwindPlan.h index 43ee40d..8bf7ea5 100644 --- a/lldb/include/lldb/Symbol/UnwindPlan.h +++ b/lldb/include/lldb/Symbol/UnwindPlan.h @@ -50,8 +50,8 @@ public: unspecified, // not specified, we may be able to assume this // is the same register. gcc doesn't specify all // initial values so we really don't know... - isUndefined, // reg is not available, e.g. volatile reg - isSame, // reg is unchanged + undefined, // reg is not available, e.g. volatile reg + same, // reg is unchanged atCFAPlusOffset, // reg = deref(CFA + offset) isCFAPlusOffset, // reg = CFA + offset inOtherRegister, // reg = other reg @@ -68,39 +68,129 @@ public: bool operator == (const RegisterLocation& rhs) const; - void SetUnspecified(); + bool + operator != (const RegisterLocation &rhs) const + { + return !(*this == rhs); + } + + void + SetUnspecified() + { + m_type = unspecified; + } - void SetUndefined(); + void + SetUndefined() + { + m_type = undefined; + } - void SetSame(); + void + SetSame() + { + m_type = same; + } - bool IsSame () const { return m_type == isSame; } + bool + IsSame () const + { + return m_type == same; + } - bool IsUnspecified () const { return m_type == unspecified; } + bool + IsUnspecified () const + { + return m_type == unspecified; + } - bool IsCFAPlusOffset () const { return m_type == isCFAPlusOffset; } + bool + IsCFAPlusOffset () const + { + return m_type == isCFAPlusOffset; + } - bool IsAtCFAPlusOffset () const { return m_type == atCFAPlusOffset; } + bool + IsAtCFAPlusOffset () const + { + return m_type == atCFAPlusOffset; + } - bool IsInOtherRegister () const { return m_type == inOtherRegister; } + bool + IsInOtherRegister () const + { + return m_type == inOtherRegister; + } - bool IsAtDWARFExpression () const { return m_type == atDWARFExpression; } + bool + IsAtDWARFExpression () const + { + return m_type == atDWARFExpression; + } - bool IsDWARFExpression () const { return m_type == isDWARFExpression; } + bool + IsDWARFExpression () const + { + return m_type == isDWARFExpression; + } - void SetAtCFAPlusOffset (int32_t offset); + void + SetAtCFAPlusOffset (int32_t offset) + { + m_type = atCFAPlusOffset; + m_location.offset = offset; + } - void SetIsCFAPlusOffset (int32_t offset); + void + SetIsCFAPlusOffset (int32_t offset) + { + m_type = isCFAPlusOffset; + m_location.offset = offset; + } - void SetInRegister (uint32_t reg_num); + void + SetInRegister (uint32_t reg_num) + { + m_type = inOtherRegister; + m_location.reg_num = reg_num; + } - uint32_t GetRegisterNumber () const { return m_location.reg_num; } + uint32_t + GetRegisterNumber () const + { + if (m_type == inOtherRegister) + return m_location.reg_num; + return LLDB_INVALID_REGNUM; + } - RestoreType GetLocationType () const { return m_type; } + RestoreType + GetLocationType () const + { + return m_type; + } - int32_t GetOffset () const { return m_location.offset; } + int32_t + GetOffset () const + { + if (m_type == atCFAPlusOffset || m_type == isCFAPlusOffset) + return m_location.offset; + return 0; + } - void GetDWARFExpr (const uint8_t **opcodes, uint16_t& len) const { *opcodes = m_location.expr.opcodes; len = m_location.expr.length; } + void + GetDWARFExpr (const uint8_t **opcodes, uint16_t& len) const + { + if (m_type == atDWARFExpression || m_type == isDWARFExpression) + { + *opcodes = m_location.expr.opcodes; + len = m_location.expr.length; + } + else + { + *opcodes = NULL; + len = 0; + } + } void SetAtDWARFExpression (const uint8_t *opcodes, uint32_t len); @@ -109,13 +199,27 @@ public: SetIsDWARFExpression (const uint8_t *opcodes, uint32_t len); const uint8_t * - GetDWARFExpressionBytes () { return m_location.expr.opcodes; } + GetDWARFExpressionBytes () + { + if (m_type == atDWARFExpression || m_type == isDWARFExpression) + return m_location.expr.opcodes; + return NULL; + } int - GetDWARFExpressionLength () { return m_location.expr.length; } + GetDWARFExpressionLength () + { + if (m_type == atDWARFExpression || m_type == isDWARFExpression) + return m_location.expr.length; + return 0; + } void - Dump (Stream &s) const; + Dump (Stream &s, + const UnwindPlan* unwind_plan, + const UnwindPlan::Row* row, + Thread* thread, + bool verbose) const; private: RestoreType m_type; // How do we locate this register? @@ -165,12 +269,39 @@ public: { return m_cfa_reg_num; } + + bool + SetRegisterLocationToAtCFAPlusOffset (uint32_t reg_num, + int32_t offset, + bool can_replace); + + bool + SetRegisterLocationToIsCFAPlusOffset (uint32_t reg_num, + int32_t offset, + bool can_replace); + + bool + SetRegisterLocationToUndefined (uint32_t reg_num, + bool can_replace, + bool can_replace_only_if_unspecified); + + bool + SetRegisterLocationToUnspecified (uint32_t reg_num, + bool can_replace); + + bool + SetRegisterLocationToRegister (uint32_t reg_num, + uint32_t other_reg_num, + bool can_replace); + + bool + SetRegisterLocationToSame (uint32_t reg_num, + bool must_replace); + + void - SetCFARegister (uint32_t reg_num) - { - m_cfa_reg_num = reg_num; - } + SetCFARegister (uint32_t reg_num); int32_t GetCFAOffset () const @@ -195,7 +326,28 @@ public: Clear (); void - Dump (Stream& s, int register_kind, Thread* thread) const; + Dump (Stream& s, const UnwindPlan* unwind_plan, Thread* thread, lldb::addr_t base_addr) const; + + bool + operator == (const Row &rhs) const + { + if (m_offset == rhs.m_offset && + m_cfa_reg_num != rhs.m_cfa_reg_num && + m_cfa_offset != rhs.m_cfa_offset) + return m_register_locations == rhs.m_register_locations; + return false; + } + + bool + operator != (const Row &rhs) const + { + if (m_offset != rhs.m_offset || + m_cfa_reg_num != rhs.m_cfa_reg_num || + m_cfa_offset != rhs.m_cfa_offset) + return true; + + return m_register_locations != rhs.m_register_locations; + } protected: typedef std::map<uint32_t, RegisterLocation> collection; @@ -208,10 +360,10 @@ public: public: - UnwindPlan () : + UnwindPlan (uint32_t reg_kind) : m_row_list (), m_plan_valid_address_range (), - m_register_kind (UINT32_MAX), + m_register_kind (reg_kind), m_source_name () { } @@ -221,7 +373,7 @@ public: } void - Dump (Stream& s, Thread* thread) const; + Dump (Stream& s, Thread* thread, lldb::addr_t base_addr) const; void AppendRow (const Row& row); @@ -233,11 +385,25 @@ public: const Row* GetRowForFunctionOffset (int offset) const; - void - SetRegisterKind (uint32_t rk); + uint32_t + GetRegisterKind () const + { + return m_register_kind; + } + void + SetRegisterKind (uint32_t kind) + { + m_register_kind = kind; + } + uint32_t - GetRegisterKind (void) const; + GetInitialCFARegister () const + { + if (m_row_list.empty()) + return LLDB_INVALID_REGNUM; + return m_row_list.front().GetCFARegister(); + } // This UnwindPlan may not be valid at every address of the function span. // For instance, a FastUnwindPlan will not be valid at the prologue setup @@ -245,6 +411,12 @@ public: void SetPlanValidAddressRange (const AddressRange& range); + const AddressRange & + GetAddressRange () const + { + return m_plan_valid_address_range; + } + bool PlanValidAtAddress (Address addr); @@ -254,6 +426,9 @@ public: const UnwindPlan::Row& GetRowAtIndex (uint32_t idx) const; + const UnwindPlan::Row& + GetLastRow () const; + lldb_private::ConstString GetSourceName () const; @@ -268,12 +443,16 @@ public: { m_row_list.clear(); m_plan_valid_address_range.Clear(); - m_register_kind = UINT32_MAX; + m_register_kind = lldb::eRegisterKindDWARF; m_source_name.Clear(); } + const RegisterInfo * + GetRegisterInfo (Thread* thread, uint32_t reg_num) const; + private: + typedef std::vector<Row> collection; collection m_row_list; AddressRange m_plan_valid_address_range; diff --git a/lldb/include/lldb/Target/ABI.h b/lldb/include/lldb/Target/ABI.h index a185e86..3f3b75d 100644 --- a/lldb/include/lldb/Target/ABI.h +++ b/lldb/include/lldb/Target/ABI.h @@ -45,9 +45,19 @@ public: virtual bool GetReturnValue (Thread &thread, Value &value) const = 0; - - static ABI* + + virtual bool + CreateFunctionEntryUnwindPlan (UnwindPlan &unwind_plan) = 0; + + virtual bool + CreateDefaultUnwindPlan (UnwindPlan &unwind_plan) = 0; + + virtual bool + RegisterIsVolatile (const RegisterInfo *reg_info) = 0; + + static lldb::ABISP FindPlugin (const ArchSpec &arch); + protected: //------------------------------------------------------------------ // Classes that inherit from ABI can see and modify these diff --git a/lldb/include/lldb/Target/ArchDefaultUnwindPlan.h b/lldb/include/lldb/Target/ArchDefaultUnwindPlan.h deleted file mode 100644 index ad848fa..0000000 --- a/lldb/include/lldb/Target/ArchDefaultUnwindPlan.h +++ /dev/null @@ -1,43 +0,0 @@ -//===-- ArchDefaultUnwindPlan.h ---------------------------------*- C++ -*-===// -// -// The LLVM Compiler Infrastructure -// -// This file is distributed under the University of Illinois Open Source -// License. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#ifndef utility_ArchDefaultUnwindPlan_h_ -#define utility_ArchDefaultUnwindPlan_h_ - -#include "lldb/lldb-private.h" -#include "lldb/Core/PluginInterface.h" - -namespace lldb_private { - -class ArchDefaultUnwindPlan : - public PluginInterface -{ -public: - - virtual - ~ArchDefaultUnwindPlan(); - - virtual lldb::UnwindPlanSP - GetArchDefaultUnwindPlan (Thread& thread, - const Address ¤t_pc) = 0; - - static lldb::ArchDefaultUnwindPlanSP - FindPlugin (const ArchSpec &arch); - -protected: - ArchDefaultUnwindPlan(); -private: - DISALLOW_COPY_AND_ASSIGN (ArchDefaultUnwindPlan); -}; - -} // namespace lldb_private - -#endif //utility_ArchDefaultUnwindPlan_h_ - - diff --git a/lldb/include/lldb/Target/ArchVolatileRegs.h b/lldb/include/lldb/Target/ArchVolatileRegs.h deleted file mode 100644 index 130471f..0000000 --- a/lldb/include/lldb/Target/ArchVolatileRegs.h +++ /dev/null @@ -1,53 +0,0 @@ -//===-- ArchVolatileRegs.h --------------------------------------*- C++ -*-===// -// -// The LLVM Compiler Infrastructure -// -// This file is distributed under the University of Illinois Open Source -// License. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#ifndef utility_ArchVolatileRegs_h_ -#define utility_ArchVolatileRegs_h_ - -#include "lldb/lldb-private.h" -#include "lldb/Core/PluginInterface.h" - -namespace lldb_private { - -class ArchVolatileRegs : - public PluginInterface -{ -public: - - virtual - ~ArchVolatileRegs(); - - // Given a register number (in the eRegisterKindLLDB register numbering - // scheme), returns true if the register is defined to be "volatile" in - // this architecture -- that is, a function is not required to preserve - // the contents of the register. - // If r8 is defined to be volatile, it means that a function can put - // values in that register without saving the previous contents. - // If r8 is defined to be non-volatile (preseved), a function must save - // the value in the register before it is used. - - // The thread reference is needed to get a RegisterContext to look up by - // register names. - - virtual bool - RegisterIsVolatile (lldb_private::Thread& thread, uint32_t regnum) = 0; - - static ArchVolatileRegs* - FindPlugin (const ArchSpec &arch); - -protected: - ArchVolatileRegs(); -private: - DISALLOW_COPY_AND_ASSIGN (ArchVolatileRegs); -}; - -} // namespace lldb_private - -#endif //utility_ArchVolatileRegs_h_ - diff --git a/lldb/include/lldb/Target/Process.h b/lldb/include/lldb/Target/Process.h index ca2cabe..93819bb 100644 --- a/lldb/include/lldb/Target/Process.h +++ b/lldb/include/lldb/Target/Process.h @@ -2457,7 +2457,7 @@ protected: ShouldBroadcastEvent (Event *event_ptr); public: - const ABI * + const lldb::ABISP & GetABI (); DynamicLoader * diff --git a/lldb/include/lldb/lldb-forward-rtti.h b/lldb/include/lldb/lldb-forward-rtti.h index 98feb2d..ae07c06 100644 --- a/lldb/include/lldb/lldb-forward-rtti.h +++ b/lldb/include/lldb/lldb-forward-rtti.h @@ -21,7 +21,6 @@ namespace lldb { typedef SharedPtr<lldb_private::ABI>::Type ABISP; typedef SharedPtr<lldb_private::AddressResolver>::Type AddressResolverSP; - typedef SharedPtr<lldb_private::ArchDefaultUnwindPlan>::Type ArchDefaultUnwindPlanSP; typedef SharedPtr<lldb_private::Baton>::Type BatonSP; typedef SharedPtr<lldb_private::Block>::Type BlockSP; typedef SharedPtr<lldb_private::Breakpoint>::Type BreakpointSP; diff --git a/lldb/include/lldb/lldb-forward.h b/lldb/include/lldb/lldb-forward.h index a8c71d5..d053591 100644 --- a/lldb/include/lldb/lldb-forward.h +++ b/lldb/include/lldb/lldb-forward.h @@ -22,8 +22,6 @@ class Address; class AddressRange; class AddressResolver; class ArchSpec; -class ArchDefaultUnwindPlan; -class ArchVolatileRegs; class Args; class Baton; class Block; diff --git a/lldb/include/lldb/lldb-private-interfaces.h b/lldb/include/lldb/lldb-private-interfaces.h index 0111c92..1ff3d04 100644 --- a/lldb/include/lldb/lldb-private-interfaces.h +++ b/lldb/include/lldb/lldb-private-interfaces.h @@ -16,7 +16,7 @@ namespace lldb_private { - typedef ABI* (*ABICreateInstance) (const ArchSpec &arch); + typedef lldb::ABISP (*ABICreateInstance) (const ArchSpec &arch); typedef Disassembler* (*DisassemblerCreateInstance) (const ArchSpec &arch); typedef DynamicLoader* (*DynamicLoaderCreateInstance) (Process* process, bool force); typedef ObjectContainer* (*ObjectContainerCreateInstance) (Module* module, lldb::DataBufferSP& dataSP, const FileSpec *file, lldb::addr_t offset, lldb::addr_t length); @@ -32,8 +32,6 @@ namespace lldb_private typedef bool (*WatchpointHitCallback) (void *baton, StoppointCallbackContext *context, lldb::user_id_t watch_id, uint32_t type); typedef ThreadPlan * (*ThreadPlanShouldStopHereCallback) (ThreadPlan *current_plan, Flags &flags, void *baton); typedef UnwindAssembly* (*UnwindAssemblyCreateInstance) (const ArchSpec &arch); - typedef ArchDefaultUnwindPlan* (*ArchDefaultUnwindPlanCreateInstance) (const ArchSpec &arch); - typedef ArchVolatileRegs* (*ArchVolatileRegsCreateInstance) (const ArchSpec &arch); typedef int (*ComparisonFunction)(const void *, const void *); } // namespace lldb_private diff --git a/lldb/lldb.xcodeproj/project.pbxproj b/lldb/lldb.xcodeproj/project.pbxproj index d48b395..517d564 100644 --- a/lldb/lldb.xcodeproj/project.pbxproj +++ b/lldb/lldb.xcodeproj/project.pbxproj @@ -13,8 +13,6 @@ 261744781168585B005ADD65 /* SBType.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 261744771168585B005ADD65 /* SBType.cpp */; }; 2617447A11685869005ADD65 /* SBType.h in Headers */ = {isa = PBXBuildFile; fileRef = 2617447911685869005ADD65 /* SBType.h */; settings = {ATTRIBUTES = (Public, ); }; }; 262CFC7711A4510000946C6C /* debugserver in Resources */ = {isa = PBXBuildFile; fileRef = 26CE05A0115C31E50022F371 /* debugserver */; }; - 2630BFAF1365F3220070C534 /* ArchDefaultUnwindPlan.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 2630BFAD1365F3220070C534 /* ArchDefaultUnwindPlan.cpp */; }; - 2630BFB01365F3220070C534 /* ArchVolatileRegs.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 2630BFAE1365F3220070C534 /* ArchVolatileRegs.cpp */; }; 26368A3C126B697600E8659F /* darwin-debug.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 26368A3B126B697600E8659F /* darwin-debug.cpp */; }; 26368AF7126B960500E8659F /* darwin-debug in Resources */ = {isa = PBXBuildFile; fileRef = 26579F68126A25920007C5CB /* darwin-debug */; }; 263E949F13661AEA00E7D1CE /* UnwindAssembly-x86.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 263E949D13661AE400E7D1CE /* UnwindAssembly-x86.cpp */; }; @@ -214,8 +212,6 @@ 2689008713353E2200698AC0 /* ScriptInterpreter.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9A82010B10FFB49800182560 /* ScriptInterpreter.cpp */; }; 2689008813353E2200698AC0 /* ScriptInterpreterNone.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9A2771FC1135A37500E6ADB6 /* ScriptInterpreterNone.cpp */; }; 2689008913353E2200698AC0 /* ScriptInterpreterPython.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 26BC7F0C10F1B8DD00F91463 /* ScriptInterpreterPython.cpp */; }; - 2689008A13353E4200698AC0 /* ABIMacOSX_i386.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 497650CE11A21BEE008DDB57 /* ABIMacOSX_i386.cpp */; }; - 2689008B13353E4200698AC0 /* ABISysV_x86_64.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 493C63F11189203300914D5E /* ABISysV_x86_64.cpp */; }; 2689008C13353E4200698AC0 /* DisassemblerLLVM.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 260C897410F57C5600BB2B04 /* DisassemblerLLVM.cpp */; }; 2689008D13353E4200698AC0 /* DynamicLoaderMacOSXDYLD.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 260C897A10F57C5600BB2B04 /* DynamicLoaderMacOSXDYLD.cpp */; }; 2689008E13353E4200698AC0 /* DynamicLoaderStatic.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 268A683D1321B53B000E3FB8 /* DynamicLoaderStatic.cpp */; }; @@ -370,10 +366,9 @@ 268F9D55123AA16600B91E9B /* SBSymbolContextList.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 268F9D54123AA16600B91E9B /* SBSymbolContextList.cpp */; }; 2692BA15136610C100F9E14D /* UnwindAssemblyInstEmulation.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 2692BA13136610C100F9E14D /* UnwindAssemblyInstEmulation.cpp */; }; 2692BA16136610C100F9E14D /* UnwindAssemblyInstEmulation.h in Headers */ = {isa = PBXBuildFile; fileRef = 2692BA14136610C100F9E14D /* UnwindAssemblyInstEmulation.h */; }; - 2692BA1F136614D800F9E14D /* ArchDefaultUnwindPlan-x86.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 2692BA1D136614D000F9E14D /* ArchDefaultUnwindPlan-x86.cpp */; }; - 2692BA231366150100F9E14D /* ArchVolatileRegs-x86.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 2692BA21136614FC00F9E14D /* ArchVolatileRegs-x86.cpp */; }; 2697A54D133A6305004E4240 /* PlatformDarwin.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 2697A54B133A6305004E4240 /* PlatformDarwin.cpp */; }; 2697A54E133A6305004E4240 /* PlatformDarwin.h in Headers */ = {isa = PBXBuildFile; fileRef = 2697A54C133A6305004E4240 /* PlatformDarwin.h */; }; + 26A69C5F137A17A500262477 /* RegisterValue.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 26C6886E137880C400407EDF /* RegisterValue.cpp */; }; 26A7A035135E6E4200FB369E /* NamedOptionValue.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 26A7A034135E6E4200FB369E /* NamedOptionValue.cpp */; }; 26B1FA1413380E61002886E2 /* LLDBWrapPython.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 26A4EEB511682AAC007A372A /* LLDBWrapPython.cpp */; }; 26B1FCB813381071002886E2 /* CoreFoundation.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 26F5C39010F3FA26009D5894 /* CoreFoundation.framework */; }; @@ -386,13 +381,15 @@ 26B42C4D1187ABA50079C8C8 /* LLDB.h in Headers */ = {isa = PBXBuildFile; fileRef = 26B42C4C1187ABA50079C8C8 /* LLDB.h */; settings = {ATTRIBUTES = (Public, ); }; }; 26BCFC521368AE38006DC050 /* OptionGroupFormat.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 26BCFC511368AE38006DC050 /* OptionGroupFormat.cpp */; }; 26BD407F135D2AE000237D80 /* FileLineResolver.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 26BD407E135D2ADF00237D80 /* FileLineResolver.cpp */; }; - 26C6886F137880C400407EDF /* RegisterValue.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 26C6886E137880C400407EDF /* RegisterValue.cpp */; }; 26C72C94124322890068DC16 /* SBStream.h in Headers */ = {isa = PBXBuildFile; fileRef = 26C72C93124322890068DC16 /* SBStream.h */; settings = {ATTRIBUTES = (Public, ); }; }; 26C72C961243229A0068DC16 /* SBStream.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 26C72C951243229A0068DC16 /* SBStream.cpp */; }; 26D265A2136B40EE002EEE45 /* SharingPtr.h in Headers */ = {isa = PBXBuildFile; fileRef = 261B5A5311C3F2AD00AABD0A /* SharingPtr.h */; settings = {ATTRIBUTES = (Public, ); }; }; 26D265BC136B4269002EEE45 /* lldb-public.h in Headers */ = {isa = PBXBuildFile; fileRef = 26651A14133BEC76005B64B7 /* lldb-public.h */; settings = {ATTRIBUTES = (Public, ); }; }; 26D5E15F135BAEA2006EA0A7 /* OptionGroupArchitecture.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 26D5E15E135BAEA2006EA0A7 /* OptionGroupArchitecture.cpp */; }; 26D5E163135BB054006EA0A7 /* OptionGroupPlatform.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 26D5E162135BB054006EA0A7 /* OptionGroupPlatform.cpp */; }; + 26DB3E161379E7AD0080DC73 /* ABIMacOSX_arm.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 26DB3E071379E7AD0080DC73 /* ABIMacOSX_arm.cpp */; }; + 26DB3E1C1379E7AD0080DC73 /* ABIMacOSX_i386.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 26DB3E0F1379E7AD0080DC73 /* ABIMacOSX_i386.cpp */; }; + 26DB3E1F1379E7AD0080DC73 /* ABISysV_x86_64.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 26DB3E131379E7AD0080DC73 /* ABISysV_x86_64.cpp */; }; 26DC6A171337FE8000FF7998 /* liblldb-core.a in Frameworks */ = {isa = PBXBuildFile; fileRef = 2689FFCA13353D7A00698AC0 /* liblldb-core.a */; }; 26DC6A1D1337FECA00FF7998 /* lldb-platform.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 26DC6A1C1337FECA00FF7998 /* lldb-platform.cpp */; }; 26DE1E6B11616C2E00A093E2 /* lldb-forward-rtti.h in Headers */ = {isa = PBXBuildFile; fileRef = 26DE1E6911616C2E00A093E2 /* lldb-forward-rtti.h */; settings = {ATTRIBUTES = (Public, ); }; }; @@ -650,10 +647,6 @@ 261B5A5311C3F2AD00AABD0A /* SharingPtr.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = SharingPtr.h; path = include/lldb/Utility/SharingPtr.h; sourceTree = "<group>"; }; 26217930133BC8640083B112 /* lldb-private-types.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = "lldb-private-types.h"; path = "include/lldb/lldb-private-types.h"; sourceTree = "<group>"; }; 26217932133BCB850083B112 /* lldb-private-enumerations.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = "lldb-private-enumerations.h"; path = "include/lldb/lldb-private-enumerations.h"; sourceTree = "<group>"; }; - 2630BFAB1365F3140070C534 /* ArchDefaultUnwindPlan.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = ArchDefaultUnwindPlan.h; path = include/lldb/Target/ArchDefaultUnwindPlan.h; sourceTree = "<group>"; }; - 2630BFAC1365F3140070C534 /* ArchVolatileRegs.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = ArchVolatileRegs.h; path = include/lldb/Target/ArchVolatileRegs.h; sourceTree = "<group>"; }; - 2630BFAD1365F3220070C534 /* ArchDefaultUnwindPlan.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = ArchDefaultUnwindPlan.cpp; path = source/Target/ArchDefaultUnwindPlan.cpp; sourceTree = "<group>"; }; - 2630BFAE1365F3220070C534 /* ArchVolatileRegs.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = ArchVolatileRegs.cpp; path = source/Target/ArchVolatileRegs.cpp; sourceTree = "<group>"; }; 263664921140A4930075843B /* Debugger.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = Debugger.cpp; path = source/Core/Debugger.cpp; sourceTree = "<group>"; }; 263664941140A4C10075843B /* Debugger.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = Debugger.h; path = include/lldb/Core/Debugger.h; sourceTree = "<group>"; }; 26368A3B126B697600E8659F /* darwin-debug.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = "darwin-debug.cpp"; path = "tools/darwin-debug/darwin-debug.cpp"; sourceTree = "<group>"; }; @@ -734,10 +727,6 @@ 268F9D54123AA16600B91E9B /* SBSymbolContextList.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SBSymbolContextList.cpp; path = source/API/SBSymbolContextList.cpp; sourceTree = "<group>"; }; 2692BA13136610C100F9E14D /* UnwindAssemblyInstEmulation.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = UnwindAssemblyInstEmulation.cpp; sourceTree = "<group>"; }; 2692BA14136610C100F9E14D /* UnwindAssemblyInstEmulation.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = UnwindAssemblyInstEmulation.h; sourceTree = "<group>"; }; - 2692BA1D136614D000F9E14D /* ArchDefaultUnwindPlan-x86.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = "ArchDefaultUnwindPlan-x86.cpp"; sourceTree = "<group>"; }; - 2692BA1E136614D000F9E14D /* ArchDefaultUnwindPlan-x86.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "ArchDefaultUnwindPlan-x86.h"; sourceTree = "<group>"; }; - 2692BA21136614FC00F9E14D /* ArchVolatileRegs-x86.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = "ArchVolatileRegs-x86.cpp"; sourceTree = "<group>"; }; - 2692BA22136614FC00F9E14D /* ArchVolatileRegs-x86.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = "ArchVolatileRegs-x86.h"; sourceTree = "<group>"; }; 269416AD119A024800FF2715 /* CommandObjectTarget.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = CommandObjectTarget.cpp; path = source/Commands/CommandObjectTarget.cpp; sourceTree = "<group>"; }; 269416AE119A024800FF2715 /* CommandObjectTarget.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = CommandObjectTarget.h; path = source/Commands/CommandObjectTarget.h; sourceTree = "<group>"; }; 2697A54B133A6305004E4240 /* PlatformDarwin.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = PlatformDarwin.cpp; sourceTree = "<group>"; }; @@ -1036,6 +1025,12 @@ 26D9FDC612F784E60003F2EE /* EmulateInstruction.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = EmulateInstruction.h; path = include/lldb/Core/EmulateInstruction.h; sourceTree = "<group>"; }; 26D9FDC812F784FD0003F2EE /* EmulateInstruction.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = EmulateInstruction.cpp; path = source/Core/EmulateInstruction.cpp; sourceTree = "<group>"; }; 26DAFD9711529BC7005A394E /* ExecutionContextScope.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ExecutionContextScope.h; path = include/lldb/Target/ExecutionContextScope.h; sourceTree = "<group>"; }; + 26DB3E071379E7AD0080DC73 /* ABIMacOSX_arm.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ABIMacOSX_arm.cpp; sourceTree = "<group>"; }; + 26DB3E081379E7AD0080DC73 /* ABIMacOSX_arm.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ABIMacOSX_arm.h; sourceTree = "<group>"; }; + 26DB3E0F1379E7AD0080DC73 /* ABIMacOSX_i386.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ABIMacOSX_i386.cpp; sourceTree = "<group>"; }; + 26DB3E101379E7AD0080DC73 /* ABIMacOSX_i386.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ABIMacOSX_i386.h; sourceTree = "<group>"; }; + 26DB3E131379E7AD0080DC73 /* ABISysV_x86_64.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ABISysV_x86_64.cpp; sourceTree = "<group>"; }; + 26DB3E141379E7AD0080DC73 /* ABISysV_x86_64.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ABISysV_x86_64.h; sourceTree = "<group>"; }; 26DC6A101337FE6900FF7998 /* lldb-platform */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; includeInIndex = 0; path = "lldb-platform"; sourceTree = BUILT_PRODUCTS_DIR; }; 26DC6A1C1337FECA00FF7998 /* lldb-platform.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = "lldb-platform.cpp"; path = "tools/lldb-platform/lldb-platform.cpp"; sourceTree = "<group>"; }; 26DE1E6911616C2E00A093E2 /* lldb-forward-rtti.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = "lldb-forward-rtti.h"; path = "include/lldb/lldb-forward-rtti.h"; sourceTree = "<group>"; }; @@ -1091,15 +1086,11 @@ 491193501226386000578B7F /* ASTStructExtractor.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = ASTStructExtractor.cpp; path = source/Expression/ASTStructExtractor.cpp; sourceTree = "<group>"; }; 49307AAD11DEA4D90081F992 /* IRForTarget.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = IRForTarget.cpp; path = source/Expression/IRForTarget.cpp; sourceTree = "<group>"; }; 49307AB111DEA4F20081F992 /* IRForTarget.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = IRForTarget.h; path = include/lldb/Expression/IRForTarget.h; sourceTree = "<group>"; }; - 493C63F01189203300914D5E /* ABISysV_x86_64.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ABISysV_x86_64.h; path = "ABI/SysV-x86_64/ABISysV_x86_64.h"; sourceTree = "<group>"; }; - 493C63F11189203300914D5E /* ABISysV_x86_64.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = ABISysV_x86_64.cpp; path = "ABI/SysV-x86_64/ABISysV_x86_64.cpp"; sourceTree = "<group>"; }; 49445C2512245E3600C11A81 /* ClangExpressionParser.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = ClangExpressionParser.cpp; path = source/Expression/ClangExpressionParser.cpp; sourceTree = "<group>"; }; 49445C2912245E5500C11A81 /* ClangExpressionParser.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ClangExpressionParser.h; path = include/lldb/Expression/ClangExpressionParser.h; sourceTree = "<group>"; }; 49445E341225AB6A00C11A81 /* ClangUserExpression.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ClangUserExpression.h; path = include/lldb/Expression/ClangUserExpression.h; sourceTree = "<group>"; }; 495BBACB119A0DBE00418BEA /* PathMappingList.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = PathMappingList.cpp; path = source/Target/PathMappingList.cpp; sourceTree = "<group>"; }; 495BBACF119A0DE700418BEA /* PathMappingList.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = PathMappingList.h; path = include/lldb/Target/PathMappingList.h; sourceTree = "<group>"; }; - 497650CE11A21BEE008DDB57 /* ABIMacOSX_i386.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = ABIMacOSX_i386.cpp; path = "ABI/MacOSX-i386/ABIMacOSX_i386.cpp"; sourceTree = "<group>"; }; - 497650CF11A21BEE008DDB57 /* ABIMacOSX_i386.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ABIMacOSX_i386.h; path = "ABI/MacOSX-i386/ABIMacOSX_i386.h"; sourceTree = "<group>"; }; 497C86BD122823D800B54702 /* ClangUtilityFunction.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = ClangUtilityFunction.cpp; path = source/Expression/ClangUtilityFunction.cpp; sourceTree = "<group>"; }; 497C86C1122823F300B54702 /* ClangUtilityFunction.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ClangUtilityFunction.h; path = include/lldb/Expression/ClangUtilityFunction.h; sourceTree = "<group>"; }; 497E7B331188ED300065CCA1 /* ABI.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ABI.h; path = include/lldb/Target/ABI.h; sourceTree = "<group>"; }; @@ -1376,9 +1367,7 @@ 260C897110F57C5600BB2B04 /* Plugins */ = { isa = PBXGroup; children = ( - 26AC3F481365F4620065C7EF /* ArchDefaultUnwindPlan */, - 26AC3F4C1365F5260065C7EF /* ArchVolatileRegs */, - 493C63D711891A8000914D5E /* ABI */, + 26DB3E051379E7AD0080DC73 /* ABI */, 260C897210F57C5600BB2B04 /* Disassembler */, 260C897810F57C5600BB2B04 /* DynamicLoader */, 26D9FDCA12F785120003F2EE /* Instruction */, @@ -1828,24 +1817,6 @@ path = x86; sourceTree = "<group>"; }; - 2692BA1C136614D000F9E14D /* x86 */ = { - isa = PBXGroup; - children = ( - 2692BA1D136614D000F9E14D /* ArchDefaultUnwindPlan-x86.cpp */, - 2692BA1E136614D000F9E14D /* ArchDefaultUnwindPlan-x86.h */, - ); - path = x86; - sourceTree = "<group>"; - }; - 2692BA20136614FC00F9E14D /* x86 */ = { - isa = PBXGroup; - children = ( - 2692BA21136614FC00F9E14D /* ArchVolatileRegs-x86.cpp */, - 2692BA22136614FC00F9E14D /* ArchVolatileRegs-x86.h */, - ); - path = x86; - sourceTree = "<group>"; - }; 26A3B4AB1181454800381BC2 /* BSD-Archive */ = { isa = PBXGroup; children = ( @@ -1864,22 +1835,6 @@ path = UnwindAssembly; sourceTree = "<group>"; }; - 26AC3F481365F4620065C7EF /* ArchDefaultUnwindPlan */ = { - isa = PBXGroup; - children = ( - 2692BA1C136614D000F9E14D /* x86 */, - ); - path = ArchDefaultUnwindPlan; - sourceTree = "<group>"; - }; - 26AC3F4C1365F5260065C7EF /* ArchVolatileRegs */ = { - isa = PBXGroup; - children = ( - 2692BA20136614FC00F9E14D /* x86 */, - ); - path = ArchVolatileRegs; - sourceTree = "<group>"; - }; 26B4666E11A2080F00CF6220 /* Utility */ = { isa = PBXGroup; children = ( @@ -2308,10 +2263,6 @@ children = ( 497E7B331188ED300065CCA1 /* ABI.h */, 497E7B9D1188F6690065CCA1 /* ABI.cpp */, - 2630BFAB1365F3140070C534 /* ArchDefaultUnwindPlan.h */, - 2630BFAD1365F3220070C534 /* ArchDefaultUnwindPlan.cpp */, - 2630BFAC1365F3140070C534 /* ArchVolatileRegs.h */, - 2630BFAE1365F3220070C534 /* ArchVolatileRegs.cpp */, 4CB443BB1249920C00C13DC2 /* CPPLanguageRuntime.h */, 4CB443BC1249920C00C13DC2 /* CPPLanguageRuntime.cpp */, 26BC7DF110F1B81A00F91463 /* DynamicLoader.h */, @@ -2455,6 +2406,43 @@ path = ARM; sourceTree = "<group>"; }; + 26DB3E051379E7AD0080DC73 /* ABI */ = { + isa = PBXGroup; + children = ( + 26DB3E061379E7AD0080DC73 /* MacOSX-arm */, + 26DB3E0E1379E7AD0080DC73 /* MacOSX-i386 */, + 26DB3E121379E7AD0080DC73 /* SysV-x86_64 */, + ); + path = ABI; + sourceTree = "<group>"; + }; + 26DB3E061379E7AD0080DC73 /* MacOSX-arm */ = { + isa = PBXGroup; + children = ( + 26DB3E071379E7AD0080DC73 /* ABIMacOSX_arm.cpp */, + 26DB3E081379E7AD0080DC73 /* ABIMacOSX_arm.h */, + ); + path = "MacOSX-arm"; + sourceTree = "<group>"; + }; + 26DB3E0E1379E7AD0080DC73 /* MacOSX-i386 */ = { + isa = PBXGroup; + children = ( + 26DB3E0F1379E7AD0080DC73 /* ABIMacOSX_i386.cpp */, + 26DB3E101379E7AD0080DC73 /* ABIMacOSX_i386.h */, + ); + path = "MacOSX-i386"; + sourceTree = "<group>"; + }; + 26DB3E121379E7AD0080DC73 /* SysV-x86_64 */ = { + isa = PBXGroup; + children = ( + 26DB3E131379E7AD0080DC73 /* ABISysV_x86_64.cpp */, + 26DB3E141379E7AD0080DC73 /* ABISysV_x86_64.h */, + ); + path = "SysV-x86_64"; + sourceTree = "<group>"; + }; 26DC6A1B1337FEA400FF7998 /* lldb-platform */ = { isa = PBXGroup; children = ( @@ -2503,33 +2491,6 @@ sourceTree = "<group>"; usesTabs = 0; }; - 493C63D711891A8000914D5E /* ABI */ = { - isa = PBXGroup; - children = ( - 497650CD11A21BD8008DDB57 /* MacOSX-i386 */, - 493C63EA11891FCD00914D5E /* SysV-x86_64 */, - ); - name = ABI; - sourceTree = "<group>"; - }; - 493C63EA11891FCD00914D5E /* SysV-x86_64 */ = { - isa = PBXGroup; - children = ( - 493C63F11189203300914D5E /* ABISysV_x86_64.cpp */, - 493C63F01189203300914D5E /* ABISysV_x86_64.h */, - ); - name = "SysV-x86_64"; - sourceTree = "<group>"; - }; - 497650CD11A21BD8008DDB57 /* MacOSX-i386 */ = { - isa = PBXGroup; - children = ( - 497650CE11A21BEE008DDB57 /* ABIMacOSX_i386.cpp */, - 497650CF11A21BEE008DDB57 /* ABIMacOSX_i386.h */, - ); - name = "MacOSX-i386"; - sourceTree = "<group>"; - }; 4C139EA0124A8AC7000BFF8D /* CPlusPlus */ = { isa = PBXGroup; children = ( @@ -3125,8 +3086,6 @@ 2689008713353E2200698AC0 /* ScriptInterpreter.cpp in Sources */, 2689008813353E2200698AC0 /* ScriptInterpreterNone.cpp in Sources */, 2689008913353E2200698AC0 /* ScriptInterpreterPython.cpp in Sources */, - 2689008A13353E4200698AC0 /* ABIMacOSX_i386.cpp in Sources */, - 2689008B13353E4200698AC0 /* ABISysV_x86_64.cpp in Sources */, 2689008C13353E4200698AC0 /* DisassemblerLLVM.cpp in Sources */, 2689008D13353E4200698AC0 /* DynamicLoaderMacOSXDYLD.cpp in Sources */, 2689008E13353E4200698AC0 /* DynamicLoaderStatic.cpp in Sources */, @@ -3273,11 +3232,7 @@ 9A22A161135E30370024DDC3 /* EmulateInstructionARM.cpp in Sources */, 9A22A163135E30370024DDC3 /* EmulationStateARM.cpp in Sources */, 9A4F35101368A51A00823F52 /* StreamAsynchronousIO.cpp in Sources */, - 2630BFAF1365F3220070C534 /* ArchDefaultUnwindPlan.cpp in Sources */, - 2630BFB01365F3220070C534 /* ArchVolatileRegs.cpp in Sources */, 2692BA15136610C100F9E14D /* UnwindAssemblyInstEmulation.cpp in Sources */, - 2692BA1F136614D800F9E14D /* ArchDefaultUnwindPlan-x86.cpp in Sources */, - 2692BA231366150100F9E14D /* ArchVolatileRegs-x86.cpp in Sources */, 263E949F13661AEA00E7D1CE /* UnwindAssembly-x86.cpp in Sources */, 264D8D5013661BD7003A368F /* UnwindAssembly.cpp in Sources */, 26ECA04313665FED008D1F18 /* ARM_DWARF_Registers.cpp in Sources */, @@ -3288,7 +3243,10 @@ 260E07C8136FAB9200CF21D3 /* OptionGroupFile.cpp in Sources */, 2686536C1370ACB200D186A3 /* OptionGroupBoolean.cpp in Sources */, 268653701370AE7200D186A3 /* OptionGroupUInt64.cpp in Sources */, - 26C6886F137880C400407EDF /* RegisterValue.cpp in Sources */, + 26DB3E161379E7AD0080DC73 /* ABIMacOSX_arm.cpp in Sources */, + 26DB3E1C1379E7AD0080DC73 /* ABIMacOSX_i386.cpp in Sources */, + 26DB3E1F1379E7AD0080DC73 /* ABISysV_x86_64.cpp in Sources */, + 26A69C5F137A17A500262477 /* RegisterValue.cpp in Sources */, ); runOnlyForDeploymentPostprocessing = 0; }; @@ -3488,8 +3446,6 @@ "$(inherited)", "$(LLVM_BUILD_DIR)", ); - LLVM_BUILD_DIR = "$(SRCROOT)/llvm"; - LLVM_CONFIGURATION = "Debug+Asserts"; OTHER_CFLAGS = "-Wparentheses"; OTHER_CPLUSPLUSFLAGS = ( "-fno-rtti", @@ -3539,8 +3495,6 @@ "$(inherited)", "$(LLVM_BUILD_DIR)", ); - LLVM_BUILD_DIR = "$(SRCROOT)/llvm"; - LLVM_CONFIGURATION = "Debug+Asserts"; OTHER_CFLAGS = "-Wparentheses"; OTHER_CPLUSPLUSFLAGS = ( "-fno-rtti", @@ -3582,8 +3536,6 @@ "$(inherited)", "$(LLVM_BUILD_DIR)", ); - LLVM_BUILD_DIR = "$(SRCROOT)/llvm"; - LLVM_CONFIGURATION = "Debug+Asserts"; MACH_O_TYPE = staticlib; MACOSX_DEPLOYMENT_TARGET = 10.6; OTHER_CFLAGS = "-Wparentheses"; @@ -3624,8 +3576,6 @@ "$(inherited)", "$(LLVM_BUILD_DIR)", ); - LLVM_BUILD_DIR = "$(SRCROOT)/llvm"; - LLVM_CONFIGURATION = "Debug+Asserts"; MACH_O_TYPE = staticlib; MACOSX_DEPLOYMENT_TARGET = 10.6; OTHER_CFLAGS = "-Wparentheses"; @@ -3868,7 +3818,6 @@ 26F5C26C10F3D9A5009D5894 /* Debug */ = { isa = XCBuildConfiguration; buildSettings = { - CODE_SIGN_IDENTITY = lldb_codesign; COPY_PHASE_STRIP = NO; CURRENT_PROJECT_VERSION = 46; DEBUG_INFORMATION_FORMAT = dwarf; @@ -3901,7 +3850,6 @@ 26F5C26D10F3D9A5009D5894 /* Release */ = { isa = XCBuildConfiguration; buildSettings = { - CODE_SIGN_IDENTITY = lldb_codesign; COPY_PHASE_STRIP = YES; CURRENT_PROJECT_VERSION = 46; DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; diff --git a/lldb/lldb.xcodeproj/xcshareddata/xcschemes/lldb-tool.xcscheme b/lldb/lldb.xcodeproj/xcshareddata/xcschemes/lldb-tool.xcscheme index 4852a2b..74678a6 100644 --- a/lldb/lldb.xcodeproj/xcshareddata/xcschemes/lldb-tool.xcscheme +++ b/lldb/lldb.xcodeproj/xcshareddata/xcschemes/lldb-tool.xcscheme @@ -75,7 +75,8 @@ selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB" selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB" launchStyle = "0" - useCustomWorkingDirectory = "NO" + useCustomWorkingDirectory = "YES" + customWorkingDirectory = "/Volumes/work/gclayton/Documents/devb/attach" buildConfiguration = "Debug" ignoresPersistentStateOnLaunch = "YES"> <BuildableProductRunnable> diff --git a/lldb/source/Commands/CommandObjectArgs.cpp b/lldb/source/Commands/CommandObjectArgs.cpp index 09363d7..bfa1006 100644 --- a/lldb/source/Commands/CommandObjectArgs.cpp +++ b/lldb/source/Commands/CommandObjectArgs.cpp @@ -113,7 +113,7 @@ CommandObjectArgs::Execute return false; } - const ABI *abi = process->GetABI (); + const ABI *abi = process->GetABI().get(); if (!abi) { result.AppendError ("The current process has no ABI."); diff --git a/lldb/source/Core/EmulateInstruction.cpp b/lldb/source/Core/EmulateInstruction.cpp index ac149e0..a30dcd8 100644 --- a/lldb/source/Core/EmulateInstruction.cpp +++ b/lldb/source/Core/EmulateInstruction.cpp @@ -372,8 +372,10 @@ EmulateInstruction::ReadMemoryDefault (EmulateInstruction *instruction, void *dst, size_t length) { - fprintf (stdout, " Read from Memory (address = 0x%llx, length = %zu, context = ", addr, length); - context.Dump (stdout, instruction); + StreamFile strm (stdout, false); + strm.Printf (" Read from Memory (address = 0x%llx, length = %zu, context = ", addr, length); + context.Dump (strm, instruction); + strm.EOL(); *((uint64_t *) dst) = 0xdeadbeef; return length; } @@ -386,8 +388,10 @@ EmulateInstruction::WriteMemoryDefault (EmulateInstruction *instruction, const void *dst, size_t length) { - fprintf (stdout, " Write to Memory (address = 0x%llx, length = %zu, context = ", addr, length); - context.Dump (stdout, instruction); + StreamFile strm (stdout, false); + strm.Printf (" Write to Memory (address = 0x%llx, length = %zu, context = ", addr, length); + context.Dump (strm, instruction); + strm.EOL(); return length; } @@ -397,7 +401,8 @@ EmulateInstruction::ReadRegisterDefault (EmulateInstruction *instruction, const RegisterInfo *reg_info, RegisterValue ®_value) { - fprintf (stdout, " Read Register (%s)\n", reg_info->name); + StreamFile strm (stdout, false); + strm.Printf (" Read Register (%s)\n", reg_info->name); uint32_t reg_kind, reg_num; if (GetBestRegisterKindAndNumber (reg_info, reg_kind, reg_num)) reg_value.SetUInt64((uint64_t)reg_kind << 24 | reg_num); @@ -418,86 +423,87 @@ EmulateInstruction::WriteRegisterDefault (EmulateInstruction *instruction, strm.Printf (" Write to Register (name = %s, value = " , reg_info->name); reg_value.Dump(&strm, reg_info, false); strm.PutCString (", context = "); - context.Dump (stdout, instruction); + context.Dump (strm, instruction); + strm.EOL(); return true; } void -EmulateInstruction::Context::Dump (FILE *fh, +EmulateInstruction::Context::Dump (Stream &strm, EmulateInstruction *instruction) const { switch (type) { case eContextReadOpcode: - fprintf (fh, "reading opcode"); + strm.PutCString ("reading opcode"); break; case eContextImmediate: - fprintf (fh, "immediate"); + strm.PutCString ("immediate"); break; case eContextPushRegisterOnStack: - fprintf (fh, "push register"); + strm.PutCString ("push register"); break; case eContextPopRegisterOffStack: - fprintf (fh, "pop register"); + strm.PutCString ("pop register"); break; case eContextAdjustStackPointer: - fprintf (fh, "adjust sp"); + strm.PutCString ("adjust sp"); break; case eContextAdjustBaseRegister: - fprintf (fh, "adjusting (writing value back to) a base register"); + strm.PutCString ("adjusting (writing value back to) a base register"); break; case eContextRegisterPlusOffset: - fprintf (fh, "register + offset"); + strm.PutCString ("register + offset"); break; case eContextRegisterStore: - fprintf (fh, "store register"); + strm.PutCString ("store register"); break; case eContextRegisterLoad: - fprintf (fh, "load register"); + strm.PutCString ("load register"); break; case eContextRelativeBranchImmediate: - fprintf (fh, "relative branch immediate"); + strm.PutCString ("relative branch immediate"); break; case eContextAbsoluteBranchRegister: - fprintf (fh, "absolute branch register"); + strm.PutCString ("absolute branch register"); break; case eContextSupervisorCall: - fprintf (fh, "supervisor call"); + strm.PutCString ("supervisor call"); break; case eContextTableBranchReadMemory: - fprintf (fh, "table branch read memory"); + strm.PutCString ("table branch read memory"); break; case eContextWriteRegisterRandomBits: - fprintf (fh, "write random bits to a register"); + strm.PutCString ("write random bits to a register"); break; case eContextWriteMemoryRandomBits: - fprintf (fh, "write random bits to a memory address"); + strm.PutCString ("write random bits to a memory address"); break; case eContextArithmetic: - fprintf (fh, "arithmetic"); + strm.PutCString ("arithmetic"); break; case eContextReturnFromException: - fprintf (fh, "return from exception"); + strm.PutCString ("return from exception"); break; default: - fprintf (fh, "unrecognized context."); + strm.PutCString ("unrecognized context."); break; } @@ -505,99 +511,93 @@ EmulateInstruction::Context::Dump (FILE *fh, { case eInfoTypeRegisterPlusOffset: { - fprintf (fh, - " (reg_plus_offset = %s%+lld)\n", - info.RegisterPlusOffset.reg.name, - info.RegisterPlusOffset.signed_offset); + strm.Printf (" (reg_plus_offset = %s%+lld)", + info.RegisterPlusOffset.reg.name, + info.RegisterPlusOffset.signed_offset); } break; case eInfoTypeRegisterPlusIndirectOffset: { - fprintf (fh, " (reg_plus_reg = %s + %s)\n", - info.RegisterPlusIndirectOffset.base_reg.name, - info.RegisterPlusIndirectOffset.offset_reg.name); + strm.Printf (" (reg_plus_reg = %s + %s)", + info.RegisterPlusIndirectOffset.base_reg.name, + info.RegisterPlusIndirectOffset.offset_reg.name); } break; case eInfoTypeRegisterToRegisterPlusOffset: { - fprintf (fh, " (base_and_imm_offset = %s%+lld, data_reg = %s)\n", - info.RegisterToRegisterPlusOffset.base_reg.name, - info.RegisterToRegisterPlusOffset.offset, - info.RegisterToRegisterPlusOffset.data_reg.name); + strm.Printf (" (base_and_imm_offset = %s%+lld, data_reg = %s)", + info.RegisterToRegisterPlusOffset.base_reg.name, + info.RegisterToRegisterPlusOffset.offset, + info.RegisterToRegisterPlusOffset.data_reg.name); } break; case eInfoTypeRegisterToRegisterPlusIndirectOffset: { - fprintf (fh, " (base_and_reg_offset = %s + %s, data_reg = %s)\n", - info.RegisterToRegisterPlusIndirectOffset.base_reg.name, - info.RegisterToRegisterPlusIndirectOffset.offset_reg.name, - info.RegisterToRegisterPlusIndirectOffset.data_reg.name); + strm.Printf (" (base_and_reg_offset = %s + %s, data_reg = %s)", + info.RegisterToRegisterPlusIndirectOffset.base_reg.name, + info.RegisterToRegisterPlusIndirectOffset.offset_reg.name, + info.RegisterToRegisterPlusIndirectOffset.data_reg.name); } break; case eInfoTypeRegisterRegisterOperands: { - fprintf (fh, " (register to register binary op: %s and %s)\n", - info.RegisterRegisterOperands.operand1.name, - info.RegisterRegisterOperands.operand2.name); + strm.Printf (" (register to register binary op: %s and %s)", + info.RegisterRegisterOperands.operand1.name, + info.RegisterRegisterOperands.operand2.name); } break; case eInfoTypeOffset: - fprintf (fh, " (signed_offset = %+lld)\n", info.signed_offset); + strm.Printf (" (signed_offset = %+lld)", info.signed_offset); break; case eInfoTypeRegister: - fprintf (fh, " (reg = %s)\n", info.reg.name); + strm.Printf (" (reg = %s)", info.reg.name); break; case eInfoTypeImmediate: - fprintf (fh, - " (unsigned_immediate = %llu (0x%16.16llx))\n", - info.unsigned_immediate, - info.unsigned_immediate); + strm.Printf (" (unsigned_immediate = %llu (0x%16.16llx))", + info.unsigned_immediate, + info.unsigned_immediate); break; case eInfoTypeImmediateSigned: - fprintf (fh, - " (signed_immediate = %+lld (0x%16.16llx))\n", - info.signed_immediate, - info.signed_immediate); + strm.Printf (" (signed_immediate = %+lld (0x%16.16llx))", + info.signed_immediate, + info.signed_immediate); break; case eInfoTypeAddress: - fprintf (fh, " (address = 0x%llx)\n", info.address); + strm.Printf (" (address = 0x%llx)", info.address); break; case eInfoTypeISAAndImmediate: - fprintf (fh, - " (isa = %u, unsigned_immediate = %u (0x%8.8x))\n", - info.ISAAndImmediate.isa, - info.ISAAndImmediate.unsigned_data32, - info.ISAAndImmediate.unsigned_data32); + strm.Printf (" (isa = %u, unsigned_immediate = %u (0x%8.8x))", + info.ISAAndImmediate.isa, + info.ISAAndImmediate.unsigned_data32, + info.ISAAndImmediate.unsigned_data32); break; case eInfoTypeISAAndImmediateSigned: - fprintf (fh, - " (isa = %u, signed_immediate = %i (0x%8.8x))\n", - info.ISAAndImmediateSigned.isa, - info.ISAAndImmediateSigned.signed_data32, - info.ISAAndImmediateSigned.signed_data32); + strm.Printf (" (isa = %u, signed_immediate = %i (0x%8.8x))", + info.ISAAndImmediateSigned.isa, + info.ISAAndImmediateSigned.signed_data32, + info.ISAAndImmediateSigned.signed_data32); break; case eInfoTypeISA: - fprintf (fh, " (isa = %u)\n", info.isa); + strm.Printf (" (isa = %u)", info.isa); break; case eInfoTypeNoArgs: - fprintf (fh, " \n"); break; default: - fprintf (fh, " (unknown <info_type>)\n"); + strm.Printf (" (unknown <info_type>)"); break; } } diff --git a/lldb/source/Core/PluginManager.cpp b/lldb/source/Core/PluginManager.cpp index fae96333..d1903df 100644 --- a/lldb/source/Core/PluginManager.cpp +++ b/lldb/source/Core/PluginManager.cpp @@ -1663,213 +1663,3 @@ PluginManager::GetUnwindAssemblyCreateCallbackForPluginName (const char *name) return NULL; } -#pragma mark ArchDefaultUnwindPlan - -struct ArchDefaultUnwindPlanInstance -{ - ArchDefaultUnwindPlanInstance() : - name(), - description(), - create_callback(NULL) - { - } - - std::string name; - std::string description; - ArchDefaultUnwindPlanCreateInstance create_callback; -}; - -typedef std::vector<ArchDefaultUnwindPlanInstance> ArchDefaultUnwindPlanInstances; - -static Mutex & -GetArchDefaultUnwindPlanMutex () -{ - static Mutex g_instances_mutex (Mutex::eMutexTypeRecursive); - return g_instances_mutex; -} - -static ArchDefaultUnwindPlanInstances & -GetArchDefaultUnwindPlanInstances () -{ - static ArchDefaultUnwindPlanInstances g_instances; - return g_instances; -} - - -bool -PluginManager::RegisterPlugin -( - const char *name, - const char *description, - ArchDefaultUnwindPlanCreateInstance create_callback -) -{ - if (create_callback) - { - ArchDefaultUnwindPlanInstance instance; - assert (name && name[0]); - instance.name = name; - if (description && description[0]) - instance.description = description; - instance.create_callback = create_callback; - Mutex::Locker locker (GetArchDefaultUnwindPlanMutex ()); - GetArchDefaultUnwindPlanInstances ().push_back (instance); - } - return false; -} - -bool -PluginManager::UnregisterPlugin (ArchDefaultUnwindPlanCreateInstance create_callback) -{ - if (create_callback) - { - Mutex::Locker locker (GetArchDefaultUnwindPlanMutex ()); - ArchDefaultUnwindPlanInstances &instances = GetArchDefaultUnwindPlanInstances (); - - ArchDefaultUnwindPlanInstances::iterator pos, end = instances.end(); - for (pos = instances.begin(); pos != end; ++ pos) - { - if (pos->create_callback == create_callback) - { - instances.erase(pos); - return true; - } - } - } - return false; -} - -ArchDefaultUnwindPlanCreateInstance -PluginManager::GetArchDefaultUnwindPlanCreateCallbackAtIndex (uint32_t idx) -{ - Mutex::Locker locker (GetArchDefaultUnwindPlanMutex ()); - ArchDefaultUnwindPlanInstances &instances = GetArchDefaultUnwindPlanInstances (); - if (idx < instances.size()) - return instances[idx].create_callback; - return NULL; -} - - -ArchDefaultUnwindPlanCreateInstance -PluginManager::GetArchDefaultUnwindPlanCreateCallbackForPluginName (const char *name) -{ - if (name && name[0]) - { - llvm::StringRef name_sref(name); - Mutex::Locker locker (GetArchDefaultUnwindPlanMutex ()); - ArchDefaultUnwindPlanInstances &instances = GetArchDefaultUnwindPlanInstances (); - - ArchDefaultUnwindPlanInstances::iterator pos, end = instances.end(); - for (pos = instances.begin(); pos != end; ++ pos) - { - if (name_sref.equals (pos->name)) - return pos->create_callback; - } - } - return NULL; -} - -#pragma mark ArchVolatileRegs - -struct ArchVolatileRegsInstance -{ - ArchVolatileRegsInstance() : - name(), - description(), - create_callback(NULL) - { - } - - std::string name; - std::string description; - ArchVolatileRegsCreateInstance create_callback; -}; - -typedef std::vector<ArchVolatileRegsInstance> ArchVolatileRegsInstances; - -static Mutex & -GetArchVolatileRegsMutex () -{ - static Mutex g_instances_mutex (Mutex::eMutexTypeRecursive); - return g_instances_mutex; -} - -static ArchVolatileRegsInstances & -GetArchVolatileRegsInstances () -{ - static ArchVolatileRegsInstances g_instances; - return g_instances; -} - -bool -PluginManager::RegisterPlugin -( - const char *name, - const char *description, - ArchVolatileRegsCreateInstance create_callback -) -{ - if (create_callback) - { - ArchVolatileRegsInstance instance; - assert (name && name[0]); - instance.name = name; - if (description && description[0]) - instance.description = description; - instance.create_callback = create_callback; - Mutex::Locker locker (GetArchVolatileRegsMutex ()); - GetArchVolatileRegsInstances ().push_back (instance); - } - return false; -} - -bool -PluginManager::UnregisterPlugin (ArchVolatileRegsCreateInstance create_callback) -{ - if (create_callback) - { - Mutex::Locker locker (GetArchVolatileRegsMutex ()); - ArchVolatileRegsInstances &instances = GetArchVolatileRegsInstances (); - - ArchVolatileRegsInstances::iterator pos, end = instances.end(); - for (pos = instances.begin(); pos != end; ++ pos) - { - if (pos->create_callback == create_callback) - { - instances.erase(pos); - return true; - } - } - } - return false; -} - -ArchVolatileRegsCreateInstance -PluginManager::GetArchVolatileRegsCreateCallbackAtIndex (uint32_t idx) -{ - Mutex::Locker locker (GetArchVolatileRegsMutex ()); - ArchVolatileRegsInstances &instances = GetArchVolatileRegsInstances (); - if (idx < instances.size()) - return instances[idx].create_callback; - return NULL; -} - -ArchVolatileRegsCreateInstance -PluginManager::GetArchVolatileRegsCreateCallbackForPluginName (const char *name) -{ - if (name && name[0]) - { - llvm::StringRef name_sref(name); - Mutex::Locker locker (GetArchVolatileRegsMutex ()); - ArchVolatileRegsInstances &instances = GetArchVolatileRegsInstances (); - - ArchVolatileRegsInstances::iterator pos, end = instances.end(); - for (pos = instances.begin(); pos != end; ++ pos) - { - if (name_sref.equals (pos->name)) - return pos->create_callback; - } - } - return NULL; -} - diff --git a/lldb/source/Plugins/ABI/MacOSX-arm/ABIMacOSX_arm.cpp b/lldb/source/Plugins/ABI/MacOSX-arm/ABIMacOSX_arm.cpp new file mode 100644 index 0000000..0f9bab1 --- /dev/null +++ b/lldb/source/Plugins/ABI/MacOSX-arm/ABIMacOSX_arm.cpp @@ -0,0 +1,807 @@ +//===-- ABIMacOSX_arm.cpp --------------------------------------*- C++ -*-===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#include "ABIMacOSX_arm.h" + +#include "lldb/Core/ConstString.h" +#include "lldb/Core/Error.h" +#include "lldb/Core/Module.h" +#include "lldb/Core/PluginManager.h" +#include "lldb/Core/Scalar.h" +#include "lldb/Core/Value.h" +#include "lldb/Symbol/ClangASTContext.h" +#include "lldb/Symbol/UnwindPlan.h" +#include "lldb/Target/Process.h" +#include "lldb/Target/RegisterContext.h" +#include "lldb/Target/Target.h" +#include "lldb/Target/Thread.h" + +#include "llvm/ADT/Triple.h" + +#include "Utility/ARM_DWARF_Registers.h" + +#include <vector> + +using namespace lldb; +using namespace lldb_private; + +static const char *pluginName = "ABIMacOSX_arm"; +static const char *pluginDesc = "Mac OS X ABI for arm targets"; +static const char *pluginShort = "abi.macosx-arm"; + +size_t +ABIMacOSX_arm::GetRedZoneSize () const +{ + return 0; +} + +//------------------------------------------------------------------ +// Static Functions +//------------------------------------------------------------------ +ABISP +ABIMacOSX_arm::CreateInstance (const ArchSpec &arch) +{ + static ABISP g_abi_sp; + const llvm::Triple::ArchType arch_type = arch.GetTriple().getArch(); + if ((arch_type == llvm::Triple::arm) || + (arch_type == llvm::Triple::thumb)) + { + if (!g_abi_sp) + g_abi_sp.reset (new ABIMacOSX_arm); + return g_abi_sp; + } + return ABISP(); +} + +bool +ABIMacOSX_arm::PrepareTrivialCall (Thread &thread, + addr_t sp, + addr_t functionAddress, + addr_t returnAddress, + addr_t arg, + addr_t *this_arg, + addr_t *cmd_arg) const +{ +// RegisterContext *reg_ctx = thread.GetRegisterContext().get(); +// if (!reg_ctx) +// return false; +//#define CHAIN_EBP +// +//#ifndef CHAIN_EBP +// uint32_t ebpID = reg_ctx->ConvertRegisterKindToRegisterNumber (eRegisterKindGeneric, LLDB_REGNUM_GENERIC_FP); +//#endif +// uint32_t eipID = reg_ctx->ConvertRegisterKindToRegisterNumber (eRegisterKindGeneric, LLDB_REGNUM_GENERIC_PC); +// uint32_t espID = reg_ctx->ConvertRegisterKindToRegisterNumber (eRegisterKindGeneric, LLDB_REGNUM_GENERIC_SP); +// +// // Make room for the argument(s) on the stack +// +// if (this_arg && cmd_arg) +// sp -= 12; +// else if (this_arg) +// sp -= 8; +// else +// sp -= 4; +// +// // Align the SP +// +// sp &= ~(0xfull); // 16-byte alignment +// +// // Write the argument on the stack +// +// Error error; +// +// if (this_arg && cmd_arg) +// { +// uint32_t cmd_argU32 = *cmd_arg & 0xffffffffull; +// uint32_t this_argU32 = *this_arg & 0xffffffffull; +// uint32_t argU32 = arg & 0xffffffffull; +// +// if (thread.GetProcess().WriteMemory(sp, &this_argU32, sizeof(this_argU32), error) != sizeof(this_argU32)) +// return false; +// if (thread.GetProcess().WriteMemory(sp + 4, &cmd_argU32, sizeof(cmd_argU32), error) != sizeof(cmd_argU32)) +// return false; +// if (thread.GetProcess().WriteMemory(sp + 8, &argU32, sizeof(argU32), error) != sizeof(argU32)) +// return false; +// } +// else if (this_arg) +// { +// uint32_t this_argU32 = *this_arg & 0xffffffffull; +// uint32_t argU32 = arg & 0xffffffffull; +// +// if (thread.GetProcess().WriteMemory(sp, &this_argU32, sizeof(this_argU32), error) != sizeof(this_argU32)) +// return false; +// if (thread.GetProcess().WriteMemory(sp + 4, &argU32, sizeof(argU32), error) != sizeof(argU32)) +// return false; +// } +// else +// { +// uint32_t argU32 = arg & 0xffffffffull; +// +// if (thread.GetProcess().WriteMemory (sp, &argU32, sizeof(argU32), error) != sizeof(argU32)) +// return false; +// } +// +// // The return address is pushed onto the stack. +// +// sp -= 4; +// uint32_t returnAddressU32 = returnAddress; +// if (thread.GetProcess().WriteMemory (sp, &returnAddressU32, sizeof(returnAddressU32), error) != sizeof(returnAddressU32)) +// return false; +// +// // %esp is set to the actual stack value. +// +// if (!reg_ctx->WriteRegisterFromUnsigned(espID, sp)) +// return false; +// +//#ifndef CHAIN_EBP +// // %ebp is set to a fake value, in our case 0x0x00000000 +// +// if (!reg_ctx->WriteRegisterFromUnsigned(ebpID, 0x00000000)) +// return false; +//#endif +// +// // %eip is set to the address of the called function. +// +// if (!reg_ctx->WriteRegisterFromUnsigned(eipID, functionAddress)) +// return false; +// +// return true; + return false; +} + +bool +ABIMacOSX_arm::PrepareNormalCall (Thread &thread, + addr_t sp, + addr_t functionAddress, + addr_t returnAddress, + ValueList &args) const +{ +// RegisterContext *reg_ctx = thread.GetRegisterContext().get(); +// if (!reg_ctx) +// return false; +// Error error; +// uint32_t ebpID = reg_ctx->ConvertRegisterKindToRegisterNumber (eRegisterKindGeneric, LLDB_REGNUM_GENERIC_FP); +// uint32_t eipID = reg_ctx->ConvertRegisterKindToRegisterNumber (eRegisterKindGeneric, LLDB_REGNUM_GENERIC_PC); +// uint32_t espID = reg_ctx->ConvertRegisterKindToRegisterNumber (eRegisterKindGeneric, LLDB_REGNUM_GENERIC_SP); +// +// // Do the argument layout +// +// std::vector <uint32_t> argLayout; // 4-byte chunks, as discussed in the ABI Function Call Guide +// +// size_t numArgs = args.GetSize(); +// size_t index; +// +// for (index = 0; index < numArgs; ++index) +// { +// Value *val = args.GetValueAtIndex(index); +// +// if (!val) +// return false; +// +// switch (val->GetValueType()) +// { +// case Value::eValueTypeScalar: +// { +// Scalar &scalar = val->GetScalar(); +// switch (scalar.GetType()) +// { +// case Scalar::e_void: +// default: +// return false; +// case Scalar::e_sint: +// case Scalar::e_uint: +// case Scalar::e_slong: +// case Scalar::e_ulong: +// case Scalar::e_slonglong: +// case Scalar::e_ulonglong: +// { +// uint64_t data = scalar.ULongLong(); +// +// switch (scalar.GetByteSize()) +// { +// default: +// return false; +// case 1: +// argLayout.push_back((uint32_t)(data & 0xffull)); +// break; +// case 2: +// argLayout.push_back((uint32_t)(data & 0xffffull)); +// break; +// case 4: +// argLayout.push_back((uint32_t)(data & 0xffffffffull)); +// break; +// case 8: +// argLayout.push_back((uint32_t)(data & 0xffffffffull)); +// argLayout.push_back((uint32_t)(data >> 32)); +// break; +// } +// } +// break; +// case Scalar::e_float: +// { +// float data = scalar.Float(); +// uint32_t dataRaw = *((uint32_t*)(&data)); +// argLayout.push_back(dataRaw); +// } +// break; +// case Scalar::e_double: +// { +// double data = scalar.Double(); +// uint32_t *dataRaw = ((uint32_t*)(&data)); +// argLayout.push_back(dataRaw[0]); +// argLayout.push_back(dataRaw[1]); +// } +// break; +// case Scalar::e_long_double: +// { +// long double data = scalar.Double(); +// uint32_t *dataRaw = ((uint32_t*)(&data)); +// while ((argLayout.size() * 4) & 0xf) +// argLayout.push_back(0); +// argLayout.push_back(dataRaw[0]); +// argLayout.push_back(dataRaw[1]); +// argLayout.push_back(dataRaw[2]); +// argLayout.push_back(dataRaw[3]); +// } +// break; +// } +// } +// break; +// case Value::eValueTypeHostAddress: +// switch (val->GetContextType()) +// { +// default: +// return false; +// case Value::eContextTypeClangType: +// { +// void *val_type = val->GetClangType(); +// uint32_t cstr_length; +// +// if (ClangASTContext::IsCStringType (val_type, cstr_length)) +// { +// const char *cstr = (const char*)val->GetScalar().ULongLong(); +// cstr_length = strlen(cstr); +// +// // Push the string onto the stack immediately. +// +// sp -= (cstr_length + 1); +// +// if (thread.GetProcess().WriteMemory(sp, cstr, cstr_length + 1, error) != (cstr_length + 1)) +// return false; +// +// // Put the address of the string into the argument array. +// +// argLayout.push_back((uint32_t)(sp & 0xffffffff)); +// } +// else +// { +// return false; +// } +// } +// break; +// } +// break; +// case Value::eValueTypeFileAddress: +// case Value::eValueTypeLoadAddress: +// default: +// return false; +// } +// } +// +// // Make room for the arguments on the stack +// +// sp -= 4 * argLayout.size(); +// +// // Align the SP +// +// sp &= ~(0xfull); // 16-byte alignment +// +// // Write the arguments on the stack +// +// size_t numChunks = argLayout.size(); +// +// for (index = 0; index < numChunks; ++index) +// if (thread.GetProcess().WriteMemory(sp + (index * 4), &argLayout[index], sizeof(uint32_t), error) != sizeof(uint32_t)) +// return false; +// +// // The return address is pushed onto the stack. +// +// sp -= 4; +// uint32_t returnAddressU32 = returnAddress; +// if (thread.GetProcess().WriteMemory (sp, &returnAddressU32, sizeof(returnAddressU32), error) != sizeof(returnAddressU32)) +// return false; +// +// // %esp is set to the actual stack value. +// +// if (!reg_ctx->WriteRegisterFromUnsigned(espID, sp)) +// return false; +// +// // %ebp is set to a fake value, in our case 0x0x00000000 +// +// if (!reg_ctx->WriteRegisterFromUnsigned(ebpID, 0x00000000)) +// return false; +// +// // %eip is set to the address of the called function. +// +// if (!reg_ctx->WriteRegisterFromUnsigned(eipID, functionAddress)) +// return false; +// +// return true; + return false; +} + +static bool +ReadIntegerArgument (Scalar &scalar, + unsigned int bit_width, + bool is_signed, + Process &process, + addr_t ¤t_stack_argument) +{ +// if (bit_width > 64) +// return false; // Scalar can't hold large integer arguments +// +// uint64_t arg_contents; +// uint32_t read_data; +// Error error; +// +// if (bit_width > 32) +// { +// if (process.ReadMemory(current_stack_argument, &read_data, sizeof(read_data), error) != sizeof(read_data)) +// return false; +// +// arg_contents = read_data; +// +// if (process.ReadMemory(current_stack_argument + 4, &read_data, sizeof(read_data), error) != sizeof(read_data)) +// return false; +// +// arg_contents |= ((uint64_t)read_data) << 32; +// +// current_stack_argument += 8; +// } +// else { +// if (process.ReadMemory(current_stack_argument, &read_data, sizeof(read_data), error) != sizeof(read_data)) +// return false; +// +// arg_contents = read_data; +// +// current_stack_argument += 4; +// } +// +// if (is_signed) +// { +// switch (bit_width) +// { +// default: +// return false; +// case 8: +// scalar = (int8_t)(arg_contents & 0xff); +// break; +// case 16: +// scalar = (int16_t)(arg_contents & 0xffff); +// break; +// case 32: +// scalar = (int32_t)(arg_contents & 0xffffffff); +// break; +// case 64: +// scalar = (int64_t)arg_contents; +// break; +// } +// } +// else +// { +// switch (bit_width) +// { +// default: +// return false; +// case 8: +// scalar = (uint8_t)(arg_contents & 0xff); +// break; +// case 16: +// scalar = (uint16_t)(arg_contents & 0xffff); +// break; +// case 32: +// scalar = (uint32_t)(arg_contents & 0xffffffff); +// break; +// case 64: +// scalar = (uint64_t)arg_contents; +// break; +// } +// } +// +// return true; + return false; +} + +bool +ABIMacOSX_arm::GetArgumentValues (Thread &thread, + ValueList &values) const +{ +// unsigned int num_values = values.GetSize(); +// unsigned int value_index; +// +// // Extract the Clang AST context from the PC so that we can figure out type +// // sizes +// +// clang::ASTContext *ast_context = thread.CalculateTarget()->GetScratchClangASTContext()->getASTContext(); +// +// // Get the pointer to the first stack argument so we have a place to start +// // when reading data +// +// RegisterContext *reg_ctx = thread.GetRegisterContext().get(); +// +// if (!reg_ctx) +// return false; +// +// addr_t sp = reg_ctx->GetSP(0); +// +// if (!sp) +// return false; +// +// addr_t current_stack_argument = sp + 4; // jump over return address +// +// for (value_index = 0; +// value_index < num_values; +// ++value_index) +// { +// Value *value = values.GetValueAtIndex(value_index); +// +// if (!value) +// return false; +// +// // We currently only support extracting values with Clang QualTypes. +// // Do we care about others? +// switch (value->GetContextType()) +// { +// default: +// return false; +// case Value::eContextTypeClangType: +// { +// void *value_type = value->GetClangType(); +// bool is_signed; +// +// if (ClangASTContext::IsIntegerType (value_type, is_signed)) +// { +// size_t bit_width = ClangASTType::GetClangTypeBitWidth(ast_context, value_type); +// +// ReadIntegerArgument(value->GetScalar(), +// bit_width, +// is_signed, +// thread.GetProcess(), +// current_stack_argument); +// } +// else if (ClangASTContext::IsPointerType (value_type)) +// { +// ReadIntegerArgument(value->GetScalar(), +// 32, +// false, +// thread.GetProcess(), +// current_stack_argument); +// } +// } +// break; +// } +// } +// +// return true; + return false; +} + +bool +ABIMacOSX_arm::GetReturnValue (Thread &thread, + Value &value) const +{ +// switch (value.GetContextType()) +// { +// default: +// return false; +// case Value::eContextTypeClangType: +// { +// // Extract the Clang AST context from the PC so that we can figure out type +// // sizes +// +// clang::ASTContext *ast_context = thread.CalculateTarget()->GetScratchClangASTContext()->getASTContext(); +// +// // Get the pointer to the first stack argument so we have a place to start +// // when reading data +// +// RegisterContext *reg_ctx = thread.GetRegisterContext().get(); +// +// void *value_type = value.GetClangType(); +// bool is_signed; +// +// if (ClangASTContext::IsIntegerType (value_type, is_signed)) +// { +// size_t bit_width = ClangASTType::GetClangTypeBitWidth(ast_context, value_type); +// +// unsigned eax_id = reg_ctx->GetRegisterInfoByName("eax", 0)->kinds[eRegisterKindLLDB]; +// unsigned edx_id = reg_ctx->GetRegisterInfoByName("edx", 0)->kinds[eRegisterKindLLDB]; +// +// switch (bit_width) +// { +// default: +// case 128: +// // Scalar can't hold 128-bit literals, so we don't handle this +// return false; +// case 64: +// uint64_t raw_value; +// raw_value = thread.GetRegisterContext()->ReadRegisterAsUnsigned(eax_id, 0) & 0xffffffff; +// raw_value |= (thread.GetRegisterContext()->ReadRegisterAsUnsigned(edx_id, 0) & 0xffffffff) << 32; +// if (is_signed) +// value.GetScalar() = (int64_t)raw_value; +// else +// value.GetScalar() = (uint64_t)raw_value; +// break; +// case 32: +// if (is_signed) +// value.GetScalar() = (int32_t)(thread.GetRegisterContext()->ReadRegisterAsUnsigned(eax_id, 0) & 0xffffffff); +// else +// value.GetScalar() = (uint32_t)(thread.GetRegisterContext()->ReadRegisterAsUnsigned(eax_id, 0) & 0xffffffff); +// break; +// case 16: +// if (is_signed) +// value.GetScalar() = (int16_t)(thread.GetRegisterContext()->ReadRegisterAsUnsigned(eax_id, 0) & 0xffff); +// else +// value.GetScalar() = (uint16_t)(thread.GetRegisterContext()->ReadRegisterAsUnsigned(eax_id, 0) & 0xffff); +// break; +// case 8: +// if (is_signed) +// value.GetScalar() = (int8_t)(thread.GetRegisterContext()->ReadRegisterAsUnsigned(eax_id, 0) & 0xff); +// else +// value.GetScalar() = (uint8_t)(thread.GetRegisterContext()->ReadRegisterAsUnsigned(eax_id, 0) & 0xff); +// break; +// } +// } +// else if (ClangASTContext::IsPointerType (value_type)) +// { +// unsigned eax_id = reg_ctx->GetRegisterInfoByName("eax", 0)->kinds[eRegisterKindLLDB]; +// uint32_t ptr = thread.GetRegisterContext()->ReadRegisterAsUnsigned(eax_id, 0) & 0xffffffff; +// value.GetScalar() = ptr; +// } +// else +// { +// // not handled yet +// return false; +// } +// } +// break; +// } +// +// return true; + return false; +} + +bool +ABIMacOSX_arm::CreateFunctionEntryUnwindPlan (UnwindPlan &unwind_plan) +{ + uint32_t reg_kind = unwind_plan.GetRegisterKind(); + uint32_t lr_reg_num = LLDB_INVALID_REGNUM; + uint32_t sp_reg_num = LLDB_INVALID_REGNUM; + uint32_t pc_reg_num = LLDB_INVALID_REGNUM; + + switch (reg_kind) + { + case eRegisterKindDWARF: + case eRegisterKindGCC: + lr_reg_num = dwarf_lr; + sp_reg_num = dwarf_sp; + pc_reg_num = dwarf_pc; + break; + + case eRegisterKindGeneric: + lr_reg_num = LLDB_REGNUM_GENERIC_RA; + sp_reg_num = LLDB_REGNUM_GENERIC_SP; + pc_reg_num = LLDB_REGNUM_GENERIC_PC; + break; + } + + if (lr_reg_num == LLDB_INVALID_REGNUM || + sp_reg_num == LLDB_INVALID_REGNUM || + pc_reg_num == LLDB_INVALID_REGNUM) + return false; + + unwind_plan.Clear(); + unwind_plan.SetRegisterKind (eRegisterKindDWARF); + + UnwindPlan::Row row; + + // Our previous Call Frame Address is the stack pointer + row.SetCFARegister (sp_reg_num); + + // Our previous PC is in the LR + row.SetRegisterLocationToRegister(pc_reg_num, lr_reg_num, true); + unwind_plan.AppendRow (row); + + // All other registers are the same. + + unwind_plan.SetSourceName (pluginName); + return true; +} + +bool +ABIMacOSX_arm::CreateDefaultUnwindPlan (UnwindPlan &unwind_plan) +{ + uint32_t reg_kind = unwind_plan.GetRegisterKind(); + uint32_t fp_reg_num = LLDB_INVALID_REGNUM; + uint32_t sp_reg_num = LLDB_INVALID_REGNUM; + uint32_t pc_reg_num = LLDB_INVALID_REGNUM; + + switch (reg_kind) + { + case eRegisterKindDWARF: + case eRegisterKindGCC: + fp_reg_num = dwarf_r7; // apple uses r7 for all frames. Normal arm uses r11 + sp_reg_num = dwarf_sp; + pc_reg_num = dwarf_pc; + break; + + case eRegisterKindGeneric: + fp_reg_num = LLDB_REGNUM_GENERIC_FP; + sp_reg_num = LLDB_REGNUM_GENERIC_SP; + pc_reg_num = LLDB_REGNUM_GENERIC_PC; + break; + } + + if (fp_reg_num == LLDB_INVALID_REGNUM || + sp_reg_num == LLDB_INVALID_REGNUM || + pc_reg_num == LLDB_INVALID_REGNUM) + return false; + + UnwindPlan::Row row; + const int32_t ptr_size = 8; + + unwind_plan.SetRegisterKind (eRegisterKindGeneric); + row.SetCFARegister (fp_reg_num); + row.SetCFAOffset (2 * ptr_size); + row.SetOffset (0); + + row.SetRegisterLocationToAtCFAPlusOffset(fp_reg_num, ptr_size * -2, true); + row.SetRegisterLocationToAtCFAPlusOffset(pc_reg_num, ptr_size * -1, true); + + unwind_plan.AppendRow (row); + unwind_plan.SetSourceName ("arm-apple-darwin default unwind plan"); + return true; +} + +bool +ABIMacOSX_arm::RegisterIsVolatile (const RegisterInfo *reg_info) +{ + if (reg_info) + { + // Volatile registers include: ebx, ebp, esi, edi, esp, eip + const char *name = reg_info->name; + if (name[0] == 'r') + { + switch (name[1]) + { + case '0': return name[2] == '\0'; // r0 + case '1': + switch (name[2]) + { + case '\0': + return true; // r1 + case '2': + case '3': + return name[2] == '\0'; // r12 - r13 + default: + break; + } + break; + + case '2': return name[2] == '\0'; // r2 + case '3': return name[2] == '\0'; // r3 + case '9': return name[2] == '\0'; // r9 (apple-darwin only...) + + break; + } + } + else if (name[0] == 'd') + { + switch (name[1]) + { + case '0': + return name[2] == '\0'; // d0 + + case '1': + switch (name[2]) + { + case '\0': + return true; // d1; + case '6': + case '7': + case '8': + case '9': + return name[3] == '\0'; // d16 - d19 + default: + break; + } + break; + + case '2': + switch (name[2]) + { + case '\0': + return true; // d2; + case '0': + case '1': + case '2': + case '3': + case '4': + case '5': + case '6': + case '7': + case '8': + case '9': + return name[3] == '\0'; // d20 - d29 + default: + break; + } + break; + + case '3': + switch (name[2]) + { + case '\0': + return true; // d3; + case '0': + case '1': + return name[3] == '\0'; // d30 - d31 + default: + break; + } + case '4': + case '5': + case '6': + case '7': + return name[2] == '\0'; // d4 - d7 + + default: + break; + } + } + else if (name[0] == 's' && name[1] == 'p' && name[2] == '\0') + return true; + } + return false; +} + +void +ABIMacOSX_arm::Initialize() +{ + PluginManager::RegisterPlugin (pluginName, + pluginDesc, + CreateInstance); +} + +void +ABIMacOSX_arm::Terminate() +{ + PluginManager::UnregisterPlugin (CreateInstance); +} + +//------------------------------------------------------------------ +// PluginInterface protocol +//------------------------------------------------------------------ +const char * +ABIMacOSX_arm::GetPluginName() +{ + return pluginName; +} + +const char * +ABIMacOSX_arm::GetShortPluginName() +{ + return pluginShort; +} + +uint32_t +ABIMacOSX_arm::GetPluginVersion() +{ + return 1; +} + diff --git a/lldb/source/Plugins/ABI/MacOSX-arm/ABIMacOSX_arm.h b/lldb/source/Plugins/ABI/MacOSX-arm/ABIMacOSX_arm.h new file mode 100644 index 0000000..d1d5dc4 --- /dev/null +++ b/lldb/source/Plugins/ABI/MacOSX-arm/ABIMacOSX_arm.h @@ -0,0 +1,95 @@ +//===-- ABIMacOSX_arm.h ----------------------------------------*- C++ -*-===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// + +#ifndef liblldb_ABIMacOSX_arm_h_ +#define liblldb_ABIMacOSX_arm_h_ + +// C Includes +// C++ Includes +// Other libraries and framework includes +// Project includes +#include "lldb/lldb-private.h" +#include "lldb/Target/ABI.h" + +class ABIMacOSX_arm : public lldb_private::ABI +{ +public: + ~ABIMacOSX_arm() { } + + virtual size_t + GetRedZoneSize () const; + + virtual bool + PrepareTrivialCall (lldb_private::Thread &thread, + lldb::addr_t sp, + lldb::addr_t functionAddress, + lldb::addr_t returnAddress, + lldb::addr_t arg, + lldb::addr_t *this_arg, + lldb::addr_t *cmd_arg) const; + + virtual bool + PrepareNormalCall (lldb_private::Thread &thread, + lldb::addr_t sp, + lldb::addr_t functionAddress, + lldb::addr_t returnAddress, + lldb_private::ValueList &args) const; + + virtual bool + GetArgumentValues (lldb_private::Thread &thread, + lldb_private::ValueList &values) const; + + virtual bool + GetReturnValue (lldb_private::Thread &thread, + lldb_private::Value &value) const; + + virtual bool + CreateFunctionEntryUnwindPlan (lldb_private::UnwindPlan &unwind_plan); + + virtual bool + CreateDefaultUnwindPlan (lldb_private::UnwindPlan &unwind_plan); + + virtual bool + RegisterIsVolatile (const lldb_private::RegisterInfo *reg_info); + + + //------------------------------------------------------------------ + // Static Functions + //------------------------------------------------------------------ + static void + Initialize(); + + static void + Terminate(); + + static lldb::ABISP + CreateInstance (const lldb_private::ArchSpec &arch); + + //------------------------------------------------------------------ + // PluginInterface protocol + //------------------------------------------------------------------ + virtual const char * + GetPluginName(); + + virtual const char * + GetShortPluginName(); + + virtual uint32_t + GetPluginVersion(); + +protected: +private: + ABIMacOSX_arm() : + lldb_private::ABI() + { + // Call CreateInstance instead. + } +}; + +#endif // liblldb_ABIMacOSX_arm_h_ diff --git a/lldb/source/Plugins/ABI/MacOSX-arm/Makefile b/lldb/source/Plugins/ABI/MacOSX-arm/Makefile new file mode 100644 index 0000000..1807326 --- /dev/null +++ b/lldb/source/Plugins/ABI/MacOSX-arm/Makefile @@ -0,0 +1,14 @@ +##===- source/Plugins/ABI/MacOSX-arm/Makefile ------------*- Makefile -*-===## +# +# The LLVM Compiler Infrastructure +# +# This file is distributed under the University of Illinois Open Source +# License. See LICENSE.TXT for details. +# +##===--------------------------------------------------------------------===## + +LLDB_LEVEL := ../../../.. +LIBRARYNAME := lldbPluginABIMacOSX_arm +BUILD_ARCHIVE = 1 + +include $(LLDB_LEVEL)/Makefile diff --git a/lldb/source/Plugins/ABI/MacOSX-i386/ABIMacOSX_i386.cpp b/lldb/source/Plugins/ABI/MacOSX-i386/ABIMacOSX_i386.cpp index a65a2efa..8c9df14 100644 --- a/lldb/source/Plugins/ABI/MacOSX-i386/ABIMacOSX_i386.cpp +++ b/lldb/source/Plugins/ABI/MacOSX-i386/ABIMacOSX_i386.cpp @@ -15,6 +15,7 @@ #include "lldb/Core/PluginManager.h" #include "lldb/Core/Scalar.h" #include "lldb/Symbol/ClangASTContext.h" +#include "lldb/Symbol/UnwindPlan.h" #include "lldb/Target/Process.h" #include "lldb/Target/RegisterContext.h" #include "lldb/Target/Target.h" @@ -40,13 +41,17 @@ ABIMacOSX_i386::GetRedZoneSize () const //------------------------------------------------------------------ // Static Functions //------------------------------------------------------------------ -lldb_private::ABI * +ABISP ABIMacOSX_i386::CreateInstance (const ArchSpec &arch) { + static ABISP g_abi_sp; if (arch.GetTriple().getArch() == llvm::Triple::x86) - return new ABIMacOSX_i386; - - return NULL; + { + if (!g_abi_sp) + g_abi_sp.reset (new ABIMacOSX_i386); + return g_abi_sp; + } + return ABISP(); } bool @@ -560,6 +565,145 @@ ABIMacOSX_i386::GetReturnValue (Thread &thread, return true; } +bool +ABIMacOSX_i386::CreateFunctionEntryUnwindPlan (UnwindPlan &unwind_plan) +{ + uint32_t reg_kind = unwind_plan.GetRegisterKind(); + uint32_t sp_reg_num = LLDB_INVALID_REGNUM; + uint32_t pc_reg_num = LLDB_INVALID_REGNUM; + + switch (reg_kind) + { + case eRegisterKindDWARF: + sp_reg_num = dwarf_esp; + pc_reg_num = dwarf_eip; + break; + + case eRegisterKindGCC: + sp_reg_num = gcc_esp; + pc_reg_num = gcc_eip; + break; + + case eRegisterKindGDB: + sp_reg_num = gdb_esp; + pc_reg_num = gdb_eip; + break; + + case eRegisterKindGeneric: + sp_reg_num = LLDB_REGNUM_GENERIC_SP; + pc_reg_num = LLDB_REGNUM_GENERIC_PC; + break; + } + + if (sp_reg_num == LLDB_INVALID_REGNUM || + pc_reg_num == LLDB_INVALID_REGNUM) + return false; + + UnwindPlan::Row row; + row.SetCFARegister (sp_reg_num); + row.SetCFAOffset (4); + row.SetRegisterLocationToAtCFAPlusOffset(pc_reg_num, -4, false); + unwind_plan.AppendRow (row); + unwind_plan.SetSourceName (pluginName); + return true; +} + +bool +ABIMacOSX_i386::CreateDefaultUnwindPlan (UnwindPlan &unwind_plan) +{ + uint32_t reg_kind = unwind_plan.GetRegisterKind(); + uint32_t fp_reg_num = LLDB_INVALID_REGNUM; + uint32_t sp_reg_num = LLDB_INVALID_REGNUM; + uint32_t pc_reg_num = LLDB_INVALID_REGNUM; + + switch (reg_kind) + { + case eRegisterKindDWARF: + fp_reg_num = dwarf_ebp; + sp_reg_num = dwarf_esp; + pc_reg_num = dwarf_eip; + break; + + case eRegisterKindGCC: + fp_reg_num = gcc_ebp; + sp_reg_num = gcc_esp; + pc_reg_num = gcc_eip; + break; + + case eRegisterKindGDB: + fp_reg_num = gdb_ebp; + sp_reg_num = gdb_esp; + pc_reg_num = gdb_eip; + break; + + case eRegisterKindGeneric: + fp_reg_num = LLDB_REGNUM_GENERIC_FP; + sp_reg_num = LLDB_REGNUM_GENERIC_SP; + pc_reg_num = LLDB_REGNUM_GENERIC_PC; + break; + } + + if (fp_reg_num == LLDB_INVALID_REGNUM || + sp_reg_num == LLDB_INVALID_REGNUM || + pc_reg_num == LLDB_INVALID_REGNUM) + return false; + + UnwindPlan::Row row; + const int32_t ptr_size = 4; + + unwind_plan.SetRegisterKind (eRegisterKindGeneric); + row.SetCFARegister (fp_reg_num); + row.SetCFAOffset (2 * ptr_size); + row.SetOffset (0); + + row.SetRegisterLocationToAtCFAPlusOffset(fp_reg_num, ptr_size * -2, true); + row.SetRegisterLocationToAtCFAPlusOffset(pc_reg_num, ptr_size * -1, true); + row.SetRegisterLocationToAtCFAPlusOffset(sp_reg_num, ptr_size * 0, true); + + unwind_plan.AppendRow (row); + unwind_plan.SetSourceName ("i386 default unwind plan"); + return true; +} + +bool +ABIMacOSX_i386::RegisterIsVolatile (const RegisterInfo *reg_info) +{ + return RegisterIsCalleeSaved (reg_info); +} + +bool +ABIMacOSX_i386::RegisterIsCalleeSaved (const RegisterInfo *reg_info) +{ + if (reg_info) + { + // Volatile registers include: ebx, ebp, esi, edi, esp, eip + const char *name = reg_info->name; + if (name[0] == 'e') + { + switch (name[1]) + { + case 'b': + if (name[2] == 'x' || name[2] == 'p') + return name[0] == '\0'; + break; + case 'd': + if (name[2] == 'i') + return name[0] == '\0'; + break; + case 'i': + if (name[2] == 'p') + return name[0] == '\0'; + break; + case 's': + if (name[2] == 'i' || name[2] == 'p') + return name[0] == '\0'; + break; + } + } + } + return false; +} + void ABIMacOSX_i386::Initialize() { diff --git a/lldb/source/Plugins/ABI/MacOSX-i386/ABIMacOSX_i386.h b/lldb/source/Plugins/ABI/MacOSX-i386/ABIMacOSX_i386.h index 20dbc4a..e50330f 100644 --- a/lldb/source/Plugins/ABI/MacOSX-i386/ABIMacOSX_i386.h +++ b/lldb/source/Plugins/ABI/MacOSX-i386/ABIMacOSX_i386.h @@ -17,71 +17,195 @@ #include "lldb/lldb-private.h" #include "lldb/Target/ABI.h" #include "lldb/Core/Value.h" - -namespace lldb_private { - class ABIMacOSX_i386 : +class ABIMacOSX_i386 : public lldb_private::ABI +{ +public: + + enum { - public: - ~ABIMacOSX_i386() { } - - virtual size_t - GetRedZoneSize () const; - - virtual bool - PrepareTrivialCall (Thread &thread, - lldb::addr_t sp, - lldb::addr_t functionAddress, - lldb::addr_t returnAddress, - lldb::addr_t arg, - lldb::addr_t *this_arg, - lldb::addr_t *cmd_arg) const; - - virtual bool - PrepareNormalCall (Thread &thread, - lldb::addr_t sp, - lldb::addr_t functionAddress, - lldb::addr_t returnAddress, - ValueList &args) const; - - virtual bool - GetArgumentValues (Thread &thread, - ValueList &values) const; - - virtual bool - GetReturnValue (Thread &thread, - Value &value) const; - - //------------------------------------------------------------------ - // Static Functions - //------------------------------------------------------------------ - static void - Initialize(); - - static void - Terminate(); - - static lldb_private::ABI * - CreateInstance (const ArchSpec &arch); - - //------------------------------------------------------------------ - // PluginInterface protocol - //------------------------------------------------------------------ - virtual const char * - GetPluginName(); - - virtual const char * - GetShortPluginName(); - - virtual uint32_t - GetPluginVersion(); - - protected: - private: - ABIMacOSX_i386() : lldb_private::ABI() { } // Call CreateInstance instead. + gcc_eax = 0, + gcc_ecx, + gcc_edx, + gcc_ebx, + gcc_ebp, + gcc_esp, + gcc_esi, + gcc_edi, + gcc_eip, + gcc_eflags }; -} // namespace lldb_private + enum + { + dwarf_eax = 0, + dwarf_ecx, + dwarf_edx, + dwarf_ebx, + dwarf_esp, + dwarf_ebp, + dwarf_esi, + dwarf_edi, + dwarf_eip, + dwarf_eflags, + dwarf_stmm0 = 11, + dwarf_stmm1, + dwarf_stmm2, + dwarf_stmm3, + dwarf_stmm4, + dwarf_stmm5, + dwarf_stmm6, + dwarf_stmm7, + dwarf_xmm0 = 21, + dwarf_xmm1, + dwarf_xmm2, + dwarf_xmm3, + dwarf_xmm4, + dwarf_xmm5, + dwarf_xmm6, + dwarf_xmm7, + dwarf_ymm0 = dwarf_xmm0, + dwarf_ymm1 = dwarf_xmm1, + dwarf_ymm2 = dwarf_xmm2, + dwarf_ymm3 = dwarf_xmm3, + dwarf_ymm4 = dwarf_xmm4, + dwarf_ymm5 = dwarf_xmm5, + dwarf_ymm6 = dwarf_xmm6, + dwarf_ymm7 = dwarf_xmm7, + }; + + enum + { + gdb_eax = 0, + gdb_ecx = 1, + gdb_edx = 2, + gdb_ebx = 3, + gdb_esp = 4, + gdb_ebp = 5, + gdb_esi = 6, + gdb_edi = 7, + gdb_eip = 8, + gdb_eflags = 9, + gdb_cs = 10, + gdb_ss = 11, + gdb_ds = 12, + gdb_es = 13, + gdb_fs = 14, + gdb_gs = 15, + gdb_stmm0 = 16, + gdb_stmm1 = 17, + gdb_stmm2 = 18, + gdb_stmm3 = 19, + gdb_stmm4 = 20, + gdb_stmm5 = 21, + gdb_stmm6 = 22, + gdb_stmm7 = 23, + gdb_fctrl = 24, gdb_fcw = gdb_fctrl, + gdb_fstat = 25, gdb_fsw = gdb_fstat, + gdb_ftag = 26, gdb_ftw = gdb_ftag, + gdb_fiseg = 27, gdb_fpu_cs = gdb_fiseg, + gdb_fioff = 28, gdb_ip = gdb_fioff, + gdb_foseg = 29, gdb_fpu_ds = gdb_foseg, + gdb_fooff = 30, gdb_dp = gdb_fooff, + gdb_fop = 31, + gdb_xmm0 = 32, + gdb_xmm1 = 33, + gdb_xmm2 = 34, + gdb_xmm3 = 35, + gdb_xmm4 = 36, + gdb_xmm5 = 37, + gdb_xmm6 = 38, + gdb_xmm7 = 39, + gdb_mxcsr = 40, + gdb_mm0 = 41, + gdb_mm1 = 42, + gdb_mm2 = 43, + gdb_mm3 = 44, + gdb_mm4 = 45, + gdb_mm5 = 46, + gdb_mm6 = 47, + gdb_mm7 = 48, + gdb_ymm0 = gdb_xmm0, + gdb_ymm1 = gdb_xmm1, + gdb_ymm2 = gdb_xmm2, + gdb_ymm3 = gdb_xmm3, + gdb_ymm4 = gdb_xmm4, + gdb_ymm5 = gdb_xmm5, + gdb_ymm6 = gdb_xmm6, + gdb_ymm7 = gdb_xmm7 + }; + + ~ABIMacOSX_i386() { } + + virtual size_t + GetRedZoneSize () const; + + virtual bool + PrepareTrivialCall (lldb_private::Thread &thread, + lldb::addr_t sp, + lldb::addr_t functionAddress, + lldb::addr_t returnAddress, + lldb::addr_t arg, + lldb::addr_t *this_arg, + lldb::addr_t *cmd_arg) const; + + virtual bool + PrepareNormalCall (lldb_private::Thread &thread, + lldb::addr_t sp, + lldb::addr_t functionAddress, + lldb::addr_t returnAddress, + lldb_private::ValueList &args) const; + + virtual bool + GetArgumentValues (lldb_private::Thread &thread, + lldb_private::ValueList &values) const; + + virtual bool + GetReturnValue (lldb_private::Thread &thread, + lldb_private::Value &value) const; + + virtual bool + CreateFunctionEntryUnwindPlan (lldb_private::UnwindPlan &unwind_plan); + + virtual bool + CreateDefaultUnwindPlan (lldb_private::UnwindPlan &unwind_plan); + + virtual bool + RegisterIsVolatile (const lldb_private::RegisterInfo *reg_info); + + + //------------------------------------------------------------------ + // Static Functions + //------------------------------------------------------------------ + static void + Initialize(); + + static void + Terminate(); + + static lldb::ABISP + CreateInstance (const lldb_private::ArchSpec &arch); + + //------------------------------------------------------------------ + // PluginInterface protocol + //------------------------------------------------------------------ + virtual const char * + GetPluginName(); + + virtual const char * + GetShortPluginName(); + + virtual uint32_t + GetPluginVersion(); + +protected: + bool + RegisterIsCalleeSaved (const lldb_private::RegisterInfo *reg_info); + +private: + ABIMacOSX_i386() : lldb_private::ABI() { } // Call CreateInstance instead. +}; + #endif // liblldb_ABI_h_ diff --git a/lldb/source/Plugins/ABI/SysV-x86_64/ABISysV_x86_64.cpp b/lldb/source/Plugins/ABI/SysV-x86_64/ABISysV_x86_64.cpp index 5c2cd74..3ee0562 100644 --- a/lldb/source/Plugins/ABI/SysV-x86_64/ABISysV_x86_64.cpp +++ b/lldb/source/Plugins/ABI/SysV-x86_64/ABISysV_x86_64.cpp @@ -17,6 +17,7 @@ #include "lldb/Core/PluginManager.h" #include "lldb/Core/Value.h" #include "lldb/Symbol/ClangASTContext.h" +#include "lldb/Symbol/UnwindPlan.h" #include "lldb/Target/Target.h" #include "lldb/Target/Process.h" #include "lldb/Target/RegisterContext.h" @@ -32,6 +33,8 @@ static const char *pluginName = "ABISysV_x86_64"; static const char *pluginDesc = "System V ABI for x86_64 targets"; static const char *pluginShort = "abi.sysv-x86_64"; + + size_t ABISysV_x86_64::GetRedZoneSize () const { @@ -41,12 +44,17 @@ ABISysV_x86_64::GetRedZoneSize () const //------------------------------------------------------------------ // Static Functions //------------------------------------------------------------------ -lldb_private::ABI * +ABISP ABISysV_x86_64::CreateInstance (const ArchSpec &arch) { + static ABISP g_abi_sp; if (arch.GetTriple().getArch() == llvm::Triple::x86_64) - return new ABISysV_x86_64; - return NULL; + { + if (!g_abi_sp) + g_abi_sp.reset (new ABISysV_x86_64); + return g_abi_sp; + } + return ABISP(); } bool @@ -446,6 +454,143 @@ ABISysV_x86_64::GetReturnValue (Thread &thread, return true; } +bool +ABISysV_x86_64::CreateFunctionEntryUnwindPlan (UnwindPlan &unwind_plan) +{ + uint32_t reg_kind = unwind_plan.GetRegisterKind(); + uint32_t sp_reg_num = LLDB_INVALID_REGNUM; + uint32_t pc_reg_num = LLDB_INVALID_REGNUM; + + switch (reg_kind) + { + case eRegisterKindDWARF: + case eRegisterKindGCC: + sp_reg_num = gcc_dwarf_rsp; + pc_reg_num = gcc_dwarf_rip; + break; + + case eRegisterKindGDB: + sp_reg_num = gdb_rsp; + pc_reg_num = gdb_rip; + break; + + case eRegisterKindGeneric: + sp_reg_num = LLDB_REGNUM_GENERIC_SP; + pc_reg_num = LLDB_REGNUM_GENERIC_PC; + break; + } + + if (sp_reg_num == LLDB_INVALID_REGNUM || + pc_reg_num == LLDB_INVALID_REGNUM) + return false; + + UnwindPlan::Row row; + row.SetCFARegister (sp_reg_num); + row.SetCFAOffset (8); + row.SetRegisterLocationToAtCFAPlusOffset(pc_reg_num, -8, false); + unwind_plan.AppendRow (row); + unwind_plan.SetSourceName (pluginName); + return true; +} + +bool +ABISysV_x86_64::CreateDefaultUnwindPlan (UnwindPlan &unwind_plan) +{ + uint32_t reg_kind = unwind_plan.GetRegisterKind(); + uint32_t fp_reg_num = LLDB_INVALID_REGNUM; + uint32_t sp_reg_num = LLDB_INVALID_REGNUM; + uint32_t pc_reg_num = LLDB_INVALID_REGNUM; + + switch (reg_kind) + { + case eRegisterKindDWARF: + case eRegisterKindGCC: + fp_reg_num = gcc_dwarf_rbp; + sp_reg_num = gcc_dwarf_rsp; + pc_reg_num = gcc_dwarf_rip; + break; + + case eRegisterKindGDB: + fp_reg_num = gdb_rbp; + sp_reg_num = gdb_rsp; + pc_reg_num = gdb_rip; + break; + + case eRegisterKindGeneric: + fp_reg_num = LLDB_REGNUM_GENERIC_FP; + sp_reg_num = LLDB_REGNUM_GENERIC_SP; + pc_reg_num = LLDB_REGNUM_GENERIC_PC; + break; + } + + if (fp_reg_num == LLDB_INVALID_REGNUM || + sp_reg_num == LLDB_INVALID_REGNUM || + pc_reg_num == LLDB_INVALID_REGNUM) + return false; + + UnwindPlan::Row row; + + const int32_t ptr_size = 8; + row.SetCFARegister (LLDB_REGNUM_GENERIC_FP); + row.SetCFAOffset (2 * ptr_size); + row.SetOffset (0); + + row.SetRegisterLocationToAtCFAPlusOffset(fp_reg_num, ptr_size * -2, true); + row.SetRegisterLocationToAtCFAPlusOffset(pc_reg_num, ptr_size * -1, true); + row.SetRegisterLocationToAtCFAPlusOffset(sp_reg_num, ptr_size * 0, true); + + unwind_plan.AppendRow (row); + unwind_plan.SetSourceName ("x86_64 default unwind plan"); + return true; +} + +bool +ABISysV_x86_64::RegisterIsVolatile (const RegisterInfo *reg_info) +{ + return !RegisterIsCalleeSaved (reg_info); +} + +bool +ABISysV_x86_64::RegisterIsCalleeSaved (const RegisterInfo *reg_info) +{ + if (reg_info) + { + // Volatile registers include: rbx, rbp, rsp, r12, r13, r14, r15, rip + const char *name = reg_info->name; + if (name[0] == 'r') + { + switch (name[1]) + { + case '1': // r12, r13, r14, r15 + if (name[2] >= '2' && name[2] <= '5') + return name[3] == '\0'; + break; + + case 'b': // rbp, rbx + if (name[2] == 'p' || name[2] == 'x') + return name[3] == '\0'; + break; + + case 'i': // rip + if (name[2] == 'p') + return name[3] == '\0'; + break; + + case 's': // rsp + if (name[2] == 'p') + return name[3] == '\0'; + break; + + default: + break; + } + } + } + return false; +} + + + void ABISysV_x86_64::Initialize() { diff --git a/lldb/source/Plugins/ABI/SysV-x86_64/ABISysV_x86_64.h b/lldb/source/Plugins/ABI/SysV-x86_64/ABISysV_x86_64.h index beb6178..e1ac132 100644 --- a/lldb/source/Plugins/ABI/SysV-x86_64/ABISysV_x86_64.h +++ b/lldb/source/Plugins/ABI/SysV-x86_64/ABISysV_x86_64.h @@ -17,19 +17,158 @@ #include "lldb/lldb-private.h" #include "lldb/Target/ABI.h" -namespace lldb_private { - class ABISysV_x86_64 : public lldb_private::ABI { public: - ~ABISysV_x86_64() { } + + enum gcc_dwarf_regnums + { + gcc_dwarf_rax = 0, + gcc_dwarf_rdx, + gcc_dwarf_rcx, + gcc_dwarf_rbx, + gcc_dwarf_rsi, + gcc_dwarf_rdi, + gcc_dwarf_rbp, + gcc_dwarf_rsp, + gcc_dwarf_r8, + gcc_dwarf_r9, + gcc_dwarf_r10, + gcc_dwarf_r11, + gcc_dwarf_r12, + gcc_dwarf_r13, + gcc_dwarf_r14, + gcc_dwarf_r15, + gcc_dwarf_rip, + gcc_dwarf_xmm0, + gcc_dwarf_xmm1, + gcc_dwarf_xmm2, + gcc_dwarf_xmm3, + gcc_dwarf_xmm4, + gcc_dwarf_xmm5, + gcc_dwarf_xmm6, + gcc_dwarf_xmm7, + gcc_dwarf_xmm8, + gcc_dwarf_xmm9, + gcc_dwarf_xmm10, + gcc_dwarf_xmm11, + gcc_dwarf_xmm12, + gcc_dwarf_xmm13, + gcc_dwarf_xmm14, + gcc_dwarf_xmm15, + gcc_dwarf_stmm0, + gcc_dwarf_stmm1, + gcc_dwarf_stmm2, + gcc_dwarf_stmm3, + gcc_dwarf_stmm4, + gcc_dwarf_stmm5, + gcc_dwarf_stmm6, + gcc_dwarf_stmm7, + gcc_dwarf_ymm0 = gcc_dwarf_xmm0, + gcc_dwarf_ymm1 = gcc_dwarf_xmm1, + gcc_dwarf_ymm2 = gcc_dwarf_xmm2, + gcc_dwarf_ymm3 = gcc_dwarf_xmm3, + gcc_dwarf_ymm4 = gcc_dwarf_xmm4, + gcc_dwarf_ymm5 = gcc_dwarf_xmm5, + gcc_dwarf_ymm6 = gcc_dwarf_xmm6, + gcc_dwarf_ymm7 = gcc_dwarf_xmm7, + gcc_dwarf_ymm8 = gcc_dwarf_xmm8, + gcc_dwarf_ymm9 = gcc_dwarf_xmm9, + gcc_dwarf_ymm10 = gcc_dwarf_xmm10, + gcc_dwarf_ymm11 = gcc_dwarf_xmm11, + gcc_dwarf_ymm12 = gcc_dwarf_xmm12, + gcc_dwarf_ymm13 = gcc_dwarf_xmm13, + gcc_dwarf_ymm14 = gcc_dwarf_xmm14, + gcc_dwarf_ymm15 = gcc_dwarf_xmm15 + }; + + enum gdb_regnums + { + gdb_rax = 0, + gdb_rbx = 1, + gdb_rcx = 2, + gdb_rdx = 3, + gdb_rsi = 4, + gdb_rdi = 5, + gdb_rbp = 6, + gdb_rsp = 7, + gdb_r8 = 8, + gdb_r9 = 9, + gdb_r10 = 10, + gdb_r11 = 11, + gdb_r12 = 12, + gdb_r13 = 13, + gdb_r14 = 14, + gdb_r15 = 15, + gdb_rip = 16, + gdb_rflags = 17, + gdb_cs = 18, + gdb_ss = 19, + gdb_ds = 20, + gdb_es = 21, + gdb_fs = 22, + gdb_gs = 23, + gdb_stmm0 = 24, + gdb_stmm1 = 25, + gdb_stmm2 = 26, + gdb_stmm3 = 27, + gdb_stmm4 = 28, + gdb_stmm5 = 29, + gdb_stmm6 = 30, + gdb_stmm7 = 31, + gdb_fctrl = 32, gdb_fcw = gdb_fctrl, + gdb_fstat = 33, gdb_fsw = gdb_fstat, + gdb_ftag = 34, gdb_ftw = gdb_ftag, + gdb_fiseg = 35, gdb_fpu_cs = gdb_fiseg, + gdb_fioff = 36, gdb_ip = gdb_fioff, + gdb_foseg = 37, gdb_fpu_ds = gdb_foseg, + gdb_fooff = 38, gdb_dp = gdb_fooff, + gdb_fop = 39, + gdb_xmm0 = 40, + gdb_xmm1 = 41, + gdb_xmm2 = 42, + gdb_xmm3 = 43, + gdb_xmm4 = 44, + gdb_xmm5 = 45, + gdb_xmm6 = 46, + gdb_xmm7 = 47, + gdb_xmm8 = 48, + gdb_xmm9 = 49, + gdb_xmm10 = 50, + gdb_xmm11 = 51, + gdb_xmm12 = 52, + gdb_xmm13 = 53, + gdb_xmm14 = 54, + gdb_xmm15 = 55, + gdb_mxcsr = 56, + gdb_ymm0 = gdb_xmm0, + gdb_ymm1 = gdb_xmm1, + gdb_ymm2 = gdb_xmm2, + gdb_ymm3 = gdb_xmm3, + gdb_ymm4 = gdb_xmm4, + gdb_ymm5 = gdb_xmm5, + gdb_ymm6 = gdb_xmm6, + gdb_ymm7 = gdb_xmm7, + gdb_ymm8 = gdb_xmm8, + gdb_ymm9 = gdb_xmm9, + gdb_ymm10 = gdb_xmm10, + gdb_ymm11 = gdb_xmm11, + gdb_ymm12 = gdb_xmm12, + gdb_ymm13 = gdb_xmm13, + gdb_ymm14 = gdb_xmm14, + gdb_ymm15 = gdb_xmm15 + }; + + ~ABISysV_x86_64() + { + } virtual size_t GetRedZoneSize () const; virtual bool - PrepareTrivialCall (Thread &thread, + PrepareTrivialCall (lldb_private::Thread &thread, lldb::addr_t sp, lldb::addr_t functionAddress, lldb::addr_t returnAddress, @@ -38,19 +177,28 @@ public: lldb::addr_t *cmd_arg) const; virtual bool - PrepareNormalCall (Thread &thread, + PrepareNormalCall (lldb_private::Thread &thread, lldb::addr_t sp, lldb::addr_t functionAddress, lldb::addr_t returnAddress, - ValueList &args) const; + lldb_private::ValueList &args) const; + + virtual bool + GetArgumentValues (lldb_private::Thread &thread, + lldb_private::ValueList &values) const; virtual bool - GetArgumentValues (Thread &thread, - ValueList &values) const; + GetReturnValue (lldb_private::Thread &thread, + lldb_private::Value &value) const; virtual bool - GetReturnValue (Thread &thread, - Value &value) const; + CreateFunctionEntryUnwindPlan (lldb_private::UnwindPlan &unwind_plan); + + virtual bool + CreateDefaultUnwindPlan (lldb_private::UnwindPlan &unwind_plan); + + virtual bool + RegisterIsVolatile (const lldb_private::RegisterInfo *reg_info); //------------------------------------------------------------------ // Static Functions @@ -61,8 +209,8 @@ public: static void Terminate(); - static lldb_private::ABI * - CreateInstance (const ArchSpec &arch); + static lldb::ABISP + CreateInstance (const lldb_private::ArchSpec &arch); //------------------------------------------------------------------ // PluginInterface protocol @@ -77,10 +225,12 @@ public: GetPluginVersion(); protected: + + bool + RegisterIsCalleeSaved (const lldb_private::RegisterInfo *reg_info); + private: ABISysV_x86_64() : lldb_private::ABI() { } // Call CreateInstance instead. }; -} // namespace lldb_private - #endif // liblldb_ABI_h_ diff --git a/lldb/source/Plugins/ArchDefaultUnwindPlan/x86/ArchDefaultUnwindPlan-x86.cpp b/lldb/source/Plugins/ArchDefaultUnwindPlan/x86/ArchDefaultUnwindPlan-x86.cpp deleted file mode 100644 index 4be89fa..0000000 --- a/lldb/source/Plugins/ArchDefaultUnwindPlan/x86/ArchDefaultUnwindPlan-x86.cpp +++ /dev/null @@ -1,193 +0,0 @@ -//===-- ArchDefaultUnwindPlan-x86.cpp --------------------------*- C++ -*-===// -// -// The LLVM Compiler Infrastructure -// -// This file is distributed under the University of Illinois Open Source -// License. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "ArchDefaultUnwindPlan-x86.h" -#include "lldb/Core/ArchSpec.h" -#include "lldb/Core/PluginManager.h" -#include "lldb/Target/ArchDefaultUnwindPlan.h" - -using namespace lldb; -using namespace lldb_private; - -ArchDefaultUnwindPlan * -ArchDefaultUnwindPlan_x86_64::CreateInstance (const ArchSpec &arch) -{ - if (arch.GetMachine () == llvm::Triple::x86_64) - return new ArchDefaultUnwindPlan_x86_64 (); - return NULL; -} - -ArchDefaultUnwindPlan_x86_64::ArchDefaultUnwindPlan_x86_64() : - ArchDefaultUnwindPlan(), - m_unwind_plan_sp (new UnwindPlan) -{ - UnwindPlan::Row row; - UnwindPlan::Row::RegisterLocation regloc; - - m_unwind_plan_sp->SetRegisterKind (eRegisterKindGeneric); - row.SetCFARegister (LLDB_REGNUM_GENERIC_FP); - row.SetCFAOffset (2 * 8); - row.SetOffset (0); - - regloc.SetAtCFAPlusOffset (2 * -8); - row.SetRegisterInfo (LLDB_REGNUM_GENERIC_FP, regloc); - regloc.SetAtCFAPlusOffset (1 * -8); - row.SetRegisterInfo (LLDB_REGNUM_GENERIC_PC, regloc); - regloc.SetIsCFAPlusOffset (0); - row.SetRegisterInfo (LLDB_REGNUM_GENERIC_SP, regloc); - - m_unwind_plan_sp->AppendRow (row); - m_unwind_plan_sp->SetSourceName ("x86_64 architectural default"); -} - -//------------------------------------------------------------------ -// PluginInterface protocol in UnwindAssemblyParser_x86 -//------------------------------------------------------------------ - -const char * -ArchDefaultUnwindPlan_x86_64::GetPluginName() -{ - return "ArchDefaultUnwindPlan_x86_64"; -} - -const char * -ArchDefaultUnwindPlan_x86_64::GetShortPluginName() -{ - return "lldb.arch-default-unwind-plan.x86-64"; -} - - -uint32_t -ArchDefaultUnwindPlan_x86_64::GetPluginVersion() -{ - return 1; -} -void -ArchDefaultUnwindPlan_x86_64::Initialize() -{ - PluginManager::RegisterPlugin (GetPluginNameStatic(), - GetPluginDescriptionStatic(), - CreateInstance); -} - -void -ArchDefaultUnwindPlan_x86_64::Terminate() -{ - PluginManager::UnregisterPlugin (CreateInstance); -} - - -const char * -ArchDefaultUnwindPlan_x86_64::GetPluginNameStatic() -{ - return "ArchDefaultUnwindPlan_x86_64"; -} - -const char * -ArchDefaultUnwindPlan_x86_64::GetPluginDescriptionStatic() -{ - return "x86_64 architecture default unwind plan assembly plugin."; -} - -UnwindPlanSP -ArchDefaultUnwindPlan_x86_64::GetArchDefaultUnwindPlan (Thread& thread, - const Address ¤t_pc) -{ - return m_unwind_plan_sp; -} - - - -ArchDefaultUnwindPlan * -ArchDefaultUnwindPlan_i386::CreateInstance (const ArchSpec &arch) -{ - if (arch.GetMachine () == llvm::Triple::x86) - return new ArchDefaultUnwindPlan_i386 (); - return NULL; -} - -ArchDefaultUnwindPlan_i386::ArchDefaultUnwindPlan_i386() : - ArchDefaultUnwindPlan(), - m_unwind_plan_sp (new UnwindPlan) -{ - UnwindPlan::Row row; - UnwindPlan::Row::RegisterLocation regloc; - - m_unwind_plan_sp->SetRegisterKind (eRegisterKindGeneric); - row.SetCFARegister (LLDB_REGNUM_GENERIC_FP); - row.SetCFAOffset (2 * 4); - row.SetOffset (0); - - regloc.SetAtCFAPlusOffset (2 * -4); - row.SetRegisterInfo (LLDB_REGNUM_GENERIC_FP, regloc); - regloc.SetAtCFAPlusOffset (1 * -4); - row.SetRegisterInfo (LLDB_REGNUM_GENERIC_PC, regloc); - regloc.SetIsCFAPlusOffset (0); - row.SetRegisterInfo (LLDB_REGNUM_GENERIC_SP, regloc); - - m_unwind_plan_sp->AppendRow (row); - m_unwind_plan_sp->SetSourceName ("i386 architectural default"); -} - -//------------------------------------------------------------------ -// PluginInterface protocol in UnwindAssemblyParser_x86 -//------------------------------------------------------------------ - -const char * -ArchDefaultUnwindPlan_i386::GetPluginName() -{ - return "ArchDefaultUnwindPlan_i386"; -} - -const char * -ArchDefaultUnwindPlan_i386::GetShortPluginName() -{ - return "archdefaultunwindplan.x86"; -} - - -uint32_t -ArchDefaultUnwindPlan_i386::GetPluginVersion() -{ - return 1; -} - -void -ArchDefaultUnwindPlan_i386::Initialize() -{ - PluginManager::RegisterPlugin (GetPluginNameStatic(), - GetPluginDescriptionStatic(), - CreateInstance); -} - -void -ArchDefaultUnwindPlan_i386::Terminate() -{ - PluginManager::UnregisterPlugin (CreateInstance); -} - - -const char * -ArchDefaultUnwindPlan_i386::GetPluginNameStatic() -{ - return "ArchDefaultUnwindPlan_i386"; -} - -const char * -ArchDefaultUnwindPlan_i386::GetPluginDescriptionStatic() -{ - return "i386 architecture default unwind plan assembly plugin."; -} - -UnwindPlanSP -ArchDefaultUnwindPlan_i386::GetArchDefaultUnwindPlan (Thread& thread, const Address ¤t_pc) -{ - return m_unwind_plan_sp; -} - diff --git a/lldb/source/Plugins/ArchDefaultUnwindPlan/x86/ArchDefaultUnwindPlan-x86.h b/lldb/source/Plugins/ArchDefaultUnwindPlan/x86/ArchDefaultUnwindPlan-x86.h deleted file mode 100644 index ce5abb1..0000000 --- a/lldb/source/Plugins/ArchDefaultUnwindPlan/x86/ArchDefaultUnwindPlan-x86.h +++ /dev/null @@ -1,104 +0,0 @@ -//===-- ArchDefaultUnwindPlan-x86.h ----------------------------*- C++ -*-===// -// -// The LLVM Compiler Infrastructure -// -// This file is distributed under the University of Illinois Open Source -// License. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#ifndef liblldb_ArchDefaultUnwindPlan_x86_h_ -#define liblldb_ArchDefaultUnwindPlan_x86_h_ - -#include "lldb/lldb-private.h" -#include "lldb/Target/ArchDefaultUnwindPlan.h" -#include "lldb/Target/Thread.h" -#include "lldb/Symbol/UnwindPlan.h" - -class ArchDefaultUnwindPlan_x86_64 : public lldb_private::ArchDefaultUnwindPlan -{ -public: - - ~ArchDefaultUnwindPlan_x86_64 () { } - - virtual lldb::UnwindPlanSP - GetArchDefaultUnwindPlan (lldb_private::Thread& thread, - const lldb_private::Address ¤t_pc); - - static lldb_private::ArchDefaultUnwindPlan * - CreateInstance (const lldb_private::ArchSpec &arch); - - //------------------------------------------------------------------ - // PluginInterface protocol - //------------------------------------------------------------------ - static void - Initialize(); - - static void - Terminate(); - - static const char * - GetPluginNameStatic(); - - static const char * - GetPluginDescriptionStatic(); - - virtual const char * - GetPluginName(); - - virtual const char * - GetShortPluginName(); - - virtual uint32_t - GetPluginVersion(); - -private: - ArchDefaultUnwindPlan_x86_64(); // Call CreateInstance instead. - - lldb::UnwindPlanSP m_unwind_plan_sp; -}; - -class ArchDefaultUnwindPlan_i386 : public lldb_private::ArchDefaultUnwindPlan -{ -public: - - ~ArchDefaultUnwindPlan_i386 () { } - - virtual lldb::UnwindPlanSP - GetArchDefaultUnwindPlan (lldb_private::Thread& thread, - const lldb_private::Address& current_pc); - - static lldb_private::ArchDefaultUnwindPlan * - CreateInstance (const lldb_private::ArchSpec &arch); - - //------------------------------------------------------------------ - // PluginInterface protocol - //------------------------------------------------------------------ - static void - Initialize(); - - static void - Terminate(); - - static const char * - GetPluginNameStatic(); - - static const char * - GetPluginDescriptionStatic(); - - virtual const char * - GetPluginName(); - - virtual const char * - GetShortPluginName(); - - virtual uint32_t - GetPluginVersion(); - -private: - ArchDefaultUnwindPlan_i386(); // Call CreateInstance instead. - - lldb::UnwindPlanSP m_unwind_plan_sp; -}; - -#endif // liblldb_UnwindAssembly_x86_h_ diff --git a/lldb/source/Plugins/ArchVolatileRegs/x86/ArchVolatileRegs-x86.cpp b/lldb/source/Plugins/ArchVolatileRegs/x86/ArchVolatileRegs-x86.cpp deleted file mode 100644 index 915dbf9..0000000 --- a/lldb/source/Plugins/ArchVolatileRegs/x86/ArchVolatileRegs-x86.cpp +++ /dev/null @@ -1,150 +0,0 @@ -//===-- ArchVolatileRegs-x86.cpp --------------------------------*- C++ -*-===// -// -// The LLVM Compiler Infrastructure -// -// This file is distributed under the University of Illinois Open Source -// License. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#include "ArchVolatileRegs-x86.h" - -#include <set> - -#include "llvm/Support/MachO.h" - -#include "lldb/Core/ArchSpec.h" -#include "lldb/Core/PluginManager.h" -#include "lldb/Target/ArchVolatileRegs.h" -#include "lldb/Target/Thread.h" -#include "lldb/Target/RegisterContext.h" - - -using namespace lldb; -using namespace lldb_private; - -bool -ArchVolatileRegs_x86::RegisterIsVolatile (Thread& thread, uint32_t regnum) -{ - initialize_regset (thread); - if (m_non_volatile_regs.find (regnum) == m_non_volatile_regs.end()) - return true; - else - return false; -} - -lldb_private::ArchVolatileRegs * -ArchVolatileRegs_x86::CreateInstance (const lldb_private::ArchSpec &arch) -{ - llvm::Triple::ArchType cpu = arch.GetMachine (); - if (cpu == llvm::Triple::x86 || cpu == llvm::Triple::x86_64) - return new ArchVolatileRegs_x86 (cpu); - return NULL; -} - -ArchVolatileRegs_x86::ArchVolatileRegs_x86(llvm::Triple::ArchType cpu) : - lldb_private::ArchVolatileRegs(), - m_cpu(cpu), - m_non_volatile_regs() -{ -} - -void -ArchVolatileRegs_x86::initialize_regset(Thread& thread) -{ - if (m_non_volatile_regs.size() > 0) - return; - - - RegisterContext *reg_ctx = thread.GetRegisterContext().get(); - const RegisterInfo *ri; - - const char *x86_64_regnames[] = { "rbx", - "rsp", - "rbp", - "r12", - "r13", - "r14", - "r15", - "rip" }; - - const char *i386_regnames[] = { "ebx", - "ebp", - "esi", - "edi", - "esp", - "eip" }; - - - const char **names; - int namecount; - if (m_cpu == llvm::Triple::x86_64) - { - names = x86_64_regnames; - namecount = sizeof (x86_64_regnames) / sizeof (char *); - } - else - { - assert (m_cpu == llvm::Triple::x86); - names = i386_regnames; - namecount = sizeof (i386_regnames) / sizeof (char *); - } - - for (int i = 0; i < namecount; i++) - { - ri = reg_ctx->GetRegisterInfoByName (names[i]); - if (ri) - m_non_volatile_regs.insert (ri->kinds[eRegisterKindLLDB]); - } -} - - -//------------------------------------------------------------------ -// PluginInterface protocol in ArchVolatileRegs_x86 -//------------------------------------------------------------------ - -const char * -ArchVolatileRegs_x86::GetPluginName() -{ - return "ArchVolatileRegs_x86"; -} - -const char * -ArchVolatileRegs_x86::GetShortPluginName() -{ - return "archvolatileregs.x86"; -} - - -uint32_t -ArchVolatileRegs_x86::GetPluginVersion() -{ - return 1; -} - -void -ArchVolatileRegs_x86::Initialize() -{ - PluginManager::RegisterPlugin (GetPluginNameStatic(), - GetPluginDescriptionStatic(), - CreateInstance); -} - -void -ArchVolatileRegs_x86::Terminate() -{ - PluginManager::UnregisterPlugin (CreateInstance); -} - - -const char * -ArchVolatileRegs_x86::GetPluginNameStatic() -{ - return "ArchVolatileRegs_x86"; -} - -const char * -ArchVolatileRegs_x86::GetPluginDescriptionStatic() -{ - return "i386 and x86_64 architecture volatile register information."; -} diff --git a/lldb/source/Plugins/ArchVolatileRegs/x86/ArchVolatileRegs-x86.h b/lldb/source/Plugins/ArchVolatileRegs/x86/ArchVolatileRegs-x86.h deleted file mode 100644 index c01bef5..0000000 --- a/lldb/source/Plugins/ArchVolatileRegs/x86/ArchVolatileRegs-x86.h +++ /dev/null @@ -1,63 +0,0 @@ -//===-- ArchVolatileRegs-x86.h ----------------------------------*- C++ -*-===// -// -// The LLVM Compiler Infrastructure -// -// This file is distributed under the University of Illinois Open Source -// License. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// - -#ifndef liblldb_ArchVolatileRegs_x86_h_ -#define liblldb_ArchVolatileRegs_x86_h_ - -#include "lldb/lldb-private.h" -#include "lldb/Core/ArchSpec.h" -#include "lldb/Target/ArchVolatileRegs.h" -#include <set> - -class ArchVolatileRegs_x86 : public lldb_private::ArchVolatileRegs -{ -public: - - ~ArchVolatileRegs_x86 () { } - - bool - RegisterIsVolatile (lldb_private::Thread& thread, uint32_t regnum); - - static lldb_private::ArchVolatileRegs * - CreateInstance (const lldb_private::ArchSpec &arch); - - //------------------------------------------------------------------ - // PluginInterface protocol - //------------------------------------------------------------------ - static void - Initialize(); - - static void - Terminate(); - - static const char * - GetPluginNameStatic(); - - static const char * - GetPluginDescriptionStatic(); - - virtual const char * - GetPluginName(); - - virtual const char * - GetShortPluginName(); - - virtual uint32_t - GetPluginVersion(); - -private: - ArchVolatileRegs_x86(llvm::Triple::ArchType cpu); // Call CreateInstance instead. - - void initialize_regset(lldb_private::Thread& thread); - - llvm::Triple::ArchType m_cpu; - std::set<int> m_non_volatile_regs; -}; - -#endif // liblldb_ArchVolatileRegs_x86_h_ diff --git a/lldb/source/Plugins/Instruction/ARM/EmulateInstructionARM.cpp b/lldb/source/Plugins/Instruction/ARM/EmulateInstructionARM.cpp index 91f1f1c..48e5c7f 100644 --- a/lldb/source/Plugins/Instruction/ARM/EmulateInstructionARM.cpp +++ b/lldb/source/Plugins/Instruction/ARM/EmulateInstructionARM.cpp @@ -576,7 +576,7 @@ EmulateInstructionARM::EmulateADDRdSPImm (const uint32_t opcode, const ARMEncodi addr_t addr = sp + sp_offset; // a pointer to the stack area EmulateInstruction::Context context; - context.type = EmulateInstruction::eContextAdjustStackPointer; + context.type = eContextSetFramePointer; RegisterInfo sp_reg; GetRegisterInfo (eRegisterKindDWARF, dwarf_sp, sp_reg); context.SetRegisterPlusOffset (sp_reg, sp_offset); @@ -13413,17 +13413,16 @@ EmulateInstructionARM::TestEmulation (Stream *out_stream, ArchSpec &arch, Option bool EmulateInstructionARM::CreateFunctionEntryUnwind (UnwindPlan &unwind_plan) { + unwind_plan.Clear(); unwind_plan.SetRegisterKind (eRegisterKindDWARF); UnwindPlan::Row row; - UnwindPlan::Row::RegisterLocation regloc; // Our previous Call Frame Address is the stack pointer row.SetCFARegister (dwarf_sp); // Our previous PC is in the LR - regloc.SetInRegister(dwarf_lr); - row.SetRegisterInfo (dwarf_pc, regloc); + row.SetRegisterLocationToRegister(dwarf_pc, dwarf_lr, true); unwind_plan.AppendRow (row); // All other registers are the same. diff --git a/lldb/source/Plugins/LanguageRuntime/ObjC/AppleObjCRuntime/AppleObjCTrampolineHandler.cpp b/lldb/source/Plugins/LanguageRuntime/ObjC/AppleObjCRuntime/AppleObjCTrampolineHandler.cpp index 9de258e..e042cb2 100644 --- a/lldb/source/Plugins/LanguageRuntime/ObjC/AppleObjCRuntime/AppleObjCTrampolineHandler.cpp +++ b/lldb/source/Plugins/LanguageRuntime/ObjC/AppleObjCRuntime/AppleObjCTrampolineHandler.cpp @@ -391,7 +391,7 @@ AppleObjCTrampolineHandler::AppleObjCVTables::RefreshTrampolines (void *baton, // The Update function is called with the address of an added region. So we grab that address, and // feed it into ReadRegions. Of course, our friend the ABI will get the values for us. Process *process = context->exe_ctx.process; - const ABI *abi = process->GetABI(); + const ABI *abi = process->GetABI().get(); ClangASTContext *clang_ast_context = process->GetTarget().GetScratchClangASTContext(); ValueList argument_values; @@ -624,7 +624,7 @@ AppleObjCTrampolineHandler::GetStepThroughDispatchPlan (Thread &thread, bool sto lldb::StackFrameSP thread_cur_frame = thread.GetStackFrameAtIndex(0); Process *process = thread.CalculateProcess(); - const ABI *abi = process->GetABI(); + const ABI *abi = process->GetABI().get(); if (abi == NULL) return ret_plan_sp; diff --git a/lldb/source/Plugins/Process/Utility/RegisterContextLLDB.cpp b/lldb/source/Plugins/Process/Utility/RegisterContextLLDB.cpp index ef882fa..a0ca3af3 100644 --- a/lldb/source/Plugins/Process/Utility/RegisterContextLLDB.cpp +++ b/lldb/source/Plugins/Process/Utility/RegisterContextLLDB.cpp @@ -21,8 +21,7 @@ #include "lldb/Symbol/SymbolContext.h" #include "lldb/Symbol/Symbol.h" #include "lldb/Expression/DWARFExpression.h" -#include "lldb/Target/ArchDefaultUnwindPlan.h" -#include "lldb/Target/ArchVolatileRegs.h" +#include "lldb/Target/ABI.h" #include "lldb/Target/ExecutionContext.h" #include "lldb/Target/Process.h" #include "lldb/Target/StackFrame.h" @@ -247,12 +246,12 @@ RegisterContextLLDB::InitializeNonZerothFrame() log->Printf("%*sFrame %u using architectural default unwind method", m_frame_number < 100 ? m_frame_number : 100, "", m_frame_number); } - const ArchSpec &arch = m_thread.GetProcess().GetTarget().GetArchitecture (); - ArchDefaultUnwindPlanSP arch_default_sp (ArchDefaultUnwindPlan::FindPlugin (arch)); - if (arch_default_sp) + ABI *abi = m_thread.GetProcess().GetABI().get(); + if (abi) { - m_fast_unwind_plan_sp.reset(); - m_full_unwind_plan_sp = arch_default_sp->GetArchDefaultUnwindPlan (m_thread, m_current_pc); + m_fast_unwind_plan_sp.reset (); + m_full_unwind_plan_sp.reset (new UnwindPlan (lldb::eRegisterKindGeneric)); + abi->CreateDefaultUnwindPlan(*m_full_unwind_plan_sp); m_frame_type = eNormalFrame; m_all_registers_available = false; m_current_offset = -1; @@ -519,10 +518,14 @@ RegisterContextLLDB::GetFullUnwindPlanForFrame () UnwindPlanSP unwind_plan_sp; LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_UNWIND)); UnwindPlanSP arch_default_unwind_plan_sp; - const ArchSpec &arch = m_thread.GetProcess().GetTarget().GetArchitecture (); - ArchDefaultUnwindPlanSP arch_default_sp (ArchDefaultUnwindPlan::FindPlugin (arch)); - if (arch_default_sp) - arch_default_unwind_plan_sp = arch_default_sp->GetArchDefaultUnwindPlan (m_thread, m_current_pc); + + + ABI *abi = m_thread.GetProcess().GetABI().get(); + if (abi) + { + arch_default_unwind_plan_sp.reset (new UnwindPlan (lldb::eRegisterKindGeneric)); + abi->CreateDefaultUnwindPlan(*arch_default_unwind_plan_sp); + } bool behaves_like_zeroth_frame = false; if (IsFrameZero () @@ -871,18 +874,21 @@ RegisterContextLLDB::SavedLocationForRegister (uint32_t lldb_regnum, RegisterLoc { // If a volatile register is being requested, we don't want to forward m_next_frame's register contents // up the stack -- the register is not retrievable at this frame. - const ArchSpec &arch = m_thread.GetProcess().GetTarget().GetArchitecture (); - ArchVolatileRegs *volatile_regs = ArchVolatileRegs::FindPlugin (arch); - if (volatile_regs && volatile_regs->RegisterIsVolatile (m_thread, lldb_regnum)) + ABI *abi = m_thread.GetProcess().GetABI().get(); + if (abi) { - if (log) + const RegisterInfo *reg_info = GetRegisterInfoAtIndex(lldb_regnum); + if (reg_info && abi->RegisterIsVolatile (reg_info)) { - log->Printf("%*sFrame %u did not supply reg location for %d because it is volatile", - m_frame_number < 100 ? m_frame_number : 100, "", m_frame_number, - lldb_regnum); - } - return false; - } + if (log) + { + log->Printf("%*sFrame %u did not supply reg location for %d because it is volatile", + m_frame_number < 100 ? m_frame_number : 100, "", m_frame_number, + lldb_regnum); + } + return false; + } + } if (IsFrameZero ()) { diff --git a/lldb/source/Plugins/Process/Utility/UnwindLLDB.cpp b/lldb/source/Plugins/Process/Utility/UnwindLLDB.cpp index 9807819..2de786f 100644 --- a/lldb/source/Plugins/Process/Utility/UnwindLLDB.cpp +++ b/lldb/source/Plugins/Process/Utility/UnwindLLDB.cpp @@ -12,7 +12,6 @@ #include "lldb/Symbol/FuncUnwinders.h" #include "lldb/Symbol/Function.h" #include "lldb/Symbol/UnwindPlan.h" -#include "lldb/Target/ArchDefaultUnwindPlan.h" #include "lldb/Target/Thread.h" #include "lldb/Target/Target.h" #include "lldb/Target/Process.h" diff --git a/lldb/source/Plugins/Process/gdb-remote/ThreadGDBRemote.cpp b/lldb/source/Plugins/Process/gdb-remote/ThreadGDBRemote.cpp index df16f56..3e9cef3 100644 --- a/lldb/source/Plugins/Process/gdb-remote/ThreadGDBRemote.cpp +++ b/lldb/source/Plugins/Process/gdb-remote/ThreadGDBRemote.cpp @@ -147,8 +147,8 @@ ThreadGDBRemote::GetUnwinder () { case llvm::Triple::x86_64: case llvm::Triple::x86: -// case llvm::Triple::arm: -// case llvm::Triple::thumb: + case llvm::Triple::arm: + case llvm::Triple::thumb: m_unwinder_ap.reset (new UnwindLLDB (*this)); break; diff --git a/lldb/source/Plugins/UnwindAssembly/InstEmulation/UnwindAssemblyInstEmulation.cpp b/lldb/source/Plugins/UnwindAssembly/InstEmulation/UnwindAssemblyInstEmulation.cpp index 0ce503c..ee427ee 100644 --- a/lldb/source/Plugins/UnwindAssembly/InstEmulation/UnwindAssemblyInstEmulation.cpp +++ b/lldb/source/Plugins/UnwindAssembly/InstEmulation/UnwindAssemblyInstEmulation.cpp @@ -16,8 +16,9 @@ #include "lldb/Core/DataBufferHeap.h" #include "lldb/Core/Disassembler.h" #include "lldb/Core/Error.h" +#include "lldb/Core/Log.h" #include "lldb/Core/PluginManager.h" -#include "lldb/Core/StreamFile.h" +#include "lldb/Core/StreamString.h" #include "lldb/Target/ExecutionContext.h" #include "lldb/Target/Process.h" #include "lldb/Target/Thread.h" @@ -37,49 +38,19 @@ UnwindAssemblyInstEmulation::GetNonCallSiteUnwindPlanFromAssembly (AddressRange& Thread& thread, UnwindPlan& unwind_plan) { -#if 0 - UnwindPlan::Row row; - UnwindPlan::Row::RegisterLocation regloc; - - m_unwind_plan_sp->SetRegisterKind (eRegisterKindGeneric); - row.SetCFARegister (LLDB_REGNUM_GENERIC_FP); - row.SetCFAOffset (2 * 8); - row.SetOffset (0); - - regloc.SetAtCFAPlusOffset (2 * -8); - row.SetRegisterInfo (LLDB_REGNUM_GENERIC_FP, regloc); - regloc.SetAtCFAPlusOffset (1 * -8); - row.SetRegisterInfo (LLDB_REGNUM_GENERIC_PC, regloc); - regloc.SetIsCFAPlusOffset (0); - row.SetRegisterInfo (LLDB_REGNUM_GENERIC_SP, regloc); - - m_unwind_plan_sp->AppendRow (row); - m_unwind_plan_sp->SetSourceName ("x86_64 architectural default"); -#endif - if (range.GetByteSize() > 0 && range.GetBaseAddress().IsValid() && m_inst_emulator_ap.get()) { -#if 0 - Target &target = thread.GetProcess().GetTarget(); - const ArchSpec &target_arch = target.GetArchitecture(); - bool prefer_file_cache = true; - Error error; - DataBufferHeap data_buffer (range.GetByteSize(), 0); - if (target.ReadMemory (range.GetBaseAddress(), - prefer_file_cache, - data_buffer.GetBytes(), - data_buffer.GetByteSize(), - error) == data_buffer.GetByteSize()) - { - DataExtractor data (data_buffer.GetBytes(), - data_buffer.GetByteSize(), - target_arch.GetByteOrder(), - target_arch.GetAddressByteSize()); - } -#endif - StreamFile strm (stdout, false); + + // The the instruction emulation subclass setup the unwind plan for the + // first instruction. + m_inst_emulator_ap->CreateFunctionEntryUnwind (unwind_plan); + + // CreateFunctionEntryUnwind should have created the first row. If it + // doesn't, then we are done. + if (unwind_plan.GetRowCount() == 0) + return false; ExecutionContext exe_ctx; thread.CalculateExecutionContext(exe_ctx); @@ -87,6 +58,9 @@ UnwindAssemblyInstEmulation::GetNonCallSiteUnwindPlanFromAssembly (AddressRange& NULL, exe_ctx, range)); + + LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_UNWIND)); + if (disasm_sp) { @@ -98,13 +72,19 @@ UnwindAssemblyInstEmulation::GetNonCallSiteUnwindPlanFromAssembly (AddressRange& const bool show_address = true; const bool show_bytes = true; const bool raw = false; - // Initialize the stack pointer with a known value. In the 32 bit case + // Initialize the CFA with a known value. In the 32 bit case // it will be 0x80000000, and in the 64 bit case 0x8000000000000000. // We use the address byte size to be safe for any future addresss sizes - RegisterInfo sp_reg_info; - m_inst_emulator_ap->GetRegisterInfo (eRegisterKindGeneric, LLDB_REGNUM_GENERIC_SP, sp_reg_info); + m_inst_emulator_ap->GetRegisterInfo (unwind_plan.GetRegisterKind(), + unwind_plan.GetInitialCFARegister(), + m_cfa_reg_info); + + m_fp_is_cfa = false; + m_register_values.clear(); + m_pushed_regs.clear(); + m_initial_sp = (1ull << ((addr_byte_size * 8) - 1)); - SetRegisterValue(sp_reg_info, m_initial_sp); + SetRegisterValue (m_cfa_reg_info, m_initial_sp); const InstructionList &inst_list = disasm_sp->GetInstructionList (); const size_t num_instructions = inst_list.GetSize(); @@ -112,26 +92,51 @@ UnwindAssemblyInstEmulation::GetNonCallSiteUnwindPlanFromAssembly (AddressRange& { Instruction *inst = inst_list.GetInstructionAtIndex (0).get(); const addr_t base_addr = inst->GetAddress().GetFileAddress(); + // Initialize the current row with the one row that was created + // from the CreateFunctionEntryUnwind call above... + m_curr_row = unwind_plan.GetLastRow(); for (size_t idx=0; idx<num_instructions; ++idx) { inst = inst_list.GetInstructionAtIndex (idx).get(); if (inst) { - m_curr_row.Clear(); - inst->Dump(&strm, inst_list.GetMaxOpcocdeByteSize (), show_address, show_bytes, &exe_ctx, raw); - strm.EOL(); + + if (log) + { + StreamString strm; + inst->Dump(&strm, inst_list.GetMaxOpcocdeByteSize (), show_address, show_bytes, &exe_ctx, raw); + log->PutCString (strm.GetData()); + } m_inst_emulator_ap->SetInstruction (inst->GetOpcode(), inst->GetAddress(), exe_ctx.target); - m_curr_row.SetOffset (inst->GetAddress().GetFileAddress() + inst->GetOpcode().GetByteSize() - base_addr); m_inst_emulator_ap->EvaluateInstruction (eEmulateInstructionOptionIgnoreConditions); + + if (unwind_plan.GetLastRow() != m_curr_row) + { + // Be sure to not edit the offset unless our row has changed + // so that the "!=" call above doesn't trigger every time + m_curr_row.SetOffset (inst->GetAddress().GetFileAddress() + inst->GetOpcode().GetByteSize() - base_addr); + // Append the new row + unwind_plan.AppendRow (m_curr_row); + } } } } } + + if (log) + { + StreamString strm; + lldb::addr_t base_addr = range.GetBaseAddress().GetLoadAddress(&thread.GetProcess().GetTarget()); + strm.Printf ("Resulting unwind rows for [0x%llx - 0x%llx):", base_addr, base_addr + range.GetByteSize()); + unwind_plan.Dump(strm, &thread, base_addr); + log->PutCString (strm.GetData()); + } + return unwind_plan.GetRowCount() > 0; } return false; } @@ -255,12 +260,18 @@ UnwindAssemblyInstEmulation::ReadMemory (EmulateInstruction *instruction, void *dst, size_t dst_len) { - //UnwindAssemblyInstEmulation *inst_emulator = (UnwindAssemblyInstEmulation *)baton; - printf ("UnwindAssemblyInstEmulation::ReadMemory (addr = 0x%16.16llx, dst = %p, dst_len = %zu, context = ", - addr, - dst, - dst_len); - context.Dump(stdout, instruction); + LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_UNWIND)); + + if (log) + { + StreamString strm; + strm.Printf ("UnwindAssemblyInstEmulation::ReadMemory (addr = 0x%16.16llx, dst = %p, dst_len = %zu, context = ", + addr, + dst, + dst_len); + context.Dump(strm, instruction); + log->PutCString (strm.GetData ()); + } return dst_len; } @@ -272,19 +283,39 @@ UnwindAssemblyInstEmulation::WriteMemory (EmulateInstruction *instruction, const void *dst, size_t dst_len) { - UnwindAssemblyInstEmulation *inst_emulator = (UnwindAssemblyInstEmulation *)baton; - + if (baton && dst && dst_len) + return ((UnwindAssemblyInstEmulation *)baton)->WriteMemory (instruction, context, addr, dst, dst_len); + return 0; +} + +size_t +UnwindAssemblyInstEmulation::WriteMemory (EmulateInstruction *instruction, + const EmulateInstruction::Context &context, + lldb::addr_t addr, + const void *dst, + size_t dst_len) +{ DataExtractor data (dst, dst_len, instruction->GetArchitecture ().GetByteOrder(), instruction->GetArchitecture ().GetAddressByteSize()); - StreamFile strm(stdout, false); - strm.PutCString ("UnwindAssemblyInstEmulation::WriteMemory ("); - data.Dump(&strm, 0, eFormatBytes, 1, dst_len, UINT32_MAX, addr, 0, 0); - strm.PutCString (", context = "); - context.Dump(stdout, instruction); + LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_UNWIND)); + + if (log) + { + StreamString strm; + + strm.PutCString ("UnwindAssemblyInstEmulation::WriteMemory ("); + data.Dump(&strm, 0, eFormatBytes, 1, dst_len, UINT32_MAX, addr, 0, 0); + strm.PutCString (", context = "); + context.Dump(strm, instruction); + log->PutCString (strm.GetData()); + } + const bool can_replace = true; + const bool cant_replace = false; + switch (context.type) { default: @@ -307,25 +338,45 @@ UnwindAssemblyInstEmulation::WriteMemory (EmulateInstruction *instruction, case EmulateInstruction::eContextReturnFromException: case EmulateInstruction::eContextPopRegisterOffStack: case EmulateInstruction::eContextAdjustStackPointer: - assert (!"unhandled case, add code to handle this!"); break; case EmulateInstruction::eContextPushRegisterOnStack: - switch (context.info_type) { - case EmulateInstruction::eInfoTypeRegisterToRegisterPlusOffset: + uint32_t reg_num = LLDB_INVALID_REGNUM; + bool is_return_address_reg = false; + const uint32_t unwind_reg_kind = m_unwind_plan_ptr->GetRegisterKind(); + if (context.info_type == EmulateInstruction::eInfoTypeRegisterToRegisterPlusOffset) + { + reg_num = context.info.RegisterToRegisterPlusOffset.data_reg.kinds[unwind_reg_kind]; + if (context.info.RegisterToRegisterPlusOffset.data_reg.kinds[eRegisterKindGeneric] == LLDB_REGNUM_GENERIC_RA) + is_return_address_reg = true; + } + else + { + assert (!"unhandled case, add code to handle this!"); + } + + if (reg_num != LLDB_INVALID_REGNUM) + { + if (m_pushed_regs.find (reg_num) == m_pushed_regs.end()) { - UnwindPlan::Row::RegisterLocation regloc; - const uint32_t dwarf_reg_num = context.info.RegisterToRegisterPlusOffset.data_reg.kinds[eRegisterKindDWARF]; - //const addr_t reg_cfa_offset = inst_emulator->m_curr_row.GetCFAOffset() + context.info.RegisterToRegisterPlusOffset.offset; - regloc.SetAtCFAPlusOffset (addr - inst_emulator->m_initial_sp); - inst_emulator->m_curr_row.SetRegisterInfo (dwarf_reg_num, regloc); + m_pushed_regs[reg_num] = addr; + const int32_t offset = addr - m_initial_sp; + m_curr_row.SetRegisterLocationToAtCFAPlusOffset (reg_num, offset, cant_replace); + if (is_return_address_reg) + { + // This push was pushing the return address register, + // so this is also how we will unwind the PC... + RegisterInfo pc_reg_info; + if (instruction->GetRegisterInfo (eRegisterKindGeneric, LLDB_REGNUM_GENERIC_PC, pc_reg_info)) + { + uint32_t pc_reg_num = pc_reg_info.kinds[unwind_reg_kind]; + if (pc_reg_num != LLDB_INVALID_REGNUM) + m_curr_row.SetRegisterLocationToAtCFAPlusOffset (pc_reg_num, offset, can_replace); + } + } } - break; - - default: - assert (!"unhandled case, add code to handle this!"); - break; + } } break; @@ -340,15 +391,27 @@ UnwindAssemblyInstEmulation::ReadRegister (EmulateInstruction *instruction, const RegisterInfo *reg_info, RegisterValue ®_value) { + if (baton && reg_info) - { - UnwindAssemblyInstEmulation *inst_emulator = (UnwindAssemblyInstEmulation *)baton; - bool synthetic = inst_emulator->GetRegisterValue (*reg_info, reg_value); + return ((UnwindAssemblyInstEmulation *)baton)->ReadRegister (instruction, reg_info, reg_value); + return false; +} +bool +UnwindAssemblyInstEmulation::ReadRegister (EmulateInstruction *instruction, + const RegisterInfo *reg_info, + RegisterValue ®_value) +{ + bool synthetic = GetRegisterValue (*reg_info, reg_value); - StreamFile strm (stdout, false); + LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_UNWIND)); + + if (log) + { + + StreamString strm; strm.Printf ("UnwindAssemblyInstEmulation::ReadRegister (name = \"%s\") => synthetic_value = %i, value = ", reg_info->name, synthetic); reg_value.Dump(&strm, reg_info, false, eFormatDefault); - strm.EOL(); + log->PutCString(strm.GetData()); } return true; } @@ -360,17 +423,31 @@ UnwindAssemblyInstEmulation::WriteRegister (EmulateInstruction *instruction, const RegisterInfo *reg_info, const RegisterValue ®_value) { - if (!baton || !reg_info) - return false; + if (baton && reg_info) + return ((UnwindAssemblyInstEmulation *)baton)->WriteRegister (instruction, context, reg_info, reg_value); + return false; +} +bool +UnwindAssemblyInstEmulation::WriteRegister (EmulateInstruction *instruction, + const EmulateInstruction::Context &context, + const RegisterInfo *reg_info, + const RegisterValue ®_value) +{ + LogSP log(GetLogIfAllCategoriesSet (LIBLLDB_LOG_UNWIND)); - UnwindAssemblyInstEmulation *inst_emulator = (UnwindAssemblyInstEmulation *)baton; - StreamFile strm (stdout, false); - strm.Printf ("UnwindAssemblyInstEmulation::WriteRegister (name = \"%s\", value = ", reg_info->name); - reg_value.Dump(&strm, reg_info, false, eFormatDefault); - strm.PutCString (", context = "); - context.Dump(stdout, instruction); + if (log) + { + + StreamString strm; + strm.Printf ("UnwindAssemblyInstEmulation::WriteRegister (name = \"%s\", value = ", reg_info->name); + reg_value.Dump(&strm, reg_info, false, eFormatDefault); + strm.PutCString (", context = "); + context.Dump(strm, instruction); + log->PutCString(strm.GetData()); + } - inst_emulator->SetRegisterValue (*reg_info, reg_value); + const bool must_replace = true; + SetRegisterValue (*reg_info, reg_value); switch (context.type) { @@ -393,31 +470,48 @@ UnwindAssemblyInstEmulation::WriteRegister (EmulateInstruction *instruction, case EmulateInstruction::eContextAdvancePC: case EmulateInstruction::eContextReturnFromException: case EmulateInstruction::eContextPushRegisterOnStack: - assert (!"unhandled case, add code to handle this!"); +// { +// const uint32_t reg_num = reg_info->kinds[m_unwind_plan_ptr->GetRegisterKind()]; +// if (reg_num != LLDB_INVALID_REGNUM) +// { +// const bool can_replace_only_if_unspecified = true; +// +// m_curr_row.SetRegisterLocationToUndefined (reg_num, +// can_replace_only_if_unspecified, +// can_replace_only_if_unspecified); +// } +// } break; case EmulateInstruction::eContextPopRegisterOffStack: { - switch (context.info_type) + const uint32_t reg_num = reg_info->kinds[m_unwind_plan_ptr->GetRegisterKind()]; + if (reg_num != LLDB_INVALID_REGNUM) { - case EmulateInstruction::eInfoTypeRegisterPlusOffset: - { - const uint32_t dwarf_reg_num = reg_info->kinds[eRegisterKindDWARF]; - UnwindPlan::Row::RegisterLocation regloc; - regloc.SetSame(); - inst_emulator->m_curr_row.SetRegisterInfo (dwarf_reg_num, regloc); - } - break; - - default: - assert (!"unhandled case, add code to handle this!"); - break; + m_curr_row.SetRegisterLocationToSame (reg_num, must_replace); } } break; + case EmulateInstruction::eContextSetFramePointer: + if (!m_fp_is_cfa) + { + m_fp_is_cfa = true; + m_cfa_reg_info = *reg_info; + const uint32_t cfa_reg_num = reg_info->kinds[m_unwind_plan_ptr->GetRegisterKind()]; + assert (cfa_reg_num != LLDB_INVALID_REGNUM); + m_curr_row.SetCFARegister(cfa_reg_num); + m_curr_row.SetCFAOffset(m_initial_sp - reg_value.GetAsUInt64()); + } + break; + case EmulateInstruction::eContextAdjustStackPointer: - inst_emulator->m_curr_row.SetCFAOffset (reg_value.GetAsUInt64() - inst_emulator->m_initial_sp); + // If we have created a frame using the frame pointer, don't follow + // subsequent adjustments to the stack pointer. + if (!m_fp_is_cfa) + { + m_curr_row.SetCFAOffset (m_initial_sp - reg_value.GetAsUInt64()); + } break; } return true; diff --git a/lldb/source/Plugins/UnwindAssembly/InstEmulation/UnwindAssemblyInstEmulation.h b/lldb/source/Plugins/UnwindAssembly/InstEmulation/UnwindAssemblyInstEmulation.h index 96c1381..b702571 100644 --- a/lldb/source/Plugins/UnwindAssembly/InstEmulation/UnwindAssemblyInstEmulation.h +++ b/lldb/source/Plugins/UnwindAssembly/InstEmulation/UnwindAssemblyInstEmulation.h @@ -101,6 +101,31 @@ private: const lldb_private::RegisterValue ®_value); +// size_t +// ReadMemory (lldb_private::EmulateInstruction *instruction, +// const lldb_private::EmulateInstruction::Context &context, +// lldb::addr_t addr, +// void *dst, +// size_t length); + + size_t + WriteMemory (lldb_private::EmulateInstruction *instruction, + const lldb_private::EmulateInstruction::Context &context, + lldb::addr_t addr, + const void *dst, + size_t length); + + bool + ReadRegister (lldb_private::EmulateInstruction *instruction, + const lldb_private::RegisterInfo *reg_info, + lldb_private::RegisterValue ®_value); + + bool + WriteRegister (lldb_private::EmulateInstruction *instruction, + const lldb_private::EmulateInstruction::Context &context, + 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) : @@ -108,7 +133,12 @@ private: m_inst_emulator_ap (inst_emulator), m_range_ptr (NULL), m_thread_ptr (NULL), - m_unwind_plan_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() { if (m_inst_emulator_ap.get()) { @@ -133,9 +163,13 @@ private: lldb_private::Thread* m_thread_ptr; lldb_private::UnwindPlan* m_unwind_plan_ptr; lldb_private::UnwindPlan::Row m_curr_row; + typedef std::map<uint64_t, uint64_t> PushedRegisterToAddrMap; uint64_t m_initial_sp; + lldb_private::RegisterInfo m_cfa_reg_info; + bool m_fp_is_cfa; typedef std::map<uint64_t, lldb_private::RegisterValue> RegisterValueMap; RegisterValueMap m_register_values; + PushedRegisterToAddrMap m_pushed_regs; }; #endif // liblldb_UnwindAssemblyInstEmulation_h_ diff --git a/lldb/source/Symbol/FuncUnwinders.cpp b/lldb/source/Symbol/FuncUnwinders.cpp index eb8e4da..12f7794 100644 --- a/lldb/source/Symbol/FuncUnwinders.cpp +++ b/lldb/source/Symbol/FuncUnwinders.cpp @@ -14,7 +14,8 @@ #include "lldb/Symbol/ObjectFile.h" #include "lldb/Symbol/UnwindPlan.h" #include "lldb/Symbol/UnwindTable.h" -#include "lldb/Target/ArchDefaultUnwindPlan.h" +#include "lldb/Target/ABI.h" +#include "lldb/Target/Process.h" #include "lldb/Target/Thread.h" #include "lldb/Target/Target.h" #include "lldb/Target/UnwindAssembly.h" @@ -83,7 +84,7 @@ FuncUnwinders::GetUnwindPlanAtCallSite (int current_offset) DWARFCallFrameInfo *eh_frame = m_unwind_table.GetEHFrameInfo(); if (eh_frame) { - m_unwind_plan_call_site_sp.reset (new UnwindPlan); + m_unwind_plan_call_site_sp.reset (new UnwindPlan (lldb::eRegisterKindGeneric)); if (!eh_frame->GetUnwindPlan (current_pc, *m_unwind_plan_call_site_sp)) m_unwind_plan_call_site_sp.reset(); } @@ -111,7 +112,7 @@ FuncUnwinders::GetUnwindPlanAtNonCallSite (Thread& thread) if (m_tried_unwind_at_non_call_site == false && m_unwind_plan_non_call_site_sp.get() == NULL) { m_tried_unwind_at_non_call_site = true; - m_unwind_plan_non_call_site_sp.reset (new UnwindPlan); + m_unwind_plan_non_call_site_sp.reset (new UnwindPlan (lldb::eRegisterKindGeneric)); if (!m_assembly_profiler->GetNonCallSiteUnwindPlanFromAssembly (m_range, thread, *m_unwind_plan_non_call_site_sp)) m_unwind_plan_non_call_site_sp.reset(); } @@ -137,7 +138,7 @@ FuncUnwinders::GetUnwindPlanFastUnwind (Thread& thread) if (m_tried_unwind_fast == false && m_unwind_plan_fast_sp.get() == NULL) { m_tried_unwind_fast = true; - m_unwind_plan_fast_sp.reset (new UnwindPlan); + m_unwind_plan_fast_sp.reset (new UnwindPlan (lldb::eRegisterKindGeneric)); if (!m_assembly_profiler->GetFastUnwindPlan (m_range, thread, *m_unwind_plan_fast_sp)) m_unwind_plan_fast_sp.reset(); } @@ -167,9 +168,13 @@ FuncUnwinders::GetUnwindPlanArchitectureDefault (Thread& thread) Target *target = thread.CalculateTarget(); if (target) { - ArchDefaultUnwindPlanSP arch_default_sp (ArchDefaultUnwindPlan::FindPlugin (target->GetArchitecture ())); - if (arch_default_sp) - m_unwind_plan_arch_default_sp = arch_default_sp->GetArchDefaultUnwindPlan (thread, current_pc); + ABI *abi = thread.GetProcess().GetABI().get(); + if (abi) + { + m_unwind_plan_arch_default_sp.reset (new UnwindPlan (lldb::eRegisterKindGeneric)); + if (m_unwind_plan_arch_default_sp) + abi->CreateDefaultUnwindPlan(*m_unwind_plan_arch_default_sp); + } } } diff --git a/lldb/source/Symbol/UnwindPlan.cpp b/lldb/source/Symbol/UnwindPlan.cpp index 29985af..a465171 100644 --- a/lldb/source/Symbol/UnwindPlan.cpp +++ b/lldb/source/Symbol/UnwindPlan.cpp @@ -20,15 +20,29 @@ using namespace lldb_private; bool UnwindPlan::Row::RegisterLocation::operator == (const UnwindPlan::Row::RegisterLocation& rhs) const { - if (m_type != rhs.m_type) - return false; - if (m_type == atCFAPlusOffset || m_type == isCFAPlusOffset) - return m_location.offset == rhs.m_location.offset; - if (m_type == inOtherRegister) - return m_location.reg_num == rhs.m_location.reg_num; - if (m_type == atDWARFExpression || m_type == isDWARFExpression) - if (m_location.expr.length == rhs.m_location.expr.length) - return !memcmp (m_location.expr.opcodes, rhs.m_location.expr.opcodes, m_location.expr.length); + if (m_type == rhs.m_type) + { + switch (m_type) + { + case unspecified: + case undefined: + case same: + return true; + + case atCFAPlusOffset: + case isCFAPlusOffset: + return m_location.offset == rhs.m_location.offset; + + case inOtherRegister: + return m_location.reg_num == rhs.m_location.reg_num; + + case atDWARFExpression: + case isDWARFExpression: + if (m_location.expr.length == rhs.m_location.expr.length) + return !memcmp (m_location.expr.opcodes, rhs.m_location.expr.opcodes, m_location.expr.length); + break; + } + } return false; } @@ -53,74 +67,85 @@ UnwindPlan::Row::RegisterLocation::SetIsDWARFExpression (const uint8_t *opcodes, } void -UnwindPlan::Row::RegisterLocation::SetUnspecified () -{ - m_type = unspecified; -} - -void -UnwindPlan::Row::RegisterLocation::SetUndefined () -{ - m_type = isUndefined; -} - -void -UnwindPlan::Row::RegisterLocation::SetSame () -{ - m_type = isSame; -} - - -void -UnwindPlan::Row::RegisterLocation::SetAtCFAPlusOffset (int32_t offset) -{ - m_type = atCFAPlusOffset; - m_location.offset = offset; -} - -void -UnwindPlan::Row::RegisterLocation::SetIsCFAPlusOffset (int32_t offset) -{ - m_type = isCFAPlusOffset; - m_location.offset = offset; -} - -void -UnwindPlan::Row::RegisterLocation::SetInRegister (uint32_t reg_num) -{ - m_type = inOtherRegister; - m_location.reg_num = reg_num; -} - -void -UnwindPlan::Row::RegisterLocation::Dump (Stream &s) const +UnwindPlan::Row::RegisterLocation::Dump (Stream &s, const UnwindPlan* unwind_plan, const UnwindPlan::Row* row, Thread* thread, bool verbose) const { switch (m_type) { case unspecified: - s.PutCString ("unspecified"); + if (verbose) + s.PutCString ("=<unspec>"); + else + s.PutCString ("=!"); break; - case isUndefined: - s.PutCString ("isUndefined"); + case undefined: + if (verbose) + s.PutCString ("=<undef>"); + else + s.PutCString ("=?"); break; - case isSame: - s.PutCString ("isSame"); + case same: + s.PutCString ("= <same>"); break; + case atCFAPlusOffset: - s.Printf ("atCFAPlusOffset %d", m_location.offset); - break; case isCFAPlusOffset: - s.Printf ("isCFAPlusOffset %d", m_location.offset); + { + s.PutChar('='); + if (m_type == atCFAPlusOffset) + s.PutChar('['); + if (verbose) + s.Printf ("CFA%+d", m_location.offset); + + if (unwind_plan && row) + { + const uint32_t cfa_reg = row->GetCFARegister(); + const RegisterInfo *cfa_reg_info = unwind_plan->GetRegisterInfo (thread, cfa_reg); + const int32_t offset = row->GetCFAOffset() + m_location.offset; + if (verbose) + { + if (cfa_reg_info) + s.Printf (" (%s%+d)", cfa_reg_info->name, offset); + else + s.Printf (" (reg(%u)%+d)", cfa_reg_info->name, offset); + } + else + { + if (cfa_reg_info) + s.Printf ("%s", cfa_reg_info->name); + else + s.Printf ("reg(%u)", cfa_reg_info->name); + if (offset != 0) + s.Printf ("%+d", offset); + } + } + if (m_type == atCFAPlusOffset) + s.PutChar(']'); + } break; + case inOtherRegister: - s.Printf ("inOtherRegister %d", m_location.reg_num); + { + const RegisterInfo *other_reg_info = NULL; + if (unwind_plan) + other_reg_info = unwind_plan->GetRegisterInfo (thread, m_location.reg_num); + if (other_reg_info) + s.Printf ("=%s", other_reg_info->name); + else + s.Printf ("=reg(%u)", m_location.reg_num); + } break; + case atDWARFExpression: - s.PutCString ("atDWARFExpression"); - break; case isDWARFExpression: - s.PutCString ("isDWARFExpression"); + { + s.PutChar('='); + if (m_type == atDWARFExpression) + s.PutCString("[dwarf-expr]"); + else + s.PutCString("dwarf-expr"); + } break; + } } @@ -134,48 +159,30 @@ UnwindPlan::Row::Clear () } void -UnwindPlan::Row::Dump (Stream& s, int register_kind, Thread* thread) const +UnwindPlan::Row::Dump (Stream& s, const UnwindPlan* unwind_plan, Thread* thread, addr_t base_addr) const { - RegisterContext *reg_ctx = NULL; - const RegisterInfo *rinfo = NULL; - int translated_regnum; - if (thread && thread->GetRegisterContext()) - reg_ctx = thread->GetRegisterContext().get(); - - s.Printf ("offset %ld, CFA reg ", (long) GetOffset()); - if (reg_ctx - && (translated_regnum = reg_ctx->ConvertRegisterKindToRegisterNumber (register_kind, GetCFARegister())) != -1 - && (rinfo = reg_ctx->GetRegisterInfoAtIndex (translated_regnum)) != NULL - && rinfo->name != NULL - && rinfo->name[0] != '\0') - { - s.Printf ("%s, ", rinfo->name); - } + const RegisterInfo *reg_info = unwind_plan->GetRegisterInfo (thread, GetCFARegister()); + + if (base_addr != LLDB_INVALID_ADDRESS) + s.Printf ("0x%16.16llx: CFA=", base_addr + GetOffset()); else - { - s.Printf ("%d, ", (int)(int) GetCFARegister()); - } - s.Printf ("CFA offset %d", (int) GetCFAOffset ()); + s.Printf ("0x%8.8x: CFA=", GetOffset()); + + if (reg_info) + s.Printf ("%s", reg_info->name); + else + s.Printf ("reg(%u)", GetCFARegister()); + s.Printf ("%+3d =>", GetCFAOffset ()); for (collection::const_iterator idx = m_register_locations.begin (); idx != m_register_locations.end (); ++idx) { - s.PutCString (" ["); - bool printed_name = false; - if (reg_ctx) - { - translated_regnum = reg_ctx->ConvertRegisterKindToRegisterNumber (register_kind, idx->first); - rinfo = reg_ctx->GetRegisterInfoAtIndex (translated_regnum); - if (rinfo && rinfo->name) - { - s.Printf ("%s ", rinfo->name); - printed_name = true; - } - } - if (!printed_name) - { - s.Printf ("reg %d ", idx->first); - } - idx->second.Dump(s); - s.PutCString ("]"); + reg_info = unwind_plan->GetRegisterInfo (thread, idx->first); + if (reg_info) + s.Printf ("%s", reg_info->name); + else + s.Printf ("reg(%u)", idx->first); + const bool verbose = false; + idx->second.Dump(s, unwind_plan, this, thread, verbose); + s.PutChar (' '); } s.EOL(); } @@ -206,6 +213,87 @@ UnwindPlan::Row::SetRegisterInfo (uint32_t reg_num, const UnwindPlan::Row::Regis m_register_locations[reg_num] = register_location; } +bool +UnwindPlan::Row::SetRegisterLocationToAtCFAPlusOffset (uint32_t reg_num, int32_t offset, bool can_replace) +{ + if (!can_replace && m_register_locations.find(reg_num) != m_register_locations.end()) + return false; + RegisterLocation reg_loc; + reg_loc.SetAtCFAPlusOffset(offset); + m_register_locations[reg_num] = reg_loc; + return true; +} + +bool +UnwindPlan::Row::SetRegisterLocationToIsCFAPlusOffset (uint32_t reg_num, int32_t offset, bool can_replace) +{ + if (!can_replace && m_register_locations.find(reg_num) != m_register_locations.end()) + return false; + RegisterLocation reg_loc; + reg_loc.SetIsCFAPlusOffset(offset); + m_register_locations[reg_num] = reg_loc; + return true; +} + +bool +UnwindPlan::Row::SetRegisterLocationToUndefined (uint32_t reg_num, bool can_replace, bool can_replace_only_if_unspecified) +{ + collection::iterator pos = m_register_locations.find(reg_num); + collection::iterator end = m_register_locations.end(); + + if (pos != end) + { + if (!can_replace) + return false; + if (can_replace_only_if_unspecified && !pos->second.IsUnspecified()) + return false; + } + RegisterLocation reg_loc; + reg_loc.SetUndefined(); + m_register_locations[reg_num] = reg_loc; + return true; +} + +bool +UnwindPlan::Row::SetRegisterLocationToUnspecified (uint32_t reg_num, bool can_replace) +{ + if (!can_replace && m_register_locations.find(reg_num) != m_register_locations.end()) + return false; + RegisterLocation reg_loc; + reg_loc.SetUnspecified(); + m_register_locations[reg_num] = reg_loc; + return true; +} + +bool +UnwindPlan::Row::SetRegisterLocationToRegister (uint32_t reg_num, + uint32_t other_reg_num, + bool can_replace) +{ + if (!can_replace && m_register_locations.find(reg_num) != m_register_locations.end()) + return false; + RegisterLocation reg_loc; + reg_loc.SetInRegister(other_reg_num); + m_register_locations[reg_num] = reg_loc; + return true; +} + +bool +UnwindPlan::Row::SetRegisterLocationToSame (uint32_t reg_num, bool must_replace) +{ + if (must_replace && m_register_locations.find(reg_num) == m_register_locations.end()) + return false; + RegisterLocation reg_loc; + reg_loc.SetSame(); + m_register_locations[reg_num] = reg_loc; + return true; +} + +void +UnwindPlan::Row::SetCFARegister (uint32_t reg_num) +{ + m_cfa_reg_num = reg_num; +} void UnwindPlan::AppendRow (const UnwindPlan::Row &row) @@ -253,22 +341,18 @@ UnwindPlan::GetRowAtIndex (uint32_t idx) const return m_row_list[idx]; } -int -UnwindPlan::GetRowCount () const -{ - return m_row_list.size (); -} - -void -UnwindPlan::SetRegisterKind (uint32_t rk) +const UnwindPlan::Row& +UnwindPlan::GetLastRow () const { - m_register_kind = rk; + // You must call GetRowCount() first to make sure there is at least one row + assert (!m_row_list.empty()); + return m_row_list.back(); } -uint32_t -UnwindPlan::GetRegisterKind (void) const +int +UnwindPlan::GetRowCount () const { - return m_register_kind; + return m_row_list.size (); } void @@ -294,7 +378,7 @@ UnwindPlan::PlanValidAtAddress (Address addr) } void -UnwindPlan::Dump (Stream& s, Thread *thread) const +UnwindPlan::Dump (Stream& s, Thread *thread, lldb::addr_t base_addr) const { if (!m_source_name.IsEmpty()) { @@ -318,13 +402,14 @@ UnwindPlan::Dump (Stream& s, Thread *thread) const case eRegisterKindGeneric: s.PutCString (" [eRegisterKindGeneric]"); break; case eRegisterKindGDB: s.PutCString (" [eRegisterKindGDB]"); break; case eRegisterKindLLDB: s.PutCString (" [eRegisterKindLLDB]"); break; - default: break; + default: s.PutCString (" [eRegisterKind???]"); break; } s.EOL(); - for (int i = 0; IsValidRowIndex (i); i++) + collection::const_iterator pos, begin = m_row_list.begin(), end = m_row_list.end(); + for (pos = begin; pos != end; ++pos) { - s.Printf ("UnwindPlan row at index %d: ", i); - m_row_list[i].Dump(s, m_register_kind, thread); + s.Printf ("row[%u]: ", (uint32_t)std::distance (begin, pos)); + pos->Dump(s, this, thread, base_addr); } } @@ -339,3 +424,24 @@ UnwindPlan::GetSourceName () const { return m_source_name; } + +const RegisterInfo * +UnwindPlan::GetRegisterInfo (Thread* thread, uint32_t unwind_reg) const +{ + if (thread) + { + RegisterContext *reg_ctx = thread->GetRegisterContext().get(); + if (reg_ctx) + { + uint32_t reg; + if (m_register_kind == eRegisterKindLLDB) + reg = unwind_reg; + else + reg = reg_ctx->ConvertRegisterKindToRegisterNumber (m_register_kind, unwind_reg); + if (reg != LLDB_INVALID_REGNUM) + return reg_ctx->GetRegisterInfoAtIndex (reg); + } + } + return NULL; +} + diff --git a/lldb/source/Target/ABI.cpp b/lldb/source/Target/ABI.cpp index 21ac550..0ed7a0d 100644 --- a/lldb/source/Target/ABI.cpp +++ b/lldb/source/Target/ABI.cpp @@ -13,23 +13,23 @@ using namespace lldb; using namespace lldb_private; -ABI* +ABISP ABI::FindPlugin (const ArchSpec &arch) { - std::auto_ptr<ABI> abi_ap; + ABISP abi_sp; ABICreateInstance create_callback; for (uint32_t idx = 0; (create_callback = PluginManager::GetABICreateCallbackAtIndex(idx)) != NULL; ++idx) { - abi_ap.reset (create_callback(arch)); + abi_sp = create_callback(arch); - if (abi_ap.get()) - return abi_ap.release(); + if (abi_sp) + return abi_sp; } - - return NULL; + abi_sp.reset(); + return abi_sp; } //---------------------------------------------------------------------- diff --git a/lldb/source/Target/Process.cpp b/lldb/source/Target/Process.cpp index 80d1d75..47a4c1c 100644 --- a/lldb/source/Target/Process.cpp +++ b/lldb/source/Target/Process.cpp @@ -1349,13 +1349,12 @@ Process::UnloadImage (uint32_t image_token) return error; } -const ABI * +const lldb::ABISP & Process::GetABI() { - if (m_abi_sp.get() == NULL) - m_abi_sp.reset(ABI::FindPlugin(m_target.GetArchitecture())); - - return m_abi_sp.get(); + if (!m_abi_sp) + m_abi_sp = ABI::FindPlugin(m_target.GetArchitecture()); + return m_abi_sp; } LanguageRuntime * diff --git a/lldb/source/Target/ThreadPlanCallFunction.cpp b/lldb/source/Target/ThreadPlanCallFunction.cpp index 83b8270..934ac00 100644 --- a/lldb/source/Target/ThreadPlanCallFunction.cpp +++ b/lldb/source/Target/ThreadPlanCallFunction.cpp @@ -56,7 +56,7 @@ ThreadPlanCallFunction::ThreadPlanCallFunction (Thread &thread, Process& process = thread.GetProcess(); Target& target = process.GetTarget(); - const ABI *abi = process.GetABI(); + const ABI *abi = process.GetABI().get(); if (!abi) return; diff --git a/lldb/source/Target/ThreadPlanTracer.cpp b/lldb/source/Target/ThreadPlanTracer.cpp index 961c9cd..7ea16d4 100644 --- a/lldb/source/Target/ThreadPlanTracer.cpp +++ b/lldb/source/Target/ThreadPlanTracer.cpp @@ -112,7 +112,7 @@ ThreadPlanAssemblyTracer::InitializeTracer() m_disassembler = Disassembler::FindPlugin(arch, NULL); - m_abi = process.GetABI(); + m_abi = process.GetABI().get(); ModuleSP exe_module_sp (target.GetExecutableModule()); diff --git a/lldb/source/lldb.cpp b/lldb/source/lldb.cpp index 0c730ee..c8ab895 100644 --- a/lldb/source/lldb.cpp +++ b/lldb/source/lldb.cpp @@ -32,11 +32,10 @@ #include "Plugins/SymbolFile/Symtab/SymbolFileSymtab.h" #include "Plugins/UnwindAssembly/x86/UnwindAssembly-x86.h" #include "Plugins/UnwindAssembly/InstEmulation/UnwindAssemblyInstEmulation.h" -#include "Plugins/ArchDefaultUnwindPlan/x86/ArchDefaultUnwindPlan-x86.h" -#include "Plugins/ArchVolatileRegs/x86/ArchVolatileRegs-x86.h" #if defined (__APPLE__) #include "Plugins/ABI/MacOSX-i386/ABIMacOSX_i386.h" +#include "Plugins/ABI/MacOSX-arm/ABIMacOSX_arm.h" #include "Plugins/ABI/SysV-x86_64/ABISysV_x86_64.h" #include "Plugins/DynamicLoader/MacOSX-DYLD/DynamicLoaderMacOSXDYLD.h" #include "Plugins/LanguageRuntime/CPlusPlus/ItaniumABI/ItaniumABILanguageRuntime.h" @@ -85,17 +84,15 @@ lldb_private::Initialize () SymbolFileSymtab::Initialize(); UnwindAssemblyInstEmulation::Initialize(); UnwindAssembly_x86::Initialize(); - ArchDefaultUnwindPlan_x86_64::Initialize(); - ArchDefaultUnwindPlan_i386::Initialize(); - ArchVolatileRegs_x86::Initialize(); EmulateInstructionARM::Initialize (); + ABIMacOSX_i386::Initialize(); + ABIMacOSX_arm::Initialize(); + ABISysV_x86_64::Initialize(); #if defined (__APPLE__) //---------------------------------------------------------------------- // Apple/Darwin hosted plugins //---------------------------------------------------------------------- - ABIMacOSX_i386::Initialize(); - ABISysV_x86_64::Initialize(); DynamicLoaderMacOSXDYLD::Initialize(); SymbolFileDWARFDebugMap::Initialize(); ItaniumABILanguageRuntime::Initialize(); @@ -154,10 +151,10 @@ lldb_private::Terminate () SymbolFileSymtab::Terminate(); UnwindAssembly_x86::Terminate(); UnwindAssemblyInstEmulation::Terminate(); - ArchDefaultUnwindPlan_i386::Terminate(); - ArchDefaultUnwindPlan_x86_64::Terminate(); - ArchVolatileRegs_x86::Terminate(); EmulateInstructionARM::Terminate (); + ABIMacOSX_i386::Terminate(); + ABIMacOSX_arm::Terminate(); + ABISysV_x86_64::Terminate(); #if defined (__APPLE__) DynamicLoaderMacOSXDYLD::Terminate(); diff --git a/lldb/tools/debugserver/debugserver.xcodeproj/project.pbxproj b/lldb/tools/debugserver/debugserver.xcodeproj/project.pbxproj index 855e4c1..1cd2166 100644 --- a/lldb/tools/debugserver/debugserver.xcodeproj/project.pbxproj +++ b/lldb/tools/debugserver/debugserver.xcodeproj/project.pbxproj @@ -359,6 +359,7 @@ 26CE05C7115C36870022F371 /* ShellScript */, 26CE0591115C31C20022F371 /* Sources */, 26CE0592115C31C20022F371 /* Frameworks */, + 26C688951378864600407EDF /* Codesign Hack */, ); buildRules = ( ); @@ -397,6 +398,20 @@ /* End PBXProject section */ /* Begin PBXShellScriptBuildPhase section */ + 26C688951378864600407EDF /* Codesign Hack */ = { + isa = PBXShellScriptBuildPhase; + buildActionMask = 2147483647; + files = ( + ); + inputPaths = ( + ); + name = "Codesign Hack"; + outputPaths = ( + ); + runOnlyForDeploymentPostprocessing = 0; + shellPath = /bin/sh; + shellScript = "codesign --force --keychain ~/Library/Keychains/login.keychain --sign lldb_codesign \"$CODESIGNING_FOLDER_PATH\""; + }; 26CE05C7115C36870022F371 /* ShellScript */ = { isa = PBXShellScriptBuildPhase; buildActionMask = 2147483647; @@ -565,7 +580,6 @@ isa = XCBuildConfiguration; buildSettings = { "CODE_SIGN_ENTITLEMENTS[sdk=iphoneos*]" = "source/debugserver-entitlements.plist"; - "CODE_SIGN_IDENTITY[sdk=macosx*]" = lldb_codesign; COPY_PHASE_STRIP = YES; CURRENT_PROJECT_VERSION = 131; FRAMEWORK_SEARCH_PATHS = $SDKROOT/System/Library/PrivateFrameworks; @@ -595,7 +609,6 @@ ); OTHER_MIGFLAGS = "-I$(DERIVED_FILE_DIR)"; PRODUCT_NAME = debugserver; - "PROVISIONING_PROFILE[sdk=macosx*]" = ""; USER_HEADER_SEARCH_PATHS = "./source ../../source $(DERIVED_SOURCES_DIR)"; ZERO_LINK = NO; }; @@ -605,7 +618,6 @@ isa = XCBuildConfiguration; buildSettings = { "CODE_SIGN_ENTITLEMENTS[sdk=iphoneos*]" = "source/debugserver-entitlements.plist"; - "CODE_SIGN_IDENTITY[sdk=macosx*]" = lldb_codesign; COPY_PHASE_STRIP = YES; CURRENT_PROJECT_VERSION = 131; DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; @@ -635,7 +647,6 @@ ); OTHER_MIGFLAGS = "-I$(DERIVED_FILE_DIR)"; PRODUCT_NAME = debugserver; - "PROVISIONING_PROFILE[sdk=macosx*]" = ""; USER_HEADER_SEARCH_PATHS = "./source ../../source $(DERIVED_SOURCES_DIR)"; ZERO_LINK = NO; }; |