1 //===-- ValueObjectPrinter.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/DataFormatters/ValueObjectPrinter.h"
11 
12 // C Includes
13 // C++ Includes
14 // Other libraries and framework includes
15 // Project includes
16 #include "lldb/Core/Debugger.h"
17 #include "lldb/DataFormatters/DataVisualization.h"
18 #include "lldb/Interpreter/CommandInterpreter.h"
19 #include "lldb/Target/Target.h"
20 
21 using namespace lldb;
22 using namespace lldb_private;
23 
24 DumpValueObjectOptions::DumpValueObjectOptions (ValueObject& valobj) :
25 DumpValueObjectOptions()
26 {
27     m_use_dynamic = valobj.GetDynamicValueType();
28     m_use_synthetic = valobj.IsSynthetic();
29 }
30 
31 ValueObjectPrinter::ValueObjectPrinter (ValueObject* valobj,
32                                         Stream* s)
33 {
34     if (valobj)
35     {
36         DumpValueObjectOptions options(*valobj);
37         Init (valobj,s,options,options.m_max_ptr_depth,0);
38     }
39     else
40     {
41         DumpValueObjectOptions options;
42         Init (valobj,s,options,options.m_max_ptr_depth,0);
43     }
44 }
45 
46 ValueObjectPrinter::ValueObjectPrinter (ValueObject* valobj,
47                                         Stream* s,
48                                         const DumpValueObjectOptions& options)
49 {
50     Init(valobj,s,options,options.m_max_ptr_depth,0);
51 }
52 
53 ValueObjectPrinter::ValueObjectPrinter (ValueObject* valobj,
54                                         Stream* s,
55                                         const DumpValueObjectOptions& options,
56                                         uint32_t ptr_depth,
57                                         uint32_t curr_depth)
58 {
59     Init(valobj,s,options,ptr_depth,curr_depth);
60 }
61 
62 void
63 ValueObjectPrinter::Init (ValueObject* valobj,
64                           Stream* s,
65                           const DumpValueObjectOptions& options,
66                           uint32_t ptr_depth,
67                           uint32_t curr_depth)
68 {
69     m_orig_valobj = valobj;
70     m_valobj = nullptr;
71     m_stream = s;
72     this->options = options;
73     m_ptr_depth = ptr_depth;
74     m_curr_depth = curr_depth;
75     assert (m_orig_valobj && "cannot print a NULL ValueObject");
76     assert (m_stream && "cannot print to a NULL Stream");
77     m_should_print = eLazyBoolCalculate;
78     m_is_nil = eLazyBoolCalculate;
79     m_is_ptr = eLazyBoolCalculate;
80     m_is_ref = eLazyBoolCalculate;
81     m_is_aggregate = eLazyBoolCalculate;
82     m_summary_formatter = {nullptr,false};
83     m_value.assign("");
84     m_summary.assign("");
85     m_error.assign("");
86 }
87 
88 bool
89 ValueObjectPrinter::PrintValueObject ()
90 {
91     if (!GetMostSpecializedValue () || m_valobj == nullptr)
92         return false;
93 
94     if (ShouldPrintValueObject())
95     {
96         PrintValidationMarkerIfNeeded();
97 
98         PrintLocationIfNeeded();
99         m_stream->Indent();
100 
101         bool show_type = PrintTypeIfNeeded();
102 
103         PrintNameIfNeeded(show_type);
104     }
105 
106     bool value_printed = false;
107     bool summary_printed = false;
108 
109     bool val_summary_ok = PrintValueAndSummaryIfNeeded (value_printed,summary_printed);
110 
111     if (val_summary_ok)
112         PrintChildrenIfNeeded (value_printed, summary_printed);
113     else
114         m_stream->EOL();
115 
116     PrintValidationErrorIfNeeded();
117 
118     return true;
119 }
120 
121 bool
122 ValueObjectPrinter::GetMostSpecializedValue ()
123 {
124     if (m_valobj)
125         return true;
126     bool update_success = m_orig_valobj->UpdateValueIfNeeded (true);
127     if (!update_success)
128     {
129         m_valobj = m_orig_valobj;
130     }
131     else
132     {
133         if (m_orig_valobj->IsDynamic())
134         {
135             if (options.m_use_dynamic == eNoDynamicValues)
136             {
137                 ValueObject *static_value = m_orig_valobj->GetStaticValue().get();
138                 if (static_value)
139                     m_valobj = static_value;
140                 else
141                     m_valobj = m_orig_valobj;
142             }
143             else
144                 m_valobj = m_orig_valobj;
145         }
146         else
147         {
148             if (options.m_use_dynamic != eNoDynamicValues)
149             {
150                 ValueObject *dynamic_value = m_orig_valobj->GetDynamicValue(options.m_use_dynamic).get();
151                 if (dynamic_value)
152                     m_valobj = dynamic_value;
153                 else
154                     m_valobj = m_orig_valobj;
155             }
156             else
157                 m_valobj = m_orig_valobj;
158         }
159 
160         if (m_valobj->IsSynthetic())
161         {
162             if (options.m_use_synthetic == false)
163             {
164                 ValueObject *non_synthetic = m_valobj->GetNonSyntheticValue().get();
165                 if (non_synthetic)
166                     m_valobj = non_synthetic;
167             }
168         }
169         else
170         {
171             if (options.m_use_synthetic == true)
172             {
173                 ValueObject *synthetic = m_valobj->GetSyntheticValue().get();
174                 if (synthetic)
175                     m_valobj = synthetic;
176             }
177         }
178     }
179     m_clang_type = m_valobj->GetClangType();
180     m_type_flags = m_clang_type.GetTypeInfo ();
181     return true;
182 }
183 
184 const char*
185 ValueObjectPrinter::GetDescriptionForDisplay ()
186 {
187     const char* str = m_valobj->GetObjectDescription();
188     if (!str)
189         str = m_valobj->GetSummaryAsCString();
190     if (!str)
191         str = m_valobj->GetValueAsCString();
192     return str;
193 }
194 
195 const char*
196 ValueObjectPrinter::GetRootNameForDisplay (const char* if_fail)
197 {
198     const char *root_valobj_name = options.m_root_valobj_name.empty() ?
199         m_valobj->GetName().AsCString() :
200         options.m_root_valobj_name.c_str();
201     return root_valobj_name ? root_valobj_name : if_fail;
202 }
203 
204 bool
205 ValueObjectPrinter::ShouldPrintValueObject ()
206 {
207     if (m_should_print == eLazyBoolCalculate)
208         m_should_print = (options.m_flat_output == false || m_type_flags.Test (eTypeHasValue)) ? eLazyBoolYes : eLazyBoolNo;
209     return m_should_print == eLazyBoolYes;
210 }
211 
212 bool
213 ValueObjectPrinter::IsNil ()
214 {
215     if (m_is_nil == eLazyBoolCalculate)
216         m_is_nil = m_valobj->IsObjCNil() ? eLazyBoolYes : eLazyBoolNo;
217     return m_is_nil == eLazyBoolYes;
218 }
219 
220 bool
221 ValueObjectPrinter::IsPtr ()
222 {
223     if (m_is_ptr == eLazyBoolCalculate)
224         m_is_ptr = m_type_flags.Test (eTypeIsPointer) ? eLazyBoolYes : eLazyBoolNo;
225     return m_is_ptr == eLazyBoolYes;
226 }
227 
228 bool
229 ValueObjectPrinter::IsRef ()
230 {
231     if (m_is_ref == eLazyBoolCalculate)
232         m_is_ref = m_type_flags.Test (eTypeIsReference) ? eLazyBoolYes : eLazyBoolNo;
233     return m_is_ref == eLazyBoolYes;
234 }
235 
236 bool
237 ValueObjectPrinter::IsAggregate ()
238 {
239     if (m_is_aggregate == eLazyBoolCalculate)
240         m_is_aggregate = m_type_flags.Test (eTypeHasChildren) ? eLazyBoolYes : eLazyBoolNo;
241     return m_is_aggregate == eLazyBoolYes;
242 }
243 
244 bool
245 ValueObjectPrinter::PrintLocationIfNeeded ()
246 {
247     if (options.m_show_location)
248     {
249         m_stream->Printf("%s: ", m_valobj->GetLocationAsCString());
250         return true;
251     }
252     return false;
253 }
254 
255 bool
256 ValueObjectPrinter::PrintTypeIfNeeded ()
257 {
258     bool show_type = true;
259     // if we are at the root-level and been asked to hide the root's type, then hide it
260     if (m_curr_depth == 0 && options.m_hide_root_type)
261         show_type = false;
262     else
263         // otherwise decide according to the usual rules (asked to show types - always at the root level)
264         show_type = options.m_show_types || (m_curr_depth == 0 && !options.m_flat_output);
265 
266     if (show_type)
267     {
268         // Some ValueObjects don't have types (like registers sets). Only print
269         // the type if there is one to print
270         ConstString type_name;
271         if (options.m_use_type_display_name)
272             type_name = m_valobj->GetDisplayTypeName();
273         else
274             type_name = m_valobj->GetQualifiedTypeName();
275         if (type_name)
276             m_stream->Printf("(%s) ", type_name.GetCString());
277         else
278             show_type = false;
279     }
280     return show_type;
281 }
282 
283 bool
284 ValueObjectPrinter::PrintNameIfNeeded (bool show_type)
285 {
286     if (options.m_flat_output)
287     {
288         // If we are showing types, also qualify the C++ base classes
289         const bool qualify_cxx_base_classes = show_type;
290         if (!options.m_hide_name)
291         {
292             m_valobj->GetExpressionPath(*m_stream, qualify_cxx_base_classes);
293             m_stream->PutCString(" =");
294             return true;
295         }
296     }
297     else if (!options.m_hide_name)
298     {
299         const char *name_cstr = GetRootNameForDisplay("");
300         m_stream->Printf ("%s =", name_cstr);
301         return true;
302     }
303     return false;
304 }
305 
306 bool
307 ValueObjectPrinter::CheckScopeIfNeeded ()
308 {
309     if (options.m_scope_already_checked)
310         return true;
311     return m_valobj->IsInScope();
312 }
313 
314 TypeSummaryImpl*
315 ValueObjectPrinter::GetSummaryFormatter ()
316 {
317     if (m_summary_formatter.second == false)
318     {
319         TypeSummaryImpl* entry = options.m_summary_sp ? options.m_summary_sp.get() : m_valobj->GetSummaryFormat().get();
320 
321         if (options.m_omit_summary_depth > 0)
322             entry = NULL;
323         m_summary_formatter.first = entry;
324         m_summary_formatter.second = true;
325     }
326     return m_summary_formatter.first;
327 }
328 
329 void
330 ValueObjectPrinter::GetValueSummaryError (std::string& value,
331                                           std::string& summary,
332                                           std::string& error)
333 {
334     if (options.m_format != eFormatDefault && options.m_format != m_valobj->GetFormat())
335     {
336         m_valobj->GetValueAsCString(options.m_format,
337                                     value);
338     }
339     else
340     {
341         const char* val_cstr = m_valobj->GetValueAsCString();
342         if (val_cstr)
343             value.assign(val_cstr);
344     }
345     const char* err_cstr = m_valobj->GetError().AsCString();
346     if (err_cstr)
347         error.assign(err_cstr);
348 
349     if (ShouldPrintValueObject())
350     {
351         if (IsNil())
352             summary.assign("nil");
353         else if (options.m_omit_summary_depth == 0)
354         {
355             TypeSummaryImpl* entry = GetSummaryFormatter();
356             if (entry)
357                 m_valobj->GetSummaryAsCString(entry, summary);
358             else
359             {
360                 const char* sum_cstr = m_valobj->GetSummaryAsCString();
361                 if (sum_cstr)
362                     summary.assign(sum_cstr);
363             }
364         }
365     }
366 }
367 
368 bool
369 ValueObjectPrinter::PrintValueAndSummaryIfNeeded (bool& value_printed,
370                                                   bool& summary_printed)
371 {
372     bool error_printed = false;
373     if (ShouldPrintValueObject())
374     {
375         if (!CheckScopeIfNeeded())
376             m_error.assign("out of scope");
377         if (m_error.empty())
378         {
379             GetValueSummaryError(m_value, m_summary, m_error);
380         }
381         if (m_error.size())
382         {
383             error_printed = true;
384             m_stream->Printf (" <%s>\n", m_error.c_str());
385         }
386         else
387         {
388             // Make sure we have a value and make sure the summary didn't
389             // specify that the value should not be printed - and do not print
390             // the value if this thing is nil
391             // (but show the value if the user passes a format explicitly)
392             TypeSummaryImpl* entry = GetSummaryFormatter();
393             if (!IsNil() && !m_value.empty() && (entry == NULL || (entry->DoesPrintValue(m_valobj) || options.m_format != eFormatDefault) || m_summary.empty()) && !options.m_hide_value)
394             {
395                 m_stream->Printf(" %s", m_value.c_str());
396                 value_printed = true;
397             }
398 
399             if (m_summary.size())
400             {
401                 m_stream->Printf(" %s", m_summary.c_str());
402                 summary_printed = true;
403             }
404         }
405     }
406     return !error_printed;
407 }
408 
409 bool
410 ValueObjectPrinter::PrintObjectDescriptionIfNeeded (bool value_printed,
411                                                     bool summary_printed)
412 {
413     if (ShouldPrintValueObject())
414     {
415         // let's avoid the overly verbose no description error for a nil thing
416         if (options.m_use_objc && !IsNil())
417         {
418             if (!options.m_hide_value || !options.m_hide_name)
419                 m_stream->Printf(" ");
420             const char *object_desc = nullptr;
421             if (value_printed || summary_printed)
422                 object_desc = m_valobj->GetObjectDescription();
423             else
424                 object_desc = GetDescriptionForDisplay();
425             if (object_desc && *object_desc)
426             {
427                 m_stream->Printf("%s\n", object_desc);
428                 return true;
429             }
430             else if (value_printed == false && summary_printed == false)
431                 return true;
432             else
433                 return false;
434         }
435     }
436     return true;
437 }
438 
439 bool
440 ValueObjectPrinter::ShouldPrintChildren (bool is_failed_description,
441                                          uint32_t& curr_ptr_depth)
442 {
443     const bool is_ref = IsRef ();
444     const bool is_ptr = IsPtr ();
445 
446     if (is_failed_description || m_curr_depth < options.m_max_depth)
447     {
448         // We will show children for all concrete types. We won't show
449         // pointer contents unless a pointer depth has been specified.
450         // We won't reference contents unless the reference is the
451         // root object (depth of zero).
452 
453         // Use a new temporary pointer depth in case we override the
454         // current pointer depth below...
455 
456         if (is_ptr || is_ref)
457         {
458             // We have a pointer or reference whose value is an address.
459             // Make sure that address is not NULL
460             AddressType ptr_address_type;
461             if (m_valobj->GetPointerValue (&ptr_address_type) == 0)
462                 return false;
463 
464             else if (is_ref && m_curr_depth == 0 && curr_ptr_depth == 0)
465             {
466                 // If this is the root object (depth is zero) that we are showing
467                 // and it is a reference, and no pointer depth has been supplied
468                 // print out what it references. Don't do this at deeper depths
469                 // otherwise we can end up with infinite recursion...
470                 curr_ptr_depth = 1;
471             }
472 
473             return (curr_ptr_depth > 0);
474         }
475 
476         TypeSummaryImpl* entry = GetSummaryFormatter();
477 
478         return (!entry || entry->DoesPrintChildren(m_valobj) || m_summary.empty());
479     }
480     return false;
481 }
482 
483 ValueObject*
484 ValueObjectPrinter::GetValueObjectForChildrenGeneration ()
485 {
486     return m_valobj;
487 }
488 
489 void
490 ValueObjectPrinter::PrintChildrenPreamble ()
491 {
492     if (options.m_flat_output)
493     {
494         if (ShouldPrintValueObject())
495             m_stream->EOL();
496     }
497     else
498     {
499         if (ShouldPrintValueObject())
500             m_stream->PutCString(IsRef () ? ": {\n" : " {\n");
501         m_stream->IndentMore();
502     }
503 }
504 
505 void
506 ValueObjectPrinter::PrintChild (ValueObjectSP child_sp,
507                                 uint32_t curr_ptr_depth)
508 {
509     DumpValueObjectOptions child_options(options);
510     child_options.SetFormat(options.m_format).SetSummary().SetRootValueObjectName();
511     child_options.SetScopeChecked(true).SetHideName(options.m_hide_name).SetHideValue(options.m_hide_value)
512     .SetOmitSummaryDepth(child_options.m_omit_summary_depth > 1 ? child_options.m_omit_summary_depth - 1 : 0);
513     if (child_sp.get())
514     {
515         ValueObjectPrinter child_printer(child_sp.get(),
516                                          m_stream,
517                                          child_options,
518                                          (IsPtr() || IsRef()) && curr_ptr_depth >= 1 ? curr_ptr_depth - 1 : curr_ptr_depth,
519                                          m_curr_depth + 1);
520         child_printer.PrintValueObject();
521     }
522 
523 }
524 
525 uint32_t
526 ValueObjectPrinter::GetMaxNumChildrenToPrint (bool& print_dotdotdot)
527 {
528     ValueObject* synth_m_valobj = GetValueObjectForChildrenGeneration();
529 
530     size_t num_children = synth_m_valobj->GetNumChildren();
531     print_dotdotdot = false;
532     if (num_children)
533     {
534         const size_t max_num_children = m_valobj->GetTargetSP()->GetMaximumNumberOfChildrenToDisplay();
535 
536         if (num_children > max_num_children && !options.m_ignore_cap)
537         {
538             print_dotdotdot = true;
539             return max_num_children;
540         }
541     }
542     return num_children;
543 }
544 
545 void
546 ValueObjectPrinter::PrintChildrenPostamble (bool print_dotdotdot)
547 {
548     if (!options.m_flat_output)
549     {
550         if (print_dotdotdot)
551         {
552             m_valobj->GetTargetSP()->GetDebugger().GetCommandInterpreter().ChildrenTruncated();
553             m_stream->Indent("...\n");
554         }
555         m_stream->IndentLess();
556         m_stream->Indent("}\n");
557     }
558 }
559 
560 void
561 ValueObjectPrinter::PrintChildren (uint32_t curr_ptr_depth)
562 {
563     ValueObject* synth_m_valobj = GetValueObjectForChildrenGeneration();
564 
565     bool print_dotdotdot = false;
566     size_t num_children = GetMaxNumChildrenToPrint(print_dotdotdot);
567     if (num_children)
568     {
569         PrintChildrenPreamble ();
570 
571         for (size_t idx=0; idx<num_children; ++idx)
572         {
573             ValueObjectSP child_sp(synth_m_valobj->GetChildAtIndex(idx, true));
574             PrintChild (child_sp, curr_ptr_depth);
575         }
576 
577         PrintChildrenPostamble (print_dotdotdot);
578     }
579     else if (IsAggregate())
580     {
581         // Aggregate, no children...
582         if (ShouldPrintValueObject())
583         {
584             // if it has a synthetic value, then don't print {}, the synthetic children are probably only being used to vend a value
585             if (m_valobj->DoesProvideSyntheticValue())
586                 m_stream->PutCString( "\n");
587             else
588                 m_stream->PutCString(" {}\n");
589         }
590     }
591     else
592     {
593         if (ShouldPrintValueObject())
594             m_stream->EOL();
595     }
596 }
597 
598 bool
599 ValueObjectPrinter::PrintChildrenOneLiner (bool hide_names)
600 {
601     if (!GetMostSpecializedValue () || m_valobj == nullptr)
602         return false;
603 
604     ValueObject* synth_m_valobj = GetValueObjectForChildrenGeneration();
605 
606     bool print_dotdotdot = false;
607     size_t num_children = GetMaxNumChildrenToPrint(print_dotdotdot);
608 
609     if (num_children)
610     {
611         m_stream->PutChar('(');
612 
613         for (uint32_t idx=0; idx<num_children; ++idx)
614         {
615             lldb::ValueObjectSP child_sp(synth_m_valobj->GetChildAtIndex(idx, true));
616             if (child_sp)
617                 child_sp = child_sp->GetQualifiedRepresentationIfAvailable(options.m_use_dynamic, options.m_use_synthetic);
618             if (child_sp)
619             {
620                 if (idx)
621                     m_stream->PutCString(", ");
622                 if (!hide_names)
623                 {
624                     const char* name = child_sp.get()->GetName().AsCString();
625                     if (name && *name)
626                     {
627                         m_stream->PutCString(name);
628                         m_stream->PutCString(" = ");
629                     }
630                 }
631                 child_sp->DumpPrintableRepresentation(*m_stream,
632                                                       ValueObject::eValueObjectRepresentationStyleSummary,
633                                                       lldb::eFormatInvalid,
634                                                       ValueObject::ePrintableRepresentationSpecialCasesDisable);
635             }
636         }
637 
638         if (print_dotdotdot)
639             m_stream->PutCString(", ...)");
640         else
641             m_stream->PutChar(')');
642     }
643     return true;
644 }
645 
646 void
647 ValueObjectPrinter::PrintChildrenIfNeeded (bool value_printed,
648                                            bool summary_printed)
649 {
650     // this flag controls whether we tried to display a description for this object and failed
651     // if that happens, we want to display the children, if any
652     bool is_failed_description = !PrintObjectDescriptionIfNeeded(value_printed, summary_printed);
653 
654     uint32_t curr_ptr_depth = m_ptr_depth;
655     bool print_children = ShouldPrintChildren (is_failed_description,curr_ptr_depth);
656     bool print_oneline = (curr_ptr_depth > 0 ||
657                           options.m_show_types ||
658                           !options.m_allow_oneliner_mode ||
659                           options.m_flat_output ||
660                           options.m_show_location) ? false : DataVisualization::ShouldPrintAsOneLiner(*m_valobj);
661 
662     if (print_children)
663     {
664         if (print_oneline)
665         {
666             m_stream->PutChar(' ');
667             PrintChildrenOneLiner (false);
668             m_stream->EOL();
669         }
670         else
671             PrintChildren (curr_ptr_depth);
672     }
673     else if (m_curr_depth >= options.m_max_depth && IsAggregate() && ShouldPrintValueObject())
674     {
675             m_stream->PutCString("{...}\n");
676     }
677     else
678         m_stream->EOL();
679 }
680 
681 bool
682 ValueObjectPrinter::ShouldPrintValidation ()
683 {
684     return options.m_run_validator;
685 }
686 
687 bool
688 ValueObjectPrinter::PrintValidationMarkerIfNeeded ()
689 {
690     if (!ShouldPrintValidation())
691         return false;
692 
693     m_validation = m_valobj->GetValidationStatus();
694 
695     if (TypeValidatorResult::Failure == m_validation.first)
696     {
697         m_stream->Printf("! ");
698         return true;
699     }
700 
701     return false;
702 }
703 
704 bool
705 ValueObjectPrinter::PrintValidationErrorIfNeeded ()
706 {
707     if (!ShouldPrintValidation())
708         return false;
709 
710     if (TypeValidatorResult::Success == m_validation.first)
711         return false;
712 
713     if (m_validation.second.empty())
714         m_validation.second.assign("unknown error");
715 
716     m_stream->Printf(" ! validation error: %s", m_validation.second.c_str());
717     m_stream->EOL();
718 
719     return true;
720 }
721