2010-06-09 00:52:24 +08:00
|
|
|
//===-- SBFrame.cpp ---------------------------------------------*- C++ -*-===//
|
|
|
|
//
|
|
|
|
// The LLVM Compiler Infrastructure
|
|
|
|
//
|
|
|
|
// This file is distributed under the University of Illinois Open Source
|
|
|
|
// License. See LICENSE.TXT for details.
|
|
|
|
//
|
|
|
|
//===----------------------------------------------------------------------===//
|
|
|
|
|
2010-06-09 15:44:37 +08:00
|
|
|
#include "lldb/API/SBFrame.h"
|
2010-06-09 00:52:24 +08:00
|
|
|
|
|
|
|
#include <string>
|
|
|
|
#include <algorithm>
|
|
|
|
|
|
|
|
#include "lldb/lldb-types.h"
|
|
|
|
|
|
|
|
#include "lldb/Core/Address.h"
|
|
|
|
#include "lldb/Core/ConstString.h"
|
2010-10-26 11:11:13 +08:00
|
|
|
#include "lldb/Core/Log.h"
|
2010-06-09 00:52:24 +08:00
|
|
|
#include "lldb/Core/Stream.h"
|
|
|
|
#include "lldb/Core/StreamFile.h"
|
|
|
|
#include "lldb/Core/ValueObjectRegister.h"
|
|
|
|
#include "lldb/Core/ValueObjectVariable.h"
|
2010-10-05 11:13:51 +08:00
|
|
|
#include "lldb/Expression/ClangUserExpression.h"
|
2010-06-09 00:52:24 +08:00
|
|
|
#include "lldb/Symbol/Block.h"
|
|
|
|
#include "lldb/Symbol/SymbolContext.h"
|
|
|
|
#include "lldb/Symbol/VariableList.h"
|
|
|
|
#include "lldb/Symbol/Variable.h"
|
|
|
|
#include "lldb/Target/ExecutionContext.h"
|
|
|
|
#include "lldb/Target/Target.h"
|
|
|
|
#include "lldb/Target/Process.h"
|
|
|
|
#include "lldb/Target/RegisterContext.h"
|
|
|
|
#include "lldb/Target/StackFrame.h"
|
|
|
|
#include "lldb/Target/Thread.h"
|
|
|
|
|
2010-06-09 15:44:37 +08:00
|
|
|
#include "lldb/API/SBDebugger.h"
|
|
|
|
#include "lldb/API/SBValue.h"
|
|
|
|
#include "lldb/API/SBAddress.h"
|
2010-09-20 13:20:02 +08:00
|
|
|
#include "lldb/API/SBStream.h"
|
2010-06-09 15:44:37 +08:00
|
|
|
#include "lldb/API/SBSymbolContext.h"
|
|
|
|
#include "lldb/API/SBThread.h"
|
2010-06-09 00:52:24 +08:00
|
|
|
|
|
|
|
using namespace lldb;
|
|
|
|
using namespace lldb_private;
|
|
|
|
|
|
|
|
SBFrame::SBFrame () :
|
2010-06-23 09:19:29 +08:00
|
|
|
m_opaque_sp ()
|
2010-06-09 00:52:24 +08:00
|
|
|
{
|
|
|
|
}
|
|
|
|
|
|
|
|
SBFrame::SBFrame (const lldb::StackFrameSP &lldb_object_sp) :
|
2010-06-23 09:19:29 +08:00
|
|
|
m_opaque_sp (lldb_object_sp)
|
2010-06-09 00:52:24 +08:00
|
|
|
{
|
2010-10-27 07:49:36 +08:00
|
|
|
Log *log = lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_API);
|
2010-10-26 11:11:13 +08:00
|
|
|
|
|
|
|
if (log)
|
|
|
|
{
|
|
|
|
SBStream sstr;
|
|
|
|
GetDescription (sstr);
|
2010-10-27 07:49:36 +08:00
|
|
|
log->Printf ("SBFrame::SBFrame (lldb_object_sp=%p) => this.sp = %p (%s)", lldb_object_sp.get(),
|
|
|
|
m_opaque_sp.get(), sstr.GetData());
|
|
|
|
|
2010-10-26 11:11:13 +08:00
|
|
|
}
|
2010-06-09 00:52:24 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
SBFrame::~SBFrame()
|
|
|
|
{
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void
|
|
|
|
SBFrame::SetFrame (const lldb::StackFrameSP &lldb_object_sp)
|
|
|
|
{
|
2010-06-23 09:19:29 +08:00
|
|
|
m_opaque_sp = lldb_object_sp;
|
2010-06-09 00:52:24 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
bool
|
|
|
|
SBFrame::IsValid() const
|
|
|
|
{
|
2010-06-23 09:19:29 +08:00
|
|
|
return (m_opaque_sp.get() != NULL);
|
2010-06-09 00:52:24 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
SBSymbolContext
|
|
|
|
SBFrame::GetSymbolContext (uint32_t resolve_scope) const
|
|
|
|
{
|
2010-10-26 11:11:13 +08:00
|
|
|
Log *log = lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_API);
|
|
|
|
|
2010-10-27 07:49:36 +08:00
|
|
|
//if (log)
|
|
|
|
// log->Printf ("SBFrame::GetSymbolContext (this.sp=%p, resolve_scope=%d)", m_opaque_sp.get(), resolve_scope);
|
2010-10-26 11:11:13 +08:00
|
|
|
|
2010-06-09 00:52:24 +08:00
|
|
|
SBSymbolContext sb_sym_ctx;
|
2010-06-23 09:19:29 +08:00
|
|
|
if (m_opaque_sp)
|
|
|
|
sb_sym_ctx.SetSymbolContext(&m_opaque_sp->GetSymbolContext (resolve_scope));
|
2010-10-26 11:11:13 +08:00
|
|
|
|
|
|
|
if (log)
|
2010-10-27 07:49:36 +08:00
|
|
|
log->Printf ("SBFrame::GetSymbolContext (this.sp=%p, resolve_scope=%d) => SBSymbolContext (this.ap = %p)",
|
|
|
|
m_opaque_sp.get(), resolve_scope, sb_sym_ctx.get());
|
2010-10-26 11:11:13 +08:00
|
|
|
|
2010-06-09 00:52:24 +08:00
|
|
|
return sb_sym_ctx;
|
|
|
|
}
|
|
|
|
|
|
|
|
SBModule
|
|
|
|
SBFrame::GetModule () const
|
|
|
|
{
|
2010-06-23 09:19:29 +08:00
|
|
|
SBModule sb_module (m_opaque_sp->GetSymbolContext (eSymbolContextModule).module_sp);
|
2010-06-09 00:52:24 +08:00
|
|
|
return sb_module;
|
|
|
|
}
|
|
|
|
|
|
|
|
SBCompileUnit
|
|
|
|
SBFrame::GetCompileUnit () const
|
|
|
|
{
|
2010-10-26 11:11:13 +08:00
|
|
|
Log *log = lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_API);
|
|
|
|
|
2010-10-27 07:49:36 +08:00
|
|
|
//if (log)
|
|
|
|
// log->Printf ("SBFrame::GetCompileUnit()");
|
2010-10-26 11:11:13 +08:00
|
|
|
|
2010-06-23 09:19:29 +08:00
|
|
|
SBCompileUnit sb_comp_unit(m_opaque_sp->GetSymbolContext (eSymbolContextCompUnit).comp_unit);
|
2010-10-26 11:11:13 +08:00
|
|
|
|
|
|
|
if (log)
|
2010-10-27 07:49:36 +08:00
|
|
|
log->Printf ("SBFrame::GetCompileUnit (this.sp=%p) => SBCompileUnit (this=%p)", m_opaque_sp.get(),
|
|
|
|
sb_comp_unit.get());
|
2010-10-26 11:11:13 +08:00
|
|
|
|
2010-06-09 00:52:24 +08:00
|
|
|
return sb_comp_unit;
|
|
|
|
}
|
|
|
|
|
|
|
|
SBFunction
|
|
|
|
SBFrame::GetFunction () const
|
|
|
|
{
|
2010-06-23 09:19:29 +08:00
|
|
|
SBFunction sb_function(m_opaque_sp->GetSymbolContext (eSymbolContextFunction).function);
|
2010-06-09 00:52:24 +08:00
|
|
|
return sb_function;
|
|
|
|
}
|
|
|
|
|
2010-10-05 02:37:52 +08:00
|
|
|
SBSymbol
|
|
|
|
SBFrame::GetSymbol () const
|
|
|
|
{
|
|
|
|
SBSymbol sb_symbol(m_opaque_sp->GetSymbolContext (eSymbolContextSymbol).symbol);
|
|
|
|
return sb_symbol;
|
|
|
|
}
|
|
|
|
|
2010-06-09 00:52:24 +08:00
|
|
|
SBBlock
|
|
|
|
SBFrame::GetBlock () const
|
|
|
|
{
|
2010-06-23 09:19:29 +08:00
|
|
|
SBBlock sb_block(m_opaque_sp->GetSymbolContext (eSymbolContextBlock).block);
|
2010-06-09 00:52:24 +08:00
|
|
|
return sb_block;
|
|
|
|
}
|
|
|
|
|
2010-09-07 12:20:48 +08:00
|
|
|
SBBlock
|
|
|
|
SBFrame::GetFrameBlock () const
|
|
|
|
{
|
|
|
|
SBBlock sb_block(m_opaque_sp->GetFrameBlock ());
|
|
|
|
return sb_block;
|
|
|
|
}
|
|
|
|
|
2010-06-09 00:52:24 +08:00
|
|
|
SBLineEntry
|
|
|
|
SBFrame::GetLineEntry () const
|
|
|
|
{
|
2010-06-23 09:19:29 +08:00
|
|
|
SBLineEntry sb_line_entry(&m_opaque_sp->GetSymbolContext (eSymbolContextLineEntry).line_entry);
|
2010-06-09 00:52:24 +08:00
|
|
|
return sb_line_entry;
|
|
|
|
}
|
|
|
|
|
|
|
|
uint32_t
|
|
|
|
SBFrame::GetFrameID () const
|
|
|
|
{
|
2010-06-23 09:19:29 +08:00
|
|
|
if (m_opaque_sp)
|
Added support for inlined stack frames being represented as real stack frames
which is now on by default. Frames are gotten from the unwinder as concrete
frames, then if inline frames are to be shown, extra information to track
and reconstruct these frames is cached with each Thread and exanded as needed.
I added an inline height as part of the lldb_private::StackID class, the class
that helps us uniquely identify stack frames. This allows for two frames to
shared the same call frame address, yet differ only in inline height.
Fixed setting breakpoint by address to not require addresses to resolve.
A quick example:
% cat main.cpp
% ./build/Debug/lldb test/stl/a.out
Current executable set to 'test/stl/a.out' (x86_64).
(lldb) breakpoint set --address 0x0000000100000d31
Breakpoint created: 1: address = 0x0000000100000d31, locations = 1
(lldb) r
Launching 'a.out' (x86_64)
(lldb) Process 38031 Stopped
* thread #1: tid = 0x2e03, pc = 0x0000000100000d31, where = a.out`main [inlined] std::string::_M_data() const at /usr/include/c++/4.2.1/bits/basic_string.h:280, stop reason = breakpoint 1.1, queue = com.apple.main-thread
277
278 _CharT*
279 _M_data() const
280 -> { return _M_dataplus._M_p; }
281
282 _CharT*
283 _M_data(_CharT* __p)
(lldb) bt
thread #1: tid = 0x2e03, stop reason = breakpoint 1.1, queue = com.apple.main-thread
frame #0: pc = 0x0000000100000d31, where = a.out`main [inlined] std::string::_M_data() const at /usr/include/c++/4.2.1/bits/basic_string.h:280
frame #1: pc = 0x0000000100000d31, where = a.out`main [inlined] std::string::_M_rep() const at /usr/include/c++/4.2.1/bits/basic_string.h:288
frame #2: pc = 0x0000000100000d31, where = a.out`main [inlined] std::string::size() const at /usr/include/c++/4.2.1/bits/basic_string.h:606
frame #3: pc = 0x0000000100000d31, where = a.out`main [inlined] operator<< <char, std::char_traits<char>, std::allocator<char> > at /usr/include/c++/4.2.1/bits/basic_string.h:2414
frame #4: pc = 0x0000000100000d31, where = a.out`main + 33 at /Volumes/work/gclayton/Documents/src/lldb/test/stl/main.cpp:14
frame #5: pc = 0x0000000100000d08, where = a.out`start + 52
Each inline frame contains only the variables that they contain and each inlined
stack frame is treated as a single entity.
llvm-svn: 111877
2010-08-24 08:45:41 +08:00
|
|
|
return m_opaque_sp->GetFrameIndex ();
|
2010-06-09 00:52:24 +08:00
|
|
|
else
|
|
|
|
return UINT32_MAX;
|
|
|
|
}
|
|
|
|
|
|
|
|
lldb::addr_t
|
|
|
|
SBFrame::GetPC () const
|
|
|
|
{
|
2010-10-26 11:11:13 +08:00
|
|
|
Log *log = lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_API);
|
|
|
|
|
2010-10-27 07:49:36 +08:00
|
|
|
//if (log)
|
|
|
|
// log->Printf ("SBFrame::GetPC (this.sp=%p)", m_opaque_sp.get());
|
2010-10-26 11:11:13 +08:00
|
|
|
|
|
|
|
lldb::addr_t addr = LLDB_INVALID_ADDRESS;
|
2010-06-23 09:19:29 +08:00
|
|
|
if (m_opaque_sp)
|
2010-10-26 11:11:13 +08:00
|
|
|
addr = m_opaque_sp->GetFrameCodeAddress().GetLoadAddress (&m_opaque_sp->GetThread().GetProcess().GetTarget());
|
|
|
|
|
|
|
|
if (log)
|
2010-10-27 07:49:36 +08:00
|
|
|
log->Printf ("SBFrame::GetPC (this.sp=%p) => %p", m_opaque_sp.get(), addr);
|
2010-10-26 11:11:13 +08:00
|
|
|
|
|
|
|
return addr;
|
2010-06-09 00:52:24 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
bool
|
|
|
|
SBFrame::SetPC (lldb::addr_t new_pc)
|
|
|
|
{
|
2010-10-26 11:11:13 +08:00
|
|
|
Log *log = lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_API);
|
|
|
|
|
2010-10-27 07:49:36 +08:00
|
|
|
//if (log)
|
|
|
|
// log->Printf ("SBFrame::SetPC (this.sp=%p, new_pc=%p)", m_opaque_sp.get(), new_pc);
|
2010-10-26 11:11:13 +08:00
|
|
|
|
|
|
|
bool ret_val = false;
|
2010-06-23 09:19:29 +08:00
|
|
|
if (m_opaque_sp)
|
2010-10-26 11:11:13 +08:00
|
|
|
ret_val = m_opaque_sp->GetRegisterContext()->SetPC (new_pc);
|
|
|
|
|
|
|
|
if (log)
|
2010-10-27 07:49:36 +08:00
|
|
|
log->Printf ("SBFrame::SetPC (this.sp=%p, new_pc=%p) => '%s'", m_opaque_sp.get(), new_pc,
|
|
|
|
(ret_val ? "true" : "false"));
|
2010-10-26 11:11:13 +08:00
|
|
|
|
|
|
|
return ret_val;
|
2010-06-09 00:52:24 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
lldb::addr_t
|
|
|
|
SBFrame::GetSP () const
|
|
|
|
{
|
2010-06-23 09:19:29 +08:00
|
|
|
if (m_opaque_sp)
|
|
|
|
return m_opaque_sp->GetRegisterContext()->GetSP();
|
2010-06-09 00:52:24 +08:00
|
|
|
return LLDB_INVALID_ADDRESS;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
lldb::addr_t
|
|
|
|
SBFrame::GetFP () const
|
|
|
|
{
|
2010-10-26 11:11:13 +08:00
|
|
|
Log *log = lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_API);
|
|
|
|
|
2010-10-27 07:49:36 +08:00
|
|
|
//if (log)
|
|
|
|
// log->Printf ("SBFrame::GetFP ()");
|
2010-10-26 11:11:13 +08:00
|
|
|
|
|
|
|
lldb::addr_t addr = LLDB_INVALID_ADDRESS;
|
2010-06-23 09:19:29 +08:00
|
|
|
if (m_opaque_sp)
|
2010-10-26 11:11:13 +08:00
|
|
|
addr = m_opaque_sp->GetRegisterContext()->GetFP();
|
|
|
|
|
|
|
|
if (log)
|
2010-10-27 07:49:36 +08:00
|
|
|
log->Printf ("SBFrame::GetFP (this.sp=%p) => %p", m_opaque_sp.get(), addr);
|
2010-10-26 11:11:13 +08:00
|
|
|
|
|
|
|
return addr;
|
2010-06-09 00:52:24 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
SBAddress
|
|
|
|
SBFrame::GetPCAddress () const
|
|
|
|
{
|
|
|
|
SBAddress sb_addr;
|
2010-06-23 09:19:29 +08:00
|
|
|
if (m_opaque_sp)
|
2010-08-25 05:05:24 +08:00
|
|
|
sb_addr.SetAddress (&m_opaque_sp->GetFrameCodeAddress());
|
2010-06-09 00:52:24 +08:00
|
|
|
return sb_addr;
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
SBFrame::Clear()
|
|
|
|
{
|
2010-06-23 09:19:29 +08:00
|
|
|
m_opaque_sp.reset();
|
2010-06-09 00:52:24 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
SBValue
|
|
|
|
SBFrame::LookupVar (const char *var_name)
|
|
|
|
{
|
|
|
|
lldb::VariableSP var_sp;
|
|
|
|
if (IsValid ())
|
|
|
|
{
|
|
|
|
lldb_private::VariableList variable_list;
|
|
|
|
SBSymbolContext sc = GetSymbolContext (eSymbolContextEverything);
|
|
|
|
|
|
|
|
SBBlock block = sc.GetBlock();
|
|
|
|
if (block.IsValid())
|
|
|
|
block.AppendVariables (true, true, &variable_list);
|
|
|
|
|
|
|
|
const uint32_t num_variables = variable_list.GetSize();
|
|
|
|
|
|
|
|
bool found = false;
|
2010-07-10 04:39:50 +08:00
|
|
|
for (uint32_t i = 0; i < num_variables && !found; ++i)
|
2010-06-09 00:52:24 +08:00
|
|
|
{
|
|
|
|
var_sp = variable_list.GetVariableAtIndex(i);
|
|
|
|
if (var_sp
|
|
|
|
&& (var_sp.get()->GetName() == lldb_private::ConstString(var_name)))
|
|
|
|
found = true;
|
|
|
|
}
|
|
|
|
if (!found)
|
|
|
|
var_sp.reset();
|
|
|
|
}
|
2010-09-20 13:20:02 +08:00
|
|
|
if (var_sp)
|
|
|
|
{
|
|
|
|
SBValue sb_value (ValueObjectSP (new ValueObjectVariable (var_sp)));
|
|
|
|
return sb_value;
|
|
|
|
}
|
|
|
|
|
|
|
|
SBValue sb_value;
|
2010-06-09 00:52:24 +08:00
|
|
|
return sb_value;
|
|
|
|
}
|
|
|
|
|
|
|
|
SBValue
|
|
|
|
SBFrame::LookupVarInScope (const char *var_name, const char *scope)
|
|
|
|
{
|
|
|
|
lldb::VariableSP var_sp;
|
|
|
|
if (IsValid())
|
|
|
|
{
|
|
|
|
std::string scope_str = scope;
|
|
|
|
lldb::ValueType var_scope = eValueTypeInvalid;
|
|
|
|
// Convert scope_str to be all lowercase;
|
|
|
|
std::transform (scope_str.begin(), scope_str.end(), scope_str.begin(), ::tolower);
|
|
|
|
|
|
|
|
if (scope_str.compare ("global") == 0)
|
|
|
|
var_scope = eValueTypeVariableGlobal;
|
|
|
|
else if (scope_str.compare ("local") == 0)
|
|
|
|
var_scope = eValueTypeVariableLocal;
|
|
|
|
else if (scope_str.compare ("parameter") == 0)
|
|
|
|
var_scope = eValueTypeVariableArgument;
|
|
|
|
|
|
|
|
if (var_scope != eValueTypeInvalid)
|
|
|
|
{
|
|
|
|
lldb_private::VariableList variable_list;
|
|
|
|
SBSymbolContext sc = GetSymbolContext (eSymbolContextEverything);
|
|
|
|
|
|
|
|
SBBlock block = sc.GetBlock();
|
|
|
|
if (block.IsValid())
|
|
|
|
block.AppendVariables (true, true, &variable_list);
|
|
|
|
|
|
|
|
const uint32_t num_variables = variable_list.GetSize();
|
|
|
|
|
|
|
|
bool found = false;
|
2010-07-10 04:39:50 +08:00
|
|
|
for (uint32_t i = 0; i < num_variables && !found; ++i)
|
2010-06-09 00:52:24 +08:00
|
|
|
{
|
|
|
|
var_sp = variable_list.GetVariableAtIndex(i);
|
|
|
|
if (var_sp
|
|
|
|
&& (var_sp.get()->GetName() == lldb_private::ConstString(var_name))
|
|
|
|
&& var_sp.get()->GetScope() == var_scope)
|
|
|
|
found = true;
|
|
|
|
}
|
|
|
|
if (!found)
|
|
|
|
var_sp.reset();
|
|
|
|
}
|
|
|
|
}
|
2010-09-20 13:20:02 +08:00
|
|
|
|
|
|
|
if (var_sp)
|
|
|
|
{
|
|
|
|
SBValue sb_value (ValueObjectSP (new ValueObjectVariable (var_sp)));
|
|
|
|
return sb_value;
|
|
|
|
}
|
|
|
|
|
|
|
|
SBValue sb_value;
|
2010-06-09 00:52:24 +08:00
|
|
|
return sb_value;
|
|
|
|
}
|
|
|
|
|
|
|
|
bool
|
|
|
|
SBFrame::operator == (const SBFrame &rhs) const
|
|
|
|
{
|
2010-06-23 09:19:29 +08:00
|
|
|
return m_opaque_sp.get() == rhs.m_opaque_sp.get();
|
2010-06-09 00:52:24 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
bool
|
|
|
|
SBFrame::operator != (const SBFrame &rhs) const
|
|
|
|
{
|
2010-06-23 09:19:29 +08:00
|
|
|
return m_opaque_sp.get() != rhs.m_opaque_sp.get();
|
2010-06-09 00:52:24 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
lldb_private::StackFrame *
|
|
|
|
SBFrame::operator->() const
|
|
|
|
{
|
2010-06-23 09:19:29 +08:00
|
|
|
return m_opaque_sp.get();
|
2010-06-09 00:52:24 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
lldb_private::StackFrame *
|
|
|
|
SBFrame::get() const
|
|
|
|
{
|
2010-06-23 09:19:29 +08:00
|
|
|
return m_opaque_sp.get();
|
2010-06-09 00:52:24 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
SBThread
|
|
|
|
SBFrame::GetThread () const
|
|
|
|
{
|
2010-10-26 11:11:13 +08:00
|
|
|
Log *log = lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_API);
|
|
|
|
|
2010-10-27 07:49:36 +08:00
|
|
|
//if (log)
|
|
|
|
// log->Printf ("SBFrame::GetThread ()");
|
2010-10-26 11:11:13 +08:00
|
|
|
|
2010-06-23 09:19:29 +08:00
|
|
|
SBThread sb_thread (m_opaque_sp->GetThread().GetSP());
|
2010-10-26 11:11:13 +08:00
|
|
|
|
|
|
|
if (log)
|
2010-10-27 07:49:36 +08:00
|
|
|
{
|
|
|
|
SBStream sstr;
|
|
|
|
sb_thread.GetDescription (sstr);
|
|
|
|
log->Printf ("SBFrame::GetThread (this.sp=%p) => SBThread : this.sp= %p, '%s'", m_opaque_sp.get(),
|
|
|
|
sb_thread.GetLLDBObjectPtr(), sstr.GetData());
|
|
|
|
}
|
2010-10-26 11:11:13 +08:00
|
|
|
|
2010-06-09 00:52:24 +08:00
|
|
|
return sb_thread;
|
|
|
|
}
|
|
|
|
|
|
|
|
const char *
|
|
|
|
SBFrame::Disassemble () const
|
|
|
|
{
|
2010-10-26 11:11:13 +08:00
|
|
|
Log *log = lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_API);
|
|
|
|
Log *verbose_log = lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_API | LIBLLDB_LOG_VERBOSE);
|
|
|
|
|
|
|
|
if (verbose_log)
|
2010-10-27 07:49:36 +08:00
|
|
|
verbose_log->Printf ("SBFrame::Disassemble (this.sp=%p) => %s", m_opaque_sp.get(), m_opaque_sp->Disassemble());
|
2010-10-26 11:11:13 +08:00
|
|
|
else if (log)
|
2010-10-27 07:49:36 +08:00
|
|
|
log->Printf ("SBFrame::Disassemble (this.sp=%p)", m_opaque_sp.get());
|
2010-10-26 11:11:13 +08:00
|
|
|
|
2010-06-23 09:19:29 +08:00
|
|
|
if (m_opaque_sp)
|
|
|
|
return m_opaque_sp->Disassemble();
|
2010-06-09 00:52:24 +08:00
|
|
|
return NULL;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
lldb_private::StackFrame *
|
|
|
|
SBFrame::GetLLDBObjectPtr ()
|
|
|
|
{
|
2010-06-23 09:19:29 +08:00
|
|
|
return m_opaque_sp.get();
|
2010-06-09 00:52:24 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
SBValueList
|
|
|
|
SBFrame::GetVariables (bool arguments,
|
|
|
|
bool locals,
|
|
|
|
bool statics,
|
|
|
|
bool in_scope_only)
|
|
|
|
{
|
2010-10-26 11:11:13 +08:00
|
|
|
Log *log = lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_API);
|
|
|
|
|
|
|
|
if (log)
|
2010-10-27 07:49:36 +08:00
|
|
|
log->Printf ("SBFrame::GetVariables (this_sp.get=%p, arguments=%s, locals=%s, statics=%s, in_scope_only=%s)",
|
|
|
|
m_opaque_sp.get(),
|
2010-10-26 11:11:13 +08:00
|
|
|
(arguments ? "true" : "false"),
|
|
|
|
(locals ? "true" : "false"),
|
|
|
|
(statics ? "true" : "false"),
|
|
|
|
(in_scope_only ? "true" : "false"));
|
|
|
|
|
2010-06-09 00:52:24 +08:00
|
|
|
SBValueList value_list;
|
2010-06-23 09:19:29 +08:00
|
|
|
if (m_opaque_sp)
|
2010-06-09 00:52:24 +08:00
|
|
|
{
|
|
|
|
size_t i;
|
2010-09-02 10:59:18 +08:00
|
|
|
VariableList *variable_list = m_opaque_sp->GetVariableList(true);
|
2010-06-09 00:52:24 +08:00
|
|
|
if (variable_list)
|
|
|
|
{
|
|
|
|
const size_t num_variables = variable_list->GetSize();
|
|
|
|
if (num_variables)
|
|
|
|
{
|
|
|
|
for (i = 0; i < num_variables; ++i)
|
|
|
|
{
|
|
|
|
VariableSP variable_sp (variable_list->GetVariableAtIndex(i));
|
|
|
|
if (variable_sp)
|
|
|
|
{
|
|
|
|
bool add_variable = false;
|
|
|
|
switch (variable_sp->GetScope())
|
|
|
|
{
|
|
|
|
case eValueTypeVariableGlobal:
|
|
|
|
case eValueTypeVariableStatic:
|
|
|
|
add_variable = statics;
|
|
|
|
break;
|
|
|
|
|
|
|
|
case eValueTypeVariableArgument:
|
|
|
|
add_variable = arguments;
|
|
|
|
break;
|
|
|
|
|
|
|
|
case eValueTypeVariableLocal:
|
|
|
|
add_variable = locals;
|
|
|
|
break;
|
2010-07-10 04:39:50 +08:00
|
|
|
|
|
|
|
default:
|
|
|
|
break;
|
2010-06-09 00:52:24 +08:00
|
|
|
}
|
|
|
|
if (add_variable)
|
|
|
|
{
|
2010-06-23 09:19:29 +08:00
|
|
|
if (in_scope_only && !variable_sp->IsInScope(m_opaque_sp.get()))
|
2010-06-09 00:52:24 +08:00
|
|
|
continue;
|
|
|
|
|
2010-09-02 10:59:18 +08:00
|
|
|
value_list.Append(m_opaque_sp->GetValueObjectForFrameVariable (variable_sp));
|
2010-06-09 00:52:24 +08:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2010-09-02 10:59:18 +08:00
|
|
|
}
|
2010-06-09 00:52:24 +08:00
|
|
|
}
|
2010-10-26 11:11:13 +08:00
|
|
|
|
|
|
|
if (log)
|
|
|
|
{
|
2010-10-27 07:49:36 +08:00
|
|
|
log->Printf ("SBFrame::GetVariables (this.sp=%p,...) => SBValueList (this.ap = %p)", m_opaque_sp.get(),
|
|
|
|
value_list.get());
|
2010-10-26 11:11:13 +08:00
|
|
|
//uint32_t num_vars = value_list.GetSize();
|
|
|
|
//for (uint32_t i = 0; i < num_vars; ++i)
|
|
|
|
//{
|
|
|
|
// SBValue value = value_list.GetValueAtIndex (i);
|
|
|
|
// log->Printf (" %s : %s", value.GetName(), value.GetObjectDescription (*this));
|
|
|
|
//}
|
|
|
|
}
|
|
|
|
|
2010-06-09 00:52:24 +08:00
|
|
|
return value_list;
|
|
|
|
}
|
|
|
|
|
|
|
|
lldb::SBValueList
|
|
|
|
SBFrame::GetRegisters ()
|
|
|
|
{
|
2010-10-26 11:11:13 +08:00
|
|
|
Log *log = lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_API);
|
|
|
|
|
2010-10-27 07:49:36 +08:00
|
|
|
//if (log)
|
|
|
|
// log->Printf ("SBFrame::GetRegisters ()");
|
2010-10-26 11:11:13 +08:00
|
|
|
|
2010-06-09 00:52:24 +08:00
|
|
|
SBValueList value_list;
|
2010-06-23 09:19:29 +08:00
|
|
|
if (m_opaque_sp)
|
2010-06-09 00:52:24 +08:00
|
|
|
{
|
2010-06-23 09:19:29 +08:00
|
|
|
RegisterContext *reg_ctx = m_opaque_sp->GetRegisterContext();
|
2010-06-09 00:52:24 +08:00
|
|
|
if (reg_ctx)
|
|
|
|
{
|
|
|
|
const uint32_t num_sets = reg_ctx->GetRegisterSetCount();
|
|
|
|
for (uint32_t set_idx = 0; set_idx < num_sets; ++set_idx)
|
|
|
|
{
|
2010-10-15 06:52:14 +08:00
|
|
|
value_list.Append(ValueObjectSP (new ValueObjectRegisterSet (NULL, reg_ctx, set_idx)));
|
2010-06-09 00:52:24 +08:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2010-10-26 11:11:13 +08:00
|
|
|
|
|
|
|
if (log)
|
|
|
|
{
|
2010-10-27 07:49:36 +08:00
|
|
|
log->Printf ("SBFrame::Registers (this.sp=%p) => SBValueList (this.ap = %p)", m_opaque_sp.get(),
|
|
|
|
value_list.get() );
|
2010-10-26 11:11:13 +08:00
|
|
|
//uint32_t num_vars = value_list.GetSize();
|
|
|
|
//for (uint32_t i = 0; i < num_vars; ++i)
|
|
|
|
//{
|
|
|
|
// SBValue value = value_list.GetValueAtIndex (i);
|
|
|
|
// log->Printf (" %s : %s", value.GetName(), value.GetObjectDescription (*this));
|
|
|
|
//}
|
|
|
|
}
|
|
|
|
|
2010-06-09 00:52:24 +08:00
|
|
|
return value_list;
|
|
|
|
}
|
|
|
|
|
2010-09-20 13:20:02 +08:00
|
|
|
bool
|
|
|
|
SBFrame::GetDescription (SBStream &description)
|
|
|
|
{
|
|
|
|
if (m_opaque_sp)
|
|
|
|
{
|
2010-10-28 06:07:28 +08:00
|
|
|
SBLineEntry line_entry = GetLineEntry ();
|
|
|
|
SBFileSpec file_spec = line_entry.GetFileSpec ();
|
|
|
|
uint32_t line = line_entry.GetLine ();
|
|
|
|
description.Printf("SBFrame: idx = %u ('%s', %s, line %d)", m_opaque_sp->GetFrameIndex(),
|
|
|
|
GetFunction().GetName(), file_spec.GetFilename(), line);
|
2010-09-20 13:20:02 +08:00
|
|
|
}
|
|
|
|
else
|
|
|
|
description.Printf ("No value");
|
|
|
|
|
|
|
|
return true;
|
|
|
|
}
|
2010-10-05 08:00:42 +08:00
|
|
|
|
|
|
|
lldb::SBValue
|
|
|
|
SBFrame::EvaluateExpression (const char *expr)
|
|
|
|
{
|
|
|
|
lldb::SBValue expr_result_value;
|
|
|
|
if (m_opaque_sp)
|
|
|
|
{
|
2010-10-05 11:13:51 +08:00
|
|
|
ExecutionContext exe_ctx;
|
|
|
|
m_opaque_sp->CalculateExecutionContext (exe_ctx);
|
2010-10-29 08:29:03 +08:00
|
|
|
|
|
|
|
const char *prefix = NULL;
|
|
|
|
|
|
|
|
if (exe_ctx.target)
|
|
|
|
prefix = exe_ctx.target->GetExpressionPrefixContentsAsCString();
|
|
|
|
|
|
|
|
*expr_result_value = ClangUserExpression::Evaluate (exe_ctx, expr, prefix);
|
2010-10-05 08:00:42 +08:00
|
|
|
}
|
|
|
|
return expr_result_value;
|
|
|
|
}
|