1 //===-- 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 
10 #include "lldb/Core/ValueObject.h"
11 
12 // C Includes
13 #include <stdlib.h>
14 
15 // C++ Includes
16 // Other libraries and framework includes
17 #include "llvm/Support/raw_ostream.h"
18 #include "clang/AST/Type.h"
19 
20 // Project includes
21 #include "lldb/Core/DataBufferHeap.h"
22 #include "lldb/Core/DataVisualization.h"
23 #include "lldb/Core/Debugger.h"
24 #include "lldb/Core/Log.h"
25 #include "lldb/Core/StreamString.h"
26 #include "lldb/Core/ValueObjectChild.h"
27 #include "lldb/Core/ValueObjectConstResult.h"
28 #include "lldb/Core/ValueObjectDynamicValue.h"
29 #include "lldb/Core/ValueObjectList.h"
30 #include "lldb/Core/ValueObjectMemory.h"
31 #include "lldb/Core/ValueObjectSyntheticFilter.h"
32 
33 #include "lldb/Host/Endian.h"
34 
35 #include "lldb/Interpreter/CommandInterpreter.h"
36 #include "lldb/Interpreter/ScriptInterpreterPython.h"
37 
38 #include "lldb/Symbol/ClangASTType.h"
39 #include "lldb/Symbol/ClangASTContext.h"
40 #include "lldb/Symbol/Type.h"
41 
42 #include "lldb/Target/ExecutionContext.h"
43 #include "lldb/Target/LanguageRuntime.h"
44 #include "lldb/Target/ObjCLanguageRuntime.h"
45 #include "lldb/Target/Process.h"
46 #include "lldb/Target/RegisterContext.h"
47 #include "lldb/Target/Target.h"
48 #include "lldb/Target/Thread.h"
49 
50 #include "lldb/Utility/RefCounter.h"
51 
52 using namespace lldb;
53 using namespace lldb_private;
54 using namespace lldb_utility;
55 
56 static user_id_t g_value_obj_uid = 0;
57 
58 //----------------------------------------------------------------------
59 // ValueObject constructor
60 //----------------------------------------------------------------------
61 ValueObject::ValueObject (ValueObject &parent) :
62     UserID (++g_value_obj_uid), // Unique identifier for every value object
63     m_parent (&parent),
64     m_update_point (parent.GetUpdatePoint ()),
65     m_name (),
66     m_data (),
67     m_value (),
68     m_error (),
69     m_value_str (),
70     m_old_value_str (),
71     m_location_str (),
72     m_summary_str (),
73     m_object_desc_str (),
74     m_manager(parent.GetManager()),
75     m_children (),
76     m_synthetic_children (),
77     m_dynamic_value (NULL),
78     m_synthetic_value(NULL),
79     m_deref_valobj(NULL),
80     m_format (eFormatDefault),
81     m_last_format_mgr_revision(0),
82     m_last_format_mgr_dynamic(parent.m_last_format_mgr_dynamic),
83     m_type_summary_sp(),
84     m_type_format_sp(),
85     m_synthetic_children_sp(),
86     m_user_id_of_forced_summary(),
87     m_address_type_of_ptr_or_ref_children(eAddressTypeInvalid),
88     m_value_is_valid (false),
89     m_value_did_change (false),
90     m_children_count_valid (false),
91     m_old_value_valid (false),
92     m_is_deref_of_parent (false),
93     m_is_array_item_for_pointer(false),
94     m_is_bitfield_for_scalar(false),
95     m_is_expression_path_child(false),
96     m_is_child_at_offset(false),
97     m_is_getting_summary(false),
98     m_did_calculate_complete_objc_class_type(false)
99 {
100     m_manager->ManageObject(this);
101 }
102 
103 //----------------------------------------------------------------------
104 // ValueObject constructor
105 //----------------------------------------------------------------------
106 ValueObject::ValueObject (ExecutionContextScope *exe_scope,
107                           AddressType child_ptr_or_ref_addr_type) :
108     UserID (++g_value_obj_uid), // Unique identifier for every value object
109     m_parent (NULL),
110     m_update_point (exe_scope),
111     m_name (),
112     m_data (),
113     m_value (),
114     m_error (),
115     m_value_str (),
116     m_old_value_str (),
117     m_location_str (),
118     m_summary_str (),
119     m_object_desc_str (),
120     m_manager(),
121     m_children (),
122     m_synthetic_children (),
123     m_dynamic_value (NULL),
124     m_synthetic_value(NULL),
125     m_deref_valobj(NULL),
126     m_format (eFormatDefault),
127     m_last_format_mgr_revision(0),
128     m_last_format_mgr_dynamic(eNoDynamicValues),
129     m_type_summary_sp(),
130     m_type_format_sp(),
131     m_synthetic_children_sp(),
132     m_user_id_of_forced_summary(),
133     m_address_type_of_ptr_or_ref_children(child_ptr_or_ref_addr_type),
134     m_value_is_valid (false),
135     m_value_did_change (false),
136     m_children_count_valid (false),
137     m_old_value_valid (false),
138     m_is_deref_of_parent (false),
139     m_is_array_item_for_pointer(false),
140     m_is_bitfield_for_scalar(false),
141     m_is_expression_path_child(false),
142     m_is_child_at_offset(false),
143     m_is_getting_summary(false),
144     m_did_calculate_complete_objc_class_type(false)
145 {
146     m_manager = new ValueObjectManager();
147     m_manager->ManageObject (this);
148 }
149 
150 //----------------------------------------------------------------------
151 // Destructor
152 //----------------------------------------------------------------------
153 ValueObject::~ValueObject ()
154 {
155 }
156 
157 bool
158 ValueObject::UpdateValueIfNeeded (bool update_format)
159 {
160     return UpdateValueIfNeeded(m_last_format_mgr_dynamic, update_format);
161 }
162 
163 bool
164 ValueObject::UpdateValueIfNeeded (DynamicValueType use_dynamic, bool update_format)
165 {
166 
167     bool did_change_formats = false;
168 
169     if (update_format)
170         did_change_formats = UpdateFormatsIfNeeded(use_dynamic);
171 
172     // If this is a constant value, then our success is predicated on whether
173     // we have an error or not
174     if (GetIsConstant())
175     {
176         // if you were asked to update your formatters, but did not get a chance to do it
177         // clear your own values (this serves the purpose of faking a stop-id for frozen
178         // objects (which are regarded as constant, but could have changes behind their backs
179         // because of the frozen-pointer depth limit)
180 		// TODO: decouple summary from value and then remove this code and only force-clear the summary
181         if (update_format && !did_change_formats)
182             ClearUserVisibleData(eClearUserVisibleDataItemsSummary);
183         return m_error.Success();
184     }
185 
186     bool first_update = m_update_point.IsFirstEvaluation();
187 
188     if (m_update_point.NeedsUpdating())
189     {
190         m_update_point.SetUpdated();
191 
192         // Save the old value using swap to avoid a string copy which
193         // also will clear our m_value_str
194         if (m_value_str.empty())
195         {
196             m_old_value_valid = false;
197         }
198         else
199         {
200             m_old_value_valid = true;
201             m_old_value_str.swap (m_value_str);
202             ClearUserVisibleData(eClearUserVisibleDataItemsValue);
203         }
204 
205         ClearUserVisibleData();
206 
207         if (IsInScope())
208         {
209             const bool value_was_valid = GetValueIsValid();
210             SetValueDidChange (false);
211 
212             m_error.Clear();
213 
214             // Call the pure virtual function to update the value
215             bool success = UpdateValue ();
216 
217             SetValueIsValid (success);
218 
219             if (first_update)
220                 SetValueDidChange (false);
221             else if (!m_value_did_change && success == false)
222             {
223                 // The value wasn't gotten successfully, so we mark this
224                 // as changed if the value used to be valid and now isn't
225                 SetValueDidChange (value_was_valid);
226             }
227         }
228         else
229         {
230             m_error.SetErrorString("out of scope");
231         }
232     }
233     return m_error.Success();
234 }
235 
236 bool
237 ValueObject::UpdateFormatsIfNeeded(DynamicValueType use_dynamic)
238 {
239     LogSP log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_TYPES));
240     if (log)
241         log->Printf("checking for FormatManager revisions. VO named %s is at revision %d, while the format manager is at revision %d",
242            GetName().GetCString(),
243            m_last_format_mgr_revision,
244            DataVisualization::GetCurrentRevision());
245 
246     bool any_change = false;
247 
248     if ( (m_last_format_mgr_revision != DataVisualization::GetCurrentRevision()) ||
249           m_last_format_mgr_dynamic != use_dynamic)
250     {
251         SetValueFormat(DataVisualization::ValueFormats::GetFormat (*this, eNoDynamicValues));
252         SetSummaryFormat(DataVisualization::GetSummaryFormat (*this, use_dynamic));
253         SetSyntheticChildren(DataVisualization::GetSyntheticChildren (*this, use_dynamic));
254 
255         m_last_format_mgr_revision = DataVisualization::GetCurrentRevision();
256         m_last_format_mgr_dynamic = use_dynamic;
257 
258         any_change = true;
259     }
260 
261     return any_change;
262 
263 }
264 
265 void
266 ValueObject::SetNeedsUpdate ()
267 {
268     m_update_point.SetNeedsUpdate();
269     // We have to clear the value string here so ConstResult children will notice if their values are
270     // changed by hand (i.e. with SetValueAsCString).
271     ClearUserVisibleData(eClearUserVisibleDataItemsValue);
272 }
273 
274 ClangASTType
275 ValueObject::MaybeCalculateCompleteType ()
276 {
277     ClangASTType ret(GetClangASTImpl(), GetClangTypeImpl());
278 
279     if (m_did_calculate_complete_objc_class_type)
280     {
281         if (m_override_type.IsValid())
282             return m_override_type;
283         else
284             return ret;
285     }
286 
287     clang_type_t ast_type(GetClangTypeImpl());
288     clang_type_t class_type;
289     bool is_pointer_type;
290 
291     if (ClangASTContext::IsObjCObjectPointerType(ast_type, &class_type))
292     {
293         is_pointer_type = true;
294     }
295     else if (ClangASTContext::IsObjCClassType(ast_type))
296     {
297         is_pointer_type = false;
298         class_type = ast_type;
299     }
300     else
301     {
302         return ret;
303     }
304 
305     m_did_calculate_complete_objc_class_type = true;
306 
307     if (!class_type)
308         return ret;
309 
310     std::string class_name;
311 
312     if (!ClangASTContext::GetObjCClassName(class_type, class_name))
313         return ret;
314 
315     ProcessSP process_sp(GetUpdatePoint().GetExecutionContextRef().GetProcessSP());
316 
317     if (!process_sp)
318         return ret;
319 
320     ObjCLanguageRuntime *objc_language_runtime(process_sp->GetObjCLanguageRuntime());
321 
322     if (!objc_language_runtime)
323         return ret;
324 
325     ConstString class_name_cs(class_name.c_str());
326 
327     TypeSP complete_objc_class_type_sp = objc_language_runtime->LookupInCompleteClassCache(class_name_cs);
328 
329     if (!complete_objc_class_type_sp)
330         return ret;
331 
332     ClangASTType complete_class(complete_objc_class_type_sp->GetClangAST(),
333                                 complete_objc_class_type_sp->GetClangFullType());
334 
335     if (!ClangASTContext::GetCompleteType(complete_class.GetASTContext(),
336                                           complete_class.GetOpaqueQualType()))
337         return ret;
338 
339     if (is_pointer_type)
340     {
341         clang_type_t pointer_type = ClangASTContext::CreatePointerType(complete_class.GetASTContext(),
342                                                                        complete_class.GetOpaqueQualType());
343 
344         m_override_type = ClangASTType(complete_class.GetASTContext(),
345                                        pointer_type);
346     }
347     else
348     {
349         m_override_type = complete_class;
350     }
351 
352     if (m_override_type.IsValid())
353         return m_override_type;
354     else
355         return ret;
356 }
357 
358 clang::ASTContext *
359 ValueObject::GetClangAST ()
360 {
361     ClangASTType type = MaybeCalculateCompleteType();
362 
363     return type.GetASTContext();
364 }
365 
366 lldb::clang_type_t
367 ValueObject::GetClangType ()
368 {
369     ClangASTType type = MaybeCalculateCompleteType();
370 
371     return type.GetOpaqueQualType();
372 }
373 
374 DataExtractor &
375 ValueObject::GetDataExtractor ()
376 {
377     UpdateValueIfNeeded(false);
378     return m_data;
379 }
380 
381 const Error &
382 ValueObject::GetError()
383 {
384     UpdateValueIfNeeded(false);
385     return m_error;
386 }
387 
388 const ConstString &
389 ValueObject::GetName() const
390 {
391     return m_name;
392 }
393 
394 const char *
395 ValueObject::GetLocationAsCString ()
396 {
397     if (UpdateValueIfNeeded(false))
398     {
399         if (m_location_str.empty())
400         {
401             StreamString sstr;
402 
403             switch (m_value.GetValueType())
404             {
405             default:
406                 break;
407 
408             case Value::eValueTypeScalar:
409                 if (m_value.GetContextType() == Value::eContextTypeRegisterInfo)
410                 {
411                     RegisterInfo *reg_info = m_value.GetRegisterInfo();
412                     if (reg_info)
413                     {
414                         if (reg_info->name)
415                             m_location_str = reg_info->name;
416                         else if (reg_info->alt_name)
417                             m_location_str = reg_info->alt_name;
418                         break;
419                     }
420                 }
421                 m_location_str = "scalar";
422                 break;
423 
424             case Value::eValueTypeLoadAddress:
425             case Value::eValueTypeFileAddress:
426             case Value::eValueTypeHostAddress:
427                 {
428                     uint32_t addr_nibble_size = m_data.GetAddressByteSize() * 2;
429                     sstr.Printf("0x%*.*llx", addr_nibble_size, addr_nibble_size, m_value.GetScalar().ULongLong(LLDB_INVALID_ADDRESS));
430                     m_location_str.swap(sstr.GetString());
431                 }
432                 break;
433             }
434         }
435     }
436     return m_location_str.c_str();
437 }
438 
439 Value &
440 ValueObject::GetValue()
441 {
442     return m_value;
443 }
444 
445 const Value &
446 ValueObject::GetValue() const
447 {
448     return m_value;
449 }
450 
451 bool
452 ValueObject::ResolveValue (Scalar &scalar)
453 {
454     if (UpdateValueIfNeeded(false)) // make sure that you are up to date before returning anything
455     {
456         ExecutionContext exe_ctx (GetExecutionContextRef());
457         Value tmp_value(m_value);
458         scalar = tmp_value.ResolveValue(&exe_ctx, GetClangAST ());
459         if (scalar.IsValid())
460         {
461             const uint32_t bitfield_bit_size = GetBitfieldBitSize();
462             if (bitfield_bit_size)
463                 return scalar.ExtractBitfield (bitfield_bit_size, GetBitfieldBitOffset());
464             return true;
465         }
466     }
467     return false;
468 }
469 
470 bool
471 ValueObject::GetValueIsValid () const
472 {
473     return m_value_is_valid;
474 }
475 
476 
477 void
478 ValueObject::SetValueIsValid (bool b)
479 {
480     m_value_is_valid = b;
481 }
482 
483 bool
484 ValueObject::GetValueDidChange ()
485 {
486     GetValueAsCString ();
487     return m_value_did_change;
488 }
489 
490 void
491 ValueObject::SetValueDidChange (bool value_changed)
492 {
493     m_value_did_change = value_changed;
494 }
495 
496 ValueObjectSP
497 ValueObject::GetChildAtIndex (uint32_t idx, bool can_create)
498 {
499     ValueObjectSP child_sp;
500     // We may need to update our value if we are dynamic
501     if (IsPossibleDynamicType ())
502         UpdateValueIfNeeded(false);
503     if (idx < GetNumChildren())
504     {
505         // Check if we have already made the child value object?
506         if (can_create && !m_children.HasChildAtIndex(idx))
507         {
508             // No we haven't created the child at this index, so lets have our
509             // subclass do it and cache the result for quick future access.
510             m_children.SetChildAtIndex(idx,CreateChildAtIndex (idx, false, 0));
511         }
512 
513         ValueObject* child = m_children.GetChildAtIndex(idx);
514         if (child != NULL)
515             return child->GetSP();
516     }
517     return child_sp;
518 }
519 
520 uint32_t
521 ValueObject::GetIndexOfChildWithName (const ConstString &name)
522 {
523     bool omit_empty_base_classes = true;
524     return ClangASTContext::GetIndexOfChildWithName (GetClangAST(),
525                                                      GetClangType(),
526                                                      name.GetCString(),
527                                                      omit_empty_base_classes);
528 }
529 
530 ValueObjectSP
531 ValueObject::GetChildMemberWithName (const ConstString &name, bool can_create)
532 {
533     // when getting a child by name, it could be buried inside some base
534     // classes (which really aren't part of the expression path), so we
535     // need a vector of indexes that can get us down to the correct child
536     ValueObjectSP child_sp;
537 
538     // We may need to update our value if we are dynamic
539     if (IsPossibleDynamicType ())
540         UpdateValueIfNeeded(false);
541 
542     std::vector<uint32_t> child_indexes;
543     clang::ASTContext *clang_ast = GetClangAST();
544     void *clang_type = GetClangType();
545     bool omit_empty_base_classes = true;
546     const size_t num_child_indexes =  ClangASTContext::GetIndexOfChildMemberWithName (clang_ast,
547                                                                                       clang_type,
548                                                                                       name.GetCString(),
549                                                                                       omit_empty_base_classes,
550                                                                                       child_indexes);
551     if (num_child_indexes > 0)
552     {
553         std::vector<uint32_t>::const_iterator pos = child_indexes.begin ();
554         std::vector<uint32_t>::const_iterator end = child_indexes.end ();
555 
556         child_sp = GetChildAtIndex(*pos, can_create);
557         for (++pos; pos != end; ++pos)
558         {
559             if (child_sp)
560             {
561                 ValueObjectSP new_child_sp(child_sp->GetChildAtIndex (*pos, can_create));
562                 child_sp = new_child_sp;
563             }
564             else
565             {
566                 child_sp.reset();
567             }
568 
569         }
570     }
571     return child_sp;
572 }
573 
574 
575 uint32_t
576 ValueObject::GetNumChildren ()
577 {
578     UpdateValueIfNeeded();
579     if (!m_children_count_valid)
580     {
581         SetNumChildren (CalculateNumChildren());
582     }
583     return m_children.GetChildrenCount();
584 }
585 void
586 ValueObject::SetNumChildren (uint32_t num_children)
587 {
588     m_children_count_valid = true;
589     m_children.SetChildrenCount(num_children);
590 }
591 
592 void
593 ValueObject::SetName (const ConstString &name)
594 {
595     m_name = name;
596 }
597 
598 ValueObject *
599 ValueObject::CreateChildAtIndex (uint32_t idx, bool synthetic_array_member, int32_t synthetic_index)
600 {
601     ValueObject *valobj = NULL;
602 
603     bool omit_empty_base_classes = true;
604     bool ignore_array_bounds = synthetic_array_member;
605     std::string child_name_str;
606     uint32_t child_byte_size = 0;
607     int32_t child_byte_offset = 0;
608     uint32_t child_bitfield_bit_size = 0;
609     uint32_t child_bitfield_bit_offset = 0;
610     bool child_is_base_class = false;
611     bool child_is_deref_of_parent = false;
612 
613     const bool transparent_pointers = synthetic_array_member == false;
614     clang::ASTContext *clang_ast = GetClangAST();
615     clang_type_t clang_type = GetClangType();
616     clang_type_t child_clang_type;
617 
618     ExecutionContext exe_ctx (GetExecutionContextRef());
619 
620     child_clang_type = ClangASTContext::GetChildClangTypeAtIndex (&exe_ctx,
621                                                                   clang_ast,
622                                                                   GetName().GetCString(),
623                                                                   clang_type,
624                                                                   idx,
625                                                                   transparent_pointers,
626                                                                   omit_empty_base_classes,
627                                                                   ignore_array_bounds,
628                                                                   child_name_str,
629                                                                   child_byte_size,
630                                                                   child_byte_offset,
631                                                                   child_bitfield_bit_size,
632                                                                   child_bitfield_bit_offset,
633                                                                   child_is_base_class,
634                                                                   child_is_deref_of_parent);
635     if (child_clang_type && child_byte_size)
636     {
637         if (synthetic_index)
638             child_byte_offset += child_byte_size * synthetic_index;
639 
640         ConstString child_name;
641         if (!child_name_str.empty())
642             child_name.SetCString (child_name_str.c_str());
643 
644         valobj = new ValueObjectChild (*this,
645                                        clang_ast,
646                                        child_clang_type,
647                                        child_name,
648                                        child_byte_size,
649                                        child_byte_offset,
650                                        child_bitfield_bit_size,
651                                        child_bitfield_bit_offset,
652                                        child_is_base_class,
653                                        child_is_deref_of_parent,
654                                        eAddressTypeInvalid);
655         //if (valobj)
656         //    valobj->SetAddressTypeOfChildren(eAddressTypeInvalid);
657    }
658 
659     return valobj;
660 }
661 
662 bool
663 ValueObject::GetSummaryAsCString (TypeSummaryImpl* summary_ptr,
664                                   std::string& destination)
665 {
666     destination.clear();
667 
668     // ideally we would like to bail out if passing NULL, but if we do so
669     // we end up not providing the summary for function pointers anymore
670     if (/*summary_ptr == NULL ||*/ m_is_getting_summary)
671         return false;
672 
673     m_is_getting_summary = true;
674     if (UpdateValueIfNeeded (false))
675     {
676         if (summary_ptr)
677         {
678             if (HasSyntheticValue())
679                 m_synthetic_value->UpdateValueIfNeeded(); // the summary might depend on the synthetic children being up-to-date (e.g. ${svar%#})
680             summary_ptr->FormatObject(this, destination);
681         }
682         else
683         {
684             clang_type_t clang_type = GetClangType();
685 
686             // Do some default printout for function pointers
687             if (clang_type)
688             {
689                 StreamString sstr;
690                 clang_type_t elem_or_pointee_clang_type;
691                 const Flags type_flags (ClangASTContext::GetTypeInfo (clang_type,
692                                                                       GetClangAST(),
693                                                                       &elem_or_pointee_clang_type));
694 
695                 if (ClangASTContext::IsFunctionPointerType (clang_type))
696                 {
697                     AddressType func_ptr_address_type = eAddressTypeInvalid;
698                     addr_t func_ptr_address = GetPointerValue (&func_ptr_address_type);
699                     if (func_ptr_address != 0 && func_ptr_address != LLDB_INVALID_ADDRESS)
700                     {
701                         switch (func_ptr_address_type)
702                         {
703                             case eAddressTypeInvalid:
704                             case eAddressTypeFile:
705                                 break;
706 
707                             case eAddressTypeLoad:
708                             {
709                                 ExecutionContext exe_ctx (GetExecutionContextRef());
710 
711                                 Address so_addr;
712                                 Target *target = exe_ctx.GetTargetPtr();
713                                 if (target && target->GetSectionLoadList().IsEmpty() == false)
714                                 {
715                                     if (target->GetSectionLoadList().ResolveLoadAddress(func_ptr_address, so_addr))
716                                     {
717                                         so_addr.Dump (&sstr,
718                                                       exe_ctx.GetBestExecutionContextScope(),
719                                                       Address::DumpStyleResolvedDescription,
720                                                       Address::DumpStyleSectionNameOffset);
721                                     }
722                                 }
723                             }
724                                 break;
725 
726                             case eAddressTypeHost:
727                                 break;
728                         }
729                     }
730                     if (sstr.GetSize() > 0)
731                     {
732                         destination.assign (1, '(');
733                         destination.append (sstr.GetData(), sstr.GetSize());
734                         destination.append (1, ')');
735                     }
736                 }
737             }
738         }
739     }
740     m_is_getting_summary = false;
741     return !destination.empty();
742 }
743 
744 const char *
745 ValueObject::GetSummaryAsCString ()
746 {
747     if (UpdateValueIfNeeded(true) && m_summary_str.empty())
748     {
749         GetSummaryAsCString(GetSummaryFormat().get(),
750                             m_summary_str);
751     }
752     if (m_summary_str.empty())
753         return NULL;
754     return m_summary_str.c_str();
755 }
756 
757 bool
758 ValueObject::IsCStringContainer(bool check_pointer)
759 {
760     clang_type_t elem_or_pointee_clang_type;
761     const Flags type_flags (ClangASTContext::GetTypeInfo (GetClangType(),
762                                                           GetClangAST(),
763                                                           &elem_or_pointee_clang_type));
764     bool is_char_arr_ptr (type_flags.AnySet (ClangASTContext::eTypeIsArray | ClangASTContext::eTypeIsPointer) &&
765             ClangASTContext::IsCharType (elem_or_pointee_clang_type));
766     if (!is_char_arr_ptr)
767         return false;
768     if (!check_pointer)
769         return true;
770     if (type_flags.Test(ClangASTContext::eTypeIsArray))
771         return true;
772     addr_t cstr_address = LLDB_INVALID_ADDRESS;
773     AddressType cstr_address_type = eAddressTypeInvalid;
774     cstr_address = GetAddressOf (true, &cstr_address_type);
775     return (cstr_address != LLDB_INVALID_ADDRESS);
776 }
777 
778 size_t
779 ValueObject::GetPointeeData (DataExtractor& data,
780                              uint32_t item_idx,
781                              uint32_t item_count)
782 {
783     if (!IsPointerType() && !IsArrayType())
784         return 0;
785 
786     if (item_count == 0)
787         return 0;
788 
789     uint32_t stride = 0;
790 
791     ClangASTType type(GetClangAST(),
792                       GetClangType());
793 
794     const uint64_t item_type_size = (IsPointerType() ? ClangASTType::GetTypeByteSize(GetClangAST(), type.GetPointeeType()) :
795                                      ClangASTType::GetTypeByteSize(GetClangAST(), type.GetArrayElementType(stride)));
796 
797     const uint64_t bytes = item_count * item_type_size;
798 
799     const uint64_t offset = item_idx * item_type_size;
800 
801     if (item_idx == 0 && item_count == 1) // simply a deref
802     {
803         if (IsPointerType())
804         {
805             Error error;
806             ValueObjectSP pointee_sp = Dereference(error);
807             if (error.Fail() || pointee_sp.get() == NULL)
808                 return 0;
809             return pointee_sp->GetDataExtractor().Copy(data);
810         }
811         else
812         {
813             ValueObjectSP child_sp = GetChildAtIndex(0, true);
814             if (child_sp.get() == NULL)
815                 return 0;
816             return child_sp->GetDataExtractor().Copy(data);
817         }
818         return true;
819     }
820     else /* (items > 1) */
821     {
822         Error error;
823         lldb_private::DataBufferHeap* heap_buf_ptr = NULL;
824         lldb::DataBufferSP data_sp(heap_buf_ptr = new lldb_private::DataBufferHeap());
825 
826         AddressType addr_type;
827         lldb::addr_t addr = IsPointerType() ? GetPointerValue(&addr_type) : GetAddressOf(true, &addr_type);
828 
829         switch (addr_type)
830         {
831             case eAddressTypeFile:
832                 {
833                     ModuleSP module_sp (GetModule());
834                     if (module_sp)
835                     {
836                         Address so_addr;
837                         module_sp->ResolveFileAddress(addr, so_addr);
838                         ExecutionContext exe_ctx (GetExecutionContextRef());
839                         Target* target = exe_ctx.GetTargetPtr();
840                         if (target)
841                         {
842                             heap_buf_ptr->SetByteSize(bytes);
843                             size_t bytes_read = target->ReadMemory(so_addr, false, heap_buf_ptr->GetBytes(), bytes, error);
844                             if (error.Success())
845                             {
846                                 data.SetData(data_sp);
847                                 return bytes_read;
848                             }
849                         }
850                     }
851                 }
852                 break;
853             case eAddressTypeLoad:
854                 {
855                     ExecutionContext exe_ctx (GetExecutionContextRef());
856                     Process *process = exe_ctx.GetProcessPtr();
857                     if (process)
858                     {
859                         heap_buf_ptr->SetByteSize(bytes);
860                         size_t bytes_read = process->ReadMemory(addr + offset, heap_buf_ptr->GetBytes(), bytes, error);
861                         if (error.Success())
862                         {
863                             data.SetData(data_sp);
864                             return bytes_read;
865                         }
866                     }
867                 }
868                 break;
869             case eAddressTypeHost:
870                 {
871                     heap_buf_ptr->CopyData((uint8_t*)(addr + offset), bytes);
872                     data.SetData(data_sp);
873                     return bytes;
874                 }
875                 break;
876             case eAddressTypeInvalid:
877             default:
878                 break;
879         }
880     }
881     return 0;
882 }
883 
884 size_t
885 ValueObject::GetData (DataExtractor& data)
886 {
887     UpdateValueIfNeeded(false);
888     ExecutionContext exe_ctx (GetExecutionContextRef());
889     Error error = m_value.GetValueAsData(&exe_ctx, GetClangAST(), data, 0, GetModule().get());
890     if (error.Fail())
891         return 0;
892     data.SetAddressByteSize(m_data.GetAddressByteSize());
893     data.SetByteOrder(m_data.GetByteOrder());
894     return data.GetByteSize();
895 }
896 
897 // will compute strlen(str), but without consuming more than
898 // maxlen bytes out of str (this serves the purpose of reading
899 // chunks of a string without having to worry about
900 // missing NULL terminators in the chunk)
901 // of course, if strlen(str) > maxlen, the function will return
902 // maxlen_value (which should be != maxlen, because that allows you
903 // to know whether strlen(str) == maxlen or strlen(str) > maxlen)
904 static uint32_t
905 strlen_or_inf (const char* str,
906                uint32_t maxlen,
907                uint32_t maxlen_value)
908 {
909     uint32_t len = 0;
910     if (str)
911     {
912         while(*str)
913         {
914             len++;str++;
915             if (len > maxlen)
916                 return maxlen_value;
917         }
918     }
919     return len;
920 }
921 
922 void
923 ValueObject::ReadPointedString (Stream& s,
924                                 Error& error,
925                                 uint32_t max_length,
926                                 bool honor_array,
927                                 Format item_format)
928 {
929     ExecutionContext exe_ctx (GetExecutionContextRef());
930     Target* target = exe_ctx.GetTargetPtr();
931 
932     if (target && max_length == 0)
933         max_length = target->GetMaximumSizeOfStringSummary();
934 
935     clang_type_t clang_type = GetClangType();
936     clang_type_t elem_or_pointee_clang_type;
937     const Flags type_flags (ClangASTContext::GetTypeInfo (clang_type,
938                                                           GetClangAST(),
939                                                           &elem_or_pointee_clang_type));
940     if (type_flags.AnySet (ClangASTContext::eTypeIsArray | ClangASTContext::eTypeIsPointer) &&
941         ClangASTContext::IsCharType (elem_or_pointee_clang_type))
942     {
943         if (target == NULL)
944         {
945             s << "<no target to read from>";
946         }
947         else
948         {
949             addr_t cstr_address = LLDB_INVALID_ADDRESS;
950             AddressType cstr_address_type = eAddressTypeInvalid;
951 
952             size_t cstr_len = 0;
953             bool capped_data = false;
954             if (type_flags.Test (ClangASTContext::eTypeIsArray))
955             {
956                 // We have an array
957                 cstr_len = ClangASTContext::GetArraySize (clang_type);
958                 if (cstr_len > max_length)
959                 {
960                     capped_data = true;
961                     cstr_len = max_length;
962                 }
963                 cstr_address = GetAddressOf (true, &cstr_address_type);
964             }
965             else
966             {
967                 // We have a pointer
968                 cstr_address = GetPointerValue (&cstr_address_type);
969             }
970             if (cstr_address != 0 && cstr_address != LLDB_INVALID_ADDRESS)
971             {
972                 Address cstr_so_addr (cstr_address);
973                 DataExtractor data;
974                 size_t bytes_read = 0;
975                 if (cstr_len > 0 && honor_array)
976                 {
977                     // I am using GetPointeeData() here to abstract the fact that some ValueObjects are actually frozen pointers in the host
978                     // but the pointed-to data lives in the debuggee, and GetPointeeData() automatically takes care of this
979                     GetPointeeData(data, 0, cstr_len);
980 
981                     if ((bytes_read = data.GetByteSize()) > 0)
982                     {
983                         s << '"';
984                         data.Dump (&s,
985                                    0,                 // Start offset in "data"
986                                    item_format,
987                                    1,                 // Size of item (1 byte for a char!)
988                                    bytes_read,        // How many bytes to print?
989                                    UINT32_MAX,        // num per line
990                                    LLDB_INVALID_ADDRESS,// base address
991                                    0,                 // bitfield bit size
992                                    0);                // bitfield bit offset
993                         if (capped_data)
994                             s << "...";
995                         s << '"';
996                     }
997                 }
998                 else
999                 {
1000                     cstr_len = max_length;
1001                     const size_t k_max_buf_size = 64;
1002 
1003                     size_t offset = 0;
1004 
1005                     int cstr_len_displayed = -1;
1006                     bool capped_cstr = false;
1007                     // I am using GetPointeeData() here to abstract the fact that some ValueObjects are actually frozen pointers in the host
1008                     // but the pointed-to data lives in the debuggee, and GetPointeeData() automatically takes care of this
1009                     while ((bytes_read = GetPointeeData(data, offset, k_max_buf_size)) > 0)
1010                     {
1011                         const char *cstr = data.PeekCStr(0);
1012                         size_t len = strlen_or_inf (cstr, k_max_buf_size, k_max_buf_size+1);
1013                         if (len > k_max_buf_size)
1014                             len = k_max_buf_size;
1015                         if (cstr && cstr_len_displayed < 0)
1016                             s << '"';
1017 
1018                         if (cstr_len_displayed < 0)
1019                             cstr_len_displayed = len;
1020 
1021                         if (len == 0)
1022                             break;
1023                         cstr_len_displayed += len;
1024                         if (len > bytes_read)
1025                             len = bytes_read;
1026                         if (len > cstr_len)
1027                             len = cstr_len;
1028 
1029                         data.Dump (&s,
1030                                    0,                 // Start offset in "data"
1031                                    item_format,
1032                                    1,                 // Size of item (1 byte for a char!)
1033                                    len,               // How many bytes to print?
1034                                    UINT32_MAX,        // num per line
1035                                    LLDB_INVALID_ADDRESS,// base address
1036                                    0,                 // bitfield bit size
1037                                    0);                // bitfield bit offset
1038 
1039                         if (len < k_max_buf_size)
1040                             break;
1041 
1042                         if (len >= cstr_len)
1043                         {
1044                             capped_cstr = true;
1045                             break;
1046                         }
1047 
1048                         cstr_len -= len;
1049                         offset += len;
1050                     }
1051 
1052                     if (cstr_len_displayed >= 0)
1053                     {
1054                         s << '"';
1055                         if (capped_cstr)
1056                             s << "...";
1057                     }
1058                 }
1059             }
1060         }
1061     }
1062     else
1063     {
1064         error.SetErrorString("impossible to read a string from this object");
1065         s << "<not a string object>";
1066     }
1067 }
1068 
1069 const char *
1070 ValueObject::GetObjectDescription ()
1071 {
1072 
1073     if (!UpdateValueIfNeeded (true))
1074         return NULL;
1075 
1076     if (!m_object_desc_str.empty())
1077         return m_object_desc_str.c_str();
1078 
1079     ExecutionContext exe_ctx (GetExecutionContextRef());
1080     Process *process = exe_ctx.GetProcessPtr();
1081     if (process == NULL)
1082         return NULL;
1083 
1084     StreamString s;
1085 
1086     LanguageType language = GetObjectRuntimeLanguage();
1087     LanguageRuntime *runtime = process->GetLanguageRuntime(language);
1088 
1089     if (runtime == NULL)
1090     {
1091         // Aw, hell, if the things a pointer, or even just an integer, let's try ObjC anyway...
1092         clang_type_t opaque_qual_type = GetClangType();
1093         if (opaque_qual_type != NULL)
1094         {
1095             bool is_signed;
1096             if (ClangASTContext::IsIntegerType (opaque_qual_type, is_signed)
1097                 || ClangASTContext::IsPointerType (opaque_qual_type))
1098             {
1099                 runtime = process->GetLanguageRuntime(eLanguageTypeObjC);
1100             }
1101         }
1102     }
1103 
1104     if (runtime && runtime->GetObjectDescription(s, *this))
1105     {
1106         m_object_desc_str.append (s.GetData());
1107     }
1108 
1109     if (m_object_desc_str.empty())
1110         return NULL;
1111     else
1112         return m_object_desc_str.c_str();
1113 }
1114 
1115 bool
1116 ValueObject::GetValueAsCString (lldb::Format format,
1117                                 std::string& destination)
1118 {
1119     if (ClangASTContext::IsAggregateType (GetClangType()) == false &&
1120         UpdateValueIfNeeded(false))
1121     {
1122         const Value::ContextType context_type = m_value.GetContextType();
1123 
1124         switch (context_type)
1125         {
1126             case Value::eContextTypeClangType:
1127             case Value::eContextTypeLLDBType:
1128             case Value::eContextTypeVariable:
1129             {
1130                 clang_type_t clang_type = GetClangType ();
1131                 if (clang_type)
1132                 {
1133                     StreamString sstr;
1134                     ExecutionContext exe_ctx (GetExecutionContextRef());
1135                     ClangASTType::DumpTypeValue (GetClangAST(),             // The clang AST
1136                                                  clang_type,                // The clang type to display
1137                                                  &sstr,
1138                                                  format,                    // Format to display this type with
1139                                                  m_data,                    // Data to extract from
1140                                                  0,                         // Byte offset into "m_data"
1141                                                  GetByteSize(),             // Byte size of item in "m_data"
1142                                                  GetBitfieldBitSize(),      // Bitfield bit size
1143                                                  GetBitfieldBitOffset(),    // Bitfield bit offset
1144                                                  exe_ctx.GetBestExecutionContextScope());
1145                     // Don't set the m_error to anything here otherwise
1146                     // we won't be able to re-format as anything else. The
1147                     // code for ClangASTType::DumpTypeValue() should always
1148                     // return something, even if that something contains
1149                     // an error messsage. "m_error" is used to detect errors
1150                     // when reading the valid object, not for formatting errors.
1151                     if (sstr.GetString().empty())
1152                         destination.clear();
1153                     else
1154                         destination.swap(sstr.GetString());
1155                 }
1156             }
1157                 break;
1158 
1159             case Value::eContextTypeRegisterInfo:
1160             {
1161                 const RegisterInfo *reg_info = m_value.GetRegisterInfo();
1162                 if (reg_info)
1163                 {
1164                     ExecutionContext exe_ctx (GetExecutionContextRef());
1165 
1166                     StreamString reg_sstr;
1167                     m_data.Dump (&reg_sstr,
1168                                  0,
1169                                  format,
1170                                  reg_info->byte_size,
1171                                  1,
1172                                  UINT32_MAX,
1173                                  LLDB_INVALID_ADDRESS,
1174                                  0,
1175                                  0,
1176                                  exe_ctx.GetBestExecutionContextScope());
1177                     destination.swap(reg_sstr.GetString());
1178                 }
1179             }
1180                 break;
1181 
1182             default:
1183                 break;
1184         }
1185         return !destination.empty();
1186     }
1187     else
1188         return false;
1189 }
1190 
1191 const char *
1192 ValueObject::GetValueAsCString ()
1193 {
1194     if (UpdateValueIfNeeded(true) && m_value_str.empty())
1195     {
1196         lldb::Format my_format = GetFormat();
1197         if (m_format == lldb::eFormatDefault)
1198         {
1199             if (m_type_format_sp)
1200                 my_format = m_type_format_sp->GetFormat();
1201             else
1202             {
1203                 if (m_is_bitfield_for_scalar)
1204                     my_format = eFormatUnsigned;
1205                 else
1206                 {
1207                     if (m_value.GetContextType() == Value::eContextTypeRegisterInfo)
1208                     {
1209                         const RegisterInfo *reg_info = m_value.GetRegisterInfo();
1210                         if (reg_info)
1211                             my_format = reg_info->format;
1212                     }
1213                     else
1214                     {
1215                         clang_type_t clang_type = GetClangType ();
1216                         my_format = ClangASTType::GetFormat(clang_type);
1217                     }
1218                 }
1219             }
1220         }
1221         if (GetValueAsCString(my_format, m_value_str))
1222         {
1223             if (!m_value_did_change && m_old_value_valid)
1224             {
1225                 // The value was gotten successfully, so we consider the
1226                 // value as changed if the value string differs
1227                 SetValueDidChange (m_old_value_str != m_value_str);
1228             }
1229         }
1230     }
1231     if (m_value_str.empty())
1232         return NULL;
1233     return m_value_str.c_str();
1234 }
1235 
1236 // if > 8bytes, 0 is returned. this method should mostly be used
1237 // to read address values out of pointers
1238 uint64_t
1239 ValueObject::GetValueAsUnsigned (uint64_t fail_value)
1240 {
1241     // If our byte size is zero this is an aggregate type that has children
1242     if (ClangASTContext::IsAggregateType (GetClangType()) == false)
1243     {
1244         Scalar scalar;
1245         if (ResolveValue (scalar))
1246             return scalar.GetRawBits64(fail_value);
1247     }
1248     return fail_value;
1249 }
1250 
1251 // if any more "special cases" are added to ValueObject::DumpPrintableRepresentation() please keep
1252 // this call up to date by returning true for your new special cases. We will eventually move
1253 // to checking this call result before trying to display special cases
1254 bool
1255 ValueObject::HasSpecialPrintableRepresentation(ValueObjectRepresentationStyle val_obj_display,
1256                                                Format custom_format)
1257 {
1258     clang_type_t elem_or_pointee_type;
1259     Flags flags(ClangASTContext::GetTypeInfo(GetClangType(), GetClangAST(), &elem_or_pointee_type));
1260 
1261     if (flags.AnySet(ClangASTContext::eTypeIsArray | ClangASTContext::eTypeIsPointer)
1262         && val_obj_display == ValueObject::eValueObjectRepresentationStyleValue)
1263     {
1264         if (IsCStringContainer(true) &&
1265             (custom_format == eFormatCString ||
1266              custom_format == eFormatCharArray ||
1267              custom_format == eFormatChar ||
1268              custom_format == eFormatVectorOfChar))
1269             return true;
1270 
1271         if (flags.Test(ClangASTContext::eTypeIsArray))
1272         {
1273             if ((custom_format == eFormatBytes) ||
1274                 (custom_format == eFormatBytesWithASCII))
1275                 return true;
1276 
1277             if ((custom_format == eFormatVectorOfChar) ||
1278                 (custom_format == eFormatVectorOfFloat32) ||
1279                 (custom_format == eFormatVectorOfFloat64) ||
1280                 (custom_format == eFormatVectorOfSInt16) ||
1281                 (custom_format == eFormatVectorOfSInt32) ||
1282                 (custom_format == eFormatVectorOfSInt64) ||
1283                 (custom_format == eFormatVectorOfSInt8) ||
1284                 (custom_format == eFormatVectorOfUInt128) ||
1285                 (custom_format == eFormatVectorOfUInt16) ||
1286                 (custom_format == eFormatVectorOfUInt32) ||
1287                 (custom_format == eFormatVectorOfUInt64) ||
1288                 (custom_format == eFormatVectorOfUInt8))
1289                 return true;
1290         }
1291     }
1292     return false;
1293 }
1294 
1295 bool
1296 ValueObject::DumpPrintableRepresentation(Stream& s,
1297                                          ValueObjectRepresentationStyle val_obj_display,
1298                                          Format custom_format,
1299                                          PrintableRepresentationSpecialCases special)
1300 {
1301 
1302     clang_type_t elem_or_pointee_type;
1303     Flags flags(ClangASTContext::GetTypeInfo(GetClangType(), GetClangAST(), &elem_or_pointee_type));
1304 
1305     bool allow_special = ((special & ePrintableRepresentationSpecialCasesAllow) == ePrintableRepresentationSpecialCasesAllow);
1306     bool only_special = ((special & ePrintableRepresentationSpecialCasesOnly) == ePrintableRepresentationSpecialCasesOnly);
1307 
1308     if (allow_special)
1309     {
1310         if (flags.AnySet(ClangASTContext::eTypeIsArray | ClangASTContext::eTypeIsPointer)
1311              && val_obj_display == ValueObject::eValueObjectRepresentationStyleValue)
1312         {
1313             // when being asked to get a printable display an array or pointer type directly,
1314             // try to "do the right thing"
1315 
1316             if (IsCStringContainer(true) &&
1317                 (custom_format == eFormatCString ||
1318                  custom_format == eFormatCharArray ||
1319                  custom_format == eFormatChar ||
1320                  custom_format == eFormatVectorOfChar)) // print char[] & char* directly
1321             {
1322                 Error error;
1323                 ReadPointedString(s,
1324                                   error,
1325                                   0,
1326                                   (custom_format == eFormatVectorOfChar) ||
1327                                   (custom_format == eFormatCharArray));
1328                 return !error.Fail();
1329             }
1330 
1331             if (custom_format == eFormatEnum)
1332                 return false;
1333 
1334             // this only works for arrays, because I have no way to know when
1335             // the pointed memory ends, and no special \0 end of data marker
1336             if (flags.Test(ClangASTContext::eTypeIsArray))
1337             {
1338                 if ((custom_format == eFormatBytes) ||
1339                     (custom_format == eFormatBytesWithASCII))
1340                 {
1341                     uint32_t count = GetNumChildren();
1342 
1343                     s << '[';
1344                     for (uint32_t low = 0; low < count; low++)
1345                     {
1346 
1347                         if (low)
1348                             s << ',';
1349 
1350                         ValueObjectSP child = GetChildAtIndex(low,true);
1351                         if (!child.get())
1352                         {
1353                             s << "<invalid child>";
1354                             continue;
1355                         }
1356                         child->DumpPrintableRepresentation(s, ValueObject::eValueObjectRepresentationStyleValue, custom_format);
1357                     }
1358 
1359                     s << ']';
1360 
1361                     return true;
1362                 }
1363 
1364                 if ((custom_format == eFormatVectorOfChar) ||
1365                     (custom_format == eFormatVectorOfFloat32) ||
1366                     (custom_format == eFormatVectorOfFloat64) ||
1367                     (custom_format == eFormatVectorOfSInt16) ||
1368                     (custom_format == eFormatVectorOfSInt32) ||
1369                     (custom_format == eFormatVectorOfSInt64) ||
1370                     (custom_format == eFormatVectorOfSInt8) ||
1371                     (custom_format == eFormatVectorOfUInt128) ||
1372                     (custom_format == eFormatVectorOfUInt16) ||
1373                     (custom_format == eFormatVectorOfUInt32) ||
1374                     (custom_format == eFormatVectorOfUInt64) ||
1375                     (custom_format == eFormatVectorOfUInt8)) // arrays of bytes, bytes with ASCII or any vector format should be printed directly
1376                 {
1377                     uint32_t count = GetNumChildren();
1378 
1379                     Format format = FormatManager::GetSingleItemFormat(custom_format);
1380 
1381                     s << '[';
1382                     for (uint32_t low = 0; low < count; low++)
1383                     {
1384 
1385                         if (low)
1386                             s << ',';
1387 
1388                         ValueObjectSP child = GetChildAtIndex(low,true);
1389                         if (!child.get())
1390                         {
1391                             s << "<invalid child>";
1392                             continue;
1393                         }
1394                         child->DumpPrintableRepresentation(s, ValueObject::eValueObjectRepresentationStyleValue, format);
1395                     }
1396 
1397                     s << ']';
1398 
1399                     return true;
1400                 }
1401             }
1402 
1403             if ((custom_format == eFormatBoolean) ||
1404                 (custom_format == eFormatBinary) ||
1405                 (custom_format == eFormatChar) ||
1406                 (custom_format == eFormatCharPrintable) ||
1407                 (custom_format == eFormatComplexFloat) ||
1408                 (custom_format == eFormatDecimal) ||
1409                 (custom_format == eFormatHex) ||
1410                 (custom_format == eFormatFloat) ||
1411                 (custom_format == eFormatOctal) ||
1412                 (custom_format == eFormatOSType) ||
1413                 (custom_format == eFormatUnicode16) ||
1414                 (custom_format == eFormatUnicode32) ||
1415                 (custom_format == eFormatUnsigned) ||
1416                 (custom_format == eFormatPointer) ||
1417                 (custom_format == eFormatComplexInteger) ||
1418                 (custom_format == eFormatComplex) ||
1419                 (custom_format == eFormatDefault)) // use the [] operator
1420                 return false;
1421         }
1422     }
1423 
1424     if (only_special)
1425         return false;
1426 
1427     bool var_success = false;
1428 
1429     {
1430         const char * return_value;
1431         std::string alloc_mem;
1432 
1433         if (custom_format != eFormatInvalid)
1434             SetFormat(custom_format);
1435 
1436         switch(val_obj_display)
1437         {
1438             case eValueObjectRepresentationStyleValue:
1439                 return_value = GetValueAsCString();
1440                 break;
1441 
1442             case eValueObjectRepresentationStyleSummary:
1443                 return_value = GetSummaryAsCString();
1444                 break;
1445 
1446             case eValueObjectRepresentationStyleLanguageSpecific:
1447                 return_value = GetObjectDescription();
1448                 break;
1449 
1450             case eValueObjectRepresentationStyleLocation:
1451                 return_value = GetLocationAsCString();
1452                 break;
1453 
1454             case eValueObjectRepresentationStyleChildrenCount:
1455             {
1456                 alloc_mem.resize(512);
1457                 return_value = &alloc_mem[0];
1458                 int count = GetNumChildren();
1459                 snprintf((char*)return_value, 512, "%d", count);
1460             }
1461                 break;
1462 
1463             case eValueObjectRepresentationStyleType:
1464                 return_value = GetTypeName().AsCString();
1465                 break;
1466 
1467             default:
1468                 break;
1469         }
1470 
1471         if (!return_value)
1472         {
1473             if (val_obj_display == eValueObjectRepresentationStyleValue)
1474                 return_value = GetSummaryAsCString();
1475             else if (val_obj_display == eValueObjectRepresentationStyleSummary)
1476             {
1477                 if (ClangASTContext::IsAggregateType (GetClangType()) == true)
1478                 {
1479                     // this thing has no value, and it seems to have no summary
1480                     // some combination of unitialized data and other factors can also
1481                     // raise this condition, so let's print a nice generic description
1482                     {
1483                         alloc_mem.resize(684);
1484                         return_value = &alloc_mem[0];
1485                         snprintf((char*)return_value, 684, "%s @ %s", GetTypeName().AsCString(), GetLocationAsCString());
1486                     }
1487                 }
1488                 else
1489                     return_value = GetValueAsCString();
1490             }
1491         }
1492 
1493         if (return_value)
1494             s.PutCString(return_value);
1495         else
1496         {
1497             if (m_error.Fail())
1498                 s.Printf("<%s>", m_error.AsCString());
1499             else if (val_obj_display == eValueObjectRepresentationStyleSummary)
1500                 s.PutCString("<no summary available>");
1501             else if (val_obj_display == eValueObjectRepresentationStyleValue)
1502                 s.PutCString("<no value available>");
1503             else if (val_obj_display == eValueObjectRepresentationStyleLanguageSpecific)
1504                 s.PutCString("<not a valid Objective-C object>"); // edit this if we have other runtimes that support a description
1505             else
1506                 s.PutCString("<no printable representation>");
1507         }
1508 
1509         // we should only return false here if we could not do *anything*
1510         // even if we have an error message as output, that's a success
1511         // from our callers' perspective, so return true
1512         var_success = true;
1513 
1514         if (custom_format != eFormatInvalid)
1515             SetFormat(eFormatDefault);
1516     }
1517 
1518     return var_success;
1519 }
1520 
1521 addr_t
1522 ValueObject::GetAddressOf (bool scalar_is_load_address, AddressType *address_type)
1523 {
1524     if (!UpdateValueIfNeeded(false))
1525         return LLDB_INVALID_ADDRESS;
1526 
1527     switch (m_value.GetValueType())
1528     {
1529     case Value::eValueTypeScalar:
1530         if (scalar_is_load_address)
1531         {
1532             if(address_type)
1533                 *address_type = eAddressTypeLoad;
1534             return m_value.GetScalar().ULongLong(LLDB_INVALID_ADDRESS);
1535         }
1536         break;
1537 
1538     case Value::eValueTypeLoadAddress:
1539     case Value::eValueTypeFileAddress:
1540     case Value::eValueTypeHostAddress:
1541         {
1542             if(address_type)
1543                 *address_type = m_value.GetValueAddressType ();
1544             return m_value.GetScalar().ULongLong(LLDB_INVALID_ADDRESS);
1545         }
1546         break;
1547     }
1548     if (address_type)
1549         *address_type = eAddressTypeInvalid;
1550     return LLDB_INVALID_ADDRESS;
1551 }
1552 
1553 addr_t
1554 ValueObject::GetPointerValue (AddressType *address_type)
1555 {
1556     addr_t address = LLDB_INVALID_ADDRESS;
1557     if(address_type)
1558         *address_type = eAddressTypeInvalid;
1559 
1560     if (!UpdateValueIfNeeded(false))
1561         return address;
1562 
1563     switch (m_value.GetValueType())
1564     {
1565     case Value::eValueTypeScalar:
1566         address = m_value.GetScalar().ULongLong(LLDB_INVALID_ADDRESS);
1567         break;
1568 
1569     case Value::eValueTypeHostAddress:
1570     case Value::eValueTypeLoadAddress:
1571     case Value::eValueTypeFileAddress:
1572         {
1573             uint32_t data_offset = 0;
1574             address = m_data.GetPointer(&data_offset);
1575         }
1576         break;
1577     }
1578 
1579     if (address_type)
1580         *address_type = GetAddressTypeOfChildren();
1581 
1582     return address;
1583 }
1584 
1585 bool
1586 ValueObject::SetValueFromCString (const char *value_str)
1587 {
1588     // Make sure our value is up to date first so that our location and location
1589     // type is valid.
1590     if (!UpdateValueIfNeeded(false))
1591         return false;
1592 
1593     uint32_t count = 0;
1594     Encoding encoding = ClangASTType::GetEncoding (GetClangType(), count);
1595 
1596     const size_t byte_size = GetByteSize();
1597 
1598     Value::ValueType value_type = m_value.GetValueType();
1599 
1600     if (value_type == Value::eValueTypeScalar)
1601     {
1602         // If the value is already a scalar, then let the scalar change itself:
1603         m_value.GetScalar().SetValueFromCString (value_str, encoding, byte_size);
1604     }
1605     else if (byte_size <= Scalar::GetMaxByteSize())
1606     {
1607         // If the value fits in a scalar, then make a new scalar and again let the
1608         // scalar code do the conversion, then figure out where to put the new value.
1609         Scalar new_scalar;
1610         Error error;
1611         error = new_scalar.SetValueFromCString (value_str, encoding, byte_size);
1612         if (error.Success())
1613         {
1614             switch (value_type)
1615             {
1616             case Value::eValueTypeLoadAddress:
1617                 {
1618                     // If it is a load address, then the scalar value is the storage location
1619                     // of the data, and we have to shove this value down to that load location.
1620                     ExecutionContext exe_ctx (GetExecutionContextRef());
1621                     Process *process = exe_ctx.GetProcessPtr();
1622                     if (process)
1623                     {
1624                         addr_t target_addr = m_value.GetScalar().GetRawBits64(LLDB_INVALID_ADDRESS);
1625                         size_t bytes_written = process->WriteScalarToMemory (target_addr,
1626                                                                              new_scalar,
1627                                                                              byte_size,
1628                                                                              error);
1629                         if (!error.Success() || bytes_written != byte_size)
1630                             return false;
1631                     }
1632                 }
1633                 break;
1634             case Value::eValueTypeHostAddress:
1635                 {
1636                     // If it is a host address, then we stuff the scalar as a DataBuffer into the Value's data.
1637                     DataExtractor new_data;
1638                     new_data.SetByteOrder (m_data.GetByteOrder());
1639 
1640                     DataBufferSP buffer_sp (new DataBufferHeap(byte_size, 0));
1641                     m_data.SetData(buffer_sp, 0);
1642                     bool success = new_scalar.GetData(new_data);
1643                     if (success)
1644                     {
1645                         new_data.CopyByteOrderedData (0,
1646                                                       byte_size,
1647                                                       const_cast<uint8_t *>(m_data.GetDataStart()),
1648                                                       byte_size,
1649                                                       m_data.GetByteOrder());
1650                     }
1651                     m_value.GetScalar() = (uintptr_t)m_data.GetDataStart();
1652 
1653                 }
1654                 break;
1655             case Value::eValueTypeFileAddress:
1656             case Value::eValueTypeScalar:
1657                 break;
1658             }
1659         }
1660         else
1661         {
1662             return false;
1663         }
1664     }
1665     else
1666     {
1667         // We don't support setting things bigger than a scalar at present.
1668         return false;
1669     }
1670 
1671     // If we have reached this point, then we have successfully changed the value.
1672     SetNeedsUpdate();
1673     return true;
1674 }
1675 
1676 bool
1677 ValueObject::GetDeclaration (Declaration &decl)
1678 {
1679     decl.Clear();
1680     return false;
1681 }
1682 
1683 ConstString
1684 ValueObject::GetTypeName()
1685 {
1686     return ClangASTType::GetConstTypeName (GetClangAST(), GetClangType());
1687 }
1688 
1689 ConstString
1690 ValueObject::GetQualifiedTypeName()
1691 {
1692     return ClangASTType::GetConstQualifiedTypeName (GetClangAST(), GetClangType());
1693 }
1694 
1695 
1696 LanguageType
1697 ValueObject::GetObjectRuntimeLanguage ()
1698 {
1699     return ClangASTType::GetMinimumLanguage (GetClangAST(),
1700                                              GetClangType());
1701 }
1702 
1703 void
1704 ValueObject::AddSyntheticChild (const ConstString &key, ValueObject *valobj)
1705 {
1706     m_synthetic_children[key] = valobj;
1707 }
1708 
1709 ValueObjectSP
1710 ValueObject::GetSyntheticChild (const ConstString &key) const
1711 {
1712     ValueObjectSP synthetic_child_sp;
1713     std::map<ConstString, ValueObject *>::const_iterator pos = m_synthetic_children.find (key);
1714     if (pos != m_synthetic_children.end())
1715         synthetic_child_sp = pos->second->GetSP();
1716     return synthetic_child_sp;
1717 }
1718 
1719 bool
1720 ValueObject::IsPointerType ()
1721 {
1722     return ClangASTContext::IsPointerType (GetClangType());
1723 }
1724 
1725 bool
1726 ValueObject::IsArrayType ()
1727 {
1728     return ClangASTContext::IsArrayType (GetClangType());
1729 }
1730 
1731 bool
1732 ValueObject::IsScalarType ()
1733 {
1734     return ClangASTContext::IsScalarType (GetClangType());
1735 }
1736 
1737 bool
1738 ValueObject::IsIntegerType (bool &is_signed)
1739 {
1740     return ClangASTContext::IsIntegerType (GetClangType(), is_signed);
1741 }
1742 
1743 bool
1744 ValueObject::IsPointerOrReferenceType ()
1745 {
1746     return ClangASTContext::IsPointerOrReferenceType (GetClangType());
1747 }
1748 
1749 bool
1750 ValueObject::IsPossibleCPlusPlusDynamicType ()
1751 {
1752     return ClangASTContext::IsPossibleCPlusPlusDynamicType (GetClangAST (), GetClangType());
1753 }
1754 
1755 bool
1756 ValueObject::IsPossibleDynamicType ()
1757 {
1758     return ClangASTContext::IsPossibleDynamicType (GetClangAST (), GetClangType());
1759 }
1760 
1761 ValueObjectSP
1762 ValueObject::GetSyntheticArrayMember (int32_t index, bool can_create)
1763 {
1764     if (IsArrayType())
1765         return GetSyntheticArrayMemberFromArray(index, can_create);
1766 
1767     if (IsPointerType())
1768         return GetSyntheticArrayMemberFromPointer(index, can_create);
1769 
1770     return ValueObjectSP();
1771 
1772 }
1773 
1774 ValueObjectSP
1775 ValueObject::GetSyntheticArrayMemberFromPointer (int32_t index, bool can_create)
1776 {
1777     ValueObjectSP synthetic_child_sp;
1778     if (IsPointerType ())
1779     {
1780         char index_str[64];
1781         snprintf(index_str, sizeof(index_str), "[%i]", index);
1782         ConstString index_const_str(index_str);
1783         // Check if we have already created a synthetic array member in this
1784         // valid object. If we have we will re-use it.
1785         synthetic_child_sp = GetSyntheticChild (index_const_str);
1786         if (!synthetic_child_sp)
1787         {
1788             ValueObject *synthetic_child;
1789             // We haven't made a synthetic array member for INDEX yet, so
1790             // lets make one and cache it for any future reference.
1791             synthetic_child = CreateChildAtIndex(0, true, index);
1792 
1793             // Cache the value if we got one back...
1794             if (synthetic_child)
1795             {
1796                 AddSyntheticChild(index_const_str, synthetic_child);
1797                 synthetic_child_sp = synthetic_child->GetSP();
1798                 synthetic_child_sp->SetName(ConstString(index_str));
1799                 synthetic_child_sp->m_is_array_item_for_pointer = true;
1800             }
1801         }
1802     }
1803     return synthetic_child_sp;
1804 }
1805 
1806 // This allows you to create an array member using and index
1807 // that doesn't not fall in the normal bounds of the array.
1808 // Many times structure can be defined as:
1809 // struct Collection
1810 // {
1811 //     uint32_t item_count;
1812 //     Item item_array[0];
1813 // };
1814 // The size of the "item_array" is 1, but many times in practice
1815 // there are more items in "item_array".
1816 
1817 ValueObjectSP
1818 ValueObject::GetSyntheticArrayMemberFromArray (int32_t index, bool can_create)
1819 {
1820     ValueObjectSP synthetic_child_sp;
1821     if (IsArrayType ())
1822     {
1823         char index_str[64];
1824         snprintf(index_str, sizeof(index_str), "[%i]", index);
1825         ConstString index_const_str(index_str);
1826         // Check if we have already created a synthetic array member in this
1827         // valid object. If we have we will re-use it.
1828         synthetic_child_sp = GetSyntheticChild (index_const_str);
1829         if (!synthetic_child_sp)
1830         {
1831             ValueObject *synthetic_child;
1832             // We haven't made a synthetic array member for INDEX yet, so
1833             // lets make one and cache it for any future reference.
1834             synthetic_child = CreateChildAtIndex(0, true, index);
1835 
1836             // Cache the value if we got one back...
1837             if (synthetic_child)
1838             {
1839                 AddSyntheticChild(index_const_str, synthetic_child);
1840                 synthetic_child_sp = synthetic_child->GetSP();
1841                 synthetic_child_sp->SetName(ConstString(index_str));
1842                 synthetic_child_sp->m_is_array_item_for_pointer = true;
1843             }
1844         }
1845     }
1846     return synthetic_child_sp;
1847 }
1848 
1849 ValueObjectSP
1850 ValueObject::GetSyntheticBitFieldChild (uint32_t from, uint32_t to, bool can_create)
1851 {
1852     ValueObjectSP synthetic_child_sp;
1853     if (IsScalarType ())
1854     {
1855         char index_str[64];
1856         snprintf(index_str, sizeof(index_str), "[%i-%i]", from, to);
1857         ConstString index_const_str(index_str);
1858         // Check if we have already created a synthetic array member in this
1859         // valid object. If we have we will re-use it.
1860         synthetic_child_sp = GetSyntheticChild (index_const_str);
1861         if (!synthetic_child_sp)
1862         {
1863             ValueObjectChild *synthetic_child;
1864             // We haven't made a synthetic array member for INDEX yet, so
1865             // lets make one and cache it for any future reference.
1866             synthetic_child = new ValueObjectChild(*this,
1867                                                       GetClangAST(),
1868                                                       GetClangType(),
1869                                                       index_const_str,
1870                                                       GetByteSize(),
1871                                                       0,
1872                                                       to-from+1,
1873                                                       from,
1874                                                       false,
1875                                                       false,
1876                                                       eAddressTypeInvalid);
1877 
1878             // Cache the value if we got one back...
1879             if (synthetic_child)
1880             {
1881                 AddSyntheticChild(index_const_str, synthetic_child);
1882                 synthetic_child_sp = synthetic_child->GetSP();
1883                 synthetic_child_sp->SetName(ConstString(index_str));
1884                 synthetic_child_sp->m_is_bitfield_for_scalar = true;
1885             }
1886         }
1887     }
1888     return synthetic_child_sp;
1889 }
1890 
1891 ValueObjectSP
1892 ValueObject::GetSyntheticArrayRangeChild (uint32_t from, uint32_t to, bool can_create)
1893 {
1894     ValueObjectSP synthetic_child_sp;
1895     if (IsArrayType () || IsPointerType ())
1896     {
1897         char index_str[64];
1898         snprintf(index_str, sizeof(index_str), "[%i-%i]", from, to);
1899         ConstString index_const_str(index_str);
1900         // Check if we have already created a synthetic array member in this
1901         // valid object. If we have we will re-use it.
1902         synthetic_child_sp = GetSyntheticChild (index_const_str);
1903         if (!synthetic_child_sp)
1904         {
1905             ValueObjectSynthetic *synthetic_child;
1906 
1907             // We haven't made a synthetic array member for INDEX yet, so
1908             // lets make one and cache it for any future reference.
1909             SyntheticArrayView *view = new SyntheticArrayView(SyntheticChildren::Flags());
1910             view->AddRange(from,to);
1911             SyntheticChildrenSP view_sp(view);
1912             synthetic_child = new ValueObjectSynthetic(*this, view_sp);
1913 
1914             // Cache the value if we got one back...
1915             if (synthetic_child)
1916             {
1917                 AddSyntheticChild(index_const_str, synthetic_child);
1918                 synthetic_child_sp = synthetic_child->GetSP();
1919                 synthetic_child_sp->SetName(ConstString(index_str));
1920                 synthetic_child_sp->m_is_bitfield_for_scalar = true;
1921             }
1922         }
1923     }
1924     return synthetic_child_sp;
1925 }
1926 
1927 ValueObjectSP
1928 ValueObject::GetSyntheticChildAtOffset(uint32_t offset, const ClangASTType& type, bool can_create)
1929 {
1930 
1931     ValueObjectSP synthetic_child_sp;
1932 
1933     char name_str[64];
1934     snprintf(name_str, sizeof(name_str), "@%i", offset);
1935     ConstString name_const_str(name_str);
1936 
1937     // Check if we have already created a synthetic array member in this
1938     // valid object. If we have we will re-use it.
1939     synthetic_child_sp = GetSyntheticChild (name_const_str);
1940 
1941     if (synthetic_child_sp.get())
1942         return synthetic_child_sp;
1943 
1944     if (!can_create)
1945         return ValueObjectSP();
1946 
1947     ValueObjectChild *synthetic_child = new ValueObjectChild(*this,
1948                                                              type.GetASTContext(),
1949                                                              type.GetOpaqueQualType(),
1950                                                              name_const_str,
1951                                                              type.GetTypeByteSize(),
1952                                                              offset,
1953                                                              0,
1954                                                              0,
1955                                                              false,
1956                                                              false,
1957                                                              eAddressTypeInvalid);
1958     if (synthetic_child)
1959     {
1960         AddSyntheticChild(name_const_str, synthetic_child);
1961         synthetic_child_sp = synthetic_child->GetSP();
1962         synthetic_child_sp->SetName(name_const_str);
1963         synthetic_child_sp->m_is_child_at_offset = true;
1964     }
1965     return synthetic_child_sp;
1966 }
1967 
1968 // your expression path needs to have a leading . or ->
1969 // (unless it somehow "looks like" an array, in which case it has
1970 // a leading [ symbol). while the [ is meaningful and should be shown
1971 // to the user, . and -> are just parser design, but by no means
1972 // added information for the user.. strip them off
1973 static const char*
1974 SkipLeadingExpressionPathSeparators(const char* expression)
1975 {
1976     if (!expression || !expression[0])
1977         return expression;
1978     if (expression[0] == '.')
1979         return expression+1;
1980     if (expression[0] == '-' && expression[1] == '>')
1981         return expression+2;
1982     return expression;
1983 }
1984 
1985 ValueObjectSP
1986 ValueObject::GetSyntheticExpressionPathChild(const char* expression, bool can_create)
1987 {
1988     ValueObjectSP synthetic_child_sp;
1989     ConstString name_const_string(expression);
1990     // Check if we have already created a synthetic array member in this
1991     // valid object. If we have we will re-use it.
1992     synthetic_child_sp = GetSyntheticChild (name_const_string);
1993     if (!synthetic_child_sp)
1994     {
1995         // We haven't made a synthetic array member for expression yet, so
1996         // lets make one and cache it for any future reference.
1997         synthetic_child_sp = GetValueForExpressionPath(expression);
1998 
1999         // Cache the value if we got one back...
2000         if (synthetic_child_sp.get())
2001         {
2002             AddSyntheticChild(name_const_string, synthetic_child_sp.get());
2003             synthetic_child_sp->SetName(ConstString(SkipLeadingExpressionPathSeparators(expression)));
2004             synthetic_child_sp->m_is_expression_path_child = true;
2005         }
2006     }
2007     return synthetic_child_sp;
2008 }
2009 
2010 void
2011 ValueObject::CalculateSyntheticValue (bool use_synthetic)
2012 {
2013     if (use_synthetic == false)
2014         return;
2015 
2016     TargetSP target_sp(GetTargetSP());
2017     if (target_sp && (target_sp->GetEnableSyntheticValue() == false || target_sp->GetSuppressSyntheticValue() == true))
2018     {
2019         m_synthetic_value = NULL;
2020         return;
2021     }
2022 
2023     if (!UpdateFormatsIfNeeded(m_last_format_mgr_dynamic) && m_synthetic_value)
2024         return;
2025 
2026     if (m_synthetic_children_sp.get() == NULL)
2027         return;
2028 
2029     m_synthetic_value = new ValueObjectSynthetic(*this, m_synthetic_children_sp);
2030 }
2031 
2032 void
2033 ValueObject::CalculateDynamicValue (DynamicValueType use_dynamic)
2034 {
2035     if (use_dynamic == eNoDynamicValues)
2036         return;
2037 
2038     if (!m_dynamic_value && !IsDynamic())
2039     {
2040         ExecutionContext exe_ctx (GetExecutionContextRef());
2041         Process *process = exe_ctx.GetProcessPtr();
2042         if (process)
2043         {
2044             bool worth_having_dynamic_value = false;
2045 
2046 
2047             // FIXME: Process should have some kind of "map over Runtimes" so we don't have to
2048             // hard code this everywhere.
2049             LanguageType known_type = GetObjectRuntimeLanguage();
2050             if (known_type != eLanguageTypeUnknown && known_type != eLanguageTypeC)
2051             {
2052                 LanguageRuntime *runtime = process->GetLanguageRuntime (known_type);
2053                 if (runtime)
2054                     worth_having_dynamic_value = runtime->CouldHaveDynamicValue(*this);
2055             }
2056             else
2057             {
2058                 LanguageRuntime *cpp_runtime = process->GetLanguageRuntime (eLanguageTypeC_plus_plus);
2059                 if (cpp_runtime)
2060                     worth_having_dynamic_value = cpp_runtime->CouldHaveDynamicValue(*this);
2061 
2062                 if (!worth_having_dynamic_value)
2063                 {
2064                     LanguageRuntime *objc_runtime = process->GetLanguageRuntime (eLanguageTypeObjC);
2065                     if (objc_runtime)
2066                         worth_having_dynamic_value = objc_runtime->CouldHaveDynamicValue(*this);
2067                 }
2068             }
2069 
2070             if (worth_having_dynamic_value)
2071                 m_dynamic_value = new ValueObjectDynamicValue (*this, use_dynamic);
2072         }
2073     }
2074 }
2075 
2076 ValueObjectSP
2077 ValueObject::GetDynamicValue (DynamicValueType use_dynamic)
2078 {
2079     if (use_dynamic == eNoDynamicValues)
2080         return ValueObjectSP();
2081 
2082     if (!IsDynamic() && m_dynamic_value == NULL)
2083     {
2084         CalculateDynamicValue(use_dynamic);
2085     }
2086     if (m_dynamic_value)
2087         return m_dynamic_value->GetSP();
2088     else
2089         return ValueObjectSP();
2090 }
2091 
2092 ValueObjectSP
2093 ValueObject::GetStaticValue()
2094 {
2095     return GetSP();
2096 }
2097 
2098 ValueObjectSP
2099 ValueObject::GetSyntheticValue (bool use_synthetic)
2100 {
2101     if (use_synthetic == false)
2102         return ValueObjectSP();
2103 
2104     CalculateSyntheticValue(use_synthetic);
2105 
2106     if (m_synthetic_value)
2107         return m_synthetic_value->GetSP();
2108     else
2109         return ValueObjectSP();
2110 }
2111 
2112 bool
2113 ValueObject::HasSyntheticValue()
2114 {
2115     UpdateFormatsIfNeeded(m_last_format_mgr_dynamic);
2116 
2117     if (m_synthetic_children_sp.get() == NULL)
2118         return false;
2119 
2120     CalculateSyntheticValue(true);
2121 
2122     if (m_synthetic_value)
2123         return true;
2124     else
2125         return false;
2126 }
2127 
2128 bool
2129 ValueObject::GetBaseClassPath (Stream &s)
2130 {
2131     if (IsBaseClass())
2132     {
2133         bool parent_had_base_class = GetParent() && GetParent()->GetBaseClassPath (s);
2134         clang_type_t clang_type = GetClangType();
2135         std::string cxx_class_name;
2136         bool this_had_base_class = ClangASTContext::GetCXXClassName (clang_type, cxx_class_name);
2137         if (this_had_base_class)
2138         {
2139             if (parent_had_base_class)
2140                 s.PutCString("::");
2141             s.PutCString(cxx_class_name.c_str());
2142         }
2143         return parent_had_base_class || this_had_base_class;
2144     }
2145     return false;
2146 }
2147 
2148 
2149 ValueObject *
2150 ValueObject::GetNonBaseClassParent()
2151 {
2152     if (GetParent())
2153     {
2154         if (GetParent()->IsBaseClass())
2155             return GetParent()->GetNonBaseClassParent();
2156         else
2157             return GetParent();
2158     }
2159     return NULL;
2160 }
2161 
2162 void
2163 ValueObject::GetExpressionPath (Stream &s, bool qualify_cxx_base_classes, GetExpressionPathFormat epformat)
2164 {
2165     const bool is_deref_of_parent = IsDereferenceOfParent ();
2166 
2167     if (is_deref_of_parent && epformat == eGetExpressionPathFormatDereferencePointers)
2168     {
2169         // this is the original format of GetExpressionPath() producing code like *(a_ptr).memberName, which is entirely
2170         // fine, until you put this into StackFrame::GetValueForVariableExpressionPath() which prefers to see a_ptr->memberName.
2171         // the eHonorPointers mode is meant to produce strings in this latter format
2172         s.PutCString("*(");
2173     }
2174 
2175     ValueObject* parent = GetParent();
2176 
2177     if (parent)
2178         parent->GetExpressionPath (s, qualify_cxx_base_classes, epformat);
2179 
2180     // if we are a deref_of_parent just because we are synthetic array
2181     // members made up to allow ptr[%d] syntax to work in variable
2182     // printing, then add our name ([%d]) to the expression path
2183     if (m_is_array_item_for_pointer && epformat == eGetExpressionPathFormatHonorPointers)
2184         s.PutCString(m_name.AsCString());
2185 
2186     if (!IsBaseClass())
2187     {
2188         if (!is_deref_of_parent)
2189         {
2190             ValueObject *non_base_class_parent = GetNonBaseClassParent();
2191             if (non_base_class_parent)
2192             {
2193                 clang_type_t non_base_class_parent_clang_type = non_base_class_parent->GetClangType();
2194                 if (non_base_class_parent_clang_type)
2195                 {
2196                     const uint32_t non_base_class_parent_type_info = ClangASTContext::GetTypeInfo (non_base_class_parent_clang_type, NULL, NULL);
2197 
2198                     if (parent && parent->IsDereferenceOfParent() && epformat == eGetExpressionPathFormatHonorPointers)
2199                     {
2200                         s.PutCString("->");
2201                     }
2202                     else
2203                     {
2204                         if (non_base_class_parent_type_info & ClangASTContext::eTypeIsPointer)
2205                         {
2206                             s.PutCString("->");
2207                         }
2208                         else if ((non_base_class_parent_type_info & ClangASTContext::eTypeHasChildren) &&
2209                                  !(non_base_class_parent_type_info & ClangASTContext::eTypeIsArray))
2210                         {
2211                             s.PutChar('.');
2212                         }
2213                     }
2214                 }
2215             }
2216 
2217             const char *name = GetName().GetCString();
2218             if (name)
2219             {
2220                 if (qualify_cxx_base_classes)
2221                 {
2222                     if (GetBaseClassPath (s))
2223                         s.PutCString("::");
2224                 }
2225                 s.PutCString(name);
2226             }
2227         }
2228     }
2229 
2230     if (is_deref_of_parent && epformat == eGetExpressionPathFormatDereferencePointers)
2231     {
2232         s.PutChar(')');
2233     }
2234 }
2235 
2236 ValueObjectSP
2237 ValueObject::GetValueForExpressionPath(const char* expression,
2238                                        const char** first_unparsed,
2239                                        ExpressionPathScanEndReason* reason_to_stop,
2240                                        ExpressionPathEndResultType* final_value_type,
2241                                        const GetValueForExpressionPathOptions& options,
2242                                        ExpressionPathAftermath* final_task_on_target)
2243 {
2244 
2245     const char* dummy_first_unparsed;
2246     ExpressionPathScanEndReason dummy_reason_to_stop;
2247     ExpressionPathEndResultType dummy_final_value_type;
2248     ExpressionPathAftermath dummy_final_task_on_target = ValueObject::eExpressionPathAftermathNothing;
2249 
2250     ValueObjectSP ret_val = GetValueForExpressionPath_Impl(expression,
2251                                                            first_unparsed ? first_unparsed : &dummy_first_unparsed,
2252                                                            reason_to_stop ? reason_to_stop : &dummy_reason_to_stop,
2253                                                            final_value_type ? final_value_type : &dummy_final_value_type,
2254                                                            options,
2255                                                            final_task_on_target ? final_task_on_target : &dummy_final_task_on_target);
2256 
2257     if (!final_task_on_target || *final_task_on_target == ValueObject::eExpressionPathAftermathNothing)
2258         return ret_val;
2259 
2260     if (ret_val.get() && ((final_value_type ? *final_value_type : dummy_final_value_type) == eExpressionPathEndResultTypePlain)) // I can only deref and takeaddress of plain objects
2261     {
2262         if ( (final_task_on_target ? *final_task_on_target : dummy_final_task_on_target) == ValueObject::eExpressionPathAftermathDereference)
2263         {
2264             Error error;
2265             ValueObjectSP final_value = ret_val->Dereference(error);
2266             if (error.Fail() || !final_value.get())
2267             {
2268                 if (reason_to_stop)
2269                     *reason_to_stop = ValueObject::eExpressionPathScanEndReasonDereferencingFailed;
2270                 if (final_value_type)
2271                     *final_value_type = ValueObject::eExpressionPathEndResultTypeInvalid;
2272                 return ValueObjectSP();
2273             }
2274             else
2275             {
2276                 if (final_task_on_target)
2277                     *final_task_on_target = ValueObject::eExpressionPathAftermathNothing;
2278                 return final_value;
2279             }
2280         }
2281         if (*final_task_on_target == ValueObject::eExpressionPathAftermathTakeAddress)
2282         {
2283             Error error;
2284             ValueObjectSP final_value = ret_val->AddressOf(error);
2285             if (error.Fail() || !final_value.get())
2286             {
2287                 if (reason_to_stop)
2288                     *reason_to_stop = ValueObject::eExpressionPathScanEndReasonTakingAddressFailed;
2289                 if (final_value_type)
2290                     *final_value_type = ValueObject::eExpressionPathEndResultTypeInvalid;
2291                 return ValueObjectSP();
2292             }
2293             else
2294             {
2295                 if (final_task_on_target)
2296                     *final_task_on_target = ValueObject::eExpressionPathAftermathNothing;
2297                 return final_value;
2298             }
2299         }
2300     }
2301     return ret_val; // final_task_on_target will still have its original value, so you know I did not do it
2302 }
2303 
2304 int
2305 ValueObject::GetValuesForExpressionPath(const char* expression,
2306                                         ValueObjectListSP& list,
2307                                         const char** first_unparsed,
2308                                         ExpressionPathScanEndReason* reason_to_stop,
2309                                         ExpressionPathEndResultType* final_value_type,
2310                                         const GetValueForExpressionPathOptions& options,
2311                                         ExpressionPathAftermath* final_task_on_target)
2312 {
2313     const char* dummy_first_unparsed;
2314     ExpressionPathScanEndReason dummy_reason_to_stop;
2315     ExpressionPathEndResultType dummy_final_value_type;
2316     ExpressionPathAftermath dummy_final_task_on_target = ValueObject::eExpressionPathAftermathNothing;
2317 
2318     ValueObjectSP ret_val = GetValueForExpressionPath_Impl(expression,
2319                                                            first_unparsed ? first_unparsed : &dummy_first_unparsed,
2320                                                            reason_to_stop ? reason_to_stop : &dummy_reason_to_stop,
2321                                                            final_value_type ? final_value_type : &dummy_final_value_type,
2322                                                            options,
2323                                                            final_task_on_target ? final_task_on_target : &dummy_final_task_on_target);
2324 
2325     if (!ret_val.get()) // if there are errors, I add nothing to the list
2326         return 0;
2327 
2328     if ( (reason_to_stop ? *reason_to_stop : dummy_reason_to_stop) != eExpressionPathScanEndReasonArrayRangeOperatorMet)
2329     {
2330         // I need not expand a range, just post-process the final value and return
2331         if (!final_task_on_target || *final_task_on_target == ValueObject::eExpressionPathAftermathNothing)
2332         {
2333             list->Append(ret_val);
2334             return 1;
2335         }
2336         if (ret_val.get() && (final_value_type ? *final_value_type : dummy_final_value_type) == eExpressionPathEndResultTypePlain) // I can only deref and takeaddress of plain objects
2337         {
2338             if (*final_task_on_target == ValueObject::eExpressionPathAftermathDereference)
2339             {
2340                 Error error;
2341                 ValueObjectSP final_value = ret_val->Dereference(error);
2342                 if (error.Fail() || !final_value.get())
2343                 {
2344                     *reason_to_stop = ValueObject::eExpressionPathScanEndReasonDereferencingFailed;
2345                     *final_value_type = ValueObject::eExpressionPathEndResultTypeInvalid;
2346                     return 0;
2347                 }
2348                 else
2349                 {
2350                     *final_task_on_target = ValueObject::eExpressionPathAftermathNothing;
2351                     list->Append(final_value);
2352                     return 1;
2353                 }
2354             }
2355             if (*final_task_on_target == ValueObject::eExpressionPathAftermathTakeAddress)
2356             {
2357                 Error error;
2358                 ValueObjectSP final_value = ret_val->AddressOf(error);
2359                 if (error.Fail() || !final_value.get())
2360                 {
2361                     *reason_to_stop = ValueObject::eExpressionPathScanEndReasonTakingAddressFailed;
2362                     *final_value_type = ValueObject::eExpressionPathEndResultTypeInvalid;
2363                     return 0;
2364                 }
2365                 else
2366                 {
2367                     *final_task_on_target = ValueObject::eExpressionPathAftermathNothing;
2368                     list->Append(final_value);
2369                     return 1;
2370                 }
2371             }
2372         }
2373     }
2374     else
2375     {
2376         return ExpandArraySliceExpression(first_unparsed ? *first_unparsed : dummy_first_unparsed,
2377                                           first_unparsed ? first_unparsed : &dummy_first_unparsed,
2378                                           ret_val,
2379                                           list,
2380                                           reason_to_stop ? reason_to_stop : &dummy_reason_to_stop,
2381                                           final_value_type ? final_value_type : &dummy_final_value_type,
2382                                           options,
2383                                           final_task_on_target ? final_task_on_target : &dummy_final_task_on_target);
2384     }
2385     // in any non-covered case, just do the obviously right thing
2386     list->Append(ret_val);
2387     return 1;
2388 }
2389 
2390 ValueObjectSP
2391 ValueObject::GetValueForExpressionPath_Impl(const char* expression_cstr,
2392                                             const char** first_unparsed,
2393                                             ExpressionPathScanEndReason* reason_to_stop,
2394                                             ExpressionPathEndResultType* final_result,
2395                                             const GetValueForExpressionPathOptions& options,
2396                                             ExpressionPathAftermath* what_next)
2397 {
2398     ValueObjectSP root = GetSP();
2399 
2400     if (!root.get())
2401         return ValueObjectSP();
2402 
2403     *first_unparsed = expression_cstr;
2404 
2405     while (true)
2406     {
2407 
2408         const char* expression_cstr = *first_unparsed; // hide the top level expression_cstr
2409 
2410         clang_type_t root_clang_type = root->GetClangType();
2411         clang_type_t pointee_clang_type;
2412         Flags root_clang_type_info,pointee_clang_type_info;
2413 
2414         root_clang_type_info = Flags(ClangASTContext::GetTypeInfo(root_clang_type, GetClangAST(), &pointee_clang_type));
2415         if (pointee_clang_type)
2416             pointee_clang_type_info = Flags(ClangASTContext::GetTypeInfo(pointee_clang_type, GetClangAST(), NULL));
2417 
2418         if (!expression_cstr || *expression_cstr == '\0')
2419         {
2420             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonEndOfString;
2421             return root;
2422         }
2423 
2424         switch (*expression_cstr)
2425         {
2426             case '-':
2427             {
2428                 if (options.m_check_dot_vs_arrow_syntax &&
2429                     root_clang_type_info.Test(ClangASTContext::eTypeIsPointer) ) // if you are trying to use -> on a non-pointer and I must catch the error
2430                 {
2431                     *first_unparsed = expression_cstr;
2432                     *reason_to_stop = ValueObject::eExpressionPathScanEndReasonArrowInsteadOfDot;
2433                     *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2434                     return ValueObjectSP();
2435                 }
2436                 if (root_clang_type_info.Test(ClangASTContext::eTypeIsObjC) &&  // if yo are trying to extract an ObjC IVar when this is forbidden
2437                     root_clang_type_info.Test(ClangASTContext::eTypeIsPointer) &&
2438                     options.m_no_fragile_ivar)
2439                 {
2440                     *first_unparsed = expression_cstr;
2441                     *reason_to_stop = ValueObject::eExpressionPathScanEndReasonFragileIVarNotAllowed;
2442                     *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2443                     return ValueObjectSP();
2444                 }
2445                 if (expression_cstr[1] != '>')
2446                 {
2447                     *first_unparsed = expression_cstr;
2448                     *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
2449                     *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2450                     return ValueObjectSP();
2451                 }
2452                 expression_cstr++; // skip the -
2453             }
2454             case '.': // or fallthrough from ->
2455             {
2456                 if (options.m_check_dot_vs_arrow_syntax && *expression_cstr == '.' &&
2457                     root_clang_type_info.Test(ClangASTContext::eTypeIsPointer)) // if you are trying to use . on a pointer and I must catch the error
2458                 {
2459                     *first_unparsed = expression_cstr;
2460                     *reason_to_stop = ValueObject::eExpressionPathScanEndReasonDotInsteadOfArrow;
2461                     *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2462                     return ValueObjectSP();
2463                 }
2464                 expression_cstr++; // skip .
2465                 const char *next_separator = strpbrk(expression_cstr+1,"-.[");
2466                 ConstString child_name;
2467                 if (!next_separator) // if no other separator just expand this last layer
2468                 {
2469                     child_name.SetCString (expression_cstr);
2470                     ValueObjectSP child_valobj_sp = root->GetChildMemberWithName(child_name, true);
2471 
2472                     if (child_valobj_sp.get()) // we know we are done, so just return
2473                     {
2474                         *first_unparsed = '\0';
2475                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonEndOfString;
2476                         *final_result = ValueObject::eExpressionPathEndResultTypePlain;
2477                         return child_valobj_sp;
2478                     }
2479                     else if (options.m_no_synthetic_children == false) // let's try with synthetic children
2480                     {
2481                         if (root->IsSynthetic())
2482                             child_valobj_sp = root;
2483                         else
2484                             child_valobj_sp = root->GetSyntheticValue();
2485 
2486                         if (child_valobj_sp.get())
2487                             child_valobj_sp = child_valobj_sp->GetChildMemberWithName(child_name, true);
2488                     }
2489 
2490                     // if we are here and options.m_no_synthetic_children is true, child_valobj_sp is going to be a NULL SP,
2491                     // so we hit the "else" branch, and return an error
2492                     if(child_valobj_sp.get()) // if it worked, just return
2493                     {
2494                         *first_unparsed = '\0';
2495                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonEndOfString;
2496                         *final_result = ValueObject::eExpressionPathEndResultTypePlain;
2497                         return child_valobj_sp;
2498                     }
2499                     else
2500                     {
2501                         *first_unparsed = expression_cstr;
2502                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
2503                         *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2504                         return ValueObjectSP();
2505                     }
2506                 }
2507                 else // other layers do expand
2508                 {
2509                     child_name.SetCStringWithLength(expression_cstr, next_separator - expression_cstr);
2510                     ValueObjectSP child_valobj_sp = root->GetChildMemberWithName(child_name, true);
2511                     if (child_valobj_sp.get()) // store the new root and move on
2512                     {
2513                         root = child_valobj_sp;
2514                         *first_unparsed = next_separator;
2515                         *final_result = ValueObject::eExpressionPathEndResultTypePlain;
2516                         continue;
2517                     }
2518                     else if (options.m_no_synthetic_children == false) // let's try with synthetic children
2519                     {
2520                         child_valobj_sp = root->GetSyntheticValue(true);
2521                         if (child_valobj_sp)
2522                             child_valobj_sp = child_valobj_sp->GetChildMemberWithName(child_name, true);
2523                     }
2524 
2525                     // if we are here and options.m_no_synthetic_children is true, child_valobj_sp is going to be a NULL SP,
2526                     // so we hit the "else" branch, and return an error
2527                     if(child_valobj_sp.get()) // if it worked, move on
2528                     {
2529                         root = child_valobj_sp;
2530                         *first_unparsed = next_separator;
2531                         *final_result = ValueObject::eExpressionPathEndResultTypePlain;
2532                         continue;
2533                     }
2534                     else
2535                     {
2536                         *first_unparsed = expression_cstr;
2537                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
2538                         *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2539                         return ValueObjectSP();
2540                     }
2541                 }
2542                 break;
2543             }
2544             case '[':
2545             {
2546                 if (!root_clang_type_info.Test(ClangASTContext::eTypeIsArray) && !root_clang_type_info.Test(ClangASTContext::eTypeIsPointer)) // if this is not a T[] nor a T*
2547                 {
2548                     if (!root_clang_type_info.Test(ClangASTContext::eTypeIsScalar)) // if this is not even a scalar...
2549                     {
2550                         if (options.m_no_synthetic_children) // ...only chance left is synthetic
2551                         {
2552                             *first_unparsed = expression_cstr;
2553                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorInvalid;
2554                             *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2555                             return ValueObjectSP();
2556                         }
2557                     }
2558                     else if (!options.m_allow_bitfields_syntax) // if this is a scalar, check that we can expand bitfields
2559                     {
2560                         *first_unparsed = expression_cstr;
2561                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorNotAllowed;
2562                         *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2563                         return ValueObjectSP();
2564                     }
2565                 }
2566                 if (*(expression_cstr+1) == ']') // if this is an unbounded range it only works for arrays
2567                 {
2568                     if (!root_clang_type_info.Test(ClangASTContext::eTypeIsArray))
2569                     {
2570                         *first_unparsed = expression_cstr;
2571                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonEmptyRangeNotAllowed;
2572                         *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2573                         return ValueObjectSP();
2574                     }
2575                     else // even if something follows, we cannot expand unbounded ranges, just let the caller do it
2576                     {
2577                         *first_unparsed = expression_cstr+2;
2578                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonArrayRangeOperatorMet;
2579                         *final_result = ValueObject::eExpressionPathEndResultTypeUnboundedRange;
2580                         return root;
2581                     }
2582                 }
2583                 const char *separator_position = ::strchr(expression_cstr+1,'-');
2584                 const char *close_bracket_position = ::strchr(expression_cstr+1,']');
2585                 if (!close_bracket_position) // if there is no ], this is a syntax error
2586                 {
2587                     *first_unparsed = expression_cstr;
2588                     *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
2589                     *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2590                     return ValueObjectSP();
2591                 }
2592                 if (!separator_position || separator_position > close_bracket_position) // if no separator, this is either [] or [N]
2593                 {
2594                     char *end = NULL;
2595                     unsigned long index = ::strtoul (expression_cstr+1, &end, 0);
2596                     if (!end || end != close_bracket_position) // if something weird is in our way return an error
2597                     {
2598                         *first_unparsed = expression_cstr;
2599                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
2600                         *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2601                         return ValueObjectSP();
2602                     }
2603                     if (end - expression_cstr == 1) // if this is [], only return a valid value for arrays
2604                     {
2605                         if (root_clang_type_info.Test(ClangASTContext::eTypeIsArray))
2606                         {
2607                             *first_unparsed = expression_cstr+2;
2608                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonArrayRangeOperatorMet;
2609                             *final_result = ValueObject::eExpressionPathEndResultTypeUnboundedRange;
2610                             return root;
2611                         }
2612                         else
2613                         {
2614                             *first_unparsed = expression_cstr;
2615                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonEmptyRangeNotAllowed;
2616                             *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2617                             return ValueObjectSP();
2618                         }
2619                     }
2620                     // from here on we do have a valid index
2621                     if (root_clang_type_info.Test(ClangASTContext::eTypeIsArray))
2622                     {
2623                         ValueObjectSP child_valobj_sp = root->GetChildAtIndex(index, true);
2624                         if (!child_valobj_sp)
2625                             child_valobj_sp = root->GetSyntheticArrayMemberFromArray(index, true);
2626                         if (!child_valobj_sp)
2627                             if (root->HasSyntheticValue() && root->GetSyntheticValue()->GetNumChildren() > index)
2628                                 child_valobj_sp = root->GetSyntheticValue()->GetChildAtIndex(index, true);
2629                         if (child_valobj_sp)
2630                         {
2631                             root = child_valobj_sp;
2632                             *first_unparsed = end+1; // skip ]
2633                             *final_result = ValueObject::eExpressionPathEndResultTypePlain;
2634                             continue;
2635                         }
2636                         else
2637                         {
2638                             *first_unparsed = expression_cstr;
2639                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
2640                             *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2641                             return ValueObjectSP();
2642                         }
2643                     }
2644                     else if (root_clang_type_info.Test(ClangASTContext::eTypeIsPointer))
2645                     {
2646                         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
2647                             pointee_clang_type_info.Test(ClangASTContext::eTypeIsScalar))
2648                         {
2649                             Error error;
2650                             root = root->Dereference(error);
2651                             if (error.Fail() || !root.get())
2652                             {
2653                                 *first_unparsed = expression_cstr;
2654                                 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonDereferencingFailed;
2655                                 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2656                                 return ValueObjectSP();
2657                             }
2658                             else
2659                             {
2660                                 *what_next = eExpressionPathAftermathNothing;
2661                                 continue;
2662                             }
2663                         }
2664                         else
2665                         {
2666                             if (ClangASTType::GetMinimumLanguage(root->GetClangAST(),
2667                                                                  root->GetClangType()) == eLanguageTypeObjC
2668                                 && ClangASTContext::IsPointerType(ClangASTType::GetPointeeType(root->GetClangType())) == false
2669                                 && root->HasSyntheticValue()
2670                                 && options.m_no_synthetic_children == false)
2671                             {
2672                                 root = root->GetSyntheticValue()->GetChildAtIndex(index, true);
2673                             }
2674                             else
2675                                 root = root->GetSyntheticArrayMemberFromPointer(index, true);
2676                             if (!root.get())
2677                             {
2678                                 *first_unparsed = expression_cstr;
2679                                 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
2680                                 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2681                                 return ValueObjectSP();
2682                             }
2683                             else
2684                             {
2685                                 *first_unparsed = end+1; // skip ]
2686                                 *final_result = ValueObject::eExpressionPathEndResultTypePlain;
2687                                 continue;
2688                             }
2689                         }
2690                     }
2691                     else if (ClangASTContext::IsScalarType(root_clang_type))
2692                     {
2693                         root = root->GetSyntheticBitFieldChild(index, index, true);
2694                         if (!root.get())
2695                         {
2696                             *first_unparsed = expression_cstr;
2697                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
2698                             *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2699                             return ValueObjectSP();
2700                         }
2701                         else // we do not know how to expand members of bitfields, so we just return and let the caller do any further processing
2702                         {
2703                             *first_unparsed = end+1; // skip ]
2704                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonBitfieldRangeOperatorMet;
2705                             *final_result = ValueObject::eExpressionPathEndResultTypeBitfield;
2706                             return root;
2707                         }
2708                     }
2709                     else if (options.m_no_synthetic_children == false)
2710                     {
2711                         if (root->HasSyntheticValue())
2712                             root = root->GetSyntheticValue();
2713                         else if (!root->IsSynthetic())
2714                         {
2715                             *first_unparsed = expression_cstr;
2716                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonSyntheticValueMissing;
2717                             *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2718                             return ValueObjectSP();
2719                         }
2720                         // if we are here, then root itself is a synthetic VO.. should be good to go
2721 
2722                         if (!root.get())
2723                         {
2724                             *first_unparsed = expression_cstr;
2725                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonSyntheticValueMissing;
2726                             *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2727                             return ValueObjectSP();
2728                         }
2729                         root = root->GetChildAtIndex(index, true);
2730                         if (!root.get())
2731                         {
2732                             *first_unparsed = expression_cstr;
2733                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
2734                             *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2735                             return ValueObjectSP();
2736                         }
2737                         else
2738                         {
2739                             *first_unparsed = end+1; // skip ]
2740                             *final_result = ValueObject::eExpressionPathEndResultTypePlain;
2741                             continue;
2742                         }
2743                     }
2744                     else
2745                     {
2746                         *first_unparsed = expression_cstr;
2747                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
2748                         *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2749                         return ValueObjectSP();
2750                     }
2751                 }
2752                 else // we have a low and a high index
2753                 {
2754                     char *end = NULL;
2755                     unsigned long index_lower = ::strtoul (expression_cstr+1, &end, 0);
2756                     if (!end || end != separator_position) // if something weird is in our way return an error
2757                     {
2758                         *first_unparsed = expression_cstr;
2759                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
2760                         *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2761                         return ValueObjectSP();
2762                     }
2763                     unsigned long index_higher = ::strtoul (separator_position+1, &end, 0);
2764                     if (!end || end != close_bracket_position) // if something weird is in our way return an error
2765                     {
2766                         *first_unparsed = expression_cstr;
2767                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
2768                         *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2769                         return ValueObjectSP();
2770                     }
2771                     if (index_lower > index_higher) // swap indices if required
2772                     {
2773                         unsigned long temp = index_lower;
2774                         index_lower = index_higher;
2775                         index_higher = temp;
2776                     }
2777                     if (root_clang_type_info.Test(ClangASTContext::eTypeIsScalar)) // expansion only works for scalars
2778                     {
2779                         root = root->GetSyntheticBitFieldChild(index_lower, index_higher, true);
2780                         if (!root.get())
2781                         {
2782                             *first_unparsed = expression_cstr;
2783                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
2784                             *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2785                             return ValueObjectSP();
2786                         }
2787                         else
2788                         {
2789                             *first_unparsed = end+1; // skip ]
2790                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonBitfieldRangeOperatorMet;
2791                             *final_result = ValueObject::eExpressionPathEndResultTypeBitfield;
2792                             return root;
2793                         }
2794                     }
2795                     else if (root_clang_type_info.Test(ClangASTContext::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
2796                              *what_next == ValueObject::eExpressionPathAftermathDereference &&
2797                              pointee_clang_type_info.Test(ClangASTContext::eTypeIsScalar))
2798                     {
2799                         Error error;
2800                         root = root->Dereference(error);
2801                         if (error.Fail() || !root.get())
2802                         {
2803                             *first_unparsed = expression_cstr;
2804                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonDereferencingFailed;
2805                             *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2806                             return ValueObjectSP();
2807                         }
2808                         else
2809                         {
2810                             *what_next = ValueObject::eExpressionPathAftermathNothing;
2811                             continue;
2812                         }
2813                     }
2814                     else
2815                     {
2816                         *first_unparsed = expression_cstr;
2817                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonArrayRangeOperatorMet;
2818                         *final_result = ValueObject::eExpressionPathEndResultTypeBoundedRange;
2819                         return root;
2820                     }
2821                 }
2822                 break;
2823             }
2824             default: // some non-separator is in the way
2825             {
2826                 *first_unparsed = expression_cstr;
2827                 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
2828                 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2829                 return ValueObjectSP();
2830                 break;
2831             }
2832         }
2833     }
2834 }
2835 
2836 int
2837 ValueObject::ExpandArraySliceExpression(const char* expression_cstr,
2838                                         const char** first_unparsed,
2839                                         ValueObjectSP root,
2840                                         ValueObjectListSP& list,
2841                                         ExpressionPathScanEndReason* reason_to_stop,
2842                                         ExpressionPathEndResultType* final_result,
2843                                         const GetValueForExpressionPathOptions& options,
2844                                         ExpressionPathAftermath* what_next)
2845 {
2846     if (!root.get())
2847         return 0;
2848 
2849     *first_unparsed = expression_cstr;
2850 
2851     while (true)
2852     {
2853 
2854         const char* expression_cstr = *first_unparsed; // hide the top level expression_cstr
2855 
2856         clang_type_t root_clang_type = root->GetClangType();
2857         clang_type_t pointee_clang_type;
2858         Flags root_clang_type_info,pointee_clang_type_info;
2859 
2860         root_clang_type_info = Flags(ClangASTContext::GetTypeInfo(root_clang_type, GetClangAST(), &pointee_clang_type));
2861         if (pointee_clang_type)
2862             pointee_clang_type_info = Flags(ClangASTContext::GetTypeInfo(pointee_clang_type, GetClangAST(), NULL));
2863 
2864         if (!expression_cstr || *expression_cstr == '\0')
2865         {
2866             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonEndOfString;
2867             list->Append(root);
2868             return 1;
2869         }
2870 
2871         switch (*expression_cstr)
2872         {
2873             case '[':
2874             {
2875                 if (!root_clang_type_info.Test(ClangASTContext::eTypeIsArray) && !root_clang_type_info.Test(ClangASTContext::eTypeIsPointer)) // if this is not a T[] nor a T*
2876                 {
2877                     if (!root_clang_type_info.Test(ClangASTContext::eTypeIsScalar)) // if this is not even a scalar, this syntax is just plain wrong!
2878                     {
2879                         *first_unparsed = expression_cstr;
2880                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorInvalid;
2881                         *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2882                         return 0;
2883                     }
2884                     else if (!options.m_allow_bitfields_syntax) // if this is a scalar, check that we can expand bitfields
2885                     {
2886                         *first_unparsed = expression_cstr;
2887                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorNotAllowed;
2888                         *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2889                         return 0;
2890                     }
2891                 }
2892                 if (*(expression_cstr+1) == ']') // if this is an unbounded range it only works for arrays
2893                 {
2894                     if (!root_clang_type_info.Test(ClangASTContext::eTypeIsArray))
2895                     {
2896                         *first_unparsed = expression_cstr;
2897                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonEmptyRangeNotAllowed;
2898                         *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2899                         return 0;
2900                     }
2901                     else // expand this into list
2902                     {
2903                         int max_index = root->GetNumChildren() - 1;
2904                         for (int index = 0; index < max_index; index++)
2905                         {
2906                             ValueObjectSP child =
2907                                 root->GetChildAtIndex(index, true);
2908                             list->Append(child);
2909                         }
2910                         *first_unparsed = expression_cstr+2;
2911                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorExpanded;
2912                         *final_result = ValueObject::eExpressionPathEndResultTypeValueObjectList;
2913                         return max_index; // tell me number of items I added to the VOList
2914                     }
2915                 }
2916                 const char *separator_position = ::strchr(expression_cstr+1,'-');
2917                 const char *close_bracket_position = ::strchr(expression_cstr+1,']');
2918                 if (!close_bracket_position) // if there is no ], this is a syntax error
2919                 {
2920                     *first_unparsed = expression_cstr;
2921                     *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
2922                     *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2923                     return 0;
2924                 }
2925                 if (!separator_position || separator_position > close_bracket_position) // if no separator, this is either [] or [N]
2926                 {
2927                     char *end = NULL;
2928                     unsigned long index = ::strtoul (expression_cstr+1, &end, 0);
2929                     if (!end || end != close_bracket_position) // if something weird is in our way return an error
2930                     {
2931                         *first_unparsed = expression_cstr;
2932                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
2933                         *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2934                         return 0;
2935                     }
2936                     if (end - expression_cstr == 1) // if this is [], only return a valid value for arrays
2937                     {
2938                         if (root_clang_type_info.Test(ClangASTContext::eTypeIsArray))
2939                         {
2940                             int max_index = root->GetNumChildren() - 1;
2941                             for (int index = 0; index < max_index; index++)
2942                             {
2943                                 ValueObjectSP child =
2944                                 root->GetChildAtIndex(index, true);
2945                                 list->Append(child);
2946                             }
2947                             *first_unparsed = expression_cstr+2;
2948                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorExpanded;
2949                             *final_result = ValueObject::eExpressionPathEndResultTypeValueObjectList;
2950                             return max_index; // tell me number of items I added to the VOList
2951                         }
2952                         else
2953                         {
2954                             *first_unparsed = expression_cstr;
2955                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonEmptyRangeNotAllowed;
2956                             *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2957                             return 0;
2958                         }
2959                     }
2960                     // from here on we do have a valid index
2961                     if (root_clang_type_info.Test(ClangASTContext::eTypeIsArray))
2962                     {
2963                         root = root->GetChildAtIndex(index, true);
2964                         if (!root.get())
2965                         {
2966                             *first_unparsed = expression_cstr;
2967                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
2968                             *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2969                             return 0;
2970                         }
2971                         else
2972                         {
2973                             list->Append(root);
2974                             *first_unparsed = end+1; // skip ]
2975                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorExpanded;
2976                             *final_result = ValueObject::eExpressionPathEndResultTypeValueObjectList;
2977                             return 1;
2978                         }
2979                     }
2980                     else if (root_clang_type_info.Test(ClangASTContext::eTypeIsPointer))
2981                     {
2982                         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
2983                             pointee_clang_type_info.Test(ClangASTContext::eTypeIsScalar))
2984                         {
2985                             Error error;
2986                             root = root->Dereference(error);
2987                             if (error.Fail() || !root.get())
2988                             {
2989                                 *first_unparsed = expression_cstr;
2990                                 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonDereferencingFailed;
2991                                 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
2992                                 return 0;
2993                             }
2994                             else
2995                             {
2996                                 *what_next = eExpressionPathAftermathNothing;
2997                                 continue;
2998                             }
2999                         }
3000                         else
3001                         {
3002                             root = root->GetSyntheticArrayMemberFromPointer(index, true);
3003                             if (!root.get())
3004                             {
3005                                 *first_unparsed = expression_cstr;
3006                                 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
3007                                 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
3008                                 return 0;
3009                             }
3010                             else
3011                             {
3012                                 list->Append(root);
3013                                 *first_unparsed = end+1; // skip ]
3014                                 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorExpanded;
3015                                 *final_result = ValueObject::eExpressionPathEndResultTypeValueObjectList;
3016                                 return 1;
3017                             }
3018                         }
3019                     }
3020                     else /*if (ClangASTContext::IsScalarType(root_clang_type))*/
3021                     {
3022                         root = root->GetSyntheticBitFieldChild(index, index, true);
3023                         if (!root.get())
3024                         {
3025                             *first_unparsed = expression_cstr;
3026                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
3027                             *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
3028                             return 0;
3029                         }
3030                         else // we do not know how to expand members of bitfields, so we just return and let the caller do any further processing
3031                         {
3032                             list->Append(root);
3033                             *first_unparsed = end+1; // skip ]
3034                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorExpanded;
3035                             *final_result = ValueObject::eExpressionPathEndResultTypeValueObjectList;
3036                             return 1;
3037                         }
3038                     }
3039                 }
3040                 else // we have a low and a high index
3041                 {
3042                     char *end = NULL;
3043                     unsigned long index_lower = ::strtoul (expression_cstr+1, &end, 0);
3044                     if (!end || end != separator_position) // if something weird is in our way return an error
3045                     {
3046                         *first_unparsed = expression_cstr;
3047                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
3048                         *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
3049                         return 0;
3050                     }
3051                     unsigned long index_higher = ::strtoul (separator_position+1, &end, 0);
3052                     if (!end || end != close_bracket_position) // if something weird is in our way return an error
3053                     {
3054                         *first_unparsed = expression_cstr;
3055                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
3056                         *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
3057                         return 0;
3058                     }
3059                     if (index_lower > index_higher) // swap indices if required
3060                     {
3061                         unsigned long temp = index_lower;
3062                         index_lower = index_higher;
3063                         index_higher = temp;
3064                     }
3065                     if (root_clang_type_info.Test(ClangASTContext::eTypeIsScalar)) // expansion only works for scalars
3066                     {
3067                         root = root->GetSyntheticBitFieldChild(index_lower, index_higher, true);
3068                         if (!root.get())
3069                         {
3070                             *first_unparsed = expression_cstr;
3071                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonNoSuchChild;
3072                             *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
3073                             return 0;
3074                         }
3075                         else
3076                         {
3077                             list->Append(root);
3078                             *first_unparsed = end+1; // skip ]
3079                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorExpanded;
3080                             *final_result = ValueObject::eExpressionPathEndResultTypeValueObjectList;
3081                             return 1;
3082                         }
3083                     }
3084                     else if (root_clang_type_info.Test(ClangASTContext::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
3085                              *what_next == ValueObject::eExpressionPathAftermathDereference &&
3086                              pointee_clang_type_info.Test(ClangASTContext::eTypeIsScalar))
3087                     {
3088                         Error error;
3089                         root = root->Dereference(error);
3090                         if (error.Fail() || !root.get())
3091                         {
3092                             *first_unparsed = expression_cstr;
3093                             *reason_to_stop = ValueObject::eExpressionPathScanEndReasonDereferencingFailed;
3094                             *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
3095                             return 0;
3096                         }
3097                         else
3098                         {
3099                             *what_next = ValueObject::eExpressionPathAftermathNothing;
3100                             continue;
3101                         }
3102                     }
3103                     else
3104                     {
3105                         for (unsigned long index = index_lower;
3106                              index <= index_higher; index++)
3107                         {
3108                             ValueObjectSP child =
3109                                 root->GetChildAtIndex(index, true);
3110                             list->Append(child);
3111                         }
3112                         *first_unparsed = end+1;
3113                         *reason_to_stop = ValueObject::eExpressionPathScanEndReasonRangeOperatorExpanded;
3114                         *final_result = ValueObject::eExpressionPathEndResultTypeValueObjectList;
3115                         return index_higher-index_lower+1; // tell me number of items I added to the VOList
3116                     }
3117                 }
3118                 break;
3119             }
3120             default: // some non-[ separator, or something entirely wrong, is in the way
3121             {
3122                 *first_unparsed = expression_cstr;
3123                 *reason_to_stop = ValueObject::eExpressionPathScanEndReasonUnexpectedSymbol;
3124                 *final_result = ValueObject::eExpressionPathEndResultTypeInvalid;
3125                 return 0;
3126                 break;
3127             }
3128         }
3129     }
3130 }
3131 
3132 static void
3133 DumpValueObject_Impl (Stream &s,
3134                       ValueObject *valobj,
3135                       const ValueObject::DumpValueObjectOptions& options,
3136                       uint32_t ptr_depth,
3137                       uint32_t curr_depth)
3138 {
3139     if (valobj)
3140     {
3141         bool update_success = valobj->UpdateValueIfNeeded (options.m_use_dynamic, true);
3142 
3143         const char *root_valobj_name =
3144             options.m_root_valobj_name.empty() ?
3145                 valobj->GetName().AsCString() :
3146                 options.m_root_valobj_name.c_str();
3147 
3148         if (update_success && options.m_use_dynamic != eNoDynamicValues)
3149         {
3150             ValueObject *dynamic_value = valobj->GetDynamicValue(options.m_use_dynamic).get();
3151             if (dynamic_value)
3152                 valobj = dynamic_value;
3153         }
3154 
3155         clang_type_t clang_type = valobj->GetClangType();
3156 
3157         const Flags type_flags (ClangASTContext::GetTypeInfo (clang_type, NULL, NULL));
3158         const char *err_cstr = NULL;
3159         const bool has_children = type_flags.Test (ClangASTContext::eTypeHasChildren);
3160         const bool has_value = type_flags.Test (ClangASTContext::eTypeHasValue);
3161 
3162         const bool print_valobj = options.m_flat_output == false || has_value;
3163 
3164         if (print_valobj)
3165         {
3166             if (options.m_show_location)
3167             {
3168                 s.Printf("%s: ", valobj->GetLocationAsCString());
3169             }
3170 
3171             s.Indent();
3172 
3173             // Always show the type for the top level items.
3174             if (options.m_show_types || (curr_depth == 0 && !options.m_flat_output))
3175             {
3176                 const char* typeName = valobj->GetQualifiedTypeName().AsCString("<invalid type>");
3177                 //const char* typeName = valobj->GetTypeName().AsCString("<invalid type>");
3178                 s.Printf("(%s", typeName);
3179                 // only show dynamic types if the user really wants to see types
3180                 if (options.m_show_types && options.m_use_dynamic != eNoDynamicValues &&
3181                     (/*strstr(typeName, "id") == typeName ||*/
3182                      ClangASTType::GetMinimumLanguage(valobj->GetClangAST(), valobj->GetClangType()) == eLanguageTypeObjC))
3183                 {
3184                     ExecutionContext exe_ctx (valobj->GetExecutionContextRef());
3185                     Process *process = exe_ctx.GetProcessPtr();
3186                     if (process == NULL)
3187                         s.Printf(", dynamic type: unknown) ");
3188                     else
3189                     {
3190                         ObjCLanguageRuntime *runtime = process->GetObjCLanguageRuntime();
3191                         if (runtime == NULL)
3192                             s.Printf(", dynamic type: unknown) ");
3193                         else
3194                         {
3195                             ObjCLanguageRuntime::ObjCISA isa = runtime->GetISA(*valobj);
3196                             if (!runtime->IsValidISA(isa))
3197                                 s.Printf(", dynamic type: unknown) ");
3198                             else
3199                                 s.Printf(", dynamic type: %s) ",
3200                                          runtime->GetActualTypeName(isa).GetCString());
3201                         }
3202                     }
3203                 }
3204                 else
3205                     s.Printf(") ");
3206             }
3207 
3208 
3209             if (options.m_flat_output)
3210             {
3211                 // If we are showing types, also qualify the C++ base classes
3212                 const bool qualify_cxx_base_classes = options.m_show_types;
3213                 valobj->GetExpressionPath(s, qualify_cxx_base_classes);
3214                 s.PutCString(" =");
3215             }
3216             else
3217             {
3218                 const char *name_cstr = root_valobj_name ? root_valobj_name : valobj->GetName().AsCString("");
3219                 s.Printf ("%s =", name_cstr);
3220             }
3221 
3222             if (!options.m_scope_already_checked && !valobj->IsInScope())
3223             {
3224                 err_cstr = "out of scope";
3225             }
3226         }
3227 
3228         std::string summary_str;
3229         std::string value_str;
3230         const char *val_cstr = NULL;
3231         const char *sum_cstr = NULL;
3232         TypeSummaryImpl* entry = options.m_summary_sp ? options.m_summary_sp.get() : valobj->GetSummaryFormat().get();
3233 
3234         if (options.m_omit_summary_depth > 0)
3235             entry = NULL;
3236 
3237         if (err_cstr == NULL)
3238         {
3239             if (options.m_format != eFormatDefault && options.m_format != valobj->GetFormat())
3240             {
3241                 valobj->GetValueAsCString(options.m_format,
3242                                           value_str);
3243             }
3244             else
3245             {
3246                 val_cstr = valobj->GetValueAsCString();
3247                 if (val_cstr)
3248                     value_str = val_cstr;
3249             }
3250             err_cstr = valobj->GetError().AsCString();
3251         }
3252 
3253         if (err_cstr)
3254         {
3255             s.Printf (" <%s>\n", err_cstr);
3256         }
3257         else
3258         {
3259             const bool is_ref = type_flags.Test (ClangASTContext::eTypeIsReference);
3260             if (print_valobj)
3261             {
3262                 if (options.m_omit_summary_depth == 0)
3263                 {
3264                     if (options.m_summary_sp)
3265                     {
3266                         valobj->GetSummaryAsCString(entry, summary_str);
3267                         sum_cstr = summary_str.c_str();
3268                     }
3269                     else
3270                         sum_cstr = valobj->GetSummaryAsCString();
3271                 }
3272 
3273                 // Make sure we have a value and make sure the summary didn't
3274                 // specify that the value should not be printed
3275                 if (!value_str.empty() && (entry == NULL || entry->DoesPrintValue() || sum_cstr == NULL))
3276                     s.Printf(" %s", value_str.c_str());
3277 
3278                 if (sum_cstr)
3279                     s.Printf(" %s", sum_cstr);
3280 
3281                 if (options.m_use_objc)
3282                 {
3283                     const char *object_desc = valobj->GetObjectDescription();
3284                     if (object_desc)
3285                         s.Printf(" %s\n", object_desc);
3286                     else
3287                         s.Printf (" [no Objective-C description available]\n");
3288                     return;
3289                 }
3290             }
3291 
3292             if (curr_depth < options.m_max_depth)
3293             {
3294                 // We will show children for all concrete types. We won't show
3295                 // pointer contents unless a pointer depth has been specified.
3296                 // We won't reference contents unless the reference is the
3297                 // root object (depth of zero).
3298                 bool print_children = true;
3299 
3300                 // Use a new temporary pointer depth in case we override the
3301                 // current pointer depth below...
3302                 uint32_t curr_ptr_depth = ptr_depth;
3303 
3304                 const bool is_ptr = type_flags.Test (ClangASTContext::eTypeIsPointer);
3305                 if (is_ptr || is_ref)
3306                 {
3307                     // We have a pointer or reference whose value is an address.
3308                     // Make sure that address is not NULL
3309                     AddressType ptr_address_type;
3310                     if (valobj->GetPointerValue (&ptr_address_type) == 0)
3311                         print_children = false;
3312 
3313                     else if (is_ref && curr_depth == 0)
3314                     {
3315                         // If this is the root object (depth is zero) that we are showing
3316                         // and it is a reference, and no pointer depth has been supplied
3317                         // print out what it references. Don't do this at deeper depths
3318                         // otherwise we can end up with infinite recursion...
3319                         curr_ptr_depth = 1;
3320                     }
3321 
3322                     if (curr_ptr_depth == 0)
3323                         print_children = false;
3324                 }
3325 
3326                 if (print_children && (!entry || entry->DoesPrintChildren() || !sum_cstr))
3327                 {
3328                     ValueObject* synth_valobj;
3329                     ValueObjectSP synth_valobj_sp = valobj->GetSyntheticValue (options.m_use_synthetic);
3330                     synth_valobj = (synth_valobj_sp ? synth_valobj_sp.get() : valobj);
3331 
3332                     uint32_t num_children = synth_valobj->GetNumChildren();
3333                     bool print_dotdotdot = false;
3334                     if (num_children)
3335                     {
3336                         if (options.m_flat_output)
3337                         {
3338                             if (print_valobj)
3339                                 s.EOL();
3340                         }
3341                         else
3342                         {
3343                             if (print_valobj)
3344                                 s.PutCString(is_ref ? ": {\n" : " {\n");
3345                             s.IndentMore();
3346                         }
3347 
3348                         uint32_t max_num_children = valobj->GetTargetSP()->GetMaximumNumberOfChildrenToDisplay();
3349 
3350                         if (num_children > max_num_children && !options.m_ignore_cap)
3351                         {
3352                             num_children = max_num_children;
3353                             print_dotdotdot = true;
3354                         }
3355 
3356                         ValueObject::DumpValueObjectOptions child_options(options);
3357                         child_options.SetFormat().SetSummary().SetRootValueObjectName();
3358                         child_options.SetScopeChecked(true)
3359                         .SetOmitSummaryDepth(child_options.m_omit_summary_depth > 1 ? child_options.m_omit_summary_depth - 1 : 0);
3360                         for (uint32_t idx=0; idx<num_children; ++idx)
3361                         {
3362                             ValueObjectSP child_sp(synth_valobj->GetChildAtIndex(idx, true));
3363                             if (child_sp.get())
3364                             {
3365                                 DumpValueObject_Impl (s,
3366                                                       child_sp.get(),
3367                                                       child_options,
3368                                                       (is_ptr || is_ref) ? curr_ptr_depth - 1 : curr_ptr_depth,
3369                                                       curr_depth + 1);
3370                             }
3371                         }
3372 
3373                         if (!options.m_flat_output)
3374                         {
3375                             if (print_dotdotdot)
3376                             {
3377                                 ExecutionContext exe_ctx (valobj->GetExecutionContextRef());
3378                                 Target *target = exe_ctx.GetTargetPtr();
3379                                 if (target)
3380                                     target->GetDebugger().GetCommandInterpreter().ChildrenTruncated();
3381                                 s.Indent("...\n");
3382                             }
3383                             s.IndentLess();
3384                             s.Indent("}\n");
3385                         }
3386                     }
3387                     else if (has_children)
3388                     {
3389                         // Aggregate, no children...
3390                         if (print_valobj)
3391                             s.PutCString(" {}\n");
3392                     }
3393                     else
3394                     {
3395                         if (print_valobj)
3396                             s.EOL();
3397                     }
3398 
3399                 }
3400                 else
3401                 {
3402                     s.EOL();
3403                 }
3404             }
3405             else
3406             {
3407                 if (has_children && print_valobj)
3408                 {
3409                     s.PutCString("{...}\n");
3410                 }
3411             }
3412         }
3413     }
3414 }
3415 
3416 void
3417 ValueObject::LogValueObject (Log *log,
3418                              ValueObject *valobj)
3419 {
3420     if (log && valobj)
3421         return LogValueObject (log, valobj, DumpValueObjectOptions::DefaultOptions());
3422 }
3423 
3424 void
3425 ValueObject::LogValueObject (Log *log,
3426                              ValueObject *valobj,
3427                              const DumpValueObjectOptions& options)
3428 {
3429     if (log && valobj)
3430     {
3431         StreamString s;
3432         ValueObject::DumpValueObject (s, valobj, options);
3433         if (s.GetSize())
3434             log->PutCString(s.GetData());
3435     }
3436 }
3437 
3438 void
3439 ValueObject::DumpValueObject (Stream &s,
3440                               ValueObject *valobj)
3441 {
3442 
3443     if (!valobj)
3444         return;
3445 
3446     DumpValueObject_Impl(s,
3447                          valobj,
3448                          DumpValueObjectOptions::DefaultOptions(),
3449                          0,
3450                          0);
3451 }
3452 
3453 void
3454 ValueObject::DumpValueObject (Stream &s,
3455                               ValueObject *valobj,
3456                               const DumpValueObjectOptions& options)
3457 {
3458     DumpValueObject_Impl(s,
3459                          valobj,
3460                          options,
3461                          options.m_max_ptr_depth, // max pointer depth allowed, we will go down from here
3462                          0 // current object depth is 0 since we are just starting
3463                          );
3464 }
3465 
3466 ValueObjectSP
3467 ValueObject::CreateConstantValue (const ConstString &name)
3468 {
3469     ValueObjectSP valobj_sp;
3470 
3471     if (UpdateValueIfNeeded(false) && m_error.Success())
3472     {
3473         ExecutionContext exe_ctx (GetExecutionContextRef());
3474         clang::ASTContext *ast = GetClangAST ();
3475 
3476         DataExtractor data;
3477         data.SetByteOrder (m_data.GetByteOrder());
3478         data.SetAddressByteSize(m_data.GetAddressByteSize());
3479 
3480         m_error = m_value.GetValueAsData (&exe_ctx, ast, data, 0, GetModule().get());
3481 
3482         valobj_sp = ValueObjectConstResult::Create (exe_ctx.GetBestExecutionContextScope(),
3483                                                     ast,
3484                                                     GetClangType(),
3485                                                     name,
3486                                                     data,
3487                                                     GetAddressOf());
3488     }
3489 
3490     if (!valobj_sp)
3491     {
3492         valobj_sp = ValueObjectConstResult::Create (NULL, m_error);
3493     }
3494     return valobj_sp;
3495 }
3496 
3497 ValueObjectSP
3498 ValueObject::Dereference (Error &error)
3499 {
3500     if (m_deref_valobj)
3501         return m_deref_valobj->GetSP();
3502 
3503     const bool is_pointer_type = IsPointerType();
3504     if (is_pointer_type)
3505     {
3506         bool omit_empty_base_classes = true;
3507         bool ignore_array_bounds = false;
3508 
3509         std::string child_name_str;
3510         uint32_t child_byte_size = 0;
3511         int32_t child_byte_offset = 0;
3512         uint32_t child_bitfield_bit_size = 0;
3513         uint32_t child_bitfield_bit_offset = 0;
3514         bool child_is_base_class = false;
3515         bool child_is_deref_of_parent = false;
3516         const bool transparent_pointers = false;
3517         clang::ASTContext *clang_ast = GetClangAST();
3518         clang_type_t clang_type = GetClangType();
3519         clang_type_t child_clang_type;
3520 
3521         ExecutionContext exe_ctx (GetExecutionContextRef());
3522 
3523         child_clang_type = ClangASTContext::GetChildClangTypeAtIndex (&exe_ctx,
3524                                                                       clang_ast,
3525                                                                       GetName().GetCString(),
3526                                                                       clang_type,
3527                                                                       0,
3528                                                                       transparent_pointers,
3529                                                                       omit_empty_base_classes,
3530                                                                       ignore_array_bounds,
3531                                                                       child_name_str,
3532                                                                       child_byte_size,
3533                                                                       child_byte_offset,
3534                                                                       child_bitfield_bit_size,
3535                                                                       child_bitfield_bit_offset,
3536                                                                       child_is_base_class,
3537                                                                       child_is_deref_of_parent);
3538         if (child_clang_type && child_byte_size)
3539         {
3540             ConstString child_name;
3541             if (!child_name_str.empty())
3542                 child_name.SetCString (child_name_str.c_str());
3543 
3544             m_deref_valobj = new ValueObjectChild (*this,
3545                                                    clang_ast,
3546                                                    child_clang_type,
3547                                                    child_name,
3548                                                    child_byte_size,
3549                                                    child_byte_offset,
3550                                                    child_bitfield_bit_size,
3551                                                    child_bitfield_bit_offset,
3552                                                    child_is_base_class,
3553                                                    child_is_deref_of_parent,
3554                                                    eAddressTypeInvalid);
3555         }
3556     }
3557 
3558     if (m_deref_valobj)
3559     {
3560         error.Clear();
3561         return m_deref_valobj->GetSP();
3562     }
3563     else
3564     {
3565         StreamString strm;
3566         GetExpressionPath(strm, true);
3567 
3568         if (is_pointer_type)
3569             error.SetErrorStringWithFormat("dereference failed: (%s) %s", GetTypeName().AsCString("<invalid type>"), strm.GetString().c_str());
3570         else
3571             error.SetErrorStringWithFormat("not a pointer type: (%s) %s", GetTypeName().AsCString("<invalid type>"), strm.GetString().c_str());
3572         return ValueObjectSP();
3573     }
3574 }
3575 
3576 ValueObjectSP
3577 ValueObject::AddressOf (Error &error)
3578 {
3579     if (m_addr_of_valobj_sp)
3580         return m_addr_of_valobj_sp;
3581 
3582     AddressType address_type = eAddressTypeInvalid;
3583     const bool scalar_is_load_address = false;
3584     addr_t addr = GetAddressOf (scalar_is_load_address, &address_type);
3585     error.Clear();
3586     if (addr != LLDB_INVALID_ADDRESS)
3587     {
3588         switch (address_type)
3589         {
3590         default:
3591         case eAddressTypeInvalid:
3592             {
3593                 StreamString expr_path_strm;
3594                 GetExpressionPath(expr_path_strm, true);
3595                 error.SetErrorStringWithFormat("'%s' is not in memory", expr_path_strm.GetString().c_str());
3596             }
3597             break;
3598 
3599         case eAddressTypeFile:
3600         case eAddressTypeLoad:
3601         case eAddressTypeHost:
3602             {
3603                 clang::ASTContext *ast = GetClangAST();
3604                 clang_type_t clang_type = GetClangType();
3605                 if (ast && clang_type)
3606                 {
3607                     std::string name (1, '&');
3608                     name.append (m_name.AsCString(""));
3609                     ExecutionContext exe_ctx (GetExecutionContextRef());
3610                     m_addr_of_valobj_sp = ValueObjectConstResult::Create (exe_ctx.GetBestExecutionContextScope(),
3611                                                                           ast,
3612                                                                           ClangASTContext::CreatePointerType (ast, clang_type),
3613                                                                           ConstString (name.c_str()),
3614                                                                           addr,
3615                                                                           eAddressTypeInvalid,
3616                                                                           m_data.GetAddressByteSize());
3617                 }
3618             }
3619             break;
3620         }
3621     }
3622     return m_addr_of_valobj_sp;
3623 }
3624 
3625 ValueObjectSP
3626 ValueObject::Cast (const ClangASTType &clang_ast_type)
3627 {
3628     return ValueObjectCast::Create (*this, GetName(), clang_ast_type);
3629 }
3630 
3631 ValueObjectSP
3632 ValueObject::CastPointerType (const char *name, ClangASTType &clang_ast_type)
3633 {
3634     ValueObjectSP valobj_sp;
3635     AddressType address_type;
3636     addr_t ptr_value = GetPointerValue (&address_type);
3637 
3638     if (ptr_value != LLDB_INVALID_ADDRESS)
3639     {
3640         Address ptr_addr (ptr_value);
3641         ExecutionContext exe_ctx (GetExecutionContextRef());
3642         valobj_sp = ValueObjectMemory::Create (exe_ctx.GetBestExecutionContextScope(),
3643                                                name,
3644                                                ptr_addr,
3645                                                clang_ast_type);
3646     }
3647     return valobj_sp;
3648 }
3649 
3650 ValueObjectSP
3651 ValueObject::CastPointerType (const char *name, TypeSP &type_sp)
3652 {
3653     ValueObjectSP valobj_sp;
3654     AddressType address_type;
3655     addr_t ptr_value = GetPointerValue (&address_type);
3656 
3657     if (ptr_value != LLDB_INVALID_ADDRESS)
3658     {
3659         Address ptr_addr (ptr_value);
3660         ExecutionContext exe_ctx (GetExecutionContextRef());
3661         valobj_sp = ValueObjectMemory::Create (exe_ctx.GetBestExecutionContextScope(),
3662                                                name,
3663                                                ptr_addr,
3664                                                type_sp);
3665     }
3666     return valobj_sp;
3667 }
3668 
3669 ValueObject::EvaluationPoint::EvaluationPoint () :
3670     m_mod_id(),
3671     m_exe_ctx_ref(),
3672     m_needs_update (true),
3673     m_first_update (true)
3674 {
3675 }
3676 
3677 ValueObject::EvaluationPoint::EvaluationPoint (ExecutionContextScope *exe_scope, bool use_selected):
3678     m_mod_id(),
3679     m_exe_ctx_ref(),
3680     m_needs_update (true),
3681     m_first_update (true)
3682 {
3683     ExecutionContext exe_ctx(exe_scope);
3684     TargetSP target_sp (exe_ctx.GetTargetSP());
3685     if (target_sp)
3686     {
3687         m_exe_ctx_ref.SetTargetSP (target_sp);
3688         ProcessSP process_sp (exe_ctx.GetProcessSP());
3689         if (!process_sp)
3690             process_sp = target_sp->GetProcessSP();
3691 
3692         if (process_sp)
3693         {
3694             m_mod_id = process_sp->GetModID();
3695             m_exe_ctx_ref.SetProcessSP (process_sp);
3696 
3697             ThreadSP thread_sp (exe_ctx.GetThreadSP());
3698 
3699             if (!thread_sp)
3700             {
3701                 if (use_selected)
3702                     thread_sp = process_sp->GetThreadList().GetSelectedThread();
3703             }
3704 
3705             if (thread_sp)
3706             {
3707                 m_exe_ctx_ref.SetThreadSP(thread_sp);
3708 
3709                 StackFrameSP frame_sp (exe_ctx.GetFrameSP());
3710                 if (!frame_sp)
3711                 {
3712                     if (use_selected)
3713                         frame_sp = thread_sp->GetSelectedFrame();
3714                 }
3715                 if (frame_sp)
3716                     m_exe_ctx_ref.SetFrameSP(frame_sp);
3717             }
3718         }
3719     }
3720 }
3721 
3722 ValueObject::EvaluationPoint::EvaluationPoint (const ValueObject::EvaluationPoint &rhs) :
3723     m_mod_id(),
3724     m_exe_ctx_ref(rhs.m_exe_ctx_ref),
3725     m_needs_update (true),
3726     m_first_update (true)
3727 {
3728 }
3729 
3730 ValueObject::EvaluationPoint::~EvaluationPoint ()
3731 {
3732 }
3733 
3734 // This function checks the EvaluationPoint against the current process state.  If the current
3735 // state matches the evaluation point, or the evaluation point is already invalid, then we return
3736 // false, meaning "no change".  If the current state is different, we update our state, and return
3737 // true meaning "yes, change".  If we did see a change, we also set m_needs_update to true, so
3738 // future calls to NeedsUpdate will return true.
3739 // exe_scope will be set to the current execution context scope.
3740 
3741 bool
3742 ValueObject::EvaluationPoint::SyncWithProcessState()
3743 {
3744 
3745     // Start with the target, if it is NULL, then we're obviously not going to get any further:
3746     ExecutionContext exe_ctx(m_exe_ctx_ref.Lock());
3747 
3748     if (exe_ctx.GetTargetPtr() == NULL)
3749         return false;
3750 
3751     // If we don't have a process nothing can change.
3752     Process *process = exe_ctx.GetProcessPtr();
3753     if (process == NULL)
3754         return false;
3755 
3756     // If our stop id is the current stop ID, nothing has changed:
3757     ProcessModID current_mod_id = process->GetModID();
3758 
3759     // If the current stop id is 0, either we haven't run yet, or the process state has been cleared.
3760     // In either case, we aren't going to be able to sync with the process state.
3761     if (current_mod_id.GetStopID() == 0)
3762         return false;
3763 
3764     bool changed;
3765 
3766     if (m_mod_id.IsValid())
3767     {
3768         if (m_mod_id == current_mod_id)
3769         {
3770             // Everything is already up to date in this object, no need to
3771             // update the execution context scope.
3772             changed = false;
3773         }
3774         else
3775         {
3776             m_mod_id = current_mod_id;
3777             m_needs_update = true;
3778             changed = true;
3779         }
3780     }
3781 
3782     // Now re-look up the thread and frame in case the underlying objects have gone away & been recreated.
3783     // That way we'll be sure to return a valid exe_scope.
3784     // If we used to have a thread or a frame but can't find it anymore, then mark ourselves as invalid.
3785 
3786     if (m_exe_ctx_ref.HasThreadRef())
3787     {
3788         ThreadSP thread_sp (m_exe_ctx_ref.GetThreadSP());
3789         if (thread_sp)
3790         {
3791             if (m_exe_ctx_ref.HasFrameRef())
3792             {
3793                 StackFrameSP frame_sp (m_exe_ctx_ref.GetFrameSP());
3794                 if (!frame_sp)
3795                 {
3796                     // We used to have a frame, but now it is gone
3797                     SetInvalid();
3798                 }
3799             }
3800         }
3801         else
3802         {
3803             // We used to have a thread, but now it is gone
3804             SetInvalid();
3805         }
3806 
3807     }
3808     return changed;
3809 }
3810 
3811 void
3812 ValueObject::EvaluationPoint::SetUpdated ()
3813 {
3814     ProcessSP process_sp(m_exe_ctx_ref.GetProcessSP());
3815     if (process_sp)
3816         m_mod_id = process_sp->GetModID();
3817     m_first_update = false;
3818     m_needs_update = false;
3819 }
3820 
3821 
3822 //bool
3823 //ValueObject::EvaluationPoint::SetContext (ExecutionContextScope *exe_scope)
3824 //{
3825 //    if (!IsValid())
3826 //        return false;
3827 //
3828 //    bool needs_update = false;
3829 //
3830 //    // The target has to be non-null, and the
3831 //    Target *target = exe_scope->CalculateTarget();
3832 //    if (target != NULL)
3833 //    {
3834 //        Target *old_target = m_target_sp.get();
3835 //        assert (target == old_target);
3836 //        Process *process = exe_scope->CalculateProcess();
3837 //        if (process != NULL)
3838 //        {
3839 //            // FOR NOW - assume you can't update variable objects across process boundaries.
3840 //            Process *old_process = m_process_sp.get();
3841 //            assert (process == old_process);
3842 //            ProcessModID current_mod_id = process->GetModID();
3843 //            if (m_mod_id != current_mod_id)
3844 //            {
3845 //                needs_update = true;
3846 //                m_mod_id = current_mod_id;
3847 //            }
3848 //            // See if we're switching the thread or stack context.  If no thread is given, this is
3849 //            // being evaluated in a global context.
3850 //            Thread *thread = exe_scope->CalculateThread();
3851 //            if (thread != NULL)
3852 //            {
3853 //                user_id_t new_thread_index = thread->GetIndexID();
3854 //                if (new_thread_index != m_thread_id)
3855 //                {
3856 //                    needs_update = true;
3857 //                    m_thread_id = new_thread_index;
3858 //                    m_stack_id.Clear();
3859 //                }
3860 //
3861 //                StackFrame *new_frame = exe_scope->CalculateStackFrame();
3862 //                if (new_frame != NULL)
3863 //                {
3864 //                    if (new_frame->GetStackID() != m_stack_id)
3865 //                    {
3866 //                        needs_update = true;
3867 //                        m_stack_id = new_frame->GetStackID();
3868 //                    }
3869 //                }
3870 //                else
3871 //                {
3872 //                    m_stack_id.Clear();
3873 //                    needs_update = true;
3874 //                }
3875 //            }
3876 //            else
3877 //            {
3878 //                // If this had been given a thread, and now there is none, we should update.
3879 //                // Otherwise we don't have to do anything.
3880 //                if (m_thread_id != LLDB_INVALID_UID)
3881 //                {
3882 //                    m_thread_id = LLDB_INVALID_UID;
3883 //                    m_stack_id.Clear();
3884 //                    needs_update = true;
3885 //                }
3886 //            }
3887 //        }
3888 //        else
3889 //        {
3890 //            // If there is no process, then we don't need to update anything.
3891 //            // But if we're switching from having a process to not, we should try to update.
3892 //            if (m_process_sp.get() != NULL)
3893 //            {
3894 //                needs_update = true;
3895 //                m_process_sp.reset();
3896 //                m_thread_id = LLDB_INVALID_UID;
3897 //                m_stack_id.Clear();
3898 //            }
3899 //        }
3900 //    }
3901 //    else
3902 //    {
3903 //        // If there's no target, nothing can change so we don't need to update anything.
3904 //        // But if we're switching from having a target to not, we should try to update.
3905 //        if (m_target_sp.get() != NULL)
3906 //        {
3907 //            needs_update = true;
3908 //            m_target_sp.reset();
3909 //            m_process_sp.reset();
3910 //            m_thread_id = LLDB_INVALID_UID;
3911 //            m_stack_id.Clear();
3912 //        }
3913 //    }
3914 //    if (!m_needs_update)
3915 //        m_needs_update = needs_update;
3916 //
3917 //    return needs_update;
3918 //}
3919 
3920 void
3921 ValueObject::ClearUserVisibleData(uint32_t clear_mask)
3922 {
3923     if ((clear_mask & eClearUserVisibleDataItemsValue) == eClearUserVisibleDataItemsValue)
3924         m_value_str.clear();
3925 
3926     if ((clear_mask & eClearUserVisibleDataItemsLocation) == eClearUserVisibleDataItemsLocation)
3927         m_location_str.clear();
3928 
3929     if ((clear_mask & eClearUserVisibleDataItemsSummary) == eClearUserVisibleDataItemsSummary)
3930     {
3931         m_is_getting_summary = false;
3932         m_summary_str.clear();
3933     }
3934 
3935     if ((clear_mask & eClearUserVisibleDataItemsDescription) == eClearUserVisibleDataItemsDescription)
3936         m_object_desc_str.clear();
3937 
3938     if ((clear_mask & eClearUserVisibleDataItemsSyntheticChildren) == eClearUserVisibleDataItemsSyntheticChildren)
3939     {
3940             if (m_synthetic_value)
3941                 m_synthetic_value = NULL;
3942     }
3943 }
3944 
3945 SymbolContextScope *
3946 ValueObject::GetSymbolContextScope()
3947 {
3948     if (m_parent)
3949     {
3950         if (!m_parent->IsPointerOrReferenceType())
3951             return m_parent->GetSymbolContextScope();
3952     }
3953     return NULL;
3954 }
3955