blob: d839c1a56cb7b9534288f6b2ad3b55fbeba6a594 [file] [log] [blame]
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001//===-- ValueObject.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
Daniel Malea93a64302012-12-05 00:20:57 +000010#include "lldb/lldb-python.h"
11
Chris Lattner30fdc8d2010-06-08 16:52:24 +000012#include "lldb/Core/ValueObject.h"
13
14// C Includes
Greg Claytonf5e56de2010-09-14 23:36:40 +000015#include <stdlib.h>
16
Chris Lattner30fdc8d2010-06-08 16:52:24 +000017// C++ Includes
18// Other libraries and framework includes
Chris Lattner30fdc8d2010-06-08 16:52:24 +000019#include "llvm/Support/raw_ostream.h"
Jim Ingham5a369122010-09-28 01:25:32 +000020#include "clang/AST/Type.h"
Chris Lattner30fdc8d2010-06-08 16:52:24 +000021
22// Project includes
23#include "lldb/Core/DataBufferHeap.h"
Enrico Granata4becb372011-06-29 22:27:15 +000024#include "lldb/Core/Debugger.h"
Enrico Granata6f3533f2011-07-29 19:53:35 +000025#include "lldb/Core/Log.h"
Greg Clayton1f746072012-08-29 21:13:06 +000026#include "lldb/Core/Module.h"
Chris Lattner30fdc8d2010-06-08 16:52:24 +000027#include "lldb/Core/StreamString.h"
Enrico Granata21fd13f2012-10-27 02:05:48 +000028#include "lldb/Core/ValueObjectCast.h"
Chris Lattner30fdc8d2010-06-08 16:52:24 +000029#include "lldb/Core/ValueObjectChild.h"
Greg Clayton8b2fe6d2010-12-14 02:59:59 +000030#include "lldb/Core/ValueObjectConstResult.h"
Jim Ingham78a685a2011-04-16 00:01:13 +000031#include "lldb/Core/ValueObjectDynamicValue.h"
Chris Lattner30fdc8d2010-06-08 16:52:24 +000032#include "lldb/Core/ValueObjectList.h"
Greg Claytonb2dcc362011-05-05 23:32:56 +000033#include "lldb/Core/ValueObjectMemory.h"
Enrico Granatad55546b2011-07-22 00:16:08 +000034#include "lldb/Core/ValueObjectSyntheticFilter.h"
Chris Lattner30fdc8d2010-06-08 16:52:24 +000035
Enrico Granata5548cb52013-01-28 23:47:25 +000036#include "lldb/DataFormatters/DataVisualization.h"
Enrico Granata4d93b8c2013-09-30 19:11:51 +000037#include "lldb/DataFormatters/ValueObjectPrinter.h"
Enrico Granata5548cb52013-01-28 23:47:25 +000038
Greg Clayton7fb56d02011-02-01 01:31:41 +000039#include "lldb/Host/Endian.h"
40
Enrico Granata61a80ba2011-08-12 16:42:31 +000041#include "lldb/Interpreter/CommandInterpreter.h"
Enrico Granataf2bbf712011-07-15 02:26:42 +000042#include "lldb/Interpreter/ScriptInterpreterPython.h"
43
Greg Claytone1a916a2010-07-21 22:12:05 +000044#include "lldb/Symbol/ClangASTType.h"
Chris Lattner30fdc8d2010-06-08 16:52:24 +000045#include "lldb/Symbol/ClangASTContext.h"
46#include "lldb/Symbol/Type.h"
47
Jim Ingham53c47f12010-09-10 23:12:17 +000048#include "lldb/Target/ExecutionContext.h"
Jim Ingham5a369122010-09-28 01:25:32 +000049#include "lldb/Target/LanguageRuntime.h"
Enrico Granatac3e320a2011-08-02 17:27:39 +000050#include "lldb/Target/ObjCLanguageRuntime.h"
Chris Lattner30fdc8d2010-06-08 16:52:24 +000051#include "lldb/Target/Process.h"
52#include "lldb/Target/RegisterContext.h"
Greg Claytond5944cd2013-12-06 01:12:00 +000053#include "lldb/Target/SectionLoadList.h"
Greg Claytonf5e56de2010-09-14 23:36:40 +000054#include "lldb/Target/Target.h"
Chris Lattner30fdc8d2010-06-08 16:52:24 +000055#include "lldb/Target/Thread.h"
Chris Lattner30fdc8d2010-06-08 16:52:24 +000056
57using namespace lldb;
58using namespace lldb_private;
Enrico Granataf4efecd2011-07-12 22:56:10 +000059using namespace lldb_utility;
Chris Lattner30fdc8d2010-06-08 16:52:24 +000060
Greg Claytonafacd142011-09-02 01:15:17 +000061static user_id_t g_value_obj_uid = 0;
Chris Lattner30fdc8d2010-06-08 16:52:24 +000062
63//----------------------------------------------------------------------
64// ValueObject constructor
65//----------------------------------------------------------------------
Jim Ingham6035b672011-03-31 00:19:25 +000066ValueObject::ValueObject (ValueObject &parent) :
Chris Lattner30fdc8d2010-06-08 16:52:24 +000067 UserID (++g_value_obj_uid), // Unique identifier for every value object
Jim Ingham6035b672011-03-31 00:19:25 +000068 m_parent (&parent),
Enrico Granata4873e522013-04-11 22:48:58 +000069 m_root (NULL),
Stephen Wilson71c21d12011-04-11 19:41:40 +000070 m_update_point (parent.GetUpdatePoint ()),
Chris Lattner30fdc8d2010-06-08 16:52:24 +000071 m_name (),
72 m_data (),
73 m_value (),
74 m_error (),
Greg Clayton288bdf92010-09-02 02:59:18 +000075 m_value_str (),
76 m_old_value_str (),
77 m_location_str (),
78 m_summary_str (),
Jim Ingham53c47f12010-09-10 23:12:17 +000079 m_object_desc_str (),
Enrico Granata744794a2014-09-05 21:46:22 +000080 m_validation_result(),
Jim Ingham58b59f92011-04-22 23:53:53 +000081 m_manager(parent.GetManager()),
Greg Clayton288bdf92010-09-02 02:59:18 +000082 m_children (),
83 m_synthetic_children (),
Jim Ingham58b59f92011-04-22 23:53:53 +000084 m_dynamic_value (NULL),
Enrico Granatad55546b2011-07-22 00:16:08 +000085 m_synthetic_value(NULL),
Jim Ingham58b59f92011-04-22 23:53:53 +000086 m_deref_valobj(NULL),
Greg Clayton32c40852010-10-06 03:09:11 +000087 m_format (eFormatDefault),
Enrico Granatab294fd22013-05-31 19:18:19 +000088 m_last_format (eFormatDefault),
Enrico Granata9df29e32011-07-19 20:57:44 +000089 m_last_format_mgr_revision(0),
Enrico Granata0c489f52012-03-01 04:24:26 +000090 m_type_summary_sp(),
91 m_type_format_sp(),
92 m_synthetic_children_sp(),
Enrico Granata744794a2014-09-05 21:46:22 +000093 m_type_validator_sp(),
Jim Ingham4b536182011-08-09 02:12:22 +000094 m_user_id_of_forced_summary(),
Daniel Dunbara08823f2011-10-31 22:50:49 +000095 m_address_type_of_ptr_or_ref_children(eAddressTypeInvalid),
Greg Clayton288bdf92010-09-02 02:59:18 +000096 m_value_is_valid (false),
97 m_value_did_change (false),
98 m_children_count_valid (false),
Greg Clayton8b2fe6d2010-12-14 02:59:59 +000099 m_old_value_valid (false),
Enrico Granata4becb372011-06-29 22:27:15 +0000100 m_is_deref_of_parent (false),
Enrico Granata0a3958e2011-07-02 00:25:22 +0000101 m_is_array_item_for_pointer(false),
Enrico Granata9fc19442011-07-06 02:13:41 +0000102 m_is_bitfield_for_scalar(false),
Enrico Granata6f3533f2011-07-29 19:53:35 +0000103 m_is_child_at_offset(false),
Sean Callanan72772842012-02-22 23:57:45 +0000104 m_is_getting_summary(false),
105 m_did_calculate_complete_objc_class_type(false)
Jim Ingham6035b672011-03-31 00:19:25 +0000106{
Jim Ingham58b59f92011-04-22 23:53:53 +0000107 m_manager->ManageObject(this);
Jim Ingham6035b672011-03-31 00:19:25 +0000108}
109
110//----------------------------------------------------------------------
111// ValueObject constructor
112//----------------------------------------------------------------------
Enrico Granata9128ee22011-09-06 19:20:51 +0000113ValueObject::ValueObject (ExecutionContextScope *exe_scope,
114 AddressType child_ptr_or_ref_addr_type) :
Jim Ingham6035b672011-03-31 00:19:25 +0000115 UserID (++g_value_obj_uid), // Unique identifier for every value object
116 m_parent (NULL),
Enrico Granata4873e522013-04-11 22:48:58 +0000117 m_root (NULL),
Stephen Wilson71c21d12011-04-11 19:41:40 +0000118 m_update_point (exe_scope),
Jim Ingham6035b672011-03-31 00:19:25 +0000119 m_name (),
120 m_data (),
121 m_value (),
122 m_error (),
123 m_value_str (),
124 m_old_value_str (),
125 m_location_str (),
126 m_summary_str (),
127 m_object_desc_str (),
Enrico Granata744794a2014-09-05 21:46:22 +0000128 m_validation_result(),
Jim Ingham58b59f92011-04-22 23:53:53 +0000129 m_manager(),
Jim Ingham6035b672011-03-31 00:19:25 +0000130 m_children (),
131 m_synthetic_children (),
Jim Ingham58b59f92011-04-22 23:53:53 +0000132 m_dynamic_value (NULL),
Enrico Granatad55546b2011-07-22 00:16:08 +0000133 m_synthetic_value(NULL),
Jim Ingham58b59f92011-04-22 23:53:53 +0000134 m_deref_valobj(NULL),
Jim Ingham6035b672011-03-31 00:19:25 +0000135 m_format (eFormatDefault),
Enrico Granatab294fd22013-05-31 19:18:19 +0000136 m_last_format (eFormatDefault),
Enrico Granata9df29e32011-07-19 20:57:44 +0000137 m_last_format_mgr_revision(0),
Enrico Granata0c489f52012-03-01 04:24:26 +0000138 m_type_summary_sp(),
139 m_type_format_sp(),
140 m_synthetic_children_sp(),
Enrico Granata744794a2014-09-05 21:46:22 +0000141 m_type_validator_sp(),
Jim Ingham4b536182011-08-09 02:12:22 +0000142 m_user_id_of_forced_summary(),
Daniel Dunbara08823f2011-10-31 22:50:49 +0000143 m_address_type_of_ptr_or_ref_children(child_ptr_or_ref_addr_type),
Jim Ingham6035b672011-03-31 00:19:25 +0000144 m_value_is_valid (false),
145 m_value_did_change (false),
146 m_children_count_valid (false),
147 m_old_value_valid (false),
Enrico Granata4becb372011-06-29 22:27:15 +0000148 m_is_deref_of_parent (false),
Enrico Granata0a3958e2011-07-02 00:25:22 +0000149 m_is_array_item_for_pointer(false),
Enrico Granata9fc19442011-07-06 02:13:41 +0000150 m_is_bitfield_for_scalar(false),
Enrico Granata6f3533f2011-07-29 19:53:35 +0000151 m_is_child_at_offset(false),
Sean Callanan72772842012-02-22 23:57:45 +0000152 m_is_getting_summary(false),
153 m_did_calculate_complete_objc_class_type(false)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000154{
Jim Ingham58b59f92011-04-22 23:53:53 +0000155 m_manager = new ValueObjectManager();
156 m_manager->ManageObject (this);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000157}
158
159//----------------------------------------------------------------------
160// Destructor
161//----------------------------------------------------------------------
162ValueObject::~ValueObject ()
163{
164}
165
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000166bool
Enrico Granata0a3958e2011-07-02 00:25:22 +0000167ValueObject::UpdateValueIfNeeded (bool update_format)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000168{
Enrico Granata4becb372011-06-29 22:27:15 +0000169
Enrico Granata9128ee22011-09-06 19:20:51 +0000170 bool did_change_formats = false;
171
Enrico Granata0a3958e2011-07-02 00:25:22 +0000172 if (update_format)
Enrico Granata5548cb52013-01-28 23:47:25 +0000173 did_change_formats = UpdateFormatsIfNeeded();
Enrico Granata4becb372011-06-29 22:27:15 +0000174
Greg Claytonb71f3842010-10-05 03:13:51 +0000175 // If this is a constant value, then our success is predicated on whether
176 // we have an error or not
177 if (GetIsConstant())
Enrico Granata9128ee22011-09-06 19:20:51 +0000178 {
Enrico Granatab1c6c482013-10-09 00:33:55 +0000179 // if you are constant, things might still have changed behind your back
180 // (e.g. you are a frozen object and things have changed deeper than you cared to freeze-dry yourself)
181 // in this case, your value has not changed, but "computed" entries might have, so you might now have
182 // a different summary, or a different object description. clear these so we will recompute them
Enrico Granata9128ee22011-09-06 19:20:51 +0000183 if (update_format && !did_change_formats)
Enrico Granatab1c6c482013-10-09 00:33:55 +0000184 ClearUserVisibleData(eClearUserVisibleDataItemsSummary | eClearUserVisibleDataItemsDescription);
Greg Claytonb71f3842010-10-05 03:13:51 +0000185 return m_error.Success();
Enrico Granata9128ee22011-09-06 19:20:51 +0000186 }
Greg Claytonb71f3842010-10-05 03:13:51 +0000187
Jim Ingham6035b672011-03-31 00:19:25 +0000188 bool first_update = m_update_point.IsFirstEvaluation();
189
190 if (m_update_point.NeedsUpdating())
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000191 {
Jim Ingham6035b672011-03-31 00:19:25 +0000192 m_update_point.SetUpdated();
193
194 // Save the old value using swap to avoid a string copy which
195 // also will clear our m_value_str
196 if (m_value_str.empty())
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000197 {
Jim Ingham6035b672011-03-31 00:19:25 +0000198 m_old_value_valid = false;
199 }
200 else
201 {
202 m_old_value_valid = true;
203 m_old_value_str.swap (m_value_str);
Enrico Granata86cc9822012-03-19 22:58:49 +0000204 ClearUserVisibleData(eClearUserVisibleDataItemsValue);
Jim Ingham6035b672011-03-31 00:19:25 +0000205 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000206
Enrico Granataf2bbf712011-07-15 02:26:42 +0000207 ClearUserVisibleData();
208
Greg Claytonefbc7d22012-03-09 04:23:44 +0000209 if (IsInScope())
Jim Ingham6035b672011-03-31 00:19:25 +0000210 {
Greg Claytonefbc7d22012-03-09 04:23:44 +0000211 const bool value_was_valid = GetValueIsValid();
212 SetValueDidChange (false);
213
214 m_error.Clear();
215
216 // Call the pure virtual function to update the value
217 bool success = UpdateValue ();
218
219 SetValueIsValid (success);
220
221 if (first_update)
222 SetValueDidChange (false);
223 else if (!m_value_did_change && success == false)
224 {
225 // The value wasn't gotten successfully, so we mark this
226 // as changed if the value used to be valid and now isn't
227 SetValueDidChange (value_was_valid);
228 }
229 }
230 else
231 {
232 m_error.SetErrorString("out of scope");
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000233 }
234 }
235 return m_error.Success();
236}
237
Enrico Granata9128ee22011-09-06 19:20:51 +0000238bool
Enrico Granata5548cb52013-01-28 23:47:25 +0000239ValueObject::UpdateFormatsIfNeeded()
Enrico Granata4becb372011-06-29 22:27:15 +0000240{
Greg Clayton5160ce52013-03-27 23:08:40 +0000241 Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_TYPES));
Enrico Granata6f3533f2011-07-29 19:53:35 +0000242 if (log)
Enrico Granatad2284832012-10-17 22:23:56 +0000243 log->Printf("[%s %p] checking for FormatManager revisions. ValueObject rev: %d - Global rev: %d",
Saleem Abdulrasool324a1032014-04-04 04:06:10 +0000244 GetName().GetCString(), static_cast<void*>(this),
245 m_last_format_mgr_revision,
246 DataVisualization::GetCurrentRevision());
247
Enrico Granata9128ee22011-09-06 19:20:51 +0000248 bool any_change = false;
Saleem Abdulrasool324a1032014-04-04 04:06:10 +0000249
Enrico Granata5548cb52013-01-28 23:47:25 +0000250 if ( (m_last_format_mgr_revision != DataVisualization::GetCurrentRevision()))
Enrico Granata4becb372011-06-29 22:27:15 +0000251 {
Enrico Granataa0db6ed2014-04-09 21:06:11 +0000252 m_last_format_mgr_revision = DataVisualization::GetCurrentRevision();
253 any_change = true;
254
Enrico Granata852cc952013-10-08 19:03:22 +0000255 SetValueFormat(DataVisualization::GetFormat (*this, eNoDynamicValues));
Enrico Granata5548cb52013-01-28 23:47:25 +0000256 SetSummaryFormat(DataVisualization::GetSummaryFormat (*this, GetDynamicValueType()));
Jason Molenda7a9a72b2012-05-16 00:38:08 +0000257#ifndef LLDB_DISABLE_PYTHON
Enrico Granata5548cb52013-01-28 23:47:25 +0000258 SetSyntheticChildren(DataVisualization::GetSyntheticChildren (*this, GetDynamicValueType()));
Jason Molenda7a9a72b2012-05-16 00:38:08 +0000259#endif
Enrico Granata744794a2014-09-05 21:46:22 +0000260 SetValidator(DataVisualization::GetValidator(*this, GetDynamicValueType()));
Enrico Granata4becb372011-06-29 22:27:15 +0000261 }
Saleem Abdulrasool324a1032014-04-04 04:06:10 +0000262
Enrico Granata9128ee22011-09-06 19:20:51 +0000263 return any_change;
Enrico Granata4becb372011-06-29 22:27:15 +0000264}
265
Jim Ingham16e0c682011-08-12 23:34:31 +0000266void
267ValueObject::SetNeedsUpdate ()
268{
269 m_update_point.SetNeedsUpdate();
270 // We have to clear the value string here so ConstResult children will notice if their values are
271 // changed by hand (i.e. with SetValueAsCString).
Enrico Granata86cc9822012-03-19 22:58:49 +0000272 ClearUserVisibleData(eClearUserVisibleDataItemsValue);
Jim Ingham16e0c682011-08-12 23:34:31 +0000273}
274
Enrico Granata13ac0e22012-10-17 19:03:34 +0000275void
Enrico Granatae3e91512012-10-22 18:18:36 +0000276ValueObject::ClearDynamicTypeInformation ()
Enrico Granata13ac0e22012-10-17 19:03:34 +0000277{
Enrico Granata38c54632013-10-30 00:04:29 +0000278 m_children_count_valid = false;
Enrico Granata13ac0e22012-10-17 19:03:34 +0000279 m_did_calculate_complete_objc_class_type = false;
Enrico Granatae3e91512012-10-22 18:18:36 +0000280 m_last_format_mgr_revision = 0;
Enrico Granata13ac0e22012-10-17 19:03:34 +0000281 m_override_type = ClangASTType();
Enrico Granatae3e91512012-10-22 18:18:36 +0000282 SetValueFormat(lldb::TypeFormatImplSP());
283 SetSummaryFormat(lldb::TypeSummaryImplSP());
284 SetSyntheticChildren(lldb::SyntheticChildrenSP());
Enrico Granata13ac0e22012-10-17 19:03:34 +0000285}
286
Sean Callanan72772842012-02-22 23:57:45 +0000287ClangASTType
288ValueObject::MaybeCalculateCompleteType ()
289{
Greg Clayton57ee3062013-07-11 22:46:58 +0000290 ClangASTType clang_type(GetClangTypeImpl());
Sean Callanan356e17c2012-03-30 02:04:38 +0000291
Sean Callanan72772842012-02-22 23:57:45 +0000292 if (m_did_calculate_complete_objc_class_type)
293 {
294 if (m_override_type.IsValid())
295 return m_override_type;
296 else
Greg Clayton57ee3062013-07-11 22:46:58 +0000297 return clang_type;
Sean Callanan72772842012-02-22 23:57:45 +0000298 }
299
Greg Clayton57ee3062013-07-11 22:46:58 +0000300 ClangASTType class_type;
301 bool is_pointer_type = false;
Sean Callanan72772842012-02-22 23:57:45 +0000302
Greg Clayton57ee3062013-07-11 22:46:58 +0000303 if (clang_type.IsObjCObjectPointerType(&class_type))
Sean Callanan72772842012-02-22 23:57:45 +0000304 {
305 is_pointer_type = true;
306 }
Greg Clayton57ee3062013-07-11 22:46:58 +0000307 else if (clang_type.IsObjCObjectOrInterfaceType())
Sean Callanan72772842012-02-22 23:57:45 +0000308 {
Greg Clayton57ee3062013-07-11 22:46:58 +0000309 class_type = clang_type;
Sean Callanan72772842012-02-22 23:57:45 +0000310 }
311 else
312 {
Greg Clayton57ee3062013-07-11 22:46:58 +0000313 return clang_type;
Sean Callanan72772842012-02-22 23:57:45 +0000314 }
315
316 m_did_calculate_complete_objc_class_type = true;
317
Greg Clayton57ee3062013-07-11 22:46:58 +0000318 if (class_type)
Sean Callanan72772842012-02-22 23:57:45 +0000319 {
Greg Clayton57ee3062013-07-11 22:46:58 +0000320 ConstString class_name (class_type.GetConstTypeName());
Sean Callanan72772842012-02-22 23:57:45 +0000321
Greg Clayton57ee3062013-07-11 22:46:58 +0000322 if (class_name)
323 {
324 ProcessSP process_sp(GetUpdatePoint().GetExecutionContextRef().GetProcessSP());
325
326 if (process_sp)
327 {
328 ObjCLanguageRuntime *objc_language_runtime(process_sp->GetObjCLanguageRuntime());
329
330 if (objc_language_runtime)
331 {
332 TypeSP complete_objc_class_type_sp = objc_language_runtime->LookupInCompleteClassCache(class_name);
333
334 if (complete_objc_class_type_sp)
335 {
336 ClangASTType complete_class(complete_objc_class_type_sp->GetClangFullType());
337
338 if (complete_class.GetCompleteType())
339 {
340 if (is_pointer_type)
341 {
342 m_override_type = complete_class.GetPointerType();
343 }
344 else
345 {
346 m_override_type = complete_class;
347 }
348
349 if (m_override_type.IsValid())
350 return m_override_type;
351 }
352 }
353 }
354 }
355 }
Sean Callanan72772842012-02-22 23:57:45 +0000356 }
Greg Clayton57ee3062013-07-11 22:46:58 +0000357 return clang_type;
Sean Callanan72772842012-02-22 23:57:45 +0000358}
359
Greg Clayton57ee3062013-07-11 22:46:58 +0000360ClangASTType
Sean Callanan72772842012-02-22 23:57:45 +0000361ValueObject::GetClangType ()
362{
Greg Clayton57ee3062013-07-11 22:46:58 +0000363 return MaybeCalculateCompleteType();
Sean Callanan72772842012-02-22 23:57:45 +0000364}
365
Enrico Granatadc4db5a2013-10-29 00:28:35 +0000366TypeImpl
367ValueObject::GetTypeImpl ()
368{
369 return TypeImpl(GetClangType());
370}
371
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000372DataExtractor &
373ValueObject::GetDataExtractor ()
374{
Enrico Granatac3e320a2011-08-02 17:27:39 +0000375 UpdateValueIfNeeded(false);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000376 return m_data;
377}
378
379const Error &
Greg Clayton262f80d2011-07-06 16:49:27 +0000380ValueObject::GetError()
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000381{
Enrico Granatac3e320a2011-08-02 17:27:39 +0000382 UpdateValueIfNeeded(false);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000383 return m_error;
384}
385
386const ConstString &
387ValueObject::GetName() const
388{
389 return m_name;
390}
391
392const char *
Jim Ingham6035b672011-03-31 00:19:25 +0000393ValueObject::GetLocationAsCString ()
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000394{
Enrico Granata82fabf82013-04-30 20:45:04 +0000395 return GetLocationAsCStringImpl(m_value,
396 m_data);
397}
398
399const char *
400ValueObject::GetLocationAsCStringImpl (const Value& value,
401 const DataExtractor& data)
402{
Enrico Granatac3e320a2011-08-02 17:27:39 +0000403 if (UpdateValueIfNeeded(false))
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000404 {
405 if (m_location_str.empty())
406 {
407 StreamString sstr;
Enrico Granata82fabf82013-04-30 20:45:04 +0000408
409 Value::ValueType value_type = value.GetValueType();
410
411 switch (value_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000412 {
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000413 case Value::eValueTypeScalar:
Greg Clayton0665a0f2012-10-30 18:18:43 +0000414 case Value::eValueTypeVector:
Enrico Granata82fabf82013-04-30 20:45:04 +0000415 if (value.GetContextType() == Value::eContextTypeRegisterInfo)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000416 {
Enrico Granata82fabf82013-04-30 20:45:04 +0000417 RegisterInfo *reg_info = value.GetRegisterInfo();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000418 if (reg_info)
419 {
420 if (reg_info->name)
421 m_location_str = reg_info->name;
422 else if (reg_info->alt_name)
423 m_location_str = reg_info->alt_name;
Enrico Granata82fabf82013-04-30 20:45:04 +0000424 if (m_location_str.empty())
425 m_location_str = (reg_info->encoding == lldb::eEncodingVector) ? "vector" : "scalar";
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000426 }
427 }
Enrico Granata82fabf82013-04-30 20:45:04 +0000428 if (m_location_str.empty())
429 m_location_str = (value_type == Value::eValueTypeVector) ? "vector" : "scalar";
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000430 break;
431
432 case Value::eValueTypeLoadAddress:
433 case Value::eValueTypeFileAddress:
434 case Value::eValueTypeHostAddress:
435 {
Enrico Granata82fabf82013-04-30 20:45:04 +0000436 uint32_t addr_nibble_size = data.GetAddressByteSize() * 2;
437 sstr.Printf("0x%*.*llx", addr_nibble_size, addr_nibble_size, value.GetScalar().ULongLong(LLDB_INVALID_ADDRESS));
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000438 m_location_str.swap(sstr.GetString());
439 }
440 break;
441 }
442 }
443 }
444 return m_location_str.c_str();
445}
446
447Value &
448ValueObject::GetValue()
449{
450 return m_value;
451}
452
453const Value &
454ValueObject::GetValue() const
455{
456 return m_value;
457}
458
459bool
Jim Ingham6035b672011-03-31 00:19:25 +0000460ValueObject::ResolveValue (Scalar &scalar)
Greg Clayton8f343b02010-11-04 01:54:29 +0000461{
Enrico Granata6fd87d52011-08-04 01:41:02 +0000462 if (UpdateValueIfNeeded(false)) // make sure that you are up to date before returning anything
463 {
Greg Claytoncc4d0142012-02-17 07:49:44 +0000464 ExecutionContext exe_ctx (GetExecutionContextRef());
Jim Ingham16e0c682011-08-12 23:34:31 +0000465 Value tmp_value(m_value);
Greg Clayton57ee3062013-07-11 22:46:58 +0000466 scalar = tmp_value.ResolveValue(&exe_ctx);
Greg Claytondcad5022011-12-29 01:26:56 +0000467 if (scalar.IsValid())
468 {
469 const uint32_t bitfield_bit_size = GetBitfieldBitSize();
470 if (bitfield_bit_size)
471 return scalar.ExtractBitfield (bitfield_bit_size, GetBitfieldBitOffset());
472 return true;
473 }
Enrico Granata6fd87d52011-08-04 01:41:02 +0000474 }
Greg Claytondcad5022011-12-29 01:26:56 +0000475 return false;
Greg Clayton8f343b02010-11-04 01:54:29 +0000476}
477
478bool
Greg Clayton288bdf92010-09-02 02:59:18 +0000479ValueObject::GetValueIsValid () const
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000480{
Greg Clayton288bdf92010-09-02 02:59:18 +0000481 return m_value_is_valid;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000482}
483
484
485void
486ValueObject::SetValueIsValid (bool b)
487{
Greg Clayton288bdf92010-09-02 02:59:18 +0000488 m_value_is_valid = b;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000489}
490
491bool
Jim Ingham6035b672011-03-31 00:19:25 +0000492ValueObject::GetValueDidChange ()
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000493{
Jim Ingham6035b672011-03-31 00:19:25 +0000494 GetValueAsCString ();
Greg Clayton288bdf92010-09-02 02:59:18 +0000495 return m_value_did_change;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000496}
497
498void
499ValueObject::SetValueDidChange (bool value_changed)
500{
Greg Clayton288bdf92010-09-02 02:59:18 +0000501 m_value_did_change = value_changed;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000502}
503
504ValueObjectSP
Greg Claytonc7bece562013-01-25 18:06:21 +0000505ValueObject::GetChildAtIndex (size_t idx, bool can_create)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000506{
507 ValueObjectSP child_sp;
Greg Claytondea8cb42011-06-29 22:09:02 +0000508 // We may need to update our value if we are dynamic
509 if (IsPossibleDynamicType ())
Enrico Granatac3e320a2011-08-02 17:27:39 +0000510 UpdateValueIfNeeded(false);
Greg Claytondea8cb42011-06-29 22:09:02 +0000511 if (idx < GetNumChildren())
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000512 {
Greg Claytondea8cb42011-06-29 22:09:02 +0000513 // Check if we have already made the child value object?
Enrico Granata9d60f602012-03-09 03:09:58 +0000514 if (can_create && !m_children.HasChildAtIndex(idx))
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000515 {
Greg Claytondea8cb42011-06-29 22:09:02 +0000516 // No we haven't created the child at this index, so lets have our
517 // subclass do it and cache the result for quick future access.
Enrico Granata9d60f602012-03-09 03:09:58 +0000518 m_children.SetChildAtIndex(idx,CreateChildAtIndex (idx, false, 0));
Jim Ingham78a685a2011-04-16 00:01:13 +0000519 }
Greg Claytondea8cb42011-06-29 22:09:02 +0000520
Enrico Granata9d60f602012-03-09 03:09:58 +0000521 ValueObject* child = m_children.GetChildAtIndex(idx);
522 if (child != NULL)
523 return child->GetSP();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000524 }
525 return child_sp;
526}
527
Enrico Granata3309d882013-01-12 01:00:22 +0000528ValueObjectSP
Greg Claytonc7bece562013-01-25 18:06:21 +0000529ValueObject::GetChildAtIndexPath (const std::initializer_list<size_t>& idxs,
530 size_t* index_of_error)
Enrico Granata3309d882013-01-12 01:00:22 +0000531{
532 if (idxs.size() == 0)
533 return GetSP();
534 ValueObjectSP root(GetSP());
Greg Claytonc7bece562013-01-25 18:06:21 +0000535 for (size_t idx : idxs)
Enrico Granata3309d882013-01-12 01:00:22 +0000536 {
537 root = root->GetChildAtIndex(idx, true);
538 if (!root)
539 {
540 if (index_of_error)
541 *index_of_error = idx;
542 return root;
543 }
544 }
545 return root;
546}
547
548ValueObjectSP
Greg Claytonc7bece562013-01-25 18:06:21 +0000549ValueObject::GetChildAtIndexPath (const std::initializer_list< std::pair<size_t, bool> >& idxs,
550 size_t* index_of_error)
Enrico Granata3309d882013-01-12 01:00:22 +0000551{
552 if (idxs.size() == 0)
553 return GetSP();
554 ValueObjectSP root(GetSP());
Greg Claytonc7bece562013-01-25 18:06:21 +0000555 for (std::pair<size_t, bool> idx : idxs)
Enrico Granata3309d882013-01-12 01:00:22 +0000556 {
557 root = root->GetChildAtIndex(idx.first, idx.second);
558 if (!root)
559 {
560 if (index_of_error)
561 *index_of_error = idx.first;
562 return root;
563 }
564 }
565 return root;
566}
567
568lldb::ValueObjectSP
Greg Claytonc7bece562013-01-25 18:06:21 +0000569ValueObject::GetChildAtIndexPath (const std::vector<size_t> &idxs,
570 size_t* index_of_error)
Enrico Granata3309d882013-01-12 01:00:22 +0000571{
572 if (idxs.size() == 0)
573 return GetSP();
574 ValueObjectSP root(GetSP());
Greg Claytonc7bece562013-01-25 18:06:21 +0000575 for (size_t idx : idxs)
Enrico Granata3309d882013-01-12 01:00:22 +0000576 {
577 root = root->GetChildAtIndex(idx, true);
578 if (!root)
579 {
580 if (index_of_error)
581 *index_of_error = idx;
582 return root;
583 }
584 }
585 return root;
586}
587
588lldb::ValueObjectSP
Greg Claytonc7bece562013-01-25 18:06:21 +0000589ValueObject::GetChildAtIndexPath (const std::vector< std::pair<size_t, bool> > &idxs,
590 size_t* index_of_error)
Enrico Granata3309d882013-01-12 01:00:22 +0000591{
592 if (idxs.size() == 0)
593 return GetSP();
594 ValueObjectSP root(GetSP());
Greg Claytonc7bece562013-01-25 18:06:21 +0000595 for (std::pair<size_t, bool> idx : idxs)
Enrico Granata3309d882013-01-12 01:00:22 +0000596 {
597 root = root->GetChildAtIndex(idx.first, idx.second);
598 if (!root)
599 {
600 if (index_of_error)
601 *index_of_error = idx.first;
602 return root;
603 }
604 }
605 return root;
606}
607
Enrico Granatae2e220a2013-09-12 00:48:47 +0000608lldb::ValueObjectSP
609ValueObject::GetChildAtNamePath (const std::initializer_list<ConstString> &names,
610 ConstString* name_of_error)
611{
612 if (names.size() == 0)
613 return GetSP();
614 ValueObjectSP root(GetSP());
615 for (ConstString name : names)
616 {
617 root = root->GetChildMemberWithName(name, true);
618 if (!root)
619 {
620 if (name_of_error)
621 *name_of_error = name;
622 return root;
623 }
624 }
625 return root;
626}
627
628lldb::ValueObjectSP
629ValueObject::GetChildAtNamePath (const std::vector<ConstString> &names,
630 ConstString* name_of_error)
631{
632 if (names.size() == 0)
633 return GetSP();
634 ValueObjectSP root(GetSP());
635 for (ConstString name : names)
636 {
637 root = root->GetChildMemberWithName(name, true);
638 if (!root)
639 {
640 if (name_of_error)
641 *name_of_error = name;
642 return root;
643 }
644 }
645 return root;
646}
647
648lldb::ValueObjectSP
649ValueObject::GetChildAtNamePath (const std::initializer_list< std::pair<ConstString, bool> > &names,
650 ConstString* name_of_error)
651{
652 if (names.size() == 0)
653 return GetSP();
654 ValueObjectSP root(GetSP());
655 for (std::pair<ConstString, bool> name : names)
656 {
657 root = root->GetChildMemberWithName(name.first, name.second);
658 if (!root)
659 {
660 if (name_of_error)
661 *name_of_error = name.first;
662 return root;
663 }
664 }
665 return root;
666}
667
668lldb::ValueObjectSP
669ValueObject::GetChildAtNamePath (const std::vector< std::pair<ConstString, bool> > &names,
670 ConstString* name_of_error)
671{
672 if (names.size() == 0)
673 return GetSP();
674 ValueObjectSP root(GetSP());
675 for (std::pair<ConstString, bool> name : names)
676 {
677 root = root->GetChildMemberWithName(name.first, name.second);
678 if (!root)
679 {
680 if (name_of_error)
681 *name_of_error = name.first;
682 return root;
683 }
684 }
685 return root;
686}
687
Greg Claytonc7bece562013-01-25 18:06:21 +0000688size_t
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000689ValueObject::GetIndexOfChildWithName (const ConstString &name)
690{
691 bool omit_empty_base_classes = true;
Greg Clayton57ee3062013-07-11 22:46:58 +0000692 return GetClangType().GetIndexOfChildWithName (name.GetCString(), omit_empty_base_classes);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000693}
694
695ValueObjectSP
696ValueObject::GetChildMemberWithName (const ConstString &name, bool can_create)
697{
Greg Clayton710dd5a2011-01-08 20:28:42 +0000698 // when getting a child by name, it could be buried inside some base
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000699 // classes (which really aren't part of the expression path), so we
700 // need a vector of indexes that can get us down to the correct child
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000701 ValueObjectSP child_sp;
Jim Ingham78a685a2011-04-16 00:01:13 +0000702
Greg Claytondea8cb42011-06-29 22:09:02 +0000703 // We may need to update our value if we are dynamic
704 if (IsPossibleDynamicType ())
Enrico Granatac3e320a2011-08-02 17:27:39 +0000705 UpdateValueIfNeeded(false);
Greg Claytondea8cb42011-06-29 22:09:02 +0000706
707 std::vector<uint32_t> child_indexes;
Greg Claytondea8cb42011-06-29 22:09:02 +0000708 bool omit_empty_base_classes = true;
Greg Clayton57ee3062013-07-11 22:46:58 +0000709 const size_t num_child_indexes = GetClangType().GetIndexOfChildMemberWithName (name.GetCString(),
710 omit_empty_base_classes,
711 child_indexes);
Greg Claytondea8cb42011-06-29 22:09:02 +0000712 if (num_child_indexes > 0)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000713 {
Greg Claytondea8cb42011-06-29 22:09:02 +0000714 std::vector<uint32_t>::const_iterator pos = child_indexes.begin ();
715 std::vector<uint32_t>::const_iterator end = child_indexes.end ();
716
717 child_sp = GetChildAtIndex(*pos, can_create);
718 for (++pos; pos != end; ++pos)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000719 {
Greg Claytondea8cb42011-06-29 22:09:02 +0000720 if (child_sp)
Jim Ingham78a685a2011-04-16 00:01:13 +0000721 {
Greg Claytondea8cb42011-06-29 22:09:02 +0000722 ValueObjectSP new_child_sp(child_sp->GetChildAtIndex (*pos, can_create));
723 child_sp = new_child_sp;
Jim Ingham78a685a2011-04-16 00:01:13 +0000724 }
Greg Claytondea8cb42011-06-29 22:09:02 +0000725 else
726 {
727 child_sp.reset();
728 }
729
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000730 }
731 }
732 return child_sp;
733}
734
735
Greg Claytonc7bece562013-01-25 18:06:21 +0000736size_t
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000737ValueObject::GetNumChildren ()
738{
Enrico Granatac5bc4122012-03-27 02:35:13 +0000739 UpdateValueIfNeeded();
Greg Clayton288bdf92010-09-02 02:59:18 +0000740 if (!m_children_count_valid)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000741 {
742 SetNumChildren (CalculateNumChildren());
743 }
Enrico Granata9d60f602012-03-09 03:09:58 +0000744 return m_children.GetChildrenCount();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000745}
Greg Clayton4a792072012-10-23 01:50:10 +0000746
747bool
748ValueObject::MightHaveChildren()
749{
Enrico Granatadb8142b2012-10-23 02:07:54 +0000750 bool has_children = false;
Greg Clayton2452ab72013-02-08 22:02:02 +0000751 const uint32_t type_info = GetTypeInfo();
752 if (type_info)
Greg Clayton4a792072012-10-23 01:50:10 +0000753 {
Enrico Granata622be232014-10-21 20:52:14 +0000754 if (type_info & (eTypeHasChildren |
755 eTypeIsPointer |
756 eTypeIsReference))
Greg Clayton4a792072012-10-23 01:50:10 +0000757 has_children = true;
758 }
759 else
760 {
761 has_children = GetNumChildren () > 0;
762 }
763 return has_children;
764}
765
766// Should only be called by ValueObject::GetNumChildren()
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000767void
Greg Claytonc7bece562013-01-25 18:06:21 +0000768ValueObject::SetNumChildren (size_t num_children)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000769{
Greg Clayton288bdf92010-09-02 02:59:18 +0000770 m_children_count_valid = true;
Enrico Granata9d60f602012-03-09 03:09:58 +0000771 m_children.SetChildrenCount(num_children);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000772}
773
774void
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000775ValueObject::SetName (const ConstString &name)
776{
777 m_name = name;
778}
779
Jim Ingham58b59f92011-04-22 23:53:53 +0000780ValueObject *
Greg Claytonc7bece562013-01-25 18:06:21 +0000781ValueObject::CreateChildAtIndex (size_t idx, bool synthetic_array_member, int32_t synthetic_index)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000782{
Jim Ingham2eec4872011-05-07 00:10:58 +0000783 ValueObject *valobj = NULL;
Jim Ingham78a685a2011-04-16 00:01:13 +0000784
Greg Claytondea8cb42011-06-29 22:09:02 +0000785 bool omit_empty_base_classes = true;
Greg Claytondaf515f2011-07-09 20:12:33 +0000786 bool ignore_array_bounds = synthetic_array_member;
Greg Claytondea8cb42011-06-29 22:09:02 +0000787 std::string child_name_str;
788 uint32_t child_byte_size = 0;
789 int32_t child_byte_offset = 0;
790 uint32_t child_bitfield_bit_size = 0;
791 uint32_t child_bitfield_bit_offset = 0;
792 bool child_is_base_class = false;
793 bool child_is_deref_of_parent = false;
794
795 const bool transparent_pointers = synthetic_array_member == false;
Greg Clayton57ee3062013-07-11 22:46:58 +0000796 ClangASTType child_clang_type;
Greg Claytondea8cb42011-06-29 22:09:02 +0000797
Greg Claytoncc4d0142012-02-17 07:49:44 +0000798 ExecutionContext exe_ctx (GetExecutionContextRef());
Greg Claytondea8cb42011-06-29 22:09:02 +0000799
Greg Clayton57ee3062013-07-11 22:46:58 +0000800 child_clang_type = GetClangType().GetChildClangTypeAtIndex (&exe_ctx,
Greg Clayton57ee3062013-07-11 22:46:58 +0000801 idx,
802 transparent_pointers,
803 omit_empty_base_classes,
804 ignore_array_bounds,
805 child_name_str,
806 child_byte_size,
807 child_byte_offset,
808 child_bitfield_bit_size,
809 child_bitfield_bit_offset,
810 child_is_base_class,
Greg Clayton759e7442014-07-19 00:12:57 +0000811 child_is_deref_of_parent,
812 this);
Greg Clayton4ef877f2012-12-06 02:33:54 +0000813 if (child_clang_type)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000814 {
Greg Claytondea8cb42011-06-29 22:09:02 +0000815 if (synthetic_index)
816 child_byte_offset += child_byte_size * synthetic_index;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000817
Greg Claytondea8cb42011-06-29 22:09:02 +0000818 ConstString child_name;
819 if (!child_name_str.empty())
820 child_name.SetCString (child_name_str.c_str());
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000821
Greg Claytondea8cb42011-06-29 22:09:02 +0000822 valobj = new ValueObjectChild (*this,
Greg Claytondea8cb42011-06-29 22:09:02 +0000823 child_clang_type,
824 child_name,
825 child_byte_size,
826 child_byte_offset,
827 child_bitfield_bit_size,
828 child_bitfield_bit_offset,
829 child_is_base_class,
Enrico Granata9128ee22011-09-06 19:20:51 +0000830 child_is_deref_of_parent,
831 eAddressTypeInvalid);
832 //if (valobj)
833 // valobj->SetAddressTypeOfChildren(eAddressTypeInvalid);
834 }
Jim Ingham78a685a2011-04-16 00:01:13 +0000835
Jim Ingham58b59f92011-04-22 23:53:53 +0000836 return valobj;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000837}
838
Enrico Granata0c489f52012-03-01 04:24:26 +0000839bool
840ValueObject::GetSummaryAsCString (TypeSummaryImpl* summary_ptr,
841 std::string& destination)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000842{
Enrico Granata0c489f52012-03-01 04:24:26 +0000843 destination.clear();
844
845 // ideally we would like to bail out if passing NULL, but if we do so
846 // we end up not providing the summary for function pointers anymore
847 if (/*summary_ptr == NULL ||*/ m_is_getting_summary)
848 return false;
Greg Clayton48ca8b82012-01-07 20:58:07 +0000849
850 m_is_getting_summary = true;
Enrico Granataf18c03e2012-04-04 17:34:10 +0000851
852 // this is a hot path in code and we prefer to avoid setting this string all too often also clearing out other
853 // information that we might care to see in a crash log. might be useful in very specific situations though.
854 /*Host::SetCrashDescriptionWithFormat("Trying to fetch a summary for %s %s. Summary provider's description is %s",
855 GetTypeName().GetCString(),
856 GetName().GetCString(),
857 summary_ptr->GetDescription().c_str());*/
858
Enrico Granata0c489f52012-03-01 04:24:26 +0000859 if (UpdateValueIfNeeded (false))
860 {
861 if (summary_ptr)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000862 {
Enrico Granata86cc9822012-03-19 22:58:49 +0000863 if (HasSyntheticValue())
864 m_synthetic_value->UpdateValueIfNeeded(); // the summary might depend on the synthetic children being up-to-date (e.g. ${svar%#})
865 summary_ptr->FormatObject(this, destination);
Enrico Granata0c489f52012-03-01 04:24:26 +0000866 }
867 else
868 {
Greg Clayton57ee3062013-07-11 22:46:58 +0000869 ClangASTType clang_type = GetClangType();
Enrico Granata0c489f52012-03-01 04:24:26 +0000870
871 // Do some default printout for function pointers
872 if (clang_type)
Enrico Granata4becb372011-06-29 22:27:15 +0000873 {
Greg Clayton57ee3062013-07-11 22:46:58 +0000874 if (clang_type.IsFunctionPointerType ())
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000875 {
Greg Clayton57ee3062013-07-11 22:46:58 +0000876 StreamString sstr;
Enrico Granata0c489f52012-03-01 04:24:26 +0000877 AddressType func_ptr_address_type = eAddressTypeInvalid;
878 addr_t func_ptr_address = GetPointerValue (&func_ptr_address_type);
879 if (func_ptr_address != 0 && func_ptr_address != LLDB_INVALID_ADDRESS)
Enrico Granataf2bbf712011-07-15 02:26:42 +0000880 {
Enrico Granata0c489f52012-03-01 04:24:26 +0000881 switch (func_ptr_address_type)
Jim Ingham6035b672011-03-31 00:19:25 +0000882 {
Greg Claytoncc4d0142012-02-17 07:49:44 +0000883 case eAddressTypeInvalid:
884 case eAddressTypeFile:
885 break;
Enrico Granata0c489f52012-03-01 04:24:26 +0000886
Greg Claytoncc4d0142012-02-17 07:49:44 +0000887 case eAddressTypeLoad:
Enrico Granata0c489f52012-03-01 04:24:26 +0000888 {
889 ExecutionContext exe_ctx (GetExecutionContextRef());
890
891 Address so_addr;
892 Target *target = exe_ctx.GetTargetPtr();
893 if (target && target->GetSectionLoadList().IsEmpty() == false)
Greg Claytoncc4d0142012-02-17 07:49:44 +0000894 {
Enrico Granata0c489f52012-03-01 04:24:26 +0000895 if (target->GetSectionLoadList().ResolveLoadAddress(func_ptr_address, so_addr))
Enrico Granataf2bbf712011-07-15 02:26:42 +0000896 {
Enrico Granata0c489f52012-03-01 04:24:26 +0000897 so_addr.Dump (&sstr,
898 exe_ctx.GetBestExecutionContextScope(),
899 Address::DumpStyleResolvedDescription,
900 Address::DumpStyleSectionNameOffset);
Enrico Granataf2bbf712011-07-15 02:26:42 +0000901 }
Enrico Granataf2bbf712011-07-15 02:26:42 +0000902 }
Enrico Granata0c489f52012-03-01 04:24:26 +0000903 }
Greg Claytoncc4d0142012-02-17 07:49:44 +0000904 break;
Enrico Granata0c489f52012-03-01 04:24:26 +0000905
Greg Claytoncc4d0142012-02-17 07:49:44 +0000906 case eAddressTypeHost:
907 break;
Greg Claytoncc4d0142012-02-17 07:49:44 +0000908 }
Enrico Granata0c489f52012-03-01 04:24:26 +0000909 }
910 if (sstr.GetSize() > 0)
911 {
912 destination.assign (1, '(');
913 destination.append (sstr.GetData(), sstr.GetSize());
914 destination.append (1, ')');
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000915 }
916 }
917 }
918 }
919 }
Greg Clayton48ca8b82012-01-07 20:58:07 +0000920 m_is_getting_summary = false;
Enrico Granata0c489f52012-03-01 04:24:26 +0000921 return !destination.empty();
922}
923
924const char *
925ValueObject::GetSummaryAsCString ()
926{
927 if (UpdateValueIfNeeded(true) && m_summary_str.empty())
928 {
929 GetSummaryAsCString(GetSummaryFormat().get(),
930 m_summary_str);
931 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000932 if (m_summary_str.empty())
933 return NULL;
934 return m_summary_str.c_str();
935}
936
Enrico Granataf9fa6ee2011-07-12 00:18:11 +0000937bool
938ValueObject::IsCStringContainer(bool check_pointer)
939{
Greg Clayton57ee3062013-07-11 22:46:58 +0000940 ClangASTType pointee_or_element_clang_type;
941 const Flags type_flags (GetTypeInfo (&pointee_or_element_clang_type));
Enrico Granata622be232014-10-21 20:52:14 +0000942 bool is_char_arr_ptr (type_flags.AnySet (eTypeIsArray | eTypeIsPointer) &&
Greg Clayton57ee3062013-07-11 22:46:58 +0000943 pointee_or_element_clang_type.IsCharType ());
Enrico Granataf9fa6ee2011-07-12 00:18:11 +0000944 if (!is_char_arr_ptr)
945 return false;
946 if (!check_pointer)
947 return true;
Enrico Granata622be232014-10-21 20:52:14 +0000948 if (type_flags.Test(eTypeIsArray))
Enrico Granataf9fa6ee2011-07-12 00:18:11 +0000949 return true;
Greg Claytonafacd142011-09-02 01:15:17 +0000950 addr_t cstr_address = LLDB_INVALID_ADDRESS;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +0000951 AddressType cstr_address_type = eAddressTypeInvalid;
Enrico Granata9128ee22011-09-06 19:20:51 +0000952 cstr_address = GetAddressOf (true, &cstr_address_type);
Enrico Granataf9fa6ee2011-07-12 00:18:11 +0000953 return (cstr_address != LLDB_INVALID_ADDRESS);
954}
955
Enrico Granata9128ee22011-09-06 19:20:51 +0000956size_t
957ValueObject::GetPointeeData (DataExtractor& data,
958 uint32_t item_idx,
959 uint32_t item_count)
960{
Greg Clayton57ee3062013-07-11 22:46:58 +0000961 ClangASTType pointee_or_element_clang_type;
Greg Clayton2452ab72013-02-08 22:02:02 +0000962 const uint32_t type_info = GetTypeInfo (&pointee_or_element_clang_type);
Enrico Granata622be232014-10-21 20:52:14 +0000963 const bool is_pointer_type = type_info & eTypeIsPointer;
964 const bool is_array_type = type_info & eTypeIsArray;
Greg Clayton2452ab72013-02-08 22:02:02 +0000965 if (!(is_pointer_type || is_array_type))
Enrico Granata9128ee22011-09-06 19:20:51 +0000966 return 0;
967
968 if (item_count == 0)
969 return 0;
970
Greg Clayton57ee3062013-07-11 22:46:58 +0000971 const uint64_t item_type_size = pointee_or_element_clang_type.GetByteSize();
Enrico Granata9128ee22011-09-06 19:20:51 +0000972 const uint64_t bytes = item_count * item_type_size;
Enrico Granata9128ee22011-09-06 19:20:51 +0000973 const uint64_t offset = item_idx * item_type_size;
974
975 if (item_idx == 0 && item_count == 1) // simply a deref
976 {
Greg Clayton2452ab72013-02-08 22:02:02 +0000977 if (is_pointer_type)
Enrico Granata9128ee22011-09-06 19:20:51 +0000978 {
979 Error error;
980 ValueObjectSP pointee_sp = Dereference(error);
981 if (error.Fail() || pointee_sp.get() == NULL)
982 return 0;
Sean Callanan866e91c2014-02-28 22:27:53 +0000983 return pointee_sp->GetData(data, error);
Enrico Granata9128ee22011-09-06 19:20:51 +0000984 }
985 else
986 {
987 ValueObjectSP child_sp = GetChildAtIndex(0, true);
988 if (child_sp.get() == NULL)
989 return 0;
Sean Callanan866e91c2014-02-28 22:27:53 +0000990 Error error;
991 return child_sp->GetData(data, error);
Enrico Granata9128ee22011-09-06 19:20:51 +0000992 }
993 return true;
994 }
995 else /* (items > 1) */
996 {
997 Error error;
998 lldb_private::DataBufferHeap* heap_buf_ptr = NULL;
999 lldb::DataBufferSP data_sp(heap_buf_ptr = new lldb_private::DataBufferHeap());
1000
1001 AddressType addr_type;
Greg Clayton2452ab72013-02-08 22:02:02 +00001002 lldb::addr_t addr = is_pointer_type ? GetPointerValue(&addr_type) : GetAddressOf(true, &addr_type);
Enrico Granata9128ee22011-09-06 19:20:51 +00001003
Enrico Granata9128ee22011-09-06 19:20:51 +00001004 switch (addr_type)
1005 {
1006 case eAddressTypeFile:
1007 {
Greg Claytone72dfb32012-02-24 01:59:29 +00001008 ModuleSP module_sp (GetModule());
1009 if (module_sp)
Enrico Granata9128ee22011-09-06 19:20:51 +00001010 {
Enrico Granata9c2efe32012-08-07 01:49:34 +00001011 addr = addr + offset;
Enrico Granata9128ee22011-09-06 19:20:51 +00001012 Address so_addr;
Greg Claytone72dfb32012-02-24 01:59:29 +00001013 module_sp->ResolveFileAddress(addr, so_addr);
Greg Claytoncc4d0142012-02-17 07:49:44 +00001014 ExecutionContext exe_ctx (GetExecutionContextRef());
1015 Target* target = exe_ctx.GetTargetPtr();
1016 if (target)
Enrico Granata9128ee22011-09-06 19:20:51 +00001017 {
Greg Claytoncc4d0142012-02-17 07:49:44 +00001018 heap_buf_ptr->SetByteSize(bytes);
1019 size_t bytes_read = target->ReadMemory(so_addr, false, heap_buf_ptr->GetBytes(), bytes, error);
1020 if (error.Success())
Enrico Granata9128ee22011-09-06 19:20:51 +00001021 {
Greg Claytoncc4d0142012-02-17 07:49:44 +00001022 data.SetData(data_sp);
1023 return bytes_read;
Enrico Granata9128ee22011-09-06 19:20:51 +00001024 }
1025 }
1026 }
1027 }
1028 break;
1029 case eAddressTypeLoad:
Enrico Granata9128ee22011-09-06 19:20:51 +00001030 {
Greg Claytoncc4d0142012-02-17 07:49:44 +00001031 ExecutionContext exe_ctx (GetExecutionContextRef());
1032 Process *process = exe_ctx.GetProcessPtr();
Enrico Granata9128ee22011-09-06 19:20:51 +00001033 if (process)
1034 {
1035 heap_buf_ptr->SetByteSize(bytes);
1036 size_t bytes_read = process->ReadMemory(addr + offset, heap_buf_ptr->GetBytes(), bytes, error);
Enrico Granata5e1480c2013-10-30 17:52:44 +00001037 if (error.Success() || bytes_read > 0)
Enrico Granata9128ee22011-09-06 19:20:51 +00001038 {
1039 data.SetData(data_sp);
1040 return bytes_read;
1041 }
1042 }
1043 }
1044 break;
1045 case eAddressTypeHost:
1046 {
Greg Clayton57ee3062013-07-11 22:46:58 +00001047 const uint64_t max_bytes = GetClangType().GetByteSize();
Greg Clayton2452ab72013-02-08 22:02:02 +00001048 if (max_bytes > offset)
1049 {
1050 size_t bytes_read = std::min<uint64_t>(max_bytes - offset, bytes);
1051 heap_buf_ptr->CopyData((uint8_t*)(addr + offset), bytes_read);
1052 data.SetData(data_sp);
1053 return bytes_read;
1054 }
Enrico Granata9128ee22011-09-06 19:20:51 +00001055 }
1056 break;
1057 case eAddressTypeInvalid:
Enrico Granata9128ee22011-09-06 19:20:51 +00001058 break;
1059 }
1060 }
1061 return 0;
1062}
1063
Greg Claytonfaac1112013-03-14 18:31:44 +00001064uint64_t
Sean Callanan866e91c2014-02-28 22:27:53 +00001065ValueObject::GetData (DataExtractor& data, Error &error)
Enrico Granata9128ee22011-09-06 19:20:51 +00001066{
1067 UpdateValueIfNeeded(false);
Greg Claytoncc4d0142012-02-17 07:49:44 +00001068 ExecutionContext exe_ctx (GetExecutionContextRef());
Sean Callanan866e91c2014-02-28 22:27:53 +00001069 error = m_value.GetValueAsData(&exe_ctx, data, 0, GetModule().get());
Enrico Granata9128ee22011-09-06 19:20:51 +00001070 if (error.Fail())
Sean Callananed185ab2013-04-19 19:47:32 +00001071 {
1072 if (m_data.GetByteSize())
1073 {
1074 data = m_data;
1075 return data.GetByteSize();
1076 }
1077 else
1078 {
1079 return 0;
1080 }
1081 }
Enrico Granata9128ee22011-09-06 19:20:51 +00001082 data.SetAddressByteSize(m_data.GetAddressByteSize());
1083 data.SetByteOrder(m_data.GetByteOrder());
1084 return data.GetByteSize();
1085}
1086
Sean Callanan389823e2013-04-13 01:21:23 +00001087bool
1088ValueObject::SetData (DataExtractor &data, Error &error)
1089{
1090 error.Clear();
1091 // Make sure our value is up to date first so that our location and location
1092 // type is valid.
1093 if (!UpdateValueIfNeeded(false))
1094 {
1095 error.SetErrorString("unable to read value");
1096 return false;
1097 }
1098
1099 uint64_t count = 0;
Greg Clayton57ee3062013-07-11 22:46:58 +00001100 const Encoding encoding = GetClangType().GetEncoding(count);
Sean Callanan389823e2013-04-13 01:21:23 +00001101
1102 const size_t byte_size = GetByteSize();
1103
1104 Value::ValueType value_type = m_value.GetValueType();
1105
1106 switch (value_type)
1107 {
1108 case Value::eValueTypeScalar:
1109 {
1110 Error set_error = m_value.GetScalar().SetValueFromData(data, encoding, byte_size);
1111
1112 if (!set_error.Success())
1113 {
1114 error.SetErrorStringWithFormat("unable to set scalar value: %s", set_error.AsCString());
1115 return false;
1116 }
1117 }
1118 break;
1119 case Value::eValueTypeLoadAddress:
1120 {
1121 // If it is a load address, then the scalar value is the storage location
1122 // of the data, and we have to shove this value down to that load location.
1123 ExecutionContext exe_ctx (GetExecutionContextRef());
1124 Process *process = exe_ctx.GetProcessPtr();
1125 if (process)
1126 {
1127 addr_t target_addr = m_value.GetScalar().ULongLong(LLDB_INVALID_ADDRESS);
1128 size_t bytes_written = process->WriteMemory(target_addr,
1129 data.GetDataStart(),
1130 byte_size,
1131 error);
1132 if (!error.Success())
1133 return false;
1134 if (bytes_written != byte_size)
1135 {
1136 error.SetErrorString("unable to write value to memory");
1137 return false;
1138 }
1139 }
1140 }
1141 break;
1142 case Value::eValueTypeHostAddress:
1143 {
1144 // If it is a host address, then we stuff the scalar as a DataBuffer into the Value's data.
1145 DataBufferSP buffer_sp (new DataBufferHeap(byte_size, 0));
1146 m_data.SetData(buffer_sp, 0);
1147 data.CopyByteOrderedData (0,
1148 byte_size,
1149 const_cast<uint8_t *>(m_data.GetDataStart()),
1150 byte_size,
1151 m_data.GetByteOrder());
1152 m_value.GetScalar() = (uintptr_t)m_data.GetDataStart();
1153 }
1154 break;
1155 case Value::eValueTypeFileAddress:
1156 case Value::eValueTypeVector:
1157 break;
1158 }
1159
1160 // If we have reached this point, then we have successfully changed the value.
1161 SetNeedsUpdate();
1162 return true;
1163}
1164
Enrico Granata9128ee22011-09-06 19:20:51 +00001165// will compute strlen(str), but without consuming more than
1166// maxlen bytes out of str (this serves the purpose of reading
1167// chunks of a string without having to worry about
1168// missing NULL terminators in the chunk)
1169// of course, if strlen(str) > maxlen, the function will return
1170// maxlen_value (which should be != maxlen, because that allows you
1171// to know whether strlen(str) == maxlen or strlen(str) > maxlen)
1172static uint32_t
1173strlen_or_inf (const char* str,
1174 uint32_t maxlen,
1175 uint32_t maxlen_value)
1176{
1177 uint32_t len = 0;
Greg Clayton8dd5c172011-10-05 22:19:51 +00001178 if (str)
Enrico Granata9128ee22011-09-06 19:20:51 +00001179 {
Greg Clayton8dd5c172011-10-05 22:19:51 +00001180 while(*str)
1181 {
1182 len++;str++;
Greg Clayton2452ab72013-02-08 22:02:02 +00001183 if (len >= maxlen)
Greg Clayton8dd5c172011-10-05 22:19:51 +00001184 return maxlen_value;
1185 }
Enrico Granata9128ee22011-09-06 19:20:51 +00001186 }
1187 return len;
1188}
1189
Enrico Granataea2bc0f2013-02-21 19:57:10 +00001190size_t
Greg Claytoncc4d0142012-02-17 07:49:44 +00001191ValueObject::ReadPointedString (Stream& s,
1192 Error& error,
1193 uint32_t max_length,
1194 bool honor_array,
1195 Format item_format)
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00001196{
Greg Claytoncc4d0142012-02-17 07:49:44 +00001197 ExecutionContext exe_ctx (GetExecutionContextRef());
1198 Target* target = exe_ctx.GetTargetPtr();
1199
Enrico Granata7e0db2a2013-02-28 22:01:33 +00001200 if (!target)
1201 {
1202 s << "<no target to read from>";
1203 error.SetErrorString("no target to read from");
1204 return 0;
1205 }
1206
1207 if (max_length == 0)
Greg Claytoncc4d0142012-02-17 07:49:44 +00001208 max_length = target->GetMaximumSizeOfStringSummary();
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00001209
Enrico Granataea2bc0f2013-02-21 19:57:10 +00001210 size_t bytes_read = 0;
1211 size_t total_bytes_read = 0;
1212
Greg Clayton57ee3062013-07-11 22:46:58 +00001213 ClangASTType clang_type = GetClangType();
1214 ClangASTType elem_or_pointee_clang_type;
Greg Clayton2452ab72013-02-08 22:02:02 +00001215 const Flags type_flags (GetTypeInfo (&elem_or_pointee_clang_type));
Enrico Granata622be232014-10-21 20:52:14 +00001216 if (type_flags.AnySet (eTypeIsArray | eTypeIsPointer) &&
Greg Clayton57ee3062013-07-11 22:46:58 +00001217 elem_or_pointee_clang_type.IsCharType ())
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00001218 {
Enrico Granata7e0db2a2013-02-28 22:01:33 +00001219 addr_t cstr_address = LLDB_INVALID_ADDRESS;
1220 AddressType cstr_address_type = eAddressTypeInvalid;
1221
1222 size_t cstr_len = 0;
1223 bool capped_data = false;
Enrico Granata622be232014-10-21 20:52:14 +00001224 if (type_flags.Test (eTypeIsArray))
Greg Claytoncc4d0142012-02-17 07:49:44 +00001225 {
Enrico Granata7e0db2a2013-02-28 22:01:33 +00001226 // We have an array
Greg Clayton57ee3062013-07-11 22:46:58 +00001227 uint64_t array_size = 0;
1228 if (clang_type.IsArrayType(NULL, &array_size, NULL))
Enrico Granata7e0db2a2013-02-28 22:01:33 +00001229 {
Greg Clayton57ee3062013-07-11 22:46:58 +00001230 cstr_len = array_size;
1231 if (cstr_len > max_length)
1232 {
1233 capped_data = true;
1234 cstr_len = max_length;
1235 }
Enrico Granata7e0db2a2013-02-28 22:01:33 +00001236 }
1237 cstr_address = GetAddressOf (true, &cstr_address_type);
Greg Claytoncc4d0142012-02-17 07:49:44 +00001238 }
1239 else
1240 {
Enrico Granata7e0db2a2013-02-28 22:01:33 +00001241 // We have a pointer
1242 cstr_address = GetPointerValue (&cstr_address_type);
1243 }
1244
1245 if (cstr_address == 0 || cstr_address == LLDB_INVALID_ADDRESS)
1246 {
1247 s << "<invalid address>";
1248 error.SetErrorString("invalid address");
1249 return 0;
1250 }
1251
1252 Address cstr_so_addr (cstr_address);
1253 DataExtractor data;
1254 if (cstr_len > 0 && honor_array)
1255 {
1256 // I am using GetPointeeData() here to abstract the fact that some ValueObjects are actually frozen pointers in the host
1257 // but the pointed-to data lives in the debuggee, and GetPointeeData() automatically takes care of this
1258 GetPointeeData(data, 0, cstr_len);
1259
1260 if ((bytes_read = data.GetByteSize()) > 0)
1261 {
1262 total_bytes_read = bytes_read;
1263 s << '"';
1264 data.Dump (&s,
1265 0, // Start offset in "data"
1266 item_format,
1267 1, // Size of item (1 byte for a char!)
1268 bytes_read, // How many bytes to print?
1269 UINT32_MAX, // num per line
1270 LLDB_INVALID_ADDRESS,// base address
1271 0, // bitfield bit size
1272 0); // bitfield bit offset
1273 if (capped_data)
1274 s << "...";
1275 s << '"';
1276 }
1277 }
1278 else
1279 {
1280 cstr_len = max_length;
1281 const size_t k_max_buf_size = 64;
1282
1283 size_t offset = 0;
Greg Claytoncc4d0142012-02-17 07:49:44 +00001284
Enrico Granata7e0db2a2013-02-28 22:01:33 +00001285 int cstr_len_displayed = -1;
1286 bool capped_cstr = false;
1287 // I am using GetPointeeData() here to abstract the fact that some ValueObjects are actually frozen pointers in the host
1288 // but the pointed-to data lives in the debuggee, and GetPointeeData() automatically takes care of this
1289 while ((bytes_read = GetPointeeData(data, offset, k_max_buf_size)) > 0)
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00001290 {
Enrico Granata7e0db2a2013-02-28 22:01:33 +00001291 total_bytes_read += bytes_read;
1292 const char *cstr = data.PeekCStr(0);
1293 size_t len = strlen_or_inf (cstr, k_max_buf_size, k_max_buf_size+1);
1294 if (len > k_max_buf_size)
1295 len = k_max_buf_size;
1296 if (cstr && cstr_len_displayed < 0)
1297 s << '"';
1298
1299 if (cstr_len_displayed < 0)
1300 cstr_len_displayed = len;
1301
1302 if (len == 0)
1303 break;
1304 cstr_len_displayed += len;
1305 if (len > bytes_read)
1306 len = bytes_read;
1307 if (len > cstr_len)
1308 len = cstr_len;
1309
1310 data.Dump (&s,
1311 0, // Start offset in "data"
1312 item_format,
1313 1, // Size of item (1 byte for a char!)
1314 len, // How many bytes to print?
1315 UINT32_MAX, // num per line
1316 LLDB_INVALID_ADDRESS,// base address
1317 0, // bitfield bit size
1318 0); // bitfield bit offset
1319
1320 if (len < k_max_buf_size)
1321 break;
1322
1323 if (len >= cstr_len)
Enrico Granata6f3533f2011-07-29 19:53:35 +00001324 {
Enrico Granata7e0db2a2013-02-28 22:01:33 +00001325 capped_cstr = true;
1326 break;
Greg Claytoncc4d0142012-02-17 07:49:44 +00001327 }
Enrico Granata7e0db2a2013-02-28 22:01:33 +00001328
1329 cstr_len -= len;
1330 offset += len;
Greg Claytoncc4d0142012-02-17 07:49:44 +00001331 }
Enrico Granata7e0db2a2013-02-28 22:01:33 +00001332
1333 if (cstr_len_displayed >= 0)
Greg Claytoncc4d0142012-02-17 07:49:44 +00001334 {
Enrico Granata7e0db2a2013-02-28 22:01:33 +00001335 s << '"';
1336 if (capped_cstr)
1337 s << "...";
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00001338 }
Greg Claytoncc4d0142012-02-17 07:49:44 +00001339 }
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00001340 }
1341 else
1342 {
Enrico Granata7e0db2a2013-02-28 22:01:33 +00001343 error.SetErrorString("not a string object");
Enrico Granata6f3533f2011-07-29 19:53:35 +00001344 s << "<not a string object>";
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00001345 }
Enrico Granataea2bc0f2013-02-21 19:57:10 +00001346 return total_bytes_read;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00001347}
1348
Enrico Granata744794a2014-09-05 21:46:22 +00001349std::pair<TypeValidatorResult, std::string>
1350ValueObject::GetValidationStatus ()
1351{
1352 if (!UpdateValueIfNeeded(true))
1353 return {TypeValidatorResult::Success,""}; // not the validator's job to discuss update problems
1354
1355 if (m_validation_result.hasValue())
1356 return m_validation_result.getValue();
1357
1358 if (!m_type_validator_sp)
1359 return {TypeValidatorResult::Success,""}; // no validator no failure
1360
1361 auto outcome = m_type_validator_sp->FormatObject(this);
1362
1363 return (m_validation_result = {outcome.m_result,outcome.m_message}).getValue();
1364}
1365
Jim Ingham53c47f12010-09-10 23:12:17 +00001366const char *
Jim Ingham6035b672011-03-31 00:19:25 +00001367ValueObject::GetObjectDescription ()
Jim Ingham53c47f12010-09-10 23:12:17 +00001368{
Enrico Granata0a3958e2011-07-02 00:25:22 +00001369
Enrico Granatad8b5fce2011-08-02 23:12:24 +00001370 if (!UpdateValueIfNeeded (true))
Jim Ingham53c47f12010-09-10 23:12:17 +00001371 return NULL;
Enrico Granata0a3958e2011-07-02 00:25:22 +00001372
1373 if (!m_object_desc_str.empty())
1374 return m_object_desc_str.c_str();
1375
Greg Claytoncc4d0142012-02-17 07:49:44 +00001376 ExecutionContext exe_ctx (GetExecutionContextRef());
1377 Process *process = exe_ctx.GetProcessPtr();
Jim Ingham5a369122010-09-28 01:25:32 +00001378 if (process == NULL)
Jim Ingham53c47f12010-09-10 23:12:17 +00001379 return NULL;
Jim Ingham5a369122010-09-28 01:25:32 +00001380
Jim Ingham53c47f12010-09-10 23:12:17 +00001381 StreamString s;
Jim Ingham5a369122010-09-28 01:25:32 +00001382
Greg Claytonafacd142011-09-02 01:15:17 +00001383 LanguageType language = GetObjectRuntimeLanguage();
Jim Ingham5a369122010-09-28 01:25:32 +00001384 LanguageRuntime *runtime = process->GetLanguageRuntime(language);
1385
Jim Inghama2cf2632010-12-23 02:29:54 +00001386 if (runtime == NULL)
1387 {
Jim Inghamb7603bb2011-03-18 00:05:18 +00001388 // Aw, hell, if the things a pointer, or even just an integer, let's try ObjC anyway...
Greg Clayton57ee3062013-07-11 22:46:58 +00001389 ClangASTType clang_type = GetClangType();
1390 if (clang_type)
Jim Inghama2cf2632010-12-23 02:29:54 +00001391 {
Jim Inghamb7603bb2011-03-18 00:05:18 +00001392 bool is_signed;
Greg Clayton57ee3062013-07-11 22:46:58 +00001393 if (clang_type.IsIntegerType (is_signed) || clang_type.IsPointerType ())
Jim Inghamb7603bb2011-03-18 00:05:18 +00001394 {
Greg Claytonafacd142011-09-02 01:15:17 +00001395 runtime = process->GetLanguageRuntime(eLanguageTypeObjC);
Jim Inghamb7603bb2011-03-18 00:05:18 +00001396 }
Jim Inghama2cf2632010-12-23 02:29:54 +00001397 }
1398 }
1399
Jim Ingham8d543de2011-03-31 23:01:21 +00001400 if (runtime && runtime->GetObjectDescription(s, *this))
Jim Ingham53c47f12010-09-10 23:12:17 +00001401 {
1402 m_object_desc_str.append (s.GetData());
1403 }
Sean Callanan672ad942010-10-23 00:18:49 +00001404
1405 if (m_object_desc_str.empty())
1406 return NULL;
1407 else
1408 return m_object_desc_str.c_str();
Jim Ingham53c47f12010-09-10 23:12:17 +00001409}
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001410
Enrico Granata0c489f52012-03-01 04:24:26 +00001411bool
Enrico Granata4939b982013-12-22 09:24:22 +00001412ValueObject::GetValueAsCString (const lldb_private::TypeFormatImpl& format,
1413 std::string& destination)
1414{
1415 if (UpdateValueIfNeeded(false))
1416 return format.FormatObject(this,destination);
1417 else
1418 return false;
1419}
1420
1421bool
Enrico Granata0c489f52012-03-01 04:24:26 +00001422ValueObject::GetValueAsCString (lldb::Format format,
1423 std::string& destination)
1424{
Enrico Granata30f287f2013-12-28 08:44:02 +00001425 return GetValueAsCString(TypeFormatImpl_Format(format),destination);
Enrico Granata0c489f52012-03-01 04:24:26 +00001426}
1427
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001428const char *
Jim Ingham6035b672011-03-31 00:19:25 +00001429ValueObject::GetValueAsCString ()
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001430{
Enrico Granatab294fd22013-05-31 19:18:19 +00001431 if (UpdateValueIfNeeded(true))
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001432 {
Enrico Granata4939b982013-12-22 09:24:22 +00001433 lldb::TypeFormatImplSP format_sp;
Enrico Granata0c489f52012-03-01 04:24:26 +00001434 lldb::Format my_format = GetFormat();
Enrico Granatac953a6a2012-12-11 02:17:22 +00001435 if (my_format == lldb::eFormatDefault)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001436 {
Enrico Granata0c489f52012-03-01 04:24:26 +00001437 if (m_type_format_sp)
Enrico Granata4939b982013-12-22 09:24:22 +00001438 format_sp = m_type_format_sp;
Enrico Granata0c489f52012-03-01 04:24:26 +00001439 else
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001440 {
Enrico Granata0c489f52012-03-01 04:24:26 +00001441 if (m_is_bitfield_for_scalar)
1442 my_format = eFormatUnsigned;
1443 else
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001444 {
Enrico Granata0c489f52012-03-01 04:24:26 +00001445 if (m_value.GetContextType() == Value::eContextTypeRegisterInfo)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001446 {
1447 const RegisterInfo *reg_info = m_value.GetRegisterInfo();
1448 if (reg_info)
Enrico Granata0c489f52012-03-01 04:24:26 +00001449 my_format = reg_info->format;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001450 }
Enrico Granata0c489f52012-03-01 04:24:26 +00001451 else
1452 {
Enrico Granatad07cfd32014-10-08 18:27:36 +00001453 my_format = GetValue().GetClangType().GetFormat();
Enrico Granata0c489f52012-03-01 04:24:26 +00001454 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001455 }
1456 }
1457 }
Enrico Granatab294fd22013-05-31 19:18:19 +00001458 if (my_format != m_last_format || m_value_str.empty())
Enrico Granata297e69f2012-03-06 23:21:16 +00001459 {
Enrico Granatab294fd22013-05-31 19:18:19 +00001460 m_last_format = my_format;
Enrico Granata4939b982013-12-22 09:24:22 +00001461 if (!format_sp)
Enrico Granata30f287f2013-12-28 08:44:02 +00001462 format_sp.reset(new TypeFormatImpl_Format(my_format));
Enrico Granata4939b982013-12-22 09:24:22 +00001463 if (GetValueAsCString(*format_sp.get(), m_value_str))
Enrico Granata297e69f2012-03-06 23:21:16 +00001464 {
Enrico Granatab294fd22013-05-31 19:18:19 +00001465 if (!m_value_did_change && m_old_value_valid)
1466 {
1467 // The value was gotten successfully, so we consider the
1468 // value as changed if the value string differs
1469 SetValueDidChange (m_old_value_str != m_value_str);
1470 }
Enrico Granata297e69f2012-03-06 23:21:16 +00001471 }
1472 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001473 }
1474 if (m_value_str.empty())
1475 return NULL;
1476 return m_value_str.c_str();
1477}
1478
Enrico Granatac3e320a2011-08-02 17:27:39 +00001479// if > 8bytes, 0 is returned. this method should mostly be used
1480// to read address values out of pointers
Greg Clayton56d9a1b2011-08-22 02:49:39 +00001481uint64_t
Johnny Chen3f476c42012-06-05 19:37:43 +00001482ValueObject::GetValueAsUnsigned (uint64_t fail_value, bool *success)
Enrico Granatac3e320a2011-08-02 17:27:39 +00001483{
1484 // If our byte size is zero this is an aggregate type that has children
Enrico Granatad07cfd32014-10-08 18:27:36 +00001485 if (CanProvideValue())
Enrico Granatac3e320a2011-08-02 17:27:39 +00001486 {
Greg Clayton56d9a1b2011-08-22 02:49:39 +00001487 Scalar scalar;
1488 if (ResolveValue (scalar))
Johnny Chen3f476c42012-06-05 19:37:43 +00001489 {
1490 if (success)
1491 *success = true;
Enrico Granata48ea80f2012-10-24 20:24:39 +00001492 return scalar.ULongLong(fail_value);
Johnny Chen3f476c42012-06-05 19:37:43 +00001493 }
1494 // fallthrough, otherwise...
Enrico Granatac3e320a2011-08-02 17:27:39 +00001495 }
Johnny Chen3f476c42012-06-05 19:37:43 +00001496
1497 if (success)
1498 *success = false;
Greg Clayton56d9a1b2011-08-22 02:49:39 +00001499 return fail_value;
Enrico Granatac3e320a2011-08-02 17:27:39 +00001500}
1501
Enrico Granatad7373f62013-10-31 18:57:50 +00001502int64_t
1503ValueObject::GetValueAsSigned (int64_t fail_value, bool *success)
1504{
1505 // If our byte size is zero this is an aggregate type that has children
Enrico Granatad07cfd32014-10-08 18:27:36 +00001506 if (CanProvideValue())
Enrico Granatad7373f62013-10-31 18:57:50 +00001507 {
1508 Scalar scalar;
1509 if (ResolveValue (scalar))
1510 {
1511 if (success)
1512 *success = true;
1513 return scalar.SLongLong(fail_value);
1514 }
1515 // fallthrough, otherwise...
1516 }
1517
1518 if (success)
1519 *success = false;
1520 return fail_value;
1521}
1522
Enrico Granatad64d0bc2011-08-19 21:13:46 +00001523// if any more "special cases" are added to ValueObject::DumpPrintableRepresentation() please keep
1524// this call up to date by returning true for your new special cases. We will eventually move
1525// to checking this call result before trying to display special cases
1526bool
Enrico Granata86cc9822012-03-19 22:58:49 +00001527ValueObject::HasSpecialPrintableRepresentation(ValueObjectRepresentationStyle val_obj_display,
1528 Format custom_format)
Enrico Granatad64d0bc2011-08-19 21:13:46 +00001529{
Greg Clayton57ee3062013-07-11 22:46:58 +00001530 Flags flags(GetTypeInfo());
Enrico Granata622be232014-10-21 20:52:14 +00001531 if (flags.AnySet(eTypeIsArray | eTypeIsPointer)
Enrico Granata86cc9822012-03-19 22:58:49 +00001532 && val_obj_display == ValueObject::eValueObjectRepresentationStyleValue)
Enrico Granatad64d0bc2011-08-19 21:13:46 +00001533 {
1534 if (IsCStringContainer(true) &&
Greg Claytonafacd142011-09-02 01:15:17 +00001535 (custom_format == eFormatCString ||
1536 custom_format == eFormatCharArray ||
1537 custom_format == eFormatChar ||
1538 custom_format == eFormatVectorOfChar))
Enrico Granatad64d0bc2011-08-19 21:13:46 +00001539 return true;
1540
Enrico Granata622be232014-10-21 20:52:14 +00001541 if (flags.Test(eTypeIsArray))
Enrico Granatad64d0bc2011-08-19 21:13:46 +00001542 {
Greg Claytonafacd142011-09-02 01:15:17 +00001543 if ((custom_format == eFormatBytes) ||
1544 (custom_format == eFormatBytesWithASCII))
Enrico Granatad64d0bc2011-08-19 21:13:46 +00001545 return true;
1546
Greg Claytonafacd142011-09-02 01:15:17 +00001547 if ((custom_format == eFormatVectorOfChar) ||
1548 (custom_format == eFormatVectorOfFloat32) ||
1549 (custom_format == eFormatVectorOfFloat64) ||
1550 (custom_format == eFormatVectorOfSInt16) ||
1551 (custom_format == eFormatVectorOfSInt32) ||
1552 (custom_format == eFormatVectorOfSInt64) ||
1553 (custom_format == eFormatVectorOfSInt8) ||
1554 (custom_format == eFormatVectorOfUInt128) ||
1555 (custom_format == eFormatVectorOfUInt16) ||
1556 (custom_format == eFormatVectorOfUInt32) ||
1557 (custom_format == eFormatVectorOfUInt64) ||
1558 (custom_format == eFormatVectorOfUInt8))
Enrico Granatad64d0bc2011-08-19 21:13:46 +00001559 return true;
1560 }
1561 }
1562 return false;
1563}
1564
Enrico Granata9fc19442011-07-06 02:13:41 +00001565bool
1566ValueObject::DumpPrintableRepresentation(Stream& s,
1567 ValueObjectRepresentationStyle val_obj_display,
Greg Claytonafacd142011-09-02 01:15:17 +00001568 Format custom_format,
Enrico Granata0dba9b32014-01-08 01:36:59 +00001569 PrintableRepresentationSpecialCases special,
1570 bool do_dump_error)
Enrico Granata9fc19442011-07-06 02:13:41 +00001571{
Enrico Granataf4efecd2011-07-12 22:56:10 +00001572
Greg Clayton57ee3062013-07-11 22:46:58 +00001573 Flags flags(GetTypeInfo());
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00001574
Enrico Granata86cc9822012-03-19 22:58:49 +00001575 bool allow_special = ((special & ePrintableRepresentationSpecialCasesAllow) == ePrintableRepresentationSpecialCasesAllow);
1576 bool only_special = ((special & ePrintableRepresentationSpecialCasesOnly) == ePrintableRepresentationSpecialCasesOnly);
1577
1578 if (allow_special)
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00001579 {
Enrico Granata622be232014-10-21 20:52:14 +00001580 if (flags.AnySet(eTypeIsArray | eTypeIsPointer)
Enrico Granata86cc9822012-03-19 22:58:49 +00001581 && val_obj_display == ValueObject::eValueObjectRepresentationStyleValue)
Enrico Granataf4efecd2011-07-12 22:56:10 +00001582 {
Enrico Granata86cc9822012-03-19 22:58:49 +00001583 // when being asked to get a printable display an array or pointer type directly,
1584 // try to "do the right thing"
1585
1586 if (IsCStringContainer(true) &&
1587 (custom_format == eFormatCString ||
1588 custom_format == eFormatCharArray ||
1589 custom_format == eFormatChar ||
1590 custom_format == eFormatVectorOfChar)) // print char[] & char* directly
Enrico Granataf4efecd2011-07-12 22:56:10 +00001591 {
Enrico Granata86cc9822012-03-19 22:58:49 +00001592 Error error;
1593 ReadPointedString(s,
1594 error,
1595 0,
1596 (custom_format == eFormatVectorOfChar) ||
1597 (custom_format == eFormatCharArray));
1598 return !error.Fail();
Enrico Granataf4efecd2011-07-12 22:56:10 +00001599 }
1600
Enrico Granata86cc9822012-03-19 22:58:49 +00001601 if (custom_format == eFormatEnum)
1602 return false;
1603
1604 // this only works for arrays, because I have no way to know when
1605 // the pointed memory ends, and no special \0 end of data marker
Enrico Granata622be232014-10-21 20:52:14 +00001606 if (flags.Test(eTypeIsArray))
Enrico Granataf4efecd2011-07-12 22:56:10 +00001607 {
Enrico Granata86cc9822012-03-19 22:58:49 +00001608 if ((custom_format == eFormatBytes) ||
1609 (custom_format == eFormatBytesWithASCII))
Enrico Granataf4efecd2011-07-12 22:56:10 +00001610 {
Greg Claytonc7bece562013-01-25 18:06:21 +00001611 const size_t count = GetNumChildren();
Enrico Granata86cc9822012-03-19 22:58:49 +00001612
1613 s << '[';
Greg Claytonc7bece562013-01-25 18:06:21 +00001614 for (size_t low = 0; low < count; low++)
Enrico Granataf4efecd2011-07-12 22:56:10 +00001615 {
Enrico Granata86cc9822012-03-19 22:58:49 +00001616
1617 if (low)
1618 s << ',';
1619
1620 ValueObjectSP child = GetChildAtIndex(low,true);
1621 if (!child.get())
1622 {
1623 s << "<invalid child>";
1624 continue;
1625 }
1626 child->DumpPrintableRepresentation(s, ValueObject::eValueObjectRepresentationStyleValue, custom_format);
1627 }
1628
1629 s << ']';
1630
1631 return true;
1632 }
Enrico Granataf4efecd2011-07-12 22:56:10 +00001633
Enrico Granata86cc9822012-03-19 22:58:49 +00001634 if ((custom_format == eFormatVectorOfChar) ||
1635 (custom_format == eFormatVectorOfFloat32) ||
1636 (custom_format == eFormatVectorOfFloat64) ||
1637 (custom_format == eFormatVectorOfSInt16) ||
1638 (custom_format == eFormatVectorOfSInt32) ||
1639 (custom_format == eFormatVectorOfSInt64) ||
1640 (custom_format == eFormatVectorOfSInt8) ||
1641 (custom_format == eFormatVectorOfUInt128) ||
1642 (custom_format == eFormatVectorOfUInt16) ||
1643 (custom_format == eFormatVectorOfUInt32) ||
1644 (custom_format == eFormatVectorOfUInt64) ||
1645 (custom_format == eFormatVectorOfUInt8)) // arrays of bytes, bytes with ASCII or any vector format should be printed directly
1646 {
Greg Claytonc7bece562013-01-25 18:06:21 +00001647 const size_t count = GetNumChildren();
Enrico Granata86cc9822012-03-19 22:58:49 +00001648
1649 Format format = FormatManager::GetSingleItemFormat(custom_format);
1650
1651 s << '[';
Greg Claytonc7bece562013-01-25 18:06:21 +00001652 for (size_t low = 0; low < count; low++)
Enrico Granata86cc9822012-03-19 22:58:49 +00001653 {
1654
1655 if (low)
1656 s << ',';
1657
1658 ValueObjectSP child = GetChildAtIndex(low,true);
1659 if (!child.get())
1660 {
1661 s << "<invalid child>";
1662 continue;
1663 }
1664 child->DumpPrintableRepresentation(s, ValueObject::eValueObjectRepresentationStyleValue, format);
1665 }
1666
1667 s << ']';
1668
1669 return true;
1670 }
Enrico Granataf4efecd2011-07-12 22:56:10 +00001671 }
Enrico Granata86cc9822012-03-19 22:58:49 +00001672
1673 if ((custom_format == eFormatBoolean) ||
1674 (custom_format == eFormatBinary) ||
1675 (custom_format == eFormatChar) ||
1676 (custom_format == eFormatCharPrintable) ||
1677 (custom_format == eFormatComplexFloat) ||
1678 (custom_format == eFormatDecimal) ||
1679 (custom_format == eFormatHex) ||
Enrico Granata7ec18e32012-08-09 19:33:34 +00001680 (custom_format == eFormatHexUppercase) ||
Enrico Granata86cc9822012-03-19 22:58:49 +00001681 (custom_format == eFormatFloat) ||
1682 (custom_format == eFormatOctal) ||
1683 (custom_format == eFormatOSType) ||
1684 (custom_format == eFormatUnicode16) ||
1685 (custom_format == eFormatUnicode32) ||
1686 (custom_format == eFormatUnsigned) ||
1687 (custom_format == eFormatPointer) ||
1688 (custom_format == eFormatComplexInteger) ||
1689 (custom_format == eFormatComplex) ||
1690 (custom_format == eFormatDefault)) // use the [] operator
1691 return false;
Enrico Granataf4efecd2011-07-12 22:56:10 +00001692 }
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00001693 }
Enrico Granata85933ed2011-08-18 16:38:26 +00001694
1695 if (only_special)
1696 return false;
1697
Enrico Granata86cc9822012-03-19 22:58:49 +00001698 bool var_success = false;
1699
1700 {
Greg Claytonc7bece562013-01-25 18:06:21 +00001701 const char *cstr = NULL;
Enrico Granata2c75f112013-06-21 00:04:51 +00001702
1703 // this is a local stream that we are using to ensure that the data pointed to by cstr survives
1704 // long enough for us to copy it to its destination - it is necessary to have this temporary storage
1705 // area for cases where our desired output is not backed by some other longer-term storage
Greg Claytonc7bece562013-01-25 18:06:21 +00001706 StreamString strm;
Enrico Granata86cc9822012-03-19 22:58:49 +00001707
Enrico Granata465f4bc2014-02-15 01:24:44 +00001708 if (custom_format != eFormatInvalid)
Enrico Granata86cc9822012-03-19 22:58:49 +00001709 SetFormat(custom_format);
1710
1711 switch(val_obj_display)
1712 {
1713 case eValueObjectRepresentationStyleValue:
Greg Claytonc7bece562013-01-25 18:06:21 +00001714 cstr = GetValueAsCString();
Enrico Granata86cc9822012-03-19 22:58:49 +00001715 break;
1716
1717 case eValueObjectRepresentationStyleSummary:
Greg Claytonc7bece562013-01-25 18:06:21 +00001718 cstr = GetSummaryAsCString();
Enrico Granata86cc9822012-03-19 22:58:49 +00001719 break;
1720
1721 case eValueObjectRepresentationStyleLanguageSpecific:
Greg Claytonc7bece562013-01-25 18:06:21 +00001722 cstr = GetObjectDescription();
Enrico Granata86cc9822012-03-19 22:58:49 +00001723 break;
1724
1725 case eValueObjectRepresentationStyleLocation:
Greg Claytonc7bece562013-01-25 18:06:21 +00001726 cstr = GetLocationAsCString();
Enrico Granata86cc9822012-03-19 22:58:49 +00001727 break;
1728
1729 case eValueObjectRepresentationStyleChildrenCount:
Deepak Panickal99fbc072014-03-03 15:39:47 +00001730 strm.Printf("%" PRIu64 "", (uint64_t)GetNumChildren());
Greg Claytonc7bece562013-01-25 18:06:21 +00001731 cstr = strm.GetString().c_str();
Enrico Granata86cc9822012-03-19 22:58:49 +00001732 break;
1733
1734 case eValueObjectRepresentationStyleType:
Greg Claytonc7bece562013-01-25 18:06:21 +00001735 cstr = GetTypeName().AsCString();
Enrico Granata86cc9822012-03-19 22:58:49 +00001736 break;
Enrico Granata2c75f112013-06-21 00:04:51 +00001737
1738 case eValueObjectRepresentationStyleName:
1739 cstr = GetName().AsCString();
1740 break;
1741
1742 case eValueObjectRepresentationStyleExpressionPath:
1743 GetExpressionPath(strm, false);
1744 cstr = strm.GetString().c_str();
1745 break;
Enrico Granata86cc9822012-03-19 22:58:49 +00001746 }
1747
Greg Claytonc7bece562013-01-25 18:06:21 +00001748 if (!cstr)
Enrico Granata86cc9822012-03-19 22:58:49 +00001749 {
1750 if (val_obj_display == eValueObjectRepresentationStyleValue)
Greg Claytonc7bece562013-01-25 18:06:21 +00001751 cstr = GetSummaryAsCString();
Enrico Granata86cc9822012-03-19 22:58:49 +00001752 else if (val_obj_display == eValueObjectRepresentationStyleSummary)
1753 {
Enrico Granatad07cfd32014-10-08 18:27:36 +00001754 if (!CanProvideValue())
Enrico Granata86cc9822012-03-19 22:58:49 +00001755 {
Greg Claytonc7bece562013-01-25 18:06:21 +00001756 strm.Printf("%s @ %s", GetTypeName().AsCString(), GetLocationAsCString());
1757 cstr = strm.GetString().c_str();
Enrico Granata86cc9822012-03-19 22:58:49 +00001758 }
1759 else
Greg Claytonc7bece562013-01-25 18:06:21 +00001760 cstr = GetValueAsCString();
Enrico Granata86cc9822012-03-19 22:58:49 +00001761 }
1762 }
1763
Greg Claytonc7bece562013-01-25 18:06:21 +00001764 if (cstr)
1765 s.PutCString(cstr);
Enrico Granata86cc9822012-03-19 22:58:49 +00001766 else
1767 {
1768 if (m_error.Fail())
Enrico Granata0dba9b32014-01-08 01:36:59 +00001769 {
1770 if (do_dump_error)
1771 s.Printf("<%s>", m_error.AsCString());
1772 else
1773 return false;
1774 }
Enrico Granata86cc9822012-03-19 22:58:49 +00001775 else if (val_obj_display == eValueObjectRepresentationStyleSummary)
1776 s.PutCString("<no summary available>");
1777 else if (val_obj_display == eValueObjectRepresentationStyleValue)
1778 s.PutCString("<no value available>");
1779 else if (val_obj_display == eValueObjectRepresentationStyleLanguageSpecific)
1780 s.PutCString("<not a valid Objective-C object>"); // edit this if we have other runtimes that support a description
1781 else
1782 s.PutCString("<no printable representation>");
1783 }
1784
1785 // we should only return false here if we could not do *anything*
1786 // even if we have an error message as output, that's a success
1787 // from our callers' perspective, so return true
1788 var_success = true;
Enrico Granata465f4bc2014-02-15 01:24:44 +00001789
1790 if (custom_format != eFormatInvalid)
1791 SetFormat(eFormatDefault);
Enrico Granata86cc9822012-03-19 22:58:49 +00001792 }
1793
Enrico Granataf4efecd2011-07-12 22:56:10 +00001794 return var_success;
Enrico Granata9fc19442011-07-06 02:13:41 +00001795}
1796
Greg Clayton737b9322010-09-13 03:32:57 +00001797addr_t
Enrico Granata9128ee22011-09-06 19:20:51 +00001798ValueObject::GetAddressOf (bool scalar_is_load_address, AddressType *address_type)
Greg Clayton73b472d2010-10-27 03:32:59 +00001799{
Enrico Granatac3e320a2011-08-02 17:27:39 +00001800 if (!UpdateValueIfNeeded(false))
Jim Ingham78a685a2011-04-16 00:01:13 +00001801 return LLDB_INVALID_ADDRESS;
1802
Greg Clayton73b472d2010-10-27 03:32:59 +00001803 switch (m_value.GetValueType())
1804 {
1805 case Value::eValueTypeScalar:
Greg Clayton0665a0f2012-10-30 18:18:43 +00001806 case Value::eValueTypeVector:
Greg Clayton73b472d2010-10-27 03:32:59 +00001807 if (scalar_is_load_address)
1808 {
Enrico Granata9128ee22011-09-06 19:20:51 +00001809 if(address_type)
1810 *address_type = eAddressTypeLoad;
Greg Clayton73b472d2010-10-27 03:32:59 +00001811 return m_value.GetScalar().ULongLong(LLDB_INVALID_ADDRESS);
1812 }
1813 break;
1814
1815 case Value::eValueTypeLoadAddress:
1816 case Value::eValueTypeFileAddress:
1817 case Value::eValueTypeHostAddress:
1818 {
Enrico Granata9128ee22011-09-06 19:20:51 +00001819 if(address_type)
1820 *address_type = m_value.GetValueAddressType ();
Greg Clayton73b472d2010-10-27 03:32:59 +00001821 return m_value.GetScalar().ULongLong(LLDB_INVALID_ADDRESS);
1822 }
1823 break;
1824 }
Enrico Granata9128ee22011-09-06 19:20:51 +00001825 if (address_type)
1826 *address_type = eAddressTypeInvalid;
Greg Clayton73b472d2010-10-27 03:32:59 +00001827 return LLDB_INVALID_ADDRESS;
1828}
1829
1830addr_t
Enrico Granata9128ee22011-09-06 19:20:51 +00001831ValueObject::GetPointerValue (AddressType *address_type)
Greg Clayton737b9322010-09-13 03:32:57 +00001832{
Greg Claytonafacd142011-09-02 01:15:17 +00001833 addr_t address = LLDB_INVALID_ADDRESS;
Enrico Granata9128ee22011-09-06 19:20:51 +00001834 if(address_type)
1835 *address_type = eAddressTypeInvalid;
Jim Ingham78a685a2011-04-16 00:01:13 +00001836
Enrico Granatac3e320a2011-08-02 17:27:39 +00001837 if (!UpdateValueIfNeeded(false))
Jim Ingham78a685a2011-04-16 00:01:13 +00001838 return address;
1839
Greg Clayton73b472d2010-10-27 03:32:59 +00001840 switch (m_value.GetValueType())
Greg Clayton737b9322010-09-13 03:32:57 +00001841 {
1842 case Value::eValueTypeScalar:
Greg Clayton0665a0f2012-10-30 18:18:43 +00001843 case Value::eValueTypeVector:
Enrico Granata9128ee22011-09-06 19:20:51 +00001844 address = m_value.GetScalar().ULongLong(LLDB_INVALID_ADDRESS);
Greg Clayton737b9322010-09-13 03:32:57 +00001845 break;
1846
Enrico Granata9128ee22011-09-06 19:20:51 +00001847 case Value::eValueTypeHostAddress:
Greg Clayton737b9322010-09-13 03:32:57 +00001848 case Value::eValueTypeLoadAddress:
1849 case Value::eValueTypeFileAddress:
Greg Clayton737b9322010-09-13 03:32:57 +00001850 {
Greg Claytonc7bece562013-01-25 18:06:21 +00001851 lldb::offset_t data_offset = 0;
Greg Clayton737b9322010-09-13 03:32:57 +00001852 address = m_data.GetPointer(&data_offset);
Greg Clayton737b9322010-09-13 03:32:57 +00001853 }
1854 break;
1855 }
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00001856
Enrico Granata9128ee22011-09-06 19:20:51 +00001857 if (address_type)
1858 *address_type = GetAddressTypeOfChildren();
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00001859
Greg Clayton737b9322010-09-13 03:32:57 +00001860 return address;
1861}
1862
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001863bool
Enrico Granata07a4ac22012-05-08 21:25:06 +00001864ValueObject::SetValueFromCString (const char *value_str, Error& error)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001865{
Enrico Granata07a4ac22012-05-08 21:25:06 +00001866 error.Clear();
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001867 // Make sure our value is up to date first so that our location and location
1868 // type is valid.
Enrico Granatac3e320a2011-08-02 17:27:39 +00001869 if (!UpdateValueIfNeeded(false))
Enrico Granata07a4ac22012-05-08 21:25:06 +00001870 {
1871 error.SetErrorString("unable to read value");
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001872 return false;
Enrico Granata07a4ac22012-05-08 21:25:06 +00001873 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001874
Greg Claytonfaac1112013-03-14 18:31:44 +00001875 uint64_t count = 0;
Greg Clayton57ee3062013-07-11 22:46:58 +00001876 const Encoding encoding = GetClangType().GetEncoding (count);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001877
Greg Claytonb1320972010-07-14 00:18:15 +00001878 const size_t byte_size = GetByteSize();
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001879
Jim Ingham16e0c682011-08-12 23:34:31 +00001880 Value::ValueType value_type = m_value.GetValueType();
1881
1882 if (value_type == Value::eValueTypeScalar)
1883 {
1884 // If the value is already a scalar, then let the scalar change itself:
1885 m_value.GetScalar().SetValueFromCString (value_str, encoding, byte_size);
1886 }
1887 else if (byte_size <= Scalar::GetMaxByteSize())
1888 {
1889 // If the value fits in a scalar, then make a new scalar and again let the
1890 // scalar code do the conversion, then figure out where to put the new value.
1891 Scalar new_scalar;
Jim Ingham16e0c682011-08-12 23:34:31 +00001892 error = new_scalar.SetValueFromCString (value_str, encoding, byte_size);
1893 if (error.Success())
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001894 {
Jim Ingham4b536182011-08-09 02:12:22 +00001895 switch (value_type)
1896 {
Greg Claytoncc4d0142012-02-17 07:49:44 +00001897 case Value::eValueTypeLoadAddress:
Jim Ingham16e0c682011-08-12 23:34:31 +00001898 {
1899 // If it is a load address, then the scalar value is the storage location
1900 // of the data, and we have to shove this value down to that load location.
Greg Claytoncc4d0142012-02-17 07:49:44 +00001901 ExecutionContext exe_ctx (GetExecutionContextRef());
1902 Process *process = exe_ctx.GetProcessPtr();
1903 if (process)
Jim Ingham16e0c682011-08-12 23:34:31 +00001904 {
Enrico Granata48ea80f2012-10-24 20:24:39 +00001905 addr_t target_addr = m_value.GetScalar().ULongLong(LLDB_INVALID_ADDRESS);
Greg Claytoncc4d0142012-02-17 07:49:44 +00001906 size_t bytes_written = process->WriteScalarToMemory (target_addr,
1907 new_scalar,
1908 byte_size,
1909 error);
Enrico Granata07a4ac22012-05-08 21:25:06 +00001910 if (!error.Success())
1911 return false;
1912 if (bytes_written != byte_size)
1913 {
1914 error.SetErrorString("unable to write value to memory");
1915 return false;
1916 }
Jim Ingham16e0c682011-08-12 23:34:31 +00001917 }
1918 }
Jim Ingham4b536182011-08-09 02:12:22 +00001919 break;
Greg Claytoncc4d0142012-02-17 07:49:44 +00001920 case Value::eValueTypeHostAddress:
Jim Ingham16e0c682011-08-12 23:34:31 +00001921 {
1922 // If it is a host address, then we stuff the scalar as a DataBuffer into the Value's data.
1923 DataExtractor new_data;
1924 new_data.SetByteOrder (m_data.GetByteOrder());
1925
1926 DataBufferSP buffer_sp (new DataBufferHeap(byte_size, 0));
1927 m_data.SetData(buffer_sp, 0);
1928 bool success = new_scalar.GetData(new_data);
1929 if (success)
1930 {
Greg Claytoncc4d0142012-02-17 07:49:44 +00001931 new_data.CopyByteOrderedData (0,
1932 byte_size,
1933 const_cast<uint8_t *>(m_data.GetDataStart()),
1934 byte_size,
1935 m_data.GetByteOrder());
Jim Ingham16e0c682011-08-12 23:34:31 +00001936 }
1937 m_value.GetScalar() = (uintptr_t)m_data.GetDataStart();
1938
1939 }
Jim Ingham4b536182011-08-09 02:12:22 +00001940 break;
Greg Claytoncc4d0142012-02-17 07:49:44 +00001941 case Value::eValueTypeFileAddress:
1942 case Value::eValueTypeScalar:
Greg Clayton0665a0f2012-10-30 18:18:43 +00001943 case Value::eValueTypeVector:
1944 break;
Jim Ingham4b536182011-08-09 02:12:22 +00001945 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001946 }
1947 else
1948 {
Jim Ingham16e0c682011-08-12 23:34:31 +00001949 return false;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001950 }
Jim Ingham16e0c682011-08-12 23:34:31 +00001951 }
1952 else
1953 {
1954 // We don't support setting things bigger than a scalar at present.
Enrico Granata07a4ac22012-05-08 21:25:06 +00001955 error.SetErrorString("unable to write aggregate data type");
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001956 return false;
1957 }
Jim Ingham16e0c682011-08-12 23:34:31 +00001958
1959 // If we have reached this point, then we have successfully changed the value.
1960 SetNeedsUpdate();
1961 return true;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001962}
1963
Greg Clayton81e871e2012-02-04 02:27:34 +00001964bool
1965ValueObject::GetDeclaration (Declaration &decl)
1966{
1967 decl.Clear();
1968 return false;
1969}
1970
Greg Clayton84db9102012-03-26 23:03:23 +00001971ConstString
1972ValueObject::GetTypeName()
1973{
Greg Clayton57ee3062013-07-11 22:46:58 +00001974 return GetClangType().GetConstTypeName();
Greg Clayton84db9102012-03-26 23:03:23 +00001975}
1976
1977ConstString
Enrico Granatae8daa2f2014-05-17 19:14:17 +00001978ValueObject::GetDisplayTypeName()
1979{
1980 return GetTypeName();
1981}
1982
1983ConstString
Greg Clayton84db9102012-03-26 23:03:23 +00001984ValueObject::GetQualifiedTypeName()
1985{
Greg Clayton57ee3062013-07-11 22:46:58 +00001986 return GetClangType().GetConstQualifiedTypeName();
Greg Clayton84db9102012-03-26 23:03:23 +00001987}
1988
1989
Greg Claytonafacd142011-09-02 01:15:17 +00001990LanguageType
Jim Ingham5a369122010-09-28 01:25:32 +00001991ValueObject::GetObjectRuntimeLanguage ()
1992{
Greg Clayton57ee3062013-07-11 22:46:58 +00001993 return GetClangType().GetMinimumLanguage ();
Jim Ingham5a369122010-09-28 01:25:32 +00001994}
1995
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001996void
Jim Ingham58b59f92011-04-22 23:53:53 +00001997ValueObject::AddSyntheticChild (const ConstString &key, ValueObject *valobj)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001998{
Jim Ingham58b59f92011-04-22 23:53:53 +00001999 m_synthetic_children[key] = valobj;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002000}
2001
2002ValueObjectSP
2003ValueObject::GetSyntheticChild (const ConstString &key) const
2004{
2005 ValueObjectSP synthetic_child_sp;
Jim Ingham58b59f92011-04-22 23:53:53 +00002006 std::map<ConstString, ValueObject *>::const_iterator pos = m_synthetic_children.find (key);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002007 if (pos != m_synthetic_children.end())
Jim Ingham58b59f92011-04-22 23:53:53 +00002008 synthetic_child_sp = pos->second->GetSP();
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002009 return synthetic_child_sp;
2010}
2011
Greg Clayton2452ab72013-02-08 22:02:02 +00002012uint32_t
Greg Clayton57ee3062013-07-11 22:46:58 +00002013ValueObject::GetTypeInfo (ClangASTType *pointee_or_element_clang_type)
Greg Clayton2452ab72013-02-08 22:02:02 +00002014{
Greg Clayton57ee3062013-07-11 22:46:58 +00002015 return GetClangType().GetTypeInfo (pointee_or_element_clang_type);
Greg Clayton2452ab72013-02-08 22:02:02 +00002016}
2017
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002018bool
2019ValueObject::IsPointerType ()
2020{
Greg Clayton57ee3062013-07-11 22:46:58 +00002021 return GetClangType().IsPointerType();
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002022}
2023
Jim Inghamb7603bb2011-03-18 00:05:18 +00002024bool
Greg Claytondaf515f2011-07-09 20:12:33 +00002025ValueObject::IsArrayType ()
2026{
Greg Clayton57ee3062013-07-11 22:46:58 +00002027 return GetClangType().IsArrayType (NULL, NULL, NULL);
Greg Claytondaf515f2011-07-09 20:12:33 +00002028}
2029
2030bool
Enrico Granata9fc19442011-07-06 02:13:41 +00002031ValueObject::IsScalarType ()
2032{
Greg Clayton57ee3062013-07-11 22:46:58 +00002033 return GetClangType().IsScalarType ();
Enrico Granata9fc19442011-07-06 02:13:41 +00002034}
2035
2036bool
Jim Inghamb7603bb2011-03-18 00:05:18 +00002037ValueObject::IsIntegerType (bool &is_signed)
2038{
Greg Clayton57ee3062013-07-11 22:46:58 +00002039 return GetClangType().IsIntegerType (is_signed);
Jim Inghamb7603bb2011-03-18 00:05:18 +00002040}
Greg Clayton73b472d2010-10-27 03:32:59 +00002041
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002042bool
2043ValueObject::IsPointerOrReferenceType ()
2044{
Greg Clayton57ee3062013-07-11 22:46:58 +00002045 return GetClangType().IsPointerOrReferenceType ();
Greg Clayton007d5be2011-05-30 00:49:24 +00002046}
2047
2048bool
Greg Claytondea8cb42011-06-29 22:09:02 +00002049ValueObject::IsPossibleDynamicType ()
2050{
Enrico Granatafd4c84e2012-05-21 16:51:35 +00002051 ExecutionContext exe_ctx (GetExecutionContextRef());
2052 Process *process = exe_ctx.GetProcessPtr();
2053 if (process)
2054 return process->IsPossibleDynamicValue(*this);
2055 else
Greg Clayton57ee3062013-07-11 22:46:58 +00002056 return GetClangType().IsPossibleDynamicType (NULL, true, true);
Greg Claytondea8cb42011-06-29 22:09:02 +00002057}
2058
Enrico Granata9e7b3882012-12-13 23:50:33 +00002059bool
2060ValueObject::IsObjCNil ()
2061{
Enrico Granata622be232014-10-21 20:52:14 +00002062 const uint32_t mask = eTypeIsObjC | eTypeIsPointer;
Greg Clayton57ee3062013-07-11 22:46:58 +00002063 bool isObjCpointer = (((GetClangType().GetTypeInfo(NULL)) & mask) == mask);
Enrico Granata7277d202013-03-15 23:33:15 +00002064 if (!isObjCpointer)
2065 return false;
Enrico Granata9e7b3882012-12-13 23:50:33 +00002066 bool canReadValue = true;
2067 bool isZero = GetValueAsUnsigned(0,&canReadValue) == 0;
Enrico Granata7277d202013-03-15 23:33:15 +00002068 return canReadValue && isZero;
Enrico Granata9e7b3882012-12-13 23:50:33 +00002069}
2070
Greg Claytonafacd142011-09-02 01:15:17 +00002071ValueObjectSP
Greg Claytonc7bece562013-01-25 18:06:21 +00002072ValueObject::GetSyntheticArrayMember (size_t index, bool can_create)
Enrico Granatad64d0bc2011-08-19 21:13:46 +00002073{
Greg Clayton2452ab72013-02-08 22:02:02 +00002074 const uint32_t type_info = GetTypeInfo ();
Enrico Granata622be232014-10-21 20:52:14 +00002075 if (type_info & eTypeIsArray)
Enrico Granatad64d0bc2011-08-19 21:13:46 +00002076 return GetSyntheticArrayMemberFromArray(index, can_create);
2077
Enrico Granata622be232014-10-21 20:52:14 +00002078 if (type_info & eTypeIsPointer)
Enrico Granatad64d0bc2011-08-19 21:13:46 +00002079 return GetSyntheticArrayMemberFromPointer(index, can_create);
2080
2081 return ValueObjectSP();
2082
2083}
2084
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002085ValueObjectSP
Greg Claytonc7bece562013-01-25 18:06:21 +00002086ValueObject::GetSyntheticArrayMemberFromPointer (size_t index, bool can_create)
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002087{
2088 ValueObjectSP synthetic_child_sp;
2089 if (IsPointerType ())
2090 {
2091 char index_str[64];
Deepak Panickal99fbc072014-03-03 15:39:47 +00002092 snprintf(index_str, sizeof(index_str), "[%" PRIu64 "]", (uint64_t)index);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002093 ConstString index_const_str(index_str);
2094 // Check if we have already created a synthetic array member in this
2095 // valid object. If we have we will re-use it.
2096 synthetic_child_sp = GetSyntheticChild (index_const_str);
2097 if (!synthetic_child_sp)
2098 {
Jim Ingham58b59f92011-04-22 23:53:53 +00002099 ValueObject *synthetic_child;
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002100 // We haven't made a synthetic array member for INDEX yet, so
2101 // lets make one and cache it for any future reference.
Jim Ingham58b59f92011-04-22 23:53:53 +00002102 synthetic_child = CreateChildAtIndex(0, true, index);
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002103
2104 // Cache the value if we got one back...
Jim Ingham58b59f92011-04-22 23:53:53 +00002105 if (synthetic_child)
2106 {
2107 AddSyntheticChild(index_const_str, synthetic_child);
2108 synthetic_child_sp = synthetic_child->GetSP();
Enrico Granata6f3533f2011-07-29 19:53:35 +00002109 synthetic_child_sp->SetName(ConstString(index_str));
Enrico Granata0a3958e2011-07-02 00:25:22 +00002110 synthetic_child_sp->m_is_array_item_for_pointer = true;
Jim Ingham58b59f92011-04-22 23:53:53 +00002111 }
Chris Lattner30fdc8d2010-06-08 16:52:24 +00002112 }
2113 }
2114 return synthetic_child_sp;
2115}
Jim Ingham22777012010-09-23 02:01:19 +00002116
Greg Claytondaf515f2011-07-09 20:12:33 +00002117// This allows you to create an array member using and index
2118// that doesn't not fall in the normal bounds of the array.
2119// Many times structure can be defined as:
2120// struct Collection
2121// {
2122// uint32_t item_count;
2123// Item item_array[0];
2124// };
2125// The size of the "item_array" is 1, but many times in practice
2126// there are more items in "item_array".
2127
2128ValueObjectSP
Greg Claytonc7bece562013-01-25 18:06:21 +00002129ValueObject::GetSyntheticArrayMemberFromArray (size_t index, bool can_create)
Greg Claytondaf515f2011-07-09 20:12:33 +00002130{
2131 ValueObjectSP synthetic_child_sp;
2132 if (IsArrayType ())
2133 {
2134 char index_str[64];
Deepak Panickal99fbc072014-03-03 15:39:47 +00002135 snprintf(index_str, sizeof(index_str), "[%" PRIu64 "]", (uint64_t)index);
Greg Claytondaf515f2011-07-09 20:12:33 +00002136 ConstString index_const_str(index_str);
2137 // Check if we have already created a synthetic array member in this
2138 // valid object. If we have we will re-use it.
2139 synthetic_child_sp = GetSyntheticChild (index_const_str);
2140 if (!synthetic_child_sp)
2141 {
2142 ValueObject *synthetic_child;
2143 // We haven't made a synthetic array member for INDEX yet, so
2144 // lets make one and cache it for any future reference.
2145 synthetic_child = CreateChildAtIndex(0, true, index);
2146
2147 // Cache the value if we got one back...
2148 if (synthetic_child)
2149 {
2150 AddSyntheticChild(index_const_str, synthetic_child);
2151 synthetic_child_sp = synthetic_child->GetSP();
Enrico Granata6f3533f2011-07-29 19:53:35 +00002152 synthetic_child_sp->SetName(ConstString(index_str));
Greg Claytondaf515f2011-07-09 20:12:33 +00002153 synthetic_child_sp->m_is_array_item_for_pointer = true;
2154 }
2155 }
2156 }
2157 return synthetic_child_sp;
2158}
2159
Enrico Granata9fc19442011-07-06 02:13:41 +00002160ValueObjectSP
2161ValueObject::GetSyntheticBitFieldChild (uint32_t from, uint32_t to, bool can_create)
2162{
2163 ValueObjectSP synthetic_child_sp;
2164 if (IsScalarType ())
2165 {
2166 char index_str[64];
2167 snprintf(index_str, sizeof(index_str), "[%i-%i]", from, to);
2168 ConstString index_const_str(index_str);
2169 // Check if we have already created a synthetic array member in this
2170 // valid object. If we have we will re-use it.
2171 synthetic_child_sp = GetSyntheticChild (index_const_str);
2172 if (!synthetic_child_sp)
2173 {
Enrico Granata9fc19442011-07-06 02:13:41 +00002174 // We haven't made a synthetic array member for INDEX yet, so
2175 // lets make one and cache it for any future reference.
Greg Clayton57ee3062013-07-11 22:46:58 +00002176 ValueObjectChild *synthetic_child = new ValueObjectChild (*this,
2177 GetClangType(),
2178 index_const_str,
2179 GetByteSize(),
2180 0,
2181 to-from+1,
2182 from,
2183 false,
2184 false,
2185 eAddressTypeInvalid);
Enrico Granata9fc19442011-07-06 02:13:41 +00002186
2187 // Cache the value if we got one back...
2188 if (synthetic_child)
2189 {
2190 AddSyntheticChild(index_const_str, synthetic_child);
2191 synthetic_child_sp = synthetic_child->GetSP();
Enrico Granata6f3533f2011-07-29 19:53:35 +00002192 synthetic_child_sp->SetName(ConstString(index_str));
Enrico Granata9fc19442011-07-06 02:13:41 +00002193 synthetic_child_sp->m_is_bitfield_for_scalar = true;
2194 }
2195 }
2196 }
2197 return synthetic_child_sp;
2198}
2199
Greg Claytonafacd142011-09-02 01:15:17 +00002200ValueObjectSP
Enrico Granata6f3533f2011-07-29 19:53:35 +00002201ValueObject::GetSyntheticChildAtOffset(uint32_t offset, const ClangASTType& type, bool can_create)
2202{
2203
2204 ValueObjectSP synthetic_child_sp;
2205
2206 char name_str[64];
2207 snprintf(name_str, sizeof(name_str), "@%i", offset);
2208 ConstString name_const_str(name_str);
2209
2210 // Check if we have already created a synthetic array member in this
2211 // valid object. If we have we will re-use it.
2212 synthetic_child_sp = GetSyntheticChild (name_const_str);
2213
2214 if (synthetic_child_sp.get())
2215 return synthetic_child_sp;
2216
2217 if (!can_create)
Greg Claytonafacd142011-09-02 01:15:17 +00002218 return ValueObjectSP();
Enrico Granata6f3533f2011-07-29 19:53:35 +00002219
2220 ValueObjectChild *synthetic_child = new ValueObjectChild(*this,
Greg Clayton57ee3062013-07-11 22:46:58 +00002221 type,
Enrico Granata6f3533f2011-07-29 19:53:35 +00002222 name_const_str,
Greg Clayton57ee3062013-07-11 22:46:58 +00002223 type.GetByteSize(),
Enrico Granata6f3533f2011-07-29 19:53:35 +00002224 offset,
2225 0,
2226 0,
2227 false,
Enrico Granata9128ee22011-09-06 19:20:51 +00002228 false,
2229 eAddressTypeInvalid);
Enrico Granata6f3533f2011-07-29 19:53:35 +00002230 if (synthetic_child)
2231 {
2232 AddSyntheticChild(name_const_str, synthetic_child);
2233 synthetic_child_sp = synthetic_child->GetSP();
2234 synthetic_child_sp->SetName(name_const_str);
2235 synthetic_child_sp->m_is_child_at_offset = true;
2236 }
2237 return synthetic_child_sp;
2238}
2239
Enrico Granata32556cd2014-08-26 20:54:04 +00002240ValueObjectSP
Enrico Granata59953f02014-08-26 21:35:30 +00002241ValueObject::GetSyntheticBase (uint32_t offset, const ClangASTType& type, bool can_create)
Enrico Granata32556cd2014-08-26 20:54:04 +00002242{
2243 ValueObjectSP synthetic_child_sp;
2244
2245 char name_str[64];
2246 snprintf(name_str, sizeof(name_str), "%s", type.GetTypeName().AsCString("<unknown>"));
2247 ConstString name_const_str(name_str);
2248
2249 // Check if we have already created a synthetic array member in this
2250 // valid object. If we have we will re-use it.
2251 synthetic_child_sp = GetSyntheticChild (name_const_str);
2252
2253 if (synthetic_child_sp.get())
2254 return synthetic_child_sp;
2255
2256 if (!can_create)
2257 return ValueObjectSP();
2258
Enrico Granata32556cd2014-08-26 20:54:04 +00002259 const bool is_base_class = true;
2260
2261 ValueObjectChild *synthetic_child = new ValueObjectChild(*this,
2262 type,
2263 name_const_str,
2264 type.GetByteSize(),
2265 offset,
2266 0,
2267 0,
2268 is_base_class,
2269 false,
2270 eAddressTypeInvalid);
2271 if (synthetic_child)
2272 {
2273 AddSyntheticChild(name_const_str, synthetic_child);
2274 synthetic_child_sp = synthetic_child->GetSP();
2275 synthetic_child_sp->SetName(name_const_str);
2276 }
2277 return synthetic_child_sp;
2278}
2279
2280
Enrico Granatad55546b2011-07-22 00:16:08 +00002281// your expression path needs to have a leading . or ->
2282// (unless it somehow "looks like" an array, in which case it has
2283// a leading [ symbol). while the [ is meaningful and should be shown
2284// to the user, . and -> are just parser design, but by no means
2285// added information for the user.. strip them off
2286static const char*
2287SkipLeadingExpressionPathSeparators(const char* expression)
2288{
2289 if (!expression || !expression[0])
2290 return expression;
2291 if (expression[0] == '.')
2292 return expression+1;
2293 if (expression[0] == '-' && expression[1] == '>')
2294 return expression+2;
2295 return expression;
2296}
2297
Greg Claytonafacd142011-09-02 01:15:17 +00002298ValueObjectSP
Enrico Granatad55546b2011-07-22 00:16:08 +00002299ValueObject::GetSyntheticExpressionPathChild(const char* expression, bool can_create)
2300{
2301 ValueObjectSP synthetic_child_sp;
2302 ConstString name_const_string(expression);
2303 // Check if we have already created a synthetic array member in this
2304 // valid object. If we have we will re-use it.
2305 synthetic_child_sp = GetSyntheticChild (name_const_string);
2306 if (!synthetic_child_sp)
2307 {
2308 // We haven't made a synthetic array member for expression yet, so
2309 // lets make one and cache it for any future reference.
Enrico Granatadf31a8a2012-08-02 17:34:05 +00002310 synthetic_child_sp = GetValueForExpressionPath(expression,
2311 NULL, NULL, NULL,
2312 GetValueForExpressionPathOptions().DontAllowSyntheticChildren());
Enrico Granatad55546b2011-07-22 00:16:08 +00002313
2314 // Cache the value if we got one back...
2315 if (synthetic_child_sp.get())
2316 {
Enrico Granataea2bc0f2013-02-21 19:57:10 +00002317 // FIXME: this causes a "real" child to end up with its name changed to the contents of expression
Enrico Granatad55546b2011-07-22 00:16:08 +00002318 AddSyntheticChild(name_const_string, synthetic_child_sp.get());
Enrico Granata6f3533f2011-07-29 19:53:35 +00002319 synthetic_child_sp->SetName(ConstString(SkipLeadingExpressionPathSeparators(expression)));
Enrico Granatad55546b2011-07-22 00:16:08 +00002320 }
2321 }
2322 return synthetic_child_sp;
2323}
2324
2325void
Enrico Granata86cc9822012-03-19 22:58:49 +00002326ValueObject::CalculateSyntheticValue (bool use_synthetic)
Enrico Granatad55546b2011-07-22 00:16:08 +00002327{
Enrico Granata86cc9822012-03-19 22:58:49 +00002328 if (use_synthetic == false)
Enrico Granatad55546b2011-07-22 00:16:08 +00002329 return;
2330
Enrico Granatac5bc4122012-03-27 02:35:13 +00002331 TargetSP target_sp(GetTargetSP());
Enrico Granata5d5f60c2013-09-24 22:58:37 +00002332 if (target_sp && target_sp->GetEnableSyntheticValue() == false)
Enrico Granatac5bc4122012-03-27 02:35:13 +00002333 {
2334 m_synthetic_value = NULL;
2335 return;
2336 }
2337
Enrico Granatae3e91512012-10-22 18:18:36 +00002338 lldb::SyntheticChildrenSP current_synth_sp(m_synthetic_children_sp);
2339
Enrico Granata5548cb52013-01-28 23:47:25 +00002340 if (!UpdateFormatsIfNeeded() && m_synthetic_value)
Enrico Granata86cc9822012-03-19 22:58:49 +00002341 return;
Enrico Granatad55546b2011-07-22 00:16:08 +00002342
Enrico Granata0c489f52012-03-01 04:24:26 +00002343 if (m_synthetic_children_sp.get() == NULL)
Enrico Granatad55546b2011-07-22 00:16:08 +00002344 return;
2345
Enrico Granatae3e91512012-10-22 18:18:36 +00002346 if (current_synth_sp == m_synthetic_children_sp && m_synthetic_value)
2347 return;
2348
Enrico Granata86cc9822012-03-19 22:58:49 +00002349 m_synthetic_value = new ValueObjectSynthetic(*this, m_synthetic_children_sp);
Enrico Granatad55546b2011-07-22 00:16:08 +00002350}
2351
Jim Ingham78a685a2011-04-16 00:01:13 +00002352void
Greg Claytonafacd142011-09-02 01:15:17 +00002353ValueObject::CalculateDynamicValue (DynamicValueType use_dynamic)
Jim Ingham22777012010-09-23 02:01:19 +00002354{
Greg Claytonafacd142011-09-02 01:15:17 +00002355 if (use_dynamic == eNoDynamicValues)
Jim Ingham2837b762011-05-04 03:43:18 +00002356 return;
2357
Jim Ingham58b59f92011-04-22 23:53:53 +00002358 if (!m_dynamic_value && !IsDynamic())
Jim Ingham78a685a2011-04-16 00:01:13 +00002359 {
Greg Claytoncc4d0142012-02-17 07:49:44 +00002360 ExecutionContext exe_ctx (GetExecutionContextRef());
2361 Process *process = exe_ctx.GetProcessPtr();
Enrico Granatafd4c84e2012-05-21 16:51:35 +00002362 if (process && process->IsPossibleDynamicValue(*this))
Enrico Granatae3e91512012-10-22 18:18:36 +00002363 {
2364 ClearDynamicTypeInformation ();
Enrico Granatafd4c84e2012-05-21 16:51:35 +00002365 m_dynamic_value = new ValueObjectDynamicValue (*this, use_dynamic);
Enrico Granatae3e91512012-10-22 18:18:36 +00002366 }
Jim Ingham78a685a2011-04-16 00:01:13 +00002367 }
2368}
2369
Jim Ingham58b59f92011-04-22 23:53:53 +00002370ValueObjectSP
Jim Ingham2837b762011-05-04 03:43:18 +00002371ValueObject::GetDynamicValue (DynamicValueType use_dynamic)
Jim Ingham78a685a2011-04-16 00:01:13 +00002372{
Greg Claytonafacd142011-09-02 01:15:17 +00002373 if (use_dynamic == eNoDynamicValues)
Jim Ingham2837b762011-05-04 03:43:18 +00002374 return ValueObjectSP();
2375
2376 if (!IsDynamic() && m_dynamic_value == NULL)
Jim Ingham78a685a2011-04-16 00:01:13 +00002377 {
Jim Ingham2837b762011-05-04 03:43:18 +00002378 CalculateDynamicValue(use_dynamic);
Jim Ingham78a685a2011-04-16 00:01:13 +00002379 }
Jim Ingham58b59f92011-04-22 23:53:53 +00002380 if (m_dynamic_value)
2381 return m_dynamic_value->GetSP();
2382 else
2383 return ValueObjectSP();
Jim Ingham22777012010-09-23 02:01:19 +00002384}
Greg Clayton1d3afba2010-10-05 00:00:42 +00002385
Jim Ingham60dbabb2011-12-08 19:44:08 +00002386ValueObjectSP
2387ValueObject::GetStaticValue()
2388{
2389 return GetSP();
2390}
2391
Enrico Granata886147f2012-05-08 18:47:08 +00002392lldb::ValueObjectSP
2393ValueObject::GetNonSyntheticValue ()
2394{
2395 return GetSP();
2396}
2397
Enrico Granatad55546b2011-07-22 00:16:08 +00002398ValueObjectSP
Enrico Granata86cc9822012-03-19 22:58:49 +00002399ValueObject::GetSyntheticValue (bool use_synthetic)
Enrico Granatad55546b2011-07-22 00:16:08 +00002400{
Enrico Granata86cc9822012-03-19 22:58:49 +00002401 if (use_synthetic == false)
2402 return ValueObjectSP();
2403
Enrico Granatad55546b2011-07-22 00:16:08 +00002404 CalculateSyntheticValue(use_synthetic);
2405
2406 if (m_synthetic_value)
2407 return m_synthetic_value->GetSP();
2408 else
Enrico Granata86cc9822012-03-19 22:58:49 +00002409 return ValueObjectSP();
Enrico Granatad55546b2011-07-22 00:16:08 +00002410}
2411
Greg Claytone221f822011-01-21 01:59:00 +00002412bool
Enrico Granata27b625e2011-08-09 01:04:56 +00002413ValueObject::HasSyntheticValue()
2414{
Enrico Granata5548cb52013-01-28 23:47:25 +00002415 UpdateFormatsIfNeeded();
Enrico Granata27b625e2011-08-09 01:04:56 +00002416
Enrico Granata0c489f52012-03-01 04:24:26 +00002417 if (m_synthetic_children_sp.get() == NULL)
Enrico Granata27b625e2011-08-09 01:04:56 +00002418 return false;
2419
Enrico Granata86cc9822012-03-19 22:58:49 +00002420 CalculateSyntheticValue(true);
Enrico Granata27b625e2011-08-09 01:04:56 +00002421
2422 if (m_synthetic_value)
2423 return true;
2424 else
2425 return false;
2426}
2427
2428bool
Greg Claytone221f822011-01-21 01:59:00 +00002429ValueObject::GetBaseClassPath (Stream &s)
2430{
2431 if (IsBaseClass())
2432 {
Jim Ingham78a685a2011-04-16 00:01:13 +00002433 bool parent_had_base_class = GetParent() && GetParent()->GetBaseClassPath (s);
Greg Clayton57ee3062013-07-11 22:46:58 +00002434 ClangASTType clang_type = GetClangType();
Greg Claytone221f822011-01-21 01:59:00 +00002435 std::string cxx_class_name;
Greg Clayton57ee3062013-07-11 22:46:58 +00002436 bool this_had_base_class = clang_type.GetCXXClassName (cxx_class_name);
Greg Claytone221f822011-01-21 01:59:00 +00002437 if (this_had_base_class)
2438 {
2439 if (parent_had_base_class)
2440 s.PutCString("::");
2441 s.PutCString(cxx_class_name.c_str());
2442 }
2443 return parent_had_base_class || this_had_base_class;
2444 }
2445 return false;
2446}
2447
2448
2449ValueObject *
2450ValueObject::GetNonBaseClassParent()
2451{
Jim Ingham78a685a2011-04-16 00:01:13 +00002452 if (GetParent())
Greg Claytone221f822011-01-21 01:59:00 +00002453 {
Jim Ingham78a685a2011-04-16 00:01:13 +00002454 if (GetParent()->IsBaseClass())
2455 return GetParent()->GetNonBaseClassParent();
Greg Claytone221f822011-01-21 01:59:00 +00002456 else
Jim Ingham78a685a2011-04-16 00:01:13 +00002457 return GetParent();
Greg Claytone221f822011-01-21 01:59:00 +00002458 }
2459 return NULL;
2460}
Greg Clayton1d3afba2010-10-05 00:00:42 +00002461
Enrico Granataa3c8f042014-08-19 22:29:08 +00002462
2463bool
2464ValueObject::IsBaseClass (uint32_t& depth)
2465{
2466 if (!IsBaseClass())
2467 {
2468 depth = 0;
2469 return false;
2470 }
2471 if (GetParent())
2472 {
2473 GetParent()->IsBaseClass(depth);
2474 depth = depth + 1;
2475 return true;
2476 }
2477 // TODO: a base of no parent? weird..
2478 depth = 1;
2479 return true;
2480}
2481
Greg Clayton1d3afba2010-10-05 00:00:42 +00002482void
Enrico Granata4becb372011-06-29 22:27:15 +00002483ValueObject::GetExpressionPath (Stream &s, bool qualify_cxx_base_classes, GetExpressionPathFormat epformat)
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002484{
Greg Claytone221f822011-01-21 01:59:00 +00002485 const bool is_deref_of_parent = IsDereferenceOfParent ();
Greg Claytone221f822011-01-21 01:59:00 +00002486
Enrico Granata86cc9822012-03-19 22:58:49 +00002487 if (is_deref_of_parent && epformat == eGetExpressionPathFormatDereferencePointers)
Enrico Granata85933ed2011-08-18 16:38:26 +00002488 {
Enrico Granata4becb372011-06-29 22:27:15 +00002489 // this is the original format of GetExpressionPath() producing code like *(a_ptr).memberName, which is entirely
2490 // fine, until you put this into StackFrame::GetValueForVariableExpressionPath() which prefers to see a_ptr->memberName.
2491 // the eHonorPointers mode is meant to produce strings in this latter format
2492 s.PutCString("*(");
2493 }
Greg Claytone221f822011-01-21 01:59:00 +00002494
Enrico Granata4becb372011-06-29 22:27:15 +00002495 ValueObject* parent = GetParent();
2496
2497 if (parent)
2498 parent->GetExpressionPath (s, qualify_cxx_base_classes, epformat);
Enrico Granata0a3958e2011-07-02 00:25:22 +00002499
2500 // if we are a deref_of_parent just because we are synthetic array
2501 // members made up to allow ptr[%d] syntax to work in variable
2502 // printing, then add our name ([%d]) to the expression path
Enrico Granata86cc9822012-03-19 22:58:49 +00002503 if (m_is_array_item_for_pointer && epformat == eGetExpressionPathFormatHonorPointers)
Enrico Granata0a3958e2011-07-02 00:25:22 +00002504 s.PutCString(m_name.AsCString());
Enrico Granata4becb372011-06-29 22:27:15 +00002505
Greg Claytone221f822011-01-21 01:59:00 +00002506 if (!IsBaseClass())
2507 {
2508 if (!is_deref_of_parent)
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002509 {
Greg Claytone221f822011-01-21 01:59:00 +00002510 ValueObject *non_base_class_parent = GetNonBaseClassParent();
2511 if (non_base_class_parent)
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002512 {
Greg Clayton57ee3062013-07-11 22:46:58 +00002513 ClangASTType non_base_class_parent_clang_type = non_base_class_parent->GetClangType();
Greg Claytone221f822011-01-21 01:59:00 +00002514 if (non_base_class_parent_clang_type)
2515 {
Enrico Granata86cc9822012-03-19 22:58:49 +00002516 if (parent && parent->IsDereferenceOfParent() && epformat == eGetExpressionPathFormatHonorPointers)
Greg Claytone221f822011-01-21 01:59:00 +00002517 {
2518 s.PutCString("->");
2519 }
Enrico Granata4becb372011-06-29 22:27:15 +00002520 else
2521 {
Greg Clayton57ee3062013-07-11 22:46:58 +00002522 const uint32_t non_base_class_parent_type_info = non_base_class_parent_clang_type.GetTypeInfo();
2523
Enrico Granata622be232014-10-21 20:52:14 +00002524 if (non_base_class_parent_type_info & eTypeIsPointer)
Enrico Granata4becb372011-06-29 22:27:15 +00002525 {
2526 s.PutCString("->");
2527 }
Enrico Granata622be232014-10-21 20:52:14 +00002528 else if ((non_base_class_parent_type_info & eTypeHasChildren) &&
2529 !(non_base_class_parent_type_info & eTypeIsArray))
Enrico Granata4becb372011-06-29 22:27:15 +00002530 {
2531 s.PutChar('.');
2532 }
Greg Claytone221f822011-01-21 01:59:00 +00002533 }
2534 }
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002535 }
Greg Claytone221f822011-01-21 01:59:00 +00002536
2537 const char *name = GetName().GetCString();
2538 if (name)
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002539 {
Greg Claytone221f822011-01-21 01:59:00 +00002540 if (qualify_cxx_base_classes)
2541 {
2542 if (GetBaseClassPath (s))
2543 s.PutCString("::");
2544 }
2545 s.PutCString(name);
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002546 }
2547 }
2548 }
2549
Enrico Granata86cc9822012-03-19 22:58:49 +00002550 if (is_deref_of_parent && epformat == eGetExpressionPathFormatDereferencePointers)
Enrico Granata85933ed2011-08-18 16:38:26 +00002551 {
Greg Claytone221f822011-01-21 01:59:00 +00002552 s.PutChar(')');
Enrico Granata4becb372011-06-29 22:27:15 +00002553 }
Greg Clayton8f92f0a2010-10-14 22:52:14 +00002554}
2555
Greg Claytonafacd142011-09-02 01:15:17 +00002556ValueObjectSP
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002557ValueObject::GetValueForExpressionPath(const char* expression,
2558 const char** first_unparsed,
2559 ExpressionPathScanEndReason* reason_to_stop,
2560 ExpressionPathEndResultType* final_value_type,
2561 const GetValueForExpressionPathOptions& options,
2562 ExpressionPathAftermath* final_task_on_target)
2563{
2564
2565 const char* dummy_first_unparsed;
Enrico Granataea2bc0f2013-02-21 19:57:10 +00002566 ExpressionPathScanEndReason dummy_reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnknown;
2567 ExpressionPathEndResultType dummy_final_value_type = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granata86cc9822012-03-19 22:58:49 +00002568 ExpressionPathAftermath dummy_final_task_on_target = ValueObject::eExpressionPathAftermathNothing;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002569
2570 ValueObjectSP ret_val = GetValueForExpressionPath_Impl(expression,
2571 first_unparsed ? first_unparsed : &dummy_first_unparsed,
2572 reason_to_stop ? reason_to_stop : &dummy_reason_to_stop,
2573 final_value_type ? final_value_type : &dummy_final_value_type,
2574 options,
2575 final_task_on_target ? final_task_on_target : &dummy_final_task_on_target);
2576
Enrico Granata86cc9822012-03-19 22:58:49 +00002577 if (!final_task_on_target || *final_task_on_target == ValueObject::eExpressionPathAftermathNothing)
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002578 return ret_val;
Enrico Granata385ad4e2012-03-03 00:45:57 +00002579
Enrico Granata86cc9822012-03-19 22:58:49 +00002580 if (ret_val.get() && ((final_value_type ? *final_value_type : dummy_final_value_type) == eExpressionPathEndResultTypePlain)) // I can only deref and takeaddress of plain objects
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002581 {
Enrico Granata86cc9822012-03-19 22:58:49 +00002582 if ( (final_task_on_target ? *final_task_on_target : dummy_final_task_on_target) == ValueObject::eExpressionPathAftermathDereference)
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002583 {
2584 Error error;
2585 ValueObjectSP final_value = ret_val->Dereference(error);
2586 if (error.Fail() || !final_value.get())
2587 {
Enrico Granata385ad4e2012-03-03 00:45:57 +00002588 if (reason_to_stop)
Enrico Granata86cc9822012-03-19 22:58:49 +00002589 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonDereferencingFailed;
Enrico Granata385ad4e2012-03-03 00:45:57 +00002590 if (final_value_type)
Enrico Granata86cc9822012-03-19 22:58:49 +00002591 *final_value_type = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002592 return ValueObjectSP();
2593 }
2594 else
2595 {
Enrico Granata385ad4e2012-03-03 00:45:57 +00002596 if (final_task_on_target)
Enrico Granata86cc9822012-03-19 22:58:49 +00002597 *final_task_on_target = ValueObject::eExpressionPathAftermathNothing;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002598 return final_value;
2599 }
2600 }
Enrico Granata86cc9822012-03-19 22:58:49 +00002601 if (*final_task_on_target == ValueObject::eExpressionPathAftermathTakeAddress)
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002602 {
2603 Error error;
2604 ValueObjectSP final_value = ret_val->AddressOf(error);
2605 if (error.Fail() || !final_value.get())
2606 {
Enrico Granata385ad4e2012-03-03 00:45:57 +00002607 if (reason_to_stop)
Enrico Granata86cc9822012-03-19 22:58:49 +00002608 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonTakingAddressFailed;
Enrico Granata385ad4e2012-03-03 00:45:57 +00002609 if (final_value_type)
Enrico Granata86cc9822012-03-19 22:58:49 +00002610 *final_value_type = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002611 return ValueObjectSP();
2612 }
2613 else
2614 {
Enrico Granata385ad4e2012-03-03 00:45:57 +00002615 if (final_task_on_target)
Enrico Granata86cc9822012-03-19 22:58:49 +00002616 *final_task_on_target = ValueObject::eExpressionPathAftermathNothing;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002617 return final_value;
2618 }
2619 }
2620 }
2621 return ret_val; // final_task_on_target will still have its original value, so you know I did not do it
2622}
2623
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00002624int
2625ValueObject::GetValuesForExpressionPath(const char* expression,
Greg Claytonafacd142011-09-02 01:15:17 +00002626 ValueObjectListSP& list,
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00002627 const char** first_unparsed,
2628 ExpressionPathScanEndReason* reason_to_stop,
2629 ExpressionPathEndResultType* final_value_type,
2630 const GetValueForExpressionPathOptions& options,
2631 ExpressionPathAftermath* final_task_on_target)
2632{
2633 const char* dummy_first_unparsed;
2634 ExpressionPathScanEndReason dummy_reason_to_stop;
2635 ExpressionPathEndResultType dummy_final_value_type;
Enrico Granata86cc9822012-03-19 22:58:49 +00002636 ExpressionPathAftermath dummy_final_task_on_target = ValueObject::eExpressionPathAftermathNothing;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00002637
2638 ValueObjectSP ret_val = GetValueForExpressionPath_Impl(expression,
2639 first_unparsed ? first_unparsed : &dummy_first_unparsed,
2640 reason_to_stop ? reason_to_stop : &dummy_reason_to_stop,
2641 final_value_type ? final_value_type : &dummy_final_value_type,
2642 options,
2643 final_task_on_target ? final_task_on_target : &dummy_final_task_on_target);
2644
2645 if (!ret_val.get()) // if there are errors, I add nothing to the list
2646 return 0;
2647
Enrico Granata86ea8d82012-03-29 01:34:34 +00002648 if ( (reason_to_stop ? *reason_to_stop : dummy_reason_to_stop) != eExpressionPathScanEndReasonArrayRangeOperatorMet)
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00002649 {
2650 // I need not expand a range, just post-process the final value and return
Enrico Granata86cc9822012-03-19 22:58:49 +00002651 if (!final_task_on_target || *final_task_on_target == ValueObject::eExpressionPathAftermathNothing)
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00002652 {
2653 list->Append(ret_val);
2654 return 1;
2655 }
Enrico Granata86ea8d82012-03-29 01:34:34 +00002656 if (ret_val.get() && (final_value_type ? *final_value_type : dummy_final_value_type) == eExpressionPathEndResultTypePlain) // I can only deref and takeaddress of plain objects
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00002657 {
Enrico Granata86cc9822012-03-19 22:58:49 +00002658 if (*final_task_on_target == ValueObject::eExpressionPathAftermathDereference)
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00002659 {
2660 Error error;
2661 ValueObjectSP final_value = ret_val->Dereference(error);
2662 if (error.Fail() || !final_value.get())
2663 {
Greg Clayton23f59502012-07-17 03:23:13 +00002664 if (reason_to_stop)
2665 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonDereferencingFailed;
2666 if (final_value_type)
2667 *final_value_type = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00002668 return 0;
2669 }
2670 else
2671 {
Enrico Granata86cc9822012-03-19 22:58:49 +00002672 *final_task_on_target = ValueObject::eExpressionPathAftermathNothing;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00002673 list->Append(final_value);
2674 return 1;
2675 }
2676 }
Enrico Granata86cc9822012-03-19 22:58:49 +00002677 if (*final_task_on_target == ValueObject::eExpressionPathAftermathTakeAddress)
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00002678 {
2679 Error error;
2680 ValueObjectSP final_value = ret_val->AddressOf(error);
2681 if (error.Fail() || !final_value.get())
2682 {
Greg Clayton23f59502012-07-17 03:23:13 +00002683 if (reason_to_stop)
2684 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonTakingAddressFailed;
2685 if (final_value_type)
2686 *final_value_type = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00002687 return 0;
2688 }
2689 else
2690 {
Enrico Granata86cc9822012-03-19 22:58:49 +00002691 *final_task_on_target = ValueObject::eExpressionPathAftermathNothing;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00002692 list->Append(final_value);
2693 return 1;
2694 }
2695 }
2696 }
2697 }
2698 else
2699 {
2700 return ExpandArraySliceExpression(first_unparsed ? *first_unparsed : dummy_first_unparsed,
2701 first_unparsed ? first_unparsed : &dummy_first_unparsed,
2702 ret_val,
2703 list,
2704 reason_to_stop ? reason_to_stop : &dummy_reason_to_stop,
2705 final_value_type ? final_value_type : &dummy_final_value_type,
2706 options,
2707 final_task_on_target ? final_task_on_target : &dummy_final_task_on_target);
2708 }
2709 // in any non-covered case, just do the obviously right thing
2710 list->Append(ret_val);
2711 return 1;
2712}
2713
Greg Claytonafacd142011-09-02 01:15:17 +00002714ValueObjectSP
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002715ValueObject::GetValueForExpressionPath_Impl(const char* expression_cstr,
2716 const char** first_unparsed,
2717 ExpressionPathScanEndReason* reason_to_stop,
2718 ExpressionPathEndResultType* final_result,
2719 const GetValueForExpressionPathOptions& options,
2720 ExpressionPathAftermath* what_next)
2721{
2722 ValueObjectSP root = GetSP();
2723
2724 if (!root.get())
2725 return ValueObjectSP();
2726
2727 *first_unparsed = expression_cstr;
2728
2729 while (true)
2730 {
2731
2732 const char* expression_cstr = *first_unparsed; // hide the top level expression_cstr
2733
Greg Clayton57ee3062013-07-11 22:46:58 +00002734 ClangASTType root_clang_type = root->GetClangType();
2735 ClangASTType pointee_clang_type;
2736 Flags pointee_clang_type_info;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00002737
Greg Clayton57ee3062013-07-11 22:46:58 +00002738 Flags root_clang_type_info(root_clang_type.GetTypeInfo(&pointee_clang_type));
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00002739 if (pointee_clang_type)
Greg Clayton57ee3062013-07-11 22:46:58 +00002740 pointee_clang_type_info.Reset(pointee_clang_type.GetTypeInfo());
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002741
2742 if (!expression_cstr || *expression_cstr == '\0')
2743 {
Enrico Granata86cc9822012-03-19 22:58:49 +00002744 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonEndOfString;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002745 return root;
2746 }
2747
2748 switch (*expression_cstr)
2749 {
2750 case '-':
2751 {
2752 if (options.m_check_dot_vs_arrow_syntax &&
Enrico Granata622be232014-10-21 20:52:14 +00002753 root_clang_type_info.Test(eTypeIsPointer) ) // if you are trying to use -> on a non-pointer and I must catch the error
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002754 {
2755 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00002756 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonArrowInsteadOfDot;
2757 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002758 return ValueObjectSP();
2759 }
Enrico Granata622be232014-10-21 20:52:14 +00002760 if (root_clang_type_info.Test(eTypeIsObjC) && // if yo are trying to extract an ObjC IVar when this is forbidden
2761 root_clang_type_info.Test(eTypeIsPointer) &&
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002762 options.m_no_fragile_ivar)
2763 {
2764 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00002765 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonFragileIVarNotAllowed;
2766 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002767 return ValueObjectSP();
2768 }
2769 if (expression_cstr[1] != '>')
2770 {
2771 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00002772 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
2773 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002774 return ValueObjectSP();
2775 }
2776 expression_cstr++; // skip the -
2777 }
2778 case '.': // or fallthrough from ->
2779 {
2780 if (options.m_check_dot_vs_arrow_syntax && *expression_cstr == '.' &&
Enrico Granata622be232014-10-21 20:52:14 +00002781 root_clang_type_info.Test(eTypeIsPointer)) // if you are trying to use . on a pointer and I must catch the error
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002782 {
2783 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00002784 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonDotInsteadOfArrow;
2785 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002786 return ValueObjectSP();
2787 }
2788 expression_cstr++; // skip .
2789 const char *next_separator = strpbrk(expression_cstr+1,"-.[");
2790 ConstString child_name;
2791 if (!next_separator) // if no other separator just expand this last layer
2792 {
2793 child_name.SetCString (expression_cstr);
Enrico Granata8c9d3562011-08-11 17:08:01 +00002794 ValueObjectSP child_valobj_sp = root->GetChildMemberWithName(child_name, true);
2795
2796 if (child_valobj_sp.get()) // we know we are done, so just return
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002797 {
Daniel Maleaa85e6b62012-12-07 22:21:08 +00002798 *first_unparsed = "";
Enrico Granata86cc9822012-03-19 22:58:49 +00002799 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonEndOfString;
2800 *final_result = ValueObject::eExpressionPathEndResultTypePlain;
Enrico Granata8c9d3562011-08-11 17:08:01 +00002801 return child_valobj_sp;
2802 }
2803 else if (options.m_no_synthetic_children == false) // let's try with synthetic children
2804 {
Enrico Granata86cc9822012-03-19 22:58:49 +00002805 if (root->IsSynthetic())
Enrico Granatadf31a8a2012-08-02 17:34:05 +00002806 {
2807 *first_unparsed = expression_cstr;
Enrico Granatad07cfd32014-10-08 18:27:36 +00002808 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchSyntheticChild;
Enrico Granatadf31a8a2012-08-02 17:34:05 +00002809 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2810 return ValueObjectSP();
2811 }
2812
2813 child_valobj_sp = root->GetSyntheticValue();
Enrico Granata86cc9822012-03-19 22:58:49 +00002814 if (child_valobj_sp.get())
2815 child_valobj_sp = child_valobj_sp->GetChildMemberWithName(child_name, true);
Enrico Granata8c9d3562011-08-11 17:08:01 +00002816 }
2817
2818 // if we are here and options.m_no_synthetic_children is true, child_valobj_sp is going to be a NULL SP,
2819 // so we hit the "else" branch, and return an error
2820 if(child_valobj_sp.get()) // if it worked, just return
2821 {
Daniel Maleaa85e6b62012-12-07 22:21:08 +00002822 *first_unparsed = "";
Enrico Granata86cc9822012-03-19 22:58:49 +00002823 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonEndOfString;
2824 *final_result = ValueObject::eExpressionPathEndResultTypePlain;
Enrico Granata8c9d3562011-08-11 17:08:01 +00002825 return child_valobj_sp;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002826 }
2827 else
2828 {
2829 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00002830 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
2831 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002832 return ValueObjectSP();
2833 }
2834 }
2835 else // other layers do expand
2836 {
2837 child_name.SetCStringWithLength(expression_cstr, next_separator - expression_cstr);
Enrico Granata8c9d3562011-08-11 17:08:01 +00002838 ValueObjectSP child_valobj_sp = root->GetChildMemberWithName(child_name, true);
2839 if (child_valobj_sp.get()) // store the new root and move on
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002840 {
Enrico Granata8c9d3562011-08-11 17:08:01 +00002841 root = child_valobj_sp;
2842 *first_unparsed = next_separator;
Enrico Granata86cc9822012-03-19 22:58:49 +00002843 *final_result = ValueObject::eExpressionPathEndResultTypePlain;
Enrico Granata8c9d3562011-08-11 17:08:01 +00002844 continue;
2845 }
2846 else if (options.m_no_synthetic_children == false) // let's try with synthetic children
2847 {
Enrico Granatadf31a8a2012-08-02 17:34:05 +00002848 if (root->IsSynthetic())
2849 {
2850 *first_unparsed = expression_cstr;
2851 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
2852 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2853 return ValueObjectSP();
2854 }
2855
Enrico Granata86cc9822012-03-19 22:58:49 +00002856 child_valobj_sp = root->GetSyntheticValue(true);
2857 if (child_valobj_sp)
2858 child_valobj_sp = child_valobj_sp->GetChildMemberWithName(child_name, true);
Enrico Granata8c9d3562011-08-11 17:08:01 +00002859 }
2860
2861 // if we are here and options.m_no_synthetic_children is true, child_valobj_sp is going to be a NULL SP,
2862 // so we hit the "else" branch, and return an error
2863 if(child_valobj_sp.get()) // if it worked, move on
2864 {
2865 root = child_valobj_sp;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002866 *first_unparsed = next_separator;
Enrico Granata86cc9822012-03-19 22:58:49 +00002867 *final_result = ValueObject::eExpressionPathEndResultTypePlain;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002868 continue;
2869 }
2870 else
2871 {
2872 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00002873 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
2874 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002875 return ValueObjectSP();
2876 }
2877 }
2878 break;
2879 }
2880 case '[':
2881 {
Enrico Granata622be232014-10-21 20:52:14 +00002882 if (!root_clang_type_info.Test(eTypeIsArray) && !root_clang_type_info.Test(eTypeIsPointer) && !root_clang_type_info.Test(eTypeIsVector)) // if this is not a T[] nor a T*
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002883 {
Enrico Granata622be232014-10-21 20:52:14 +00002884 if (!root_clang_type_info.Test(eTypeIsScalar)) // if this is not even a scalar...
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002885 {
Enrico Granata27b625e2011-08-09 01:04:56 +00002886 if (options.m_no_synthetic_children) // ...only chance left is synthetic
2887 {
2888 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00002889 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorInvalid;
2890 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granata27b625e2011-08-09 01:04:56 +00002891 return ValueObjectSP();
2892 }
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002893 }
2894 else if (!options.m_allow_bitfields_syntax) // if this is a scalar, check that we can expand bitfields
2895 {
2896 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00002897 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorNotAllowed;
2898 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002899 return ValueObjectSP();
2900 }
2901 }
2902 if (*(expression_cstr+1) == ']') // if this is an unbounded range it only works for arrays
2903 {
Enrico Granata622be232014-10-21 20:52:14 +00002904 if (!root_clang_type_info.Test(eTypeIsArray))
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002905 {
2906 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00002907 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonEmptyRangeNotAllowed;
2908 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002909 return ValueObjectSP();
2910 }
2911 else // even if something follows, we cannot expand unbounded ranges, just let the caller do it
2912 {
2913 *first_unparsed = expression_cstr+2;
Enrico Granata86cc9822012-03-19 22:58:49 +00002914 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonArrayRangeOperatorMet;
2915 *final_result = ValueObject::eExpressionPathEndResultTypeUnboundedRange;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002916 return root;
2917 }
2918 }
2919 const char *separator_position = ::strchr(expression_cstr+1,'-');
2920 const char *close_bracket_position = ::strchr(expression_cstr+1,']');
2921 if (!close_bracket_position) // if there is no ], this is a syntax error
2922 {
2923 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00002924 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
2925 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002926 return ValueObjectSP();
2927 }
2928 if (!separator_position || separator_position > close_bracket_position) // if no separator, this is either [] or [N]
2929 {
2930 char *end = NULL;
2931 unsigned long index = ::strtoul (expression_cstr+1, &end, 0);
2932 if (!end || end != close_bracket_position) // if something weird is in our way return an error
2933 {
2934 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00002935 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
2936 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002937 return ValueObjectSP();
2938 }
2939 if (end - expression_cstr == 1) // if this is [], only return a valid value for arrays
2940 {
Enrico Granata622be232014-10-21 20:52:14 +00002941 if (root_clang_type_info.Test(eTypeIsArray))
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002942 {
2943 *first_unparsed = expression_cstr+2;
Enrico Granata86cc9822012-03-19 22:58:49 +00002944 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonArrayRangeOperatorMet;
2945 *final_result = ValueObject::eExpressionPathEndResultTypeUnboundedRange;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002946 return root;
2947 }
2948 else
2949 {
2950 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00002951 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonEmptyRangeNotAllowed;
2952 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002953 return ValueObjectSP();
2954 }
2955 }
2956 // from here on we do have a valid index
Enrico Granata622be232014-10-21 20:52:14 +00002957 if (root_clang_type_info.Test(eTypeIsArray))
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002958 {
Greg Claytondaf515f2011-07-09 20:12:33 +00002959 ValueObjectSP child_valobj_sp = root->GetChildAtIndex(index, true);
2960 if (!child_valobj_sp)
2961 child_valobj_sp = root->GetSyntheticArrayMemberFromArray(index, true);
Enrico Granata27b625e2011-08-09 01:04:56 +00002962 if (!child_valobj_sp)
Enrico Granata86cc9822012-03-19 22:58:49 +00002963 if (root->HasSyntheticValue() && root->GetSyntheticValue()->GetNumChildren() > index)
2964 child_valobj_sp = root->GetSyntheticValue()->GetChildAtIndex(index, true);
Greg Claytondaf515f2011-07-09 20:12:33 +00002965 if (child_valobj_sp)
2966 {
2967 root = child_valobj_sp;
2968 *first_unparsed = end+1; // skip ]
Enrico Granata86cc9822012-03-19 22:58:49 +00002969 *final_result = ValueObject::eExpressionPathEndResultTypePlain;
Greg Claytondaf515f2011-07-09 20:12:33 +00002970 continue;
2971 }
2972 else
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002973 {
2974 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00002975 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
2976 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002977 return ValueObjectSP();
2978 }
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002979 }
Enrico Granata622be232014-10-21 20:52:14 +00002980 else if (root_clang_type_info.Test(eTypeIsPointer))
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002981 {
Enrico Granata86cc9822012-03-19 22:58:49 +00002982 if (*what_next == ValueObject::eExpressionPathAftermathDereference && // if this is a ptr-to-scalar, I am accessing it by index and I would have deref'ed anyway, then do it now and use this as a bitfield
Enrico Granata622be232014-10-21 20:52:14 +00002983 pointee_clang_type_info.Test(eTypeIsScalar))
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002984 {
2985 Error error;
2986 root = root->Dereference(error);
2987 if (error.Fail() || !root.get())
2988 {
2989 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00002990 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonDereferencingFailed;
2991 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002992 return ValueObjectSP();
2993 }
2994 else
2995 {
Enrico Granata86cc9822012-03-19 22:58:49 +00002996 *what_next = eExpressionPathAftermathNothing;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00002997 continue;
2998 }
2999 }
3000 else
3001 {
Greg Clayton57ee3062013-07-11 22:46:58 +00003002 if (root->GetClangType().GetMinimumLanguage() == eLanguageTypeObjC
Enrico Granata622be232014-10-21 20:52:14 +00003003 && pointee_clang_type_info.AllClear(eTypeIsPointer)
Greg Clayton84db9102012-03-26 23:03:23 +00003004 && root->HasSyntheticValue()
3005 && options.m_no_synthetic_children == false)
Enrico Granata27b625e2011-08-09 01:04:56 +00003006 {
Enrico Granata86cc9822012-03-19 22:58:49 +00003007 root = root->GetSyntheticValue()->GetChildAtIndex(index, true);
Enrico Granata27b625e2011-08-09 01:04:56 +00003008 }
3009 else
3010 root = root->GetSyntheticArrayMemberFromPointer(index, true);
Enrico Granatafc7a7f32011-07-08 02:51:01 +00003011 if (!root.get())
3012 {
3013 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003014 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
3015 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00003016 return ValueObjectSP();
3017 }
3018 else
3019 {
3020 *first_unparsed = end+1; // skip ]
Enrico Granata86cc9822012-03-19 22:58:49 +00003021 *final_result = ValueObject::eExpressionPathEndResultTypePlain;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00003022 continue;
3023 }
3024 }
3025 }
Enrico Granata622be232014-10-21 20:52:14 +00003026 else if (root_clang_type_info.Test(eTypeIsScalar))
Enrico Granatafc7a7f32011-07-08 02:51:01 +00003027 {
3028 root = root->GetSyntheticBitFieldChild(index, index, true);
3029 if (!root.get())
3030 {
3031 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003032 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
3033 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00003034 return ValueObjectSP();
3035 }
3036 else // we do not know how to expand members of bitfields, so we just return and let the caller do any further processing
3037 {
3038 *first_unparsed = end+1; // skip ]
Enrico Granata86cc9822012-03-19 22:58:49 +00003039 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonBitfieldRangeOperatorMet;
3040 *final_result = ValueObject::eExpressionPathEndResultTypeBitfield;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00003041 return root;
3042 }
3043 }
Enrico Granata622be232014-10-21 20:52:14 +00003044 else if (root_clang_type_info.Test(eTypeIsVector))
Enrico Granata08a1bb82013-06-19 00:00:45 +00003045 {
3046 root = root->GetChildAtIndex(index, true);
3047 if (!root.get())
3048 {
3049 *first_unparsed = expression_cstr;
3050 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
3051 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
3052 return ValueObjectSP();
3053 }
3054 else
3055 {
3056 *first_unparsed = end+1; // skip ]
3057 *final_result = ValueObject::eExpressionPathEndResultTypePlain;
3058 continue;
3059 }
3060 }
Enrico Granata86cc9822012-03-19 22:58:49 +00003061 else if (options.m_no_synthetic_children == false)
Enrico Granata27b625e2011-08-09 01:04:56 +00003062 {
Enrico Granata86cc9822012-03-19 22:58:49 +00003063 if (root->HasSyntheticValue())
3064 root = root->GetSyntheticValue();
3065 else if (!root->IsSynthetic())
3066 {
3067 *first_unparsed = expression_cstr;
3068 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonSyntheticValueMissing;
3069 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
3070 return ValueObjectSP();
3071 }
3072 // if we are here, then root itself is a synthetic VO.. should be good to go
3073
Enrico Granata27b625e2011-08-09 01:04:56 +00003074 if (!root.get())
3075 {
3076 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003077 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonSyntheticValueMissing;
3078 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
3079 return ValueObjectSP();
3080 }
3081 root = root->GetChildAtIndex(index, true);
3082 if (!root.get())
3083 {
3084 *first_unparsed = expression_cstr;
3085 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
3086 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granata27b625e2011-08-09 01:04:56 +00003087 return ValueObjectSP();
3088 }
Enrico Granata8c9d3562011-08-11 17:08:01 +00003089 else
3090 {
3091 *first_unparsed = end+1; // skip ]
Enrico Granata86cc9822012-03-19 22:58:49 +00003092 *final_result = ValueObject::eExpressionPathEndResultTypePlain;
Enrico Granata8c9d3562011-08-11 17:08:01 +00003093 continue;
3094 }
Enrico Granata27b625e2011-08-09 01:04:56 +00003095 }
3096 else
3097 {
3098 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003099 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
3100 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granata27b625e2011-08-09 01:04:56 +00003101 return ValueObjectSP();
3102 }
Enrico Granatafc7a7f32011-07-08 02:51:01 +00003103 }
3104 else // we have a low and a high index
3105 {
3106 char *end = NULL;
3107 unsigned long index_lower = ::strtoul (expression_cstr+1, &end, 0);
3108 if (!end || end != separator_position) // if something weird is in our way return an error
3109 {
3110 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003111 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
3112 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00003113 return ValueObjectSP();
3114 }
3115 unsigned long index_higher = ::strtoul (separator_position+1, &end, 0);
3116 if (!end || end != close_bracket_position) // if something weird is in our way return an error
3117 {
3118 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003119 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
3120 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00003121 return ValueObjectSP();
3122 }
3123 if (index_lower > index_higher) // swap indices if required
3124 {
3125 unsigned long temp = index_lower;
3126 index_lower = index_higher;
3127 index_higher = temp;
3128 }
Enrico Granata622be232014-10-21 20:52:14 +00003129 if (root_clang_type_info.Test(eTypeIsScalar)) // expansion only works for scalars
Enrico Granatafc7a7f32011-07-08 02:51:01 +00003130 {
3131 root = root->GetSyntheticBitFieldChild(index_lower, index_higher, true);
3132 if (!root.get())
3133 {
3134 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003135 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
3136 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00003137 return ValueObjectSP();
3138 }
3139 else
3140 {
3141 *first_unparsed = end+1; // skip ]
Enrico Granata86cc9822012-03-19 22:58:49 +00003142 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonBitfieldRangeOperatorMet;
3143 *final_result = ValueObject::eExpressionPathEndResultTypeBitfield;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00003144 return root;
3145 }
3146 }
Enrico Granata622be232014-10-21 20:52:14 +00003147 else if (root_clang_type_info.Test(eTypeIsPointer) && // if this is a ptr-to-scalar, I am accessing it by index and I would have deref'ed anyway, then do it now and use this as a bitfield
Enrico Granata86cc9822012-03-19 22:58:49 +00003148 *what_next == ValueObject::eExpressionPathAftermathDereference &&
Enrico Granata622be232014-10-21 20:52:14 +00003149 pointee_clang_type_info.Test(eTypeIsScalar))
Enrico Granatafc7a7f32011-07-08 02:51:01 +00003150 {
3151 Error error;
3152 root = root->Dereference(error);
3153 if (error.Fail() || !root.get())
3154 {
3155 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003156 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonDereferencingFailed;
3157 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00003158 return ValueObjectSP();
3159 }
3160 else
3161 {
Enrico Granata86cc9822012-03-19 22:58:49 +00003162 *what_next = ValueObject::eExpressionPathAftermathNothing;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00003163 continue;
3164 }
3165 }
3166 else
3167 {
3168 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003169 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonArrayRangeOperatorMet;
3170 *final_result = ValueObject::eExpressionPathEndResultTypeBoundedRange;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00003171 return root;
3172 }
3173 }
3174 break;
3175 }
3176 default: // some non-separator is in the way
3177 {
3178 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003179 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
3180 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granatafc7a7f32011-07-08 02:51:01 +00003181 return ValueObjectSP();
3182 break;
3183 }
3184 }
3185 }
3186}
3187
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003188int
3189ValueObject::ExpandArraySliceExpression(const char* expression_cstr,
3190 const char** first_unparsed,
Greg Claytonafacd142011-09-02 01:15:17 +00003191 ValueObjectSP root,
3192 ValueObjectListSP& list,
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003193 ExpressionPathScanEndReason* reason_to_stop,
3194 ExpressionPathEndResultType* final_result,
3195 const GetValueForExpressionPathOptions& options,
3196 ExpressionPathAftermath* what_next)
3197{
3198 if (!root.get())
3199 return 0;
3200
3201 *first_unparsed = expression_cstr;
3202
3203 while (true)
3204 {
3205
3206 const char* expression_cstr = *first_unparsed; // hide the top level expression_cstr
3207
Greg Clayton57ee3062013-07-11 22:46:58 +00003208 ClangASTType root_clang_type = root->GetClangType();
3209 ClangASTType pointee_clang_type;
3210 Flags pointee_clang_type_info;
3211 Flags root_clang_type_info(root_clang_type.GetTypeInfo(&pointee_clang_type));
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003212 if (pointee_clang_type)
Greg Clayton57ee3062013-07-11 22:46:58 +00003213 pointee_clang_type_info.Reset(pointee_clang_type.GetTypeInfo());
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003214
3215 if (!expression_cstr || *expression_cstr == '\0')
3216 {
Enrico Granata86cc9822012-03-19 22:58:49 +00003217 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonEndOfString;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003218 list->Append(root);
3219 return 1;
3220 }
3221
3222 switch (*expression_cstr)
3223 {
3224 case '[':
3225 {
Enrico Granata622be232014-10-21 20:52:14 +00003226 if (!root_clang_type_info.Test(eTypeIsArray) && !root_clang_type_info.Test(eTypeIsPointer)) // if this is not a T[] nor a T*
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003227 {
Enrico Granata622be232014-10-21 20:52:14 +00003228 if (!root_clang_type_info.Test(eTypeIsScalar)) // if this is not even a scalar, this syntax is just plain wrong!
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003229 {
3230 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003231 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorInvalid;
3232 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003233 return 0;
3234 }
3235 else if (!options.m_allow_bitfields_syntax) // if this is a scalar, check that we can expand bitfields
3236 {
3237 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003238 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorNotAllowed;
3239 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003240 return 0;
3241 }
3242 }
3243 if (*(expression_cstr+1) == ']') // if this is an unbounded range it only works for arrays
3244 {
Enrico Granata622be232014-10-21 20:52:14 +00003245 if (!root_clang_type_info.Test(eTypeIsArray))
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003246 {
3247 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003248 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonEmptyRangeNotAllowed;
3249 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003250 return 0;
3251 }
3252 else // expand this into list
3253 {
Greg Claytonc7bece562013-01-25 18:06:21 +00003254 const size_t max_index = root->GetNumChildren() - 1;
3255 for (size_t index = 0; index < max_index; index++)
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003256 {
3257 ValueObjectSP child =
3258 root->GetChildAtIndex(index, true);
3259 list->Append(child);
3260 }
3261 *first_unparsed = expression_cstr+2;
Enrico Granata86cc9822012-03-19 22:58:49 +00003262 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorExpanded;
3263 *final_result = ValueObject::eExpressionPathEndResultTypeValueObjectList;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003264 return max_index; // tell me number of items I added to the VOList
3265 }
3266 }
3267 const char *separator_position = ::strchr(expression_cstr+1,'-');
3268 const char *close_bracket_position = ::strchr(expression_cstr+1,']');
3269 if (!close_bracket_position) // if there is no ], this is a syntax error
3270 {
3271 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003272 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
3273 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003274 return 0;
3275 }
3276 if (!separator_position || separator_position > close_bracket_position) // if no separator, this is either [] or [N]
3277 {
3278 char *end = NULL;
3279 unsigned long index = ::strtoul (expression_cstr+1, &end, 0);
3280 if (!end || end != close_bracket_position) // if something weird is in our way return an error
3281 {
3282 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003283 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
3284 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003285 return 0;
3286 }
3287 if (end - expression_cstr == 1) // if this is [], only return a valid value for arrays
3288 {
Enrico Granata622be232014-10-21 20:52:14 +00003289 if (root_clang_type_info.Test(eTypeIsArray))
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003290 {
Greg Claytonc7bece562013-01-25 18:06:21 +00003291 const size_t max_index = root->GetNumChildren() - 1;
3292 for (size_t index = 0; index < max_index; index++)
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003293 {
3294 ValueObjectSP child =
3295 root->GetChildAtIndex(index, true);
3296 list->Append(child);
3297 }
3298 *first_unparsed = expression_cstr+2;
Enrico Granata86cc9822012-03-19 22:58:49 +00003299 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorExpanded;
3300 *final_result = ValueObject::eExpressionPathEndResultTypeValueObjectList;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003301 return max_index; // tell me number of items I added to the VOList
3302 }
3303 else
3304 {
3305 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003306 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonEmptyRangeNotAllowed;
3307 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003308 return 0;
3309 }
3310 }
3311 // from here on we do have a valid index
Enrico Granata622be232014-10-21 20:52:14 +00003312 if (root_clang_type_info.Test(eTypeIsArray))
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003313 {
3314 root = root->GetChildAtIndex(index, true);
3315 if (!root.get())
3316 {
3317 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003318 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
3319 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003320 return 0;
3321 }
3322 else
3323 {
3324 list->Append(root);
3325 *first_unparsed = end+1; // skip ]
Enrico Granata86cc9822012-03-19 22:58:49 +00003326 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorExpanded;
3327 *final_result = ValueObject::eExpressionPathEndResultTypeValueObjectList;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003328 return 1;
3329 }
3330 }
Enrico Granata622be232014-10-21 20:52:14 +00003331 else if (root_clang_type_info.Test(eTypeIsPointer))
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003332 {
Enrico Granata86cc9822012-03-19 22:58:49 +00003333 if (*what_next == ValueObject::eExpressionPathAftermathDereference && // if this is a ptr-to-scalar, I am accessing it by index and I would have deref'ed anyway, then do it now and use this as a bitfield
Enrico Granata622be232014-10-21 20:52:14 +00003334 pointee_clang_type_info.Test(eTypeIsScalar))
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003335 {
3336 Error error;
3337 root = root->Dereference(error);
3338 if (error.Fail() || !root.get())
3339 {
3340 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003341 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonDereferencingFailed;
3342 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003343 return 0;
3344 }
3345 else
3346 {
Enrico Granata86cc9822012-03-19 22:58:49 +00003347 *what_next = eExpressionPathAftermathNothing;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003348 continue;
3349 }
3350 }
3351 else
3352 {
3353 root = root->GetSyntheticArrayMemberFromPointer(index, true);
3354 if (!root.get())
3355 {
3356 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003357 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
3358 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003359 return 0;
3360 }
3361 else
3362 {
3363 list->Append(root);
3364 *first_unparsed = end+1; // skip ]
Enrico Granata86cc9822012-03-19 22:58:49 +00003365 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorExpanded;
3366 *final_result = ValueObject::eExpressionPathEndResultTypeValueObjectList;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003367 return 1;
3368 }
3369 }
3370 }
3371 else /*if (ClangASTContext::IsScalarType(root_clang_type))*/
3372 {
3373 root = root->GetSyntheticBitFieldChild(index, index, true);
3374 if (!root.get())
3375 {
3376 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003377 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
3378 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003379 return 0;
3380 }
3381 else // we do not know how to expand members of bitfields, so we just return and let the caller do any further processing
3382 {
3383 list->Append(root);
3384 *first_unparsed = end+1; // skip ]
Enrico Granata86cc9822012-03-19 22:58:49 +00003385 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorExpanded;
3386 *final_result = ValueObject::eExpressionPathEndResultTypeValueObjectList;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003387 return 1;
3388 }
3389 }
3390 }
3391 else // we have a low and a high index
3392 {
3393 char *end = NULL;
3394 unsigned long index_lower = ::strtoul (expression_cstr+1, &end, 0);
3395 if (!end || end != separator_position) // if something weird is in our way return an error
3396 {
3397 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003398 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
3399 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003400 return 0;
3401 }
3402 unsigned long index_higher = ::strtoul (separator_position+1, &end, 0);
3403 if (!end || end != close_bracket_position) // if something weird is in our way return an error
3404 {
3405 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003406 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
3407 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003408 return 0;
3409 }
3410 if (index_lower > index_higher) // swap indices if required
3411 {
3412 unsigned long temp = index_lower;
3413 index_lower = index_higher;
3414 index_higher = temp;
3415 }
Enrico Granata622be232014-10-21 20:52:14 +00003416 if (root_clang_type_info.Test(eTypeIsScalar)) // expansion only works for scalars
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003417 {
3418 root = root->GetSyntheticBitFieldChild(index_lower, index_higher, true);
3419 if (!root.get())
3420 {
3421 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003422 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
3423 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003424 return 0;
3425 }
3426 else
3427 {
3428 list->Append(root);
3429 *first_unparsed = end+1; // skip ]
Enrico Granata86cc9822012-03-19 22:58:49 +00003430 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorExpanded;
3431 *final_result = ValueObject::eExpressionPathEndResultTypeValueObjectList;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003432 return 1;
3433 }
3434 }
Enrico Granata622be232014-10-21 20:52:14 +00003435 else if (root_clang_type_info.Test(eTypeIsPointer) && // if this is a ptr-to-scalar, I am accessing it by index and I would have deref'ed anyway, then do it now and use this as a bitfield
Enrico Granata86cc9822012-03-19 22:58:49 +00003436 *what_next == ValueObject::eExpressionPathAftermathDereference &&
Enrico Granata622be232014-10-21 20:52:14 +00003437 pointee_clang_type_info.Test(eTypeIsScalar))
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003438 {
3439 Error error;
3440 root = root->Dereference(error);
3441 if (error.Fail() || !root.get())
3442 {
3443 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003444 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonDereferencingFailed;
3445 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003446 return 0;
3447 }
3448 else
3449 {
Enrico Granata86cc9822012-03-19 22:58:49 +00003450 *what_next = ValueObject::eExpressionPathAftermathNothing;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003451 continue;
3452 }
3453 }
3454 else
3455 {
Johnny Chen44805302011-07-19 19:48:13 +00003456 for (unsigned long index = index_lower;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003457 index <= index_higher; index++)
3458 {
3459 ValueObjectSP child =
3460 root->GetChildAtIndex(index, true);
3461 list->Append(child);
3462 }
3463 *first_unparsed = end+1;
Enrico Granata86cc9822012-03-19 22:58:49 +00003464 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorExpanded;
3465 *final_result = ValueObject::eExpressionPathEndResultTypeValueObjectList;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003466 return index_higher-index_lower+1; // tell me number of items I added to the VOList
3467 }
3468 }
3469 break;
3470 }
3471 default: // some non-[ separator, or something entirely wrong, is in the way
3472 {
3473 *first_unparsed = expression_cstr;
Enrico Granata86cc9822012-03-19 22:58:49 +00003474 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
3475 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
Enrico Granataf9fa6ee2011-07-12 00:18:11 +00003476 return 0;
3477 break;
3478 }
3479 }
3480 }
3481}
3482
Enrico Granata4d93b8c2013-09-30 19:11:51 +00003483void
3484ValueObject::LogValueObject (Log *log)
Greg Clayton1d3afba2010-10-05 00:00:42 +00003485{
Enrico Granata4d93b8c2013-09-30 19:11:51 +00003486 if (log)
3487 return LogValueObject (log, DumpValueObjectOptions::DefaultOptions());
Greg Clayton1d3afba2010-10-05 00:00:42 +00003488}
3489
Enrico Granata0c489f52012-03-01 04:24:26 +00003490void
Enrico Granata4d93b8c2013-09-30 19:11:51 +00003491ValueObject::LogValueObject (Log *log, const DumpValueObjectOptions& options)
Greg Claytonf830dbb2012-03-22 18:15:37 +00003492{
Enrico Granata4d93b8c2013-09-30 19:11:51 +00003493 if (log)
Greg Claytonf830dbb2012-03-22 18:15:37 +00003494 {
3495 StreamString s;
Enrico Granata4d93b8c2013-09-30 19:11:51 +00003496 Dump (s, options);
Greg Claytonf830dbb2012-03-22 18:15:37 +00003497 if (s.GetSize())
3498 log->PutCString(s.GetData());
3499 }
3500}
3501
3502void
Enrico Granata4d93b8c2013-09-30 19:11:51 +00003503ValueObject::Dump (Stream &s)
Enrico Granata0c489f52012-03-01 04:24:26 +00003504{
3505
Enrico Granata4d93b8c2013-09-30 19:11:51 +00003506 ValueObjectPrinter printer(this,&s,DumpValueObjectOptions::DefaultOptions());
3507 printer.PrintValueObject();
Enrico Granata0c489f52012-03-01 04:24:26 +00003508}
3509
3510void
Enrico Granata4d93b8c2013-09-30 19:11:51 +00003511ValueObject::Dump (Stream &s,
3512 const DumpValueObjectOptions& options)
Enrico Granata0c489f52012-03-01 04:24:26 +00003513{
Enrico Granata4d93b8c2013-09-30 19:11:51 +00003514 ValueObjectPrinter printer(this,&s,options);
3515 printer.PrintValueObject();
Enrico Granata0c489f52012-03-01 04:24:26 +00003516}
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003517
3518ValueObjectSP
Jim Ingham6035b672011-03-31 00:19:25 +00003519ValueObject::CreateConstantValue (const ConstString &name)
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003520{
3521 ValueObjectSP valobj_sp;
3522
Enrico Granatac3e320a2011-08-02 17:27:39 +00003523 if (UpdateValueIfNeeded(false) && m_error.Success())
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003524 {
Greg Claytoncc4d0142012-02-17 07:49:44 +00003525 ExecutionContext exe_ctx (GetExecutionContextRef());
Greg Claytoncc4d0142012-02-17 07:49:44 +00003526
3527 DataExtractor data;
3528 data.SetByteOrder (m_data.GetByteOrder());
3529 data.SetAddressByteSize(m_data.GetAddressByteSize());
3530
Enrico Granata9f1e2042012-04-24 22:15:37 +00003531 if (IsBitfield())
3532 {
3533 Value v(Scalar(GetValueAsUnsigned(UINT64_MAX)));
Greg Clayton57ee3062013-07-11 22:46:58 +00003534 m_error = v.GetValueAsData (&exe_ctx, data, 0, GetModule().get());
Enrico Granata9f1e2042012-04-24 22:15:37 +00003535 }
3536 else
Greg Clayton57ee3062013-07-11 22:46:58 +00003537 m_error = m_value.GetValueAsData (&exe_ctx, data, 0, GetModule().get());
Greg Claytoncc4d0142012-02-17 07:49:44 +00003538
3539 valobj_sp = ValueObjectConstResult::Create (exe_ctx.GetBestExecutionContextScope(),
Greg Claytoncc4d0142012-02-17 07:49:44 +00003540 GetClangType(),
3541 name,
3542 data,
3543 GetAddressOf());
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003544 }
Jim Ingham6035b672011-03-31 00:19:25 +00003545
3546 if (!valobj_sp)
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003547 {
Greg Claytoneeb15652013-12-10 23:16:40 +00003548 ExecutionContext exe_ctx (GetExecutionContextRef());
3549 valobj_sp = ValueObjectConstResult::Create (exe_ctx.GetBestExecutionContextScope(), m_error);
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003550 }
3551 return valobj_sp;
3552}
3553
Enrico Granata538a88a2014-10-09 18:24:30 +00003554ValueObjectSP
3555ValueObject::GetQualifiedRepresentationIfAvailable (lldb::DynamicValueType dynValue,
3556 bool synthValue)
3557{
3558 ValueObjectSP result_sp(GetSP());
3559
3560 switch (dynValue)
3561 {
3562 case lldb::eDynamicCanRunTarget:
3563 case lldb::eDynamicDontRunTarget:
3564 {
3565 if (!result_sp->IsDynamic())
3566 {
3567 if (result_sp->GetDynamicValue(dynValue))
3568 result_sp = result_sp->GetDynamicValue(dynValue);
3569 }
3570 }
3571 break;
3572 case lldb::eNoDynamicValues:
Enrico Granata538a88a2014-10-09 18:24:30 +00003573 {
3574 if (result_sp->IsDynamic())
3575 {
3576 if (result_sp->GetStaticValue())
3577 result_sp = result_sp->GetStaticValue();
3578 }
3579 }
3580 break;
3581 }
3582
3583 if (synthValue)
3584 {
3585 if (!result_sp->IsSynthetic())
3586 {
3587 if (result_sp->GetSyntheticValue())
3588 result_sp = result_sp->GetSyntheticValue();
3589 }
3590 }
3591 else
3592 {
3593 if (result_sp->IsSynthetic())
3594 {
3595 if (result_sp->GetNonSyntheticValue())
3596 result_sp = result_sp->GetNonSyntheticValue();
3597 }
3598 }
3599
3600 return result_sp;
3601}
3602
Greg Clayton759e7442014-07-19 00:12:57 +00003603lldb::addr_t
3604ValueObject::GetCPPVTableAddress (AddressType &address_type)
3605{
3606 ClangASTType pointee_type;
3607 ClangASTType this_type(GetClangType());
3608 uint32_t type_info = this_type.GetTypeInfo(&pointee_type);
3609 if (type_info)
3610 {
3611 bool ptr_or_ref = false;
Enrico Granata622be232014-10-21 20:52:14 +00003612 if (type_info & (eTypeIsPointer | eTypeIsReference))
Greg Clayton759e7442014-07-19 00:12:57 +00003613 {
3614 ptr_or_ref = true;
3615 type_info = pointee_type.GetTypeInfo();
3616 }
3617
Enrico Granata622be232014-10-21 20:52:14 +00003618 const uint32_t cpp_class = eTypeIsClass | eTypeIsCPlusPlus;
Greg Clayton759e7442014-07-19 00:12:57 +00003619 if ((type_info & cpp_class) == cpp_class)
3620 {
3621 if (ptr_or_ref)
3622 {
3623 address_type = GetAddressTypeOfChildren();
3624 return GetValueAsUnsigned(LLDB_INVALID_ADDRESS);
3625 }
3626 else
3627 return GetAddressOf (false, &address_type);
3628 }
3629 }
3630
3631 address_type = eAddressTypeInvalid;
3632 return LLDB_INVALID_ADDRESS;
3633}
3634
Greg Claytonafacd142011-09-02 01:15:17 +00003635ValueObjectSP
Greg Claytonaf67cec2010-12-20 20:49:23 +00003636ValueObject::Dereference (Error &error)
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003637{
Jim Ingham58b59f92011-04-22 23:53:53 +00003638 if (m_deref_valobj)
3639 return m_deref_valobj->GetSP();
Jim Ingham78a685a2011-04-16 00:01:13 +00003640
Greg Clayton54979cd2010-12-15 05:08:08 +00003641 const bool is_pointer_type = IsPointerType();
3642 if (is_pointer_type)
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003643 {
3644 bool omit_empty_base_classes = true;
Greg Claytondaf515f2011-07-09 20:12:33 +00003645 bool ignore_array_bounds = false;
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003646
3647 std::string child_name_str;
3648 uint32_t child_byte_size = 0;
3649 int32_t child_byte_offset = 0;
3650 uint32_t child_bitfield_bit_size = 0;
3651 uint32_t child_bitfield_bit_offset = 0;
3652 bool child_is_base_class = false;
Greg Claytone221f822011-01-21 01:59:00 +00003653 bool child_is_deref_of_parent = false;
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003654 const bool transparent_pointers = false;
Greg Clayton57ee3062013-07-11 22:46:58 +00003655 ClangASTType clang_type = GetClangType();
3656 ClangASTType child_clang_type;
Jim Inghamd555bac2011-06-24 22:03:24 +00003657
Greg Claytoncc4d0142012-02-17 07:49:44 +00003658 ExecutionContext exe_ctx (GetExecutionContextRef());
Jim Inghamd555bac2011-06-24 22:03:24 +00003659
Greg Clayton57ee3062013-07-11 22:46:58 +00003660 child_clang_type = clang_type.GetChildClangTypeAtIndex (&exe_ctx,
Greg Clayton57ee3062013-07-11 22:46:58 +00003661 0,
3662 transparent_pointers,
3663 omit_empty_base_classes,
3664 ignore_array_bounds,
3665 child_name_str,
3666 child_byte_size,
3667 child_byte_offset,
3668 child_bitfield_bit_size,
3669 child_bitfield_bit_offset,
3670 child_is_base_class,
Greg Clayton759e7442014-07-19 00:12:57 +00003671 child_is_deref_of_parent,
3672 this);
Greg Clayton3e06bd92011-01-09 21:07:35 +00003673 if (child_clang_type && child_byte_size)
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003674 {
3675 ConstString child_name;
3676 if (!child_name_str.empty())
3677 child_name.SetCString (child_name_str.c_str());
3678
Jim Ingham58b59f92011-04-22 23:53:53 +00003679 m_deref_valobj = new ValueObjectChild (*this,
Jim Ingham58b59f92011-04-22 23:53:53 +00003680 child_clang_type,
3681 child_name,
3682 child_byte_size,
3683 child_byte_offset,
3684 child_bitfield_bit_size,
3685 child_bitfield_bit_offset,
3686 child_is_base_class,
Enrico Granata9128ee22011-09-06 19:20:51 +00003687 child_is_deref_of_parent,
3688 eAddressTypeInvalid);
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003689 }
3690 }
Greg Clayton54979cd2010-12-15 05:08:08 +00003691
Jim Ingham58b59f92011-04-22 23:53:53 +00003692 if (m_deref_valobj)
Greg Clayton54979cd2010-12-15 05:08:08 +00003693 {
3694 error.Clear();
Jim Ingham58b59f92011-04-22 23:53:53 +00003695 return m_deref_valobj->GetSP();
Greg Clayton54979cd2010-12-15 05:08:08 +00003696 }
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003697 else
3698 {
Greg Clayton54979cd2010-12-15 05:08:08 +00003699 StreamString strm;
Greg Clayton6beaaa62011-01-17 03:46:26 +00003700 GetExpressionPath(strm, true);
Greg Clayton54979cd2010-12-15 05:08:08 +00003701
3702 if (is_pointer_type)
3703 error.SetErrorStringWithFormat("dereference failed: (%s) %s", GetTypeName().AsCString("<invalid type>"), strm.GetString().c_str());
3704 else
3705 error.SetErrorStringWithFormat("not a pointer type: (%s) %s", GetTypeName().AsCString("<invalid type>"), strm.GetString().c_str());
Jim Ingham58b59f92011-04-22 23:53:53 +00003706 return ValueObjectSP();
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003707 }
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003708}
3709
Greg Claytonafacd142011-09-02 01:15:17 +00003710ValueObjectSP
Greg Clayton54979cd2010-12-15 05:08:08 +00003711ValueObject::AddressOf (Error &error)
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003712{
Jim Ingham78a685a2011-04-16 00:01:13 +00003713 if (m_addr_of_valobj_sp)
3714 return m_addr_of_valobj_sp;
3715
Greg Claytone0d378b2011-03-24 21:19:54 +00003716 AddressType address_type = eAddressTypeInvalid;
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003717 const bool scalar_is_load_address = false;
Enrico Granata9128ee22011-09-06 19:20:51 +00003718 addr_t addr = GetAddressOf (scalar_is_load_address, &address_type);
Greg Clayton54979cd2010-12-15 05:08:08 +00003719 error.Clear();
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003720 if (addr != LLDB_INVALID_ADDRESS)
3721 {
3722 switch (address_type)
3723 {
3724 case eAddressTypeInvalid:
Greg Clayton54979cd2010-12-15 05:08:08 +00003725 {
3726 StreamString expr_path_strm;
Greg Clayton6beaaa62011-01-17 03:46:26 +00003727 GetExpressionPath(expr_path_strm, true);
Greg Clayton54979cd2010-12-15 05:08:08 +00003728 error.SetErrorStringWithFormat("'%s' is not in memory", expr_path_strm.GetString().c_str());
3729 }
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003730 break;
Greg Clayton54979cd2010-12-15 05:08:08 +00003731
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003732 case eAddressTypeFile:
3733 case eAddressTypeLoad:
3734 case eAddressTypeHost:
3735 {
Greg Clayton57ee3062013-07-11 22:46:58 +00003736 ClangASTType clang_type = GetClangType();
3737 if (clang_type)
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003738 {
3739 std::string name (1, '&');
3740 name.append (m_name.AsCString(""));
Greg Claytoncc4d0142012-02-17 07:49:44 +00003741 ExecutionContext exe_ctx (GetExecutionContextRef());
3742 m_addr_of_valobj_sp = ValueObjectConstResult::Create (exe_ctx.GetBestExecutionContextScope(),
Greg Clayton57ee3062013-07-11 22:46:58 +00003743 clang_type.GetPointerType(),
Jim Ingham58b59f92011-04-22 23:53:53 +00003744 ConstString (name.c_str()),
3745 addr,
3746 eAddressTypeInvalid,
3747 m_data.GetAddressByteSize());
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003748 }
3749 }
3750 break;
3751 }
3752 }
Sean Callananed185ab2013-04-19 19:47:32 +00003753 else
3754 {
3755 StreamString expr_path_strm;
3756 GetExpressionPath(expr_path_strm, true);
3757 error.SetErrorStringWithFormat("'%s' doesn't have a valid address", expr_path_strm.GetString().c_str());
3758 }
3759
Jim Ingham78a685a2011-04-16 00:01:13 +00003760 return m_addr_of_valobj_sp;
Greg Clayton8b2fe6d2010-12-14 02:59:59 +00003761}
3762
Greg Clayton9a142cf2012-02-03 05:34:10 +00003763ValueObjectSP
3764ValueObject::Cast (const ClangASTType &clang_ast_type)
3765{
Greg Clayton81e871e2012-02-04 02:27:34 +00003766 return ValueObjectCast::Create (*this, GetName(), clang_ast_type);
Greg Clayton9a142cf2012-02-03 05:34:10 +00003767}
Greg Claytonb2dcc362011-05-05 23:32:56 +00003768
Greg Claytonafacd142011-09-02 01:15:17 +00003769ValueObjectSP
Greg Claytonb2dcc362011-05-05 23:32:56 +00003770ValueObject::CastPointerType (const char *name, ClangASTType &clang_ast_type)
3771{
Greg Claytonafacd142011-09-02 01:15:17 +00003772 ValueObjectSP valobj_sp;
Greg Claytonb2dcc362011-05-05 23:32:56 +00003773 AddressType address_type;
Enrico Granata9128ee22011-09-06 19:20:51 +00003774 addr_t ptr_value = GetPointerValue (&address_type);
Greg Claytonb2dcc362011-05-05 23:32:56 +00003775
3776 if (ptr_value != LLDB_INVALID_ADDRESS)
3777 {
Greg Claytone72dfb32012-02-24 01:59:29 +00003778 Address ptr_addr (ptr_value);
Greg Claytoncc4d0142012-02-17 07:49:44 +00003779 ExecutionContext exe_ctx (GetExecutionContextRef());
3780 valobj_sp = ValueObjectMemory::Create (exe_ctx.GetBestExecutionContextScope(),
Greg Claytonb2dcc362011-05-05 23:32:56 +00003781 name,
3782 ptr_addr,
3783 clang_ast_type);
3784 }
3785 return valobj_sp;
3786}
3787
Greg Claytonafacd142011-09-02 01:15:17 +00003788ValueObjectSP
Greg Claytonb2dcc362011-05-05 23:32:56 +00003789ValueObject::CastPointerType (const char *name, TypeSP &type_sp)
3790{
Greg Claytonafacd142011-09-02 01:15:17 +00003791 ValueObjectSP valobj_sp;
Greg Claytonb2dcc362011-05-05 23:32:56 +00003792 AddressType address_type;
Enrico Granata9128ee22011-09-06 19:20:51 +00003793 addr_t ptr_value = GetPointerValue (&address_type);
Greg Claytonb2dcc362011-05-05 23:32:56 +00003794
3795 if (ptr_value != LLDB_INVALID_ADDRESS)
3796 {
Greg Claytone72dfb32012-02-24 01:59:29 +00003797 Address ptr_addr (ptr_value);
Greg Claytoncc4d0142012-02-17 07:49:44 +00003798 ExecutionContext exe_ctx (GetExecutionContextRef());
3799 valobj_sp = ValueObjectMemory::Create (exe_ctx.GetBestExecutionContextScope(),
Greg Claytonb2dcc362011-05-05 23:32:56 +00003800 name,
3801 ptr_addr,
3802 type_sp);
3803 }
3804 return valobj_sp;
3805}
3806
Jim Ingham6035b672011-03-31 00:19:25 +00003807ValueObject::EvaluationPoint::EvaluationPoint () :
Greg Claytoncc4d0142012-02-17 07:49:44 +00003808 m_mod_id(),
3809 m_exe_ctx_ref(),
3810 m_needs_update (true),
3811 m_first_update (true)
Jim Ingham6035b672011-03-31 00:19:25 +00003812{
3813}
3814
3815ValueObject::EvaluationPoint::EvaluationPoint (ExecutionContextScope *exe_scope, bool use_selected):
Greg Claytoncc4d0142012-02-17 07:49:44 +00003816 m_mod_id(),
3817 m_exe_ctx_ref(),
Jim Ingham6035b672011-03-31 00:19:25 +00003818 m_needs_update (true),
Greg Claytoncc4d0142012-02-17 07:49:44 +00003819 m_first_update (true)
Jim Ingham6035b672011-03-31 00:19:25 +00003820{
Greg Claytoncc4d0142012-02-17 07:49:44 +00003821 ExecutionContext exe_ctx(exe_scope);
3822 TargetSP target_sp (exe_ctx.GetTargetSP());
3823 if (target_sp)
Jim Ingham6035b672011-03-31 00:19:25 +00003824 {
Greg Claytoncc4d0142012-02-17 07:49:44 +00003825 m_exe_ctx_ref.SetTargetSP (target_sp);
3826 ProcessSP process_sp (exe_ctx.GetProcessSP());
3827 if (!process_sp)
3828 process_sp = target_sp->GetProcessSP();
Jim Ingham6035b672011-03-31 00:19:25 +00003829
Greg Claytoncc4d0142012-02-17 07:49:44 +00003830 if (process_sp)
Jim Ingham6035b672011-03-31 00:19:25 +00003831 {
Greg Claytoncc4d0142012-02-17 07:49:44 +00003832 m_mod_id = process_sp->GetModID();
3833 m_exe_ctx_ref.SetProcessSP (process_sp);
Jim Ingham4b536182011-08-09 02:12:22 +00003834
Greg Claytoncc4d0142012-02-17 07:49:44 +00003835 ThreadSP thread_sp (exe_ctx.GetThreadSP());
Jim Ingham6035b672011-03-31 00:19:25 +00003836
Greg Claytoncc4d0142012-02-17 07:49:44 +00003837 if (!thread_sp)
Jim Ingham6035b672011-03-31 00:19:25 +00003838 {
3839 if (use_selected)
Greg Claytoncc4d0142012-02-17 07:49:44 +00003840 thread_sp = process_sp->GetThreadList().GetSelectedThread();
Jim Ingham6035b672011-03-31 00:19:25 +00003841 }
Jim Ingham6035b672011-03-31 00:19:25 +00003842
Greg Claytoncc4d0142012-02-17 07:49:44 +00003843 if (thread_sp)
Jim Ingham6035b672011-03-31 00:19:25 +00003844 {
Greg Claytoncc4d0142012-02-17 07:49:44 +00003845 m_exe_ctx_ref.SetThreadSP(thread_sp);
Greg Claytonc14ee322011-09-22 04:58:26 +00003846
Jason Molendab57e4a12013-11-04 09:33:30 +00003847 StackFrameSP frame_sp (exe_ctx.GetFrameSP());
Greg Claytoncc4d0142012-02-17 07:49:44 +00003848 if (!frame_sp)
Jim Ingham6035b672011-03-31 00:19:25 +00003849 {
3850 if (use_selected)
Greg Claytoncc4d0142012-02-17 07:49:44 +00003851 frame_sp = thread_sp->GetSelectedFrame();
Jim Ingham6035b672011-03-31 00:19:25 +00003852 }
Greg Claytoncc4d0142012-02-17 07:49:44 +00003853 if (frame_sp)
3854 m_exe_ctx_ref.SetFrameSP(frame_sp);
Jim Ingham6035b672011-03-31 00:19:25 +00003855 }
3856 }
3857 }
Jim Ingham6035b672011-03-31 00:19:25 +00003858}
3859
3860ValueObject::EvaluationPoint::EvaluationPoint (const ValueObject::EvaluationPoint &rhs) :
Greg Claytoncc4d0142012-02-17 07:49:44 +00003861 m_mod_id(),
3862 m_exe_ctx_ref(rhs.m_exe_ctx_ref),
3863 m_needs_update (true),
3864 m_first_update (true)
Jim Ingham6035b672011-03-31 00:19:25 +00003865{
3866}
3867
3868ValueObject::EvaluationPoint::~EvaluationPoint ()
3869{
3870}
3871
Jim Ingham6035b672011-03-31 00:19:25 +00003872// This function checks the EvaluationPoint against the current process state. If the current
3873// state matches the evaluation point, or the evaluation point is already invalid, then we return
3874// false, meaning "no change". If the current state is different, we update our state, and return
3875// true meaning "yes, change". If we did see a change, we also set m_needs_update to true, so
3876// future calls to NeedsUpdate will return true.
Jim Ingham9ee01152011-12-10 01:49:43 +00003877// exe_scope will be set to the current execution context scope.
Jim Ingham6035b672011-03-31 00:19:25 +00003878
3879bool
Greg Claytoncc4d0142012-02-17 07:49:44 +00003880ValueObject::EvaluationPoint::SyncWithProcessState()
Jim Ingham6035b672011-03-31 00:19:25 +00003881{
Jim Ingham73ca05a2011-12-17 01:35:57 +00003882
3883 // Start with the target, if it is NULL, then we're obviously not going to get any further:
Greg Clayton44d93782014-01-27 23:43:24 +00003884 const bool thread_and_frame_only_if_stopped = true;
3885 ExecutionContext exe_ctx(m_exe_ctx_ref.Lock(thread_and_frame_only_if_stopped));
Jim Ingham73ca05a2011-12-17 01:35:57 +00003886
Greg Claytoncc4d0142012-02-17 07:49:44 +00003887 if (exe_ctx.GetTargetPtr() == NULL)
Jim Ingham73ca05a2011-12-17 01:35:57 +00003888 return false;
3889
Jim Ingham6035b672011-03-31 00:19:25 +00003890 // If we don't have a process nothing can change.
Greg Claytoncc4d0142012-02-17 07:49:44 +00003891 Process *process = exe_ctx.GetProcessPtr();
3892 if (process == NULL)
Jim Ingham6035b672011-03-31 00:19:25 +00003893 return false;
Jim Ingham73ca05a2011-12-17 01:35:57 +00003894
Jim Ingham6035b672011-03-31 00:19:25 +00003895 // If our stop id is the current stop ID, nothing has changed:
Greg Claytoncc4d0142012-02-17 07:49:44 +00003896 ProcessModID current_mod_id = process->GetModID();
Jim Ingham4b536182011-08-09 02:12:22 +00003897
Jim Ingham78a685a2011-04-16 00:01:13 +00003898 // If the current stop id is 0, either we haven't run yet, or the process state has been cleared.
3899 // In either case, we aren't going to be able to sync with the process state.
Jim Ingham4b536182011-08-09 02:12:22 +00003900 if (current_mod_id.GetStopID() == 0)
Jim Ingham78a685a2011-04-16 00:01:13 +00003901 return false;
Jim Ingham9ee01152011-12-10 01:49:43 +00003902
Greg Clayton23f59502012-07-17 03:23:13 +00003903 bool changed = false;
3904 const bool was_valid = m_mod_id.IsValid();
3905 if (was_valid)
Greg Clayton7e9b1fd2011-08-12 21:40:01 +00003906 {
3907 if (m_mod_id == current_mod_id)
3908 {
Jim Ingham5cfbe4a2012-01-12 22:42:34 +00003909 // Everything is already up to date in this object, no need to
Greg Clayton7e9b1fd2011-08-12 21:40:01 +00003910 // update the execution context scope.
Jim Ingham9ee01152011-12-10 01:49:43 +00003911 changed = false;
Greg Clayton7e9b1fd2011-08-12 21:40:01 +00003912 }
Jim Ingham9ee01152011-12-10 01:49:43 +00003913 else
3914 {
3915 m_mod_id = current_mod_id;
3916 m_needs_update = true;
3917 changed = true;
3918 }
Greg Clayton7e9b1fd2011-08-12 21:40:01 +00003919 }
Jim Ingham6035b672011-03-31 00:19:25 +00003920
Jim Ingham73ca05a2011-12-17 01:35:57 +00003921 // Now re-look up the thread and frame in case the underlying objects have gone away & been recreated.
3922 // That way we'll be sure to return a valid exe_scope.
3923 // If we used to have a thread or a frame but can't find it anymore, then mark ourselves as invalid.
Jim Ingham6035b672011-03-31 00:19:25 +00003924
Greg Claytoncc4d0142012-02-17 07:49:44 +00003925 if (m_exe_ctx_ref.HasThreadRef())
Jim Ingham6035b672011-03-31 00:19:25 +00003926 {
Greg Claytoncc4d0142012-02-17 07:49:44 +00003927 ThreadSP thread_sp (m_exe_ctx_ref.GetThreadSP());
3928 if (thread_sp)
Greg Clayton262f80d2011-07-06 16:49:27 +00003929 {
Greg Claytoncc4d0142012-02-17 07:49:44 +00003930 if (m_exe_ctx_ref.HasFrameRef())
3931 {
Jason Molendab57e4a12013-11-04 09:33:30 +00003932 StackFrameSP frame_sp (m_exe_ctx_ref.GetFrameSP());
Greg Claytoncc4d0142012-02-17 07:49:44 +00003933 if (!frame_sp)
3934 {
3935 // We used to have a frame, but now it is gone
3936 SetInvalid();
Greg Clayton23f59502012-07-17 03:23:13 +00003937 changed = was_valid;
Greg Claytoncc4d0142012-02-17 07:49:44 +00003938 }
3939 }
Greg Clayton262f80d2011-07-06 16:49:27 +00003940 }
Jim Ingham6035b672011-03-31 00:19:25 +00003941 else
3942 {
Greg Claytoncc4d0142012-02-17 07:49:44 +00003943 // We used to have a thread, but now it is gone
3944 SetInvalid();
Greg Clayton23f59502012-07-17 03:23:13 +00003945 changed = was_valid;
Jim Ingham6035b672011-03-31 00:19:25 +00003946 }
Greg Claytoncc4d0142012-02-17 07:49:44 +00003947
Jim Ingham6035b672011-03-31 00:19:25 +00003948 }
Jim Ingham9ee01152011-12-10 01:49:43 +00003949 return changed;
Jim Ingham6035b672011-03-31 00:19:25 +00003950}
3951
Jim Ingham61be0902011-05-02 18:13:59 +00003952void
3953ValueObject::EvaluationPoint::SetUpdated ()
3954{
Greg Claytoncc4d0142012-02-17 07:49:44 +00003955 ProcessSP process_sp(m_exe_ctx_ref.GetProcessSP());
3956 if (process_sp)
3957 m_mod_id = process_sp->GetModID();
Jim Ingham61be0902011-05-02 18:13:59 +00003958 m_first_update = false;
3959 m_needs_update = false;
Jim Ingham61be0902011-05-02 18:13:59 +00003960}
3961
3962
Enrico Granataf2bbf712011-07-15 02:26:42 +00003963
3964void
Enrico Granata86cc9822012-03-19 22:58:49 +00003965ValueObject::ClearUserVisibleData(uint32_t clear_mask)
Enrico Granataf2bbf712011-07-15 02:26:42 +00003966{
Enrico Granata86cc9822012-03-19 22:58:49 +00003967 if ((clear_mask & eClearUserVisibleDataItemsValue) == eClearUserVisibleDataItemsValue)
3968 m_value_str.clear();
3969
3970 if ((clear_mask & eClearUserVisibleDataItemsLocation) == eClearUserVisibleDataItemsLocation)
3971 m_location_str.clear();
3972
3973 if ((clear_mask & eClearUserVisibleDataItemsSummary) == eClearUserVisibleDataItemsSummary)
Enrico Granata86cc9822012-03-19 22:58:49 +00003974 m_summary_str.clear();
Enrico Granata86cc9822012-03-19 22:58:49 +00003975
3976 if ((clear_mask & eClearUserVisibleDataItemsDescription) == eClearUserVisibleDataItemsDescription)
3977 m_object_desc_str.clear();
3978
3979 if ((clear_mask & eClearUserVisibleDataItemsSyntheticChildren) == eClearUserVisibleDataItemsSyntheticChildren)
3980 {
3981 if (m_synthetic_value)
3982 m_synthetic_value = NULL;
3983 }
Enrico Granata744794a2014-09-05 21:46:22 +00003984
3985 if ((clear_mask & eClearUserVisibleDataItemsValidator) == eClearUserVisibleDataItemsValidator)
3986 m_validation_result.reset();
Johnny Chen44805302011-07-19 19:48:13 +00003987}
Enrico Granata9128ee22011-09-06 19:20:51 +00003988
3989SymbolContextScope *
3990ValueObject::GetSymbolContextScope()
3991{
3992 if (m_parent)
3993 {
3994 if (!m_parent->IsPointerOrReferenceType())
3995 return m_parent->GetSymbolContextScope();
3996 }
3997 return NULL;
3998}
Enrico Granatab2698cd2012-09-13 18:27:09 +00003999
4000lldb::ValueObjectSP
4001ValueObject::CreateValueObjectFromExpression (const char* name,
4002 const char* expression,
4003 const ExecutionContext& exe_ctx)
4004{
4005 lldb::ValueObjectSP retval_sp;
4006 lldb::TargetSP target_sp(exe_ctx.GetTargetSP());
4007 if (!target_sp)
4008 return retval_sp;
4009 if (!expression || !*expression)
4010 return retval_sp;
4011 target_sp->EvaluateExpression (expression,
4012 exe_ctx.GetFrameSP().get(),
4013 retval_sp);
4014 if (retval_sp && name && *name)
4015 retval_sp->SetName(ConstString(name));
4016 return retval_sp;
4017}
4018
4019lldb::ValueObjectSP
4020ValueObject::CreateValueObjectFromAddress (const char* name,
4021 uint64_t address,
4022 const ExecutionContext& exe_ctx,
4023 ClangASTType type)
4024{
Greg Clayton57ee3062013-07-11 22:46:58 +00004025 if (type)
Enrico Granatab2698cd2012-09-13 18:27:09 +00004026 {
Greg Clayton57ee3062013-07-11 22:46:58 +00004027 ClangASTType pointer_type(type.GetPointerType());
4028 if (pointer_type)
4029 {
4030 lldb::DataBufferSP buffer(new lldb_private::DataBufferHeap(&address,sizeof(lldb::addr_t)));
4031 lldb::ValueObjectSP ptr_result_valobj_sp(ValueObjectConstResult::Create (exe_ctx.GetBestExecutionContextScope(),
4032 pointer_type,
4033 ConstString(name),
4034 buffer,
4035 lldb::endian::InlHostByteOrder(),
4036 exe_ctx.GetAddressByteSize()));
4037 if (ptr_result_valobj_sp)
4038 {
4039 ptr_result_valobj_sp->GetValue().SetValueType(Value::eValueTypeLoadAddress);
4040 Error err;
4041 ptr_result_valobj_sp = ptr_result_valobj_sp->Dereference(err);
4042 if (ptr_result_valobj_sp && name && *name)
4043 ptr_result_valobj_sp->SetName(ConstString(name));
4044 }
4045 return ptr_result_valobj_sp;
4046 }
Enrico Granatab2698cd2012-09-13 18:27:09 +00004047 }
Greg Clayton57ee3062013-07-11 22:46:58 +00004048 return lldb::ValueObjectSP();
Enrico Granatab2698cd2012-09-13 18:27:09 +00004049}
4050
4051lldb::ValueObjectSP
4052ValueObject::CreateValueObjectFromData (const char* name,
Enrico Granata7ca1c762014-03-31 23:02:25 +00004053 const DataExtractor& data,
Enrico Granatab2698cd2012-09-13 18:27:09 +00004054 const ExecutionContext& exe_ctx,
4055 ClangASTType type)
4056{
4057 lldb::ValueObjectSP new_value_sp;
4058 new_value_sp = ValueObjectConstResult::Create (exe_ctx.GetBestExecutionContextScope(),
Greg Clayton57ee3062013-07-11 22:46:58 +00004059 type,
Enrico Granatab2698cd2012-09-13 18:27:09 +00004060 ConstString(name),
4061 data,
4062 LLDB_INVALID_ADDRESS);
4063 new_value_sp->SetAddressTypeOfChildren(eAddressTypeLoad);
4064 if (new_value_sp && name && *name)
4065 new_value_sp->SetName(ConstString(name));
4066 return new_value_sp;
4067}
Enrico Granata4873e522013-04-11 22:48:58 +00004068
4069ModuleSP
4070ValueObject::GetModule ()
4071{
4072 ValueObject* root(GetRoot());
4073 if (root != this)
4074 return root->GetModule();
4075 return lldb::ModuleSP();
4076}
4077
4078ValueObject*
4079ValueObject::GetRoot ()
4080{
4081 if (m_root)
4082 return m_root;
4083 ValueObject* parent = m_parent;
4084 if (!parent)
4085 return (m_root = this);
4086 while (parent->m_parent)
4087 {
4088 if (parent->m_root)
4089 return (m_root = parent->m_root);
4090 parent = parent->m_parent;
4091 }
4092 return (m_root = parent);
4093}
4094
4095AddressType
4096ValueObject::GetAddressTypeOfChildren()
4097{
4098 if (m_address_type_of_ptr_or_ref_children == eAddressTypeInvalid)
4099 {
4100 ValueObject* root(GetRoot());
4101 if (root != this)
4102 return root->GetAddressTypeOfChildren();
4103 }
4104 return m_address_type_of_ptr_or_ref_children;
4105}
4106
4107lldb::DynamicValueType
4108ValueObject::GetDynamicValueType ()
4109{
4110 ValueObject* with_dv_info = this;
4111 while (with_dv_info)
4112 {
4113 if (with_dv_info->HasDynamicValueTypeInfo())
4114 return with_dv_info->GetDynamicValueTypeImpl();
4115 with_dv_info = with_dv_info->m_parent;
4116 }
4117 return lldb::eNoDynamicValues;
4118}
Enrico Granata39d51412013-05-31 17:43:40 +00004119
Enrico Granata4873e522013-04-11 22:48:58 +00004120lldb::Format
4121ValueObject::GetFormat () const
4122{
4123 const ValueObject* with_fmt_info = this;
4124 while (with_fmt_info)
4125 {
4126 if (with_fmt_info->m_format != lldb::eFormatDefault)
4127 return with_fmt_info->m_format;
4128 with_fmt_info = with_fmt_info->m_parent;
4129 }
4130 return m_format;
4131}
Enrico Granatad07cfd32014-10-08 18:27:36 +00004132
4133bool
4134ValueObject::CanProvideValue ()
4135{
4136 return (false == GetClangType().IsAggregateType());
4137}