1 //===-- ValueObjectRegister.cpp ---------------------------------*- C++ -*-===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 
10 
11 #include "lldb/Core/ValueObjectRegister.h"
12 
13 // C Includes
14 // C++ Includes
15 // Other libraries and framework includes
16 // Project includes
17 #include "lldb/Core/Module.h"
18 #include "lldb/Symbol/ClangASTType.h"
19 #include "lldb/Symbol/ClangASTContext.h"
20 #include "lldb/Symbol/TypeList.h"
21 #include "lldb/Target/ExecutionContext.h"
22 #include "lldb/Target/Process.h"
23 #include "lldb/Target/RegisterContext.h"
24 #include "lldb/Target/Target.h"
25 #include "lldb/Target/Thread.h"
26 
27 using namespace lldb;
28 using namespace lldb_private;
29 
30 #pragma mark ValueObjectRegisterContext
31 
32 ValueObjectRegisterContext::ValueObjectRegisterContext (ValueObject &parent, RegisterContextSP &reg_ctx) :
33     ValueObject (parent),
34     m_reg_ctx_sp (reg_ctx)
35 {
36     assert (reg_ctx);
37     m_name.SetCString("Registers");
38     SetValueIsValid (true);
39 }
40 
41 ValueObjectRegisterContext::~ValueObjectRegisterContext()
42 {
43 }
44 
45 lldb::clang_type_t
46 ValueObjectRegisterContext::GetClangType ()
47 {
48     return NULL;
49 }
50 
51 ConstString
52 ValueObjectRegisterContext::GetTypeName()
53 {
54     ConstString empty_type_name;
55     return empty_type_name;
56 }
57 
58 uint32_t
59 ValueObjectRegisterContext::CalculateNumChildren()
60 {
61     return m_reg_ctx_sp->GetRegisterSetCount();
62 }
63 
64 clang::ASTContext *
65 ValueObjectRegisterContext::GetClangAST ()
66 {
67     return NULL;
68 }
69 
70 size_t
71 ValueObjectRegisterContext::GetByteSize()
72 {
73     return 0;
74 }
75 
76 bool
77 ValueObjectRegisterContext::UpdateValue ()
78 {
79     m_error.Clear();
80     ExecutionContextScope *exe_scope = GetExecutionContextScope();
81     StackFrame *frame = exe_scope->CalculateStackFrame();
82     if (frame)
83         m_reg_ctx_sp = frame->GetRegisterContext();
84     else
85         m_reg_ctx_sp.reset();
86 
87     if (m_reg_ctx_sp.get() == NULL)
88     {
89         SetValueIsValid (false);
90         m_error.SetErrorToGenericError();
91     }
92     else
93         SetValueIsValid (true);
94 
95     return m_error.Success();
96 }
97 
98 ValueObject *
99 ValueObjectRegisterContext::CreateChildAtIndex (uint32_t idx, bool synthetic_array_member, int32_t synthetic_index)
100 {
101     ValueObject *new_valobj = NULL;
102 
103     const uint32_t num_children = GetNumChildren();
104     if (idx < num_children)
105         new_valobj = new ValueObjectRegisterSet(GetExecutionContextScope(), m_reg_ctx_sp, idx);
106 
107     return new_valobj;
108 }
109 
110 
111 #pragma mark -
112 #pragma mark ValueObjectRegisterSet
113 
114 ValueObjectSP
115 ValueObjectRegisterSet::Create (ExecutionContextScope *exe_scope, lldb::RegisterContextSP &reg_ctx_sp, uint32_t set_idx)
116 {
117     return (new ValueObjectRegisterSet (exe_scope, reg_ctx_sp, set_idx))->GetSP();
118 }
119 
120 
121 ValueObjectRegisterSet::ValueObjectRegisterSet (ExecutionContextScope *exe_scope, lldb::RegisterContextSP &reg_ctx, uint32_t reg_set_idx) :
122     ValueObject (exe_scope),
123     m_reg_ctx_sp (reg_ctx),
124     m_reg_set (NULL),
125     m_reg_set_idx (reg_set_idx)
126 {
127     assert (reg_ctx);
128     m_reg_set = reg_ctx->GetRegisterSet(m_reg_set_idx);
129     if (m_reg_set)
130     {
131         m_name.SetCString (m_reg_set->name);
132     }
133 }
134 
135 ValueObjectRegisterSet::~ValueObjectRegisterSet()
136 {
137 }
138 
139 lldb::clang_type_t
140 ValueObjectRegisterSet::GetClangType ()
141 {
142     return NULL;
143 }
144 
145 ConstString
146 ValueObjectRegisterSet::GetTypeName()
147 {
148     return ConstString();
149 }
150 
151 uint32_t
152 ValueObjectRegisterSet::CalculateNumChildren()
153 {
154     const RegisterSet *reg_set = m_reg_ctx_sp->GetRegisterSet(m_reg_set_idx);
155     if (reg_set)
156         return reg_set->num_registers;
157     return 0;
158 }
159 
160 clang::ASTContext *
161 ValueObjectRegisterSet::GetClangAST ()
162 {
163     return NULL;
164 }
165 
166 size_t
167 ValueObjectRegisterSet::GetByteSize()
168 {
169     return 0;
170 }
171 
172 bool
173 ValueObjectRegisterSet::UpdateValue ()
174 {
175     m_error.Clear();
176     SetValueDidChange (false);
177     ExecutionContextScope *exe_scope = GetExecutionContextScope();
178     StackFrame *frame = exe_scope->CalculateStackFrame();
179     if (frame == NULL)
180         m_reg_ctx_sp.reset();
181     else
182     {
183         m_reg_ctx_sp = frame->GetRegisterContext ();
184         if (m_reg_ctx_sp)
185         {
186             const RegisterSet *reg_set = m_reg_ctx_sp->GetRegisterSet (m_reg_set_idx);
187             if (reg_set == NULL)
188                 m_reg_ctx_sp.reset();
189             else if (m_reg_set != reg_set)
190             {
191                 SetValueDidChange (true);
192                 m_name.SetCString(reg_set->name);
193             }
194         }
195     }
196     if (m_reg_ctx_sp)
197     {
198         SetValueIsValid (true);
199     }
200     else
201     {
202         SetValueIsValid (false);
203         m_error.SetErrorToGenericError ();
204         m_children.clear();
205     }
206     return m_error.Success();
207 }
208 
209 
210 ValueObject *
211 ValueObjectRegisterSet::CreateChildAtIndex (uint32_t idx, bool synthetic_array_member, int32_t synthetic_index)
212 {
213     ValueObject *valobj = NULL;
214     if (m_reg_ctx_sp && m_reg_set)
215     {
216         const uint32_t num_children = GetNumChildren();
217         if (idx < num_children)
218             valobj = new ValueObjectRegister(*this, m_reg_ctx_sp, m_reg_set->registers[idx]);
219     }
220     return valobj;
221 }
222 
223 lldb::ValueObjectSP
224 ValueObjectRegisterSet::GetChildMemberWithName (const ConstString &name, bool can_create)
225 {
226     ValueObject *valobj = NULL;
227     if (m_reg_ctx_sp && m_reg_set)
228     {
229         const RegisterInfo *reg_info = m_reg_ctx_sp->GetRegisterInfoByName (name.AsCString());
230         if (reg_info != NULL)
231             valobj = new ValueObjectRegister(*this, m_reg_ctx_sp, reg_info->kinds[eRegisterKindLLDB]);
232     }
233     if (valobj)
234         return valobj->GetSP();
235     else
236         return ValueObjectSP();
237 }
238 
239 uint32_t
240 ValueObjectRegisterSet::GetIndexOfChildWithName (const ConstString &name)
241 {
242     if (m_reg_ctx_sp && m_reg_set)
243     {
244         const RegisterInfo *reg_info = m_reg_ctx_sp->GetRegisterInfoByName (name.AsCString());
245         if (reg_info != NULL)
246             return reg_info->kinds[eRegisterKindLLDB];
247     }
248     return UINT32_MAX;
249 }
250 
251 #pragma mark -
252 #pragma mark ValueObjectRegister
253 
254 void
255 ValueObjectRegister::ConstructObject (uint32_t reg_num)
256 {
257     const RegisterInfo *reg_info = m_reg_ctx_sp->GetRegisterInfoAtIndex (reg_num);
258     if (reg_info)
259     {
260         m_reg_info = *reg_info;
261         if (reg_info->name)
262             m_name.SetCString(reg_info->name);
263         else if (reg_info->alt_name)
264             m_name.SetCString(reg_info->alt_name);
265     }
266 }
267 
268 ValueObjectRegister::ValueObjectRegister (ValueObject &parent, lldb::RegisterContextSP &reg_ctx_sp, uint32_t reg_num) :
269     ValueObject (parent),
270     m_reg_ctx_sp (reg_ctx_sp),
271     m_reg_info (),
272     m_reg_value (),
273     m_type_name (),
274     m_clang_type (NULL)
275 {
276     assert (reg_ctx_sp.get());
277     ConstructObject(reg_num);
278 }
279 
280 ValueObjectSP
281 ValueObjectRegister::Create (ExecutionContextScope *exe_scope, lldb::RegisterContextSP &reg_ctx_sp, uint32_t reg_num)
282 {
283     return (new ValueObjectRegister (exe_scope, reg_ctx_sp, reg_num))->GetSP();
284 }
285 
286 ValueObjectRegister::ValueObjectRegister (ExecutionContextScope *exe_scope, lldb::RegisterContextSP &reg_ctx, uint32_t reg_num) :
287     ValueObject (exe_scope),
288     m_reg_ctx_sp (reg_ctx),
289     m_reg_info (),
290     m_reg_value (),
291     m_type_name (),
292     m_clang_type (NULL)
293 {
294     assert (reg_ctx);
295     ConstructObject(reg_num);
296 }
297 
298 ValueObjectRegister::~ValueObjectRegister()
299 {
300 }
301 
302 lldb::clang_type_t
303 ValueObjectRegister::GetClangType ()
304 {
305     if (m_clang_type == NULL)
306     {
307         Process *process = m_reg_ctx_sp->CalculateProcess ();
308         if (process)
309         {
310             Module *exe_module = process->GetTarget().GetExecutableModulePointer();
311             if (exe_module)
312             {
313                 m_clang_type = exe_module->GetClangASTContext().GetBuiltinTypeForEncodingAndBitSize (m_reg_info.encoding,
314                                                                                                      m_reg_info.byte_size * 8);
315             }
316         }
317     }
318     return m_clang_type;
319 }
320 
321 ConstString
322 ValueObjectRegister::GetTypeName()
323 {
324     if (m_type_name.IsEmpty())
325         m_type_name = ClangASTType::GetConstTypeName (GetClangType());
326     return m_type_name;
327 }
328 
329 uint32_t
330 ValueObjectRegister::CalculateNumChildren()
331 {
332     return 0;
333 }
334 
335 clang::ASTContext *
336 ValueObjectRegister::GetClangAST ()
337 {
338     Process *process = m_reg_ctx_sp->CalculateProcess ();
339     if (process)
340     {
341         Module *exe_module = process->GetTarget().GetExecutableModulePointer();
342         if (exe_module)
343             return exe_module->GetClangASTContext().getASTContext();
344     }
345     return NULL;
346 }
347 
348 size_t
349 ValueObjectRegister::GetByteSize()
350 {
351     return m_reg_info.byte_size;
352 }
353 
354 bool
355 ValueObjectRegister::UpdateValue ()
356 {
357     m_error.Clear();
358     ExecutionContextScope *exe_scope = GetExecutionContextScope();
359     StackFrame *frame = exe_scope->CalculateStackFrame();
360     if (frame == NULL)
361     {
362         m_reg_ctx_sp.reset();
363         m_reg_value.Clear();
364     }
365 
366 
367     if (m_reg_ctx_sp)
368     {
369         if (m_reg_ctx_sp->ReadRegister (&m_reg_info, m_reg_value))
370         {
371             if (m_reg_value.GetData (m_data))
372             {
373                 m_data.SetAddressByteSize(m_reg_ctx_sp->GetThread().GetProcess().GetAddressByteSize());
374                 m_value.SetContext(Value::eContextTypeRegisterInfo, (void *)&m_reg_info);
375                 m_value.SetValueType(Value::eValueTypeHostAddress);
376                 m_value.GetScalar() = (uintptr_t)m_data.GetDataStart();
377                 SetValueIsValid (true);
378                 return true;
379             }
380         }
381     }
382 
383     SetValueIsValid (false);
384     m_error.SetErrorToGenericError ();
385     return false;
386 }
387 
388 bool
389 ValueObjectRegister::SetValueFromCString (const char *value_str)
390 {
391     // The new value will be in the m_data.  Copy that into our register value.
392     Error error = m_reg_value.SetValueFromCString (&m_reg_info, value_str);
393     if (error.Success())
394     {
395         if (m_reg_ctx_sp->WriteRegister (&m_reg_info, m_reg_value))
396         {
397             SetNeedsUpdate();
398             return true;
399         }
400         else
401             return false;
402     }
403     else
404         return false;
405 }
406 
407 bool
408 ValueObjectRegister::ResolveValue (Scalar &scalar)
409 {
410     if (UpdateValueIfNeeded(false)) // make sure that you are up to date before returning anything
411         return m_reg_value.GetScalarValue(scalar);
412     return false;
413 }
414 
415 
416