]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - contrib/llvm/tools/lldb/source/Core/ValueObjectRegister.cpp
Integrate tools/regression/acltools into tests/sys/acl
[FreeBSD/FreeBSD.git] / contrib / llvm / tools / lldb / source / Core / ValueObjectRegister.cpp
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 ClangASTType
46 ValueObjectRegisterContext::GetClangTypeImpl ()
47 {
48     return ClangASTType();
49 }
50
51 ConstString
52 ValueObjectRegisterContext::GetTypeName()
53 {
54     return ConstString();
55 }
56
57 ConstString
58 ValueObjectRegisterContext::GetDisplayTypeName()
59 {
60     return ConstString();
61 }
62
63 ConstString
64 ValueObjectRegisterContext::GetQualifiedTypeName()
65 {
66     return ConstString();
67 }
68
69 size_t
70 ValueObjectRegisterContext::CalculateNumChildren()
71 {
72     return m_reg_ctx_sp->GetRegisterSetCount();
73 }
74
75 uint64_t
76 ValueObjectRegisterContext::GetByteSize()
77 {
78     return 0;
79 }
80
81 bool
82 ValueObjectRegisterContext::UpdateValue ()
83 {
84     m_error.Clear();
85     ExecutionContext exe_ctx(GetExecutionContextRef());
86     StackFrame *frame = exe_ctx.GetFramePtr();
87     if (frame)
88         m_reg_ctx_sp = frame->GetRegisterContext();
89     else
90         m_reg_ctx_sp.reset();
91
92     if (m_reg_ctx_sp.get() == NULL)
93     {
94         SetValueIsValid (false);
95         m_error.SetErrorToGenericError();
96     }
97     else
98         SetValueIsValid (true);
99         
100     return m_error.Success();
101 }
102
103 ValueObject *
104 ValueObjectRegisterContext::CreateChildAtIndex (size_t idx, bool synthetic_array_member, int32_t synthetic_index)
105 {
106     ValueObject *new_valobj = NULL;
107     
108     const size_t num_children = GetNumChildren();
109     if (idx < num_children)
110     {
111         ExecutionContext exe_ctx(GetExecutionContextRef());
112         new_valobj = new ValueObjectRegisterSet(exe_ctx.GetBestExecutionContextScope(), m_reg_ctx_sp, idx);
113     }
114     
115     return new_valobj;
116 }
117
118
119 #pragma mark -
120 #pragma mark ValueObjectRegisterSet
121
122 ValueObjectSP
123 ValueObjectRegisterSet::Create (ExecutionContextScope *exe_scope, lldb::RegisterContextSP &reg_ctx_sp, uint32_t set_idx)
124 {
125     return (new ValueObjectRegisterSet (exe_scope, reg_ctx_sp, set_idx))->GetSP();
126 }
127
128
129 ValueObjectRegisterSet::ValueObjectRegisterSet (ExecutionContextScope *exe_scope, lldb::RegisterContextSP &reg_ctx, uint32_t reg_set_idx) :
130     ValueObject (exe_scope),
131     m_reg_ctx_sp (reg_ctx),
132     m_reg_set (NULL),
133     m_reg_set_idx (reg_set_idx)
134 {
135     assert (reg_ctx);
136     m_reg_set = reg_ctx->GetRegisterSet(m_reg_set_idx);
137     if (m_reg_set)
138     {
139         m_name.SetCString (m_reg_set->name);
140     }
141 }
142
143 ValueObjectRegisterSet::~ValueObjectRegisterSet()
144 {
145 }
146
147 ClangASTType
148 ValueObjectRegisterSet::GetClangTypeImpl ()
149 {
150     return ClangASTType();
151 }
152
153 ConstString
154 ValueObjectRegisterSet::GetTypeName()
155 {
156     return ConstString();
157 }
158
159 ConstString
160 ValueObjectRegisterSet::GetQualifiedTypeName()
161 {
162     return ConstString();
163 }
164
165 size_t
166 ValueObjectRegisterSet::CalculateNumChildren()
167 {
168     const RegisterSet *reg_set = m_reg_ctx_sp->GetRegisterSet(m_reg_set_idx);
169     if (reg_set)
170         return reg_set->num_registers;
171     return 0;
172 }
173
174 uint64_t
175 ValueObjectRegisterSet::GetByteSize()
176 {
177     return 0;
178 }
179
180 bool
181 ValueObjectRegisterSet::UpdateValue ()
182 {
183     m_error.Clear();
184     SetValueDidChange (false);
185     ExecutionContext exe_ctx(GetExecutionContextRef());
186     StackFrame *frame = exe_ctx.GetFramePtr();
187     if (frame == NULL)
188         m_reg_ctx_sp.reset();
189     else
190     {
191         m_reg_ctx_sp = frame->GetRegisterContext ();
192         if (m_reg_ctx_sp)
193         {
194             const RegisterSet *reg_set = m_reg_ctx_sp->GetRegisterSet (m_reg_set_idx);
195             if (reg_set == NULL)
196                 m_reg_ctx_sp.reset();
197             else if (m_reg_set != reg_set)
198             {
199                 SetValueDidChange (true);
200                 m_name.SetCString(reg_set->name);
201             }
202         }
203     }
204     if (m_reg_ctx_sp)
205     {
206         SetValueIsValid (true);
207     }
208     else
209     {
210         SetValueIsValid (false);
211         m_error.SetErrorToGenericError ();
212         m_children.Clear();
213     }
214     return m_error.Success();
215 }
216
217
218 ValueObject *
219 ValueObjectRegisterSet::CreateChildAtIndex (size_t idx, bool synthetic_array_member, int32_t synthetic_index)
220 {
221     ValueObject *valobj = NULL;
222     if (m_reg_ctx_sp && m_reg_set)
223     {
224         const size_t num_children = GetNumChildren();
225         if (idx < num_children)
226             valobj = new ValueObjectRegister(*this, m_reg_ctx_sp, m_reg_set->registers[idx]);
227     }
228     return valobj;
229 }
230
231 lldb::ValueObjectSP
232 ValueObjectRegisterSet::GetChildMemberWithName (const ConstString &name, bool can_create)
233 {
234     ValueObject *valobj = NULL;
235     if (m_reg_ctx_sp && m_reg_set)
236     {
237         const RegisterInfo *reg_info = m_reg_ctx_sp->GetRegisterInfoByName (name.AsCString());
238         if (reg_info != NULL)
239             valobj = new ValueObjectRegister(*this, m_reg_ctx_sp, reg_info->kinds[eRegisterKindLLDB]);
240     }
241     if (valobj)
242         return valobj->GetSP();
243     else
244         return ValueObjectSP();
245 }
246
247 size_t
248 ValueObjectRegisterSet::GetIndexOfChildWithName (const ConstString &name)
249 {
250     if (m_reg_ctx_sp && m_reg_set)
251     {
252         const RegisterInfo *reg_info = m_reg_ctx_sp->GetRegisterInfoByName (name.AsCString());
253         if (reg_info != NULL)
254             return reg_info->kinds[eRegisterKindLLDB];
255     }
256     return UINT32_MAX;
257 }
258
259 #pragma mark -
260 #pragma mark ValueObjectRegister
261
262 void
263 ValueObjectRegister::ConstructObject (uint32_t reg_num)
264 {
265     const RegisterInfo *reg_info = m_reg_ctx_sp->GetRegisterInfoAtIndex (reg_num);
266     if (reg_info)
267     {
268         m_reg_info = *reg_info;
269         if (reg_info->name)
270             m_name.SetCString(reg_info->name);
271         else if (reg_info->alt_name)
272             m_name.SetCString(reg_info->alt_name);
273     }
274 }
275
276 ValueObjectRegister::ValueObjectRegister (ValueObject &parent, lldb::RegisterContextSP &reg_ctx_sp, uint32_t reg_num) :
277     ValueObject (parent),
278     m_reg_ctx_sp (reg_ctx_sp),
279     m_reg_info (),
280     m_reg_value (),
281     m_type_name (),
282     m_clang_type ()
283 {
284     assert (reg_ctx_sp.get());
285     ConstructObject(reg_num);
286 }
287
288 ValueObjectSP
289 ValueObjectRegister::Create (ExecutionContextScope *exe_scope, lldb::RegisterContextSP &reg_ctx_sp, uint32_t reg_num)
290 {
291     return (new ValueObjectRegister (exe_scope, reg_ctx_sp, reg_num))->GetSP();
292 }
293
294 ValueObjectRegister::ValueObjectRegister (ExecutionContextScope *exe_scope, lldb::RegisterContextSP &reg_ctx, uint32_t reg_num) :
295     ValueObject (exe_scope),
296     m_reg_ctx_sp (reg_ctx),
297     m_reg_info (),
298     m_reg_value (),
299     m_type_name (),
300     m_clang_type ()
301 {
302     assert (reg_ctx);
303     ConstructObject(reg_num);
304 }
305
306 ValueObjectRegister::~ValueObjectRegister()
307 {
308 }
309
310 ClangASTType
311 ValueObjectRegister::GetClangTypeImpl ()
312 {
313     if (!m_clang_type.IsValid())
314     {
315         ExecutionContext exe_ctx (GetExecutionContextRef());
316         Target *target = exe_ctx.GetTargetPtr();
317         if (target)
318         {
319             Module *exe_module = target->GetExecutableModulePointer();
320             if (exe_module)
321             {
322                 m_clang_type = exe_module->GetClangASTContext().GetBuiltinTypeForEncodingAndBitSize (m_reg_info.encoding, 
323                                                                                                      m_reg_info.byte_size * 8);
324             }
325         }
326     }
327     return m_clang_type;
328 }
329
330 ConstString
331 ValueObjectRegister::GetTypeName()
332 {
333     if (m_type_name.IsEmpty())
334         m_type_name = GetClangType().GetConstTypeName ();
335     return m_type_name;
336 }
337
338 size_t
339 ValueObjectRegister::CalculateNumChildren()
340 {
341     return GetClangType().GetNumChildren(true);
342 }
343
344 uint64_t
345 ValueObjectRegister::GetByteSize()
346 {
347     return m_reg_info.byte_size;
348 }
349
350 bool
351 ValueObjectRegister::UpdateValue ()
352 {
353     m_error.Clear();
354     ExecutionContext exe_ctx(GetExecutionContextRef());
355     StackFrame *frame = exe_ctx.GetFramePtr();
356     if (frame == NULL)
357     {
358         m_reg_ctx_sp.reset();
359         m_reg_value.Clear();
360     }
361
362
363     if (m_reg_ctx_sp)
364     {
365         if (m_reg_ctx_sp->ReadRegister (&m_reg_info, m_reg_value))
366         {
367             if (m_reg_value.GetData (m_data))
368             {
369                 Process *process = exe_ctx.GetProcessPtr();
370                 if (process)
371                     m_data.SetAddressByteSize(process->GetAddressByteSize());
372                 m_value.SetContext(Value::eContextTypeRegisterInfo, (void *)&m_reg_info);
373                 m_value.SetValueType(Value::eValueTypeHostAddress);
374                 m_value.GetScalar() = (uintptr_t)m_data.GetDataStart();
375                 SetValueIsValid (true);
376                 return true;
377             }
378         }
379     }
380     
381     SetValueIsValid (false);
382     m_error.SetErrorToGenericError ();
383     return false;
384 }
385
386 bool
387 ValueObjectRegister::SetValueFromCString (const char *value_str, Error& error)
388 {
389     // The new value will be in the m_data.  Copy that into our register value.
390     error = m_reg_value.SetValueFromCString (&m_reg_info, value_str);
391     if (error.Success())
392     {
393         if (m_reg_ctx_sp->WriteRegister (&m_reg_info, m_reg_value))
394         {
395             SetNeedsUpdate();
396             return true;
397         }
398         else
399             return false;
400     }
401     else
402         return false;
403 }
404
405 bool
406 ValueObjectRegister::SetData (DataExtractor &data, Error &error)
407 {
408     error = m_reg_value.SetValueFromData(&m_reg_info, data, 0, false);
409     if (error.Success())
410     {
411         if (m_reg_ctx_sp->WriteRegister (&m_reg_info, m_reg_value))
412         {
413             SetNeedsUpdate();
414             return true;
415         }
416         else
417             return false;
418     }
419     else
420         return false;
421 }
422
423 bool
424 ValueObjectRegister::ResolveValue (Scalar &scalar)
425 {
426     if (UpdateValueIfNeeded(false)) // make sure that you are up to date before returning anything
427         return m_reg_value.GetScalarValue(scalar);
428     return false;
429 }
430
431 void
432 ValueObjectRegister::GetExpressionPath (Stream &s, bool qualify_cxx_base_classes, GetExpressionPathFormat epformat)
433 {
434     s.Printf("$%s", m_reg_info.name);
435 }
436
437