[Lldb-commits] [lldb] r252663 - Introduce a way for Languages to specify whether values of "reference types" are "nil" (not pointing to anything) or uninitialized (never made to point at anything)

Enrico Granata via lldb-commits lldb-commits at lists.llvm.org
Tue Nov 10 14:39:15 PST 2015


Author: enrico
Date: Tue Nov 10 16:39:15 2015
New Revision: 252663

URL: http://llvm.org/viewvc/llvm-project?rev=252663&view=rev
Log:
Introduce a way for Languages to specify whether values of "reference types" are "nil" (not pointing to anything) or uninitialized (never made to point at anything)
This latter determination may or may not be possible on a per-language basis; and neither is mandatory to implement for any language

Use this knowledge in the ValueObjectPrinter to generalize the notion of IsObjCNil() and the respective printout


Modified:
    lldb/trunk/include/lldb/Core/ValueObject.h
    lldb/trunk/include/lldb/DataFormatters/ValueObjectPrinter.h
    lldb/trunk/include/lldb/Target/Language.h
    lldb/trunk/source/Core/ValueObject.cpp
    lldb/trunk/source/DataFormatters/ValueObjectPrinter.cpp
    lldb/trunk/source/Plugins/Language/ObjC/ObjCLanguage.cpp
    lldb/trunk/source/Plugins/Language/ObjC/ObjCLanguage.h
    lldb/trunk/source/Target/Language.cpp

Modified: lldb/trunk/include/lldb/Core/ValueObject.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Core/ValueObject.h?rev=252663&r1=252662&r2=252663&view=diff
==============================================================================
--- lldb/trunk/include/lldb/Core/ValueObject.h (original)
+++ lldb/trunk/include/lldb/Core/ValueObject.h Tue Nov 10 16:39:15 2015
@@ -424,8 +424,11 @@ public:
     virtual bool
     IsPossibleDynamicType ();
 
-    virtual bool
-    IsObjCNil ();
+    bool
+    IsNilReference ();
+    
+    bool
+    IsUninitializedReference ();
     
     virtual bool
     IsBaseClass ()

Modified: lldb/trunk/include/lldb/DataFormatters/ValueObjectPrinter.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/DataFormatters/ValueObjectPrinter.h?rev=252663&r1=252662&r2=252663&view=diff
==============================================================================
--- lldb/trunk/include/lldb/DataFormatters/ValueObjectPrinter.h (original)
+++ lldb/trunk/include/lldb/DataFormatters/ValueObjectPrinter.h Tue Nov 10 16:39:15 2015
@@ -27,175 +27,179 @@
 //#include <set>
 
 namespace lldb_private {
+
+class ValueObjectPrinter
+{
+public:
+
+    ValueObjectPrinter (ValueObject* valobj,
+                        Stream* s);
+    
+    ValueObjectPrinter (ValueObject* valobj,
+                        Stream* s,
+                        const DumpValueObjectOptions& options);
+    
+    ~ValueObjectPrinter () {}
+    
+    bool
+    PrintValueObject ();
+    
+protected:
+    typedef std::set<uint64_t> InstancePointersSet;
+    typedef std::shared_ptr<InstancePointersSet> InstancePointersSetSP;
+    
+    InstancePointersSetSP m_printed_instance_pointers;
+
+    // only this class (and subclasses, if any) should ever be concerned with
+    // the depth mechanism
+    ValueObjectPrinter (ValueObject* valobj,
+                        Stream* s,
+                        const DumpValueObjectOptions& options,
+                        const DumpValueObjectOptions::PointerDepth& ptr_depth,
+                        uint32_t curr_depth,
+                        InstancePointersSetSP printed_instance_pointers);
+    
+    // we should actually be using delegating constructors here
+    // but some versions of GCC still have trouble with those
+    void
+    Init (ValueObject* valobj,
+          Stream* s,
+          const DumpValueObjectOptions& options,
+          const DumpValueObjectOptions::PointerDepth& ptr_depth,
+          uint32_t curr_depth,
+          InstancePointersSetSP printed_instance_pointers);
+    
+    bool
+    GetMostSpecializedValue ();
+    
+    const char*
+    GetDescriptionForDisplay ();
+    
+    const char*
+    GetRootNameForDisplay (const char* if_fail = nullptr);
+    
+    bool
+    ShouldPrintValueObject ();
+    
+    bool
+    ShouldPrintValidation ();
+    
+    bool
+    IsNil ();
+    
+    bool
+    IsUninitialized ();
+    
+    bool
+    IsPtr ();
+    
+    bool
+    IsRef ();
+    
+    bool
+    IsInstancePointer ();
+    
+    bool
+    IsAggregate ();
+    
+    bool
+    PrintValidationMarkerIfNeeded ();
+    
+    bool
+    PrintValidationErrorIfNeeded ();
+    
+    bool
+    PrintLocationIfNeeded ();
+    
+    void
+    PrintDecl ();
+    
+    bool
+    CheckScopeIfNeeded ();
+    
+    bool
+    ShouldPrintEmptyBrackets (bool value_printed,
+                              bool summary_printed);
+    
+    TypeSummaryImpl*
+    GetSummaryFormatter (bool null_if_omitted = true);
+    
+    void
+    GetValueSummaryError (std::string& value,
+                          std::string& summary,
+                          std::string& error);
+    
+    bool
+    PrintValueAndSummaryIfNeeded (bool& value_printed,
+                                  bool& summary_printed);
+    
+    bool
+    PrintObjectDescriptionIfNeeded (bool value_printed,
+                                    bool summary_printed);
+    
+    bool
+    ShouldPrintChildren (bool is_failed_description,
+                         DumpValueObjectOptions::PointerDepth& curr_ptr_depth);
+
+    bool
+    ShouldExpandEmptyAggregates ();
+    
+    ValueObject*
+    GetValueObjectForChildrenGeneration ();
+    
+    void
+    PrintChildrenPreamble ();
+    
+    void
+    PrintChildrenPostamble (bool print_dotdotdot);
+    
+    void
+    PrintChild (lldb::ValueObjectSP child_sp,
+                const DumpValueObjectOptions::PointerDepth& curr_ptr_depth);
+    
+    uint32_t
+    GetMaxNumChildrenToPrint (bool& print_dotdotdot);
+    
+    void
+    PrintChildren (bool value_printed,
+                   bool summary_printed,
+                   const DumpValueObjectOptions::PointerDepth& curr_ptr_depth);
+    
+    void
+    PrintChildrenIfNeeded (bool value_printed,
+                           bool summary_printed);
+    
+    bool
+    PrintChildrenOneLiner (bool hide_names);
+    
+private:
+    
+    ValueObject *m_orig_valobj;
+    ValueObject *m_valobj;
+    Stream *m_stream;
+    DumpValueObjectOptions m_options;
+    Flags m_type_flags;
+    CompilerType m_compiler_type;
+    DumpValueObjectOptions::PointerDepth m_ptr_depth;
+    uint32_t m_curr_depth;
+    LazyBool m_should_print;
+    LazyBool m_is_nil;
+    LazyBool m_is_uninit;
+    LazyBool m_is_ptr;
+    LazyBool m_is_ref;
+    LazyBool m_is_aggregate;
+    LazyBool m_is_instance_ptr;
+    std::pair<TypeSummaryImpl*,bool> m_summary_formatter;
+    std::string m_value;
+    std::string m_summary;
+    std::string m_error;
+    bool m_val_summary_ok;
+    std::pair<TypeValidatorResult,std::string> m_validation;
+    
+    friend struct StringSummaryFormat;
     
-    class ValueObjectPrinter
-    {
-    public:
-        
-        ValueObjectPrinter (ValueObject* valobj,
-                            Stream* s);
-        
-        ValueObjectPrinter (ValueObject* valobj,
-                            Stream* s,
-                            const DumpValueObjectOptions& options);
-        
-        ~ValueObjectPrinter () {}
-        
-        bool
-        PrintValueObject ();
-        
-    protected:
-        typedef std::set<uint64_t> InstancePointersSet;
-        typedef std::shared_ptr<InstancePointersSet> InstancePointersSetSP;
-        
-        InstancePointersSetSP m_printed_instance_pointers;
-        
-        // only this class (and subclasses, if any) should ever be concerned with
-        // the depth mechanism
-        ValueObjectPrinter (ValueObject* valobj,
-                            Stream* s,
-                            const DumpValueObjectOptions& options,
-                            const DumpValueObjectOptions::PointerDepth& ptr_depth,
-                            uint32_t curr_depth,
-                            InstancePointersSetSP printed_instance_pointers);
-        
-        // we should actually be using delegating constructors here
-        // but some versions of GCC still have trouble with those
-        void
-        Init (ValueObject* valobj,
-              Stream* s,
-              const DumpValueObjectOptions& options,
-              const DumpValueObjectOptions::PointerDepth& ptr_depth,
-              uint32_t curr_depth,
-              InstancePointersSetSP printed_instance_pointers);
-        
-        bool
-        GetMostSpecializedValue ();
-        
-        const char*
-        GetDescriptionForDisplay ();
-        
-        const char*
-        GetRootNameForDisplay (const char* if_fail = nullptr);
-        
-        bool
-        ShouldPrintValueObject ();
-        
-        bool
-        ShouldPrintValidation ();
-        
-        bool
-        IsNil ();
-        
-        bool
-        IsPtr ();
-        
-        bool
-        IsRef ();
-        
-        bool
-        IsInstancePointer ();
-        
-        bool
-        IsAggregate ();
-        
-        bool
-        PrintValidationMarkerIfNeeded ();
-        
-        bool
-        PrintValidationErrorIfNeeded ();
-        
-        bool
-        PrintLocationIfNeeded ();
-        
-        void
-        PrintDecl ();
-        
-        bool
-        CheckScopeIfNeeded ();
-        
-        bool
-        ShouldPrintEmptyBrackets (bool value_printed,
-                                  bool summary_printed);
-        
-        TypeSummaryImpl*
-        GetSummaryFormatter (bool null_if_omitted = true);
-        
-        void
-        GetValueSummaryError (std::string& value,
-                              std::string& summary,
-                              std::string& error);
-        
-        bool
-        PrintValueAndSummaryIfNeeded (bool& value_printed,
-                                      bool& summary_printed);
-        
-        bool
-        PrintObjectDescriptionIfNeeded (bool value_printed,
-                                        bool summary_printed);
-        
-        bool
-        ShouldPrintChildren (bool is_failed_description,
-                             DumpValueObjectOptions::PointerDepth& curr_ptr_depth);
-        
-        bool
-        ShouldExpandEmptyAggregates ();
-        
-        ValueObject*
-        GetValueObjectForChildrenGeneration ();
-        
-        void
-        PrintChildrenPreamble ();
-        
-        void
-        PrintChildrenPostamble (bool print_dotdotdot);
-        
-        void
-        PrintChild (lldb::ValueObjectSP child_sp,
-                    const DumpValueObjectOptions::PointerDepth& curr_ptr_depth);
-        
-        uint32_t
-        GetMaxNumChildrenToPrint (bool& print_dotdotdot);
-        
-        void
-        PrintChildren (bool value_printed,
-                       bool summary_printed,
-                       const DumpValueObjectOptions::PointerDepth& curr_ptr_depth);
-        
-        void
-        PrintChildrenIfNeeded (bool value_printed,
-                               bool summary_printed);
-        
-        bool
-        PrintChildrenOneLiner (bool hide_names);
-        
-    private:
-        
-        ValueObject *m_orig_valobj;
-        ValueObject *m_valobj;
-        Stream *m_stream;
-        DumpValueObjectOptions m_options;
-        Flags m_type_flags;
-        CompilerType m_compiler_type;
-        DumpValueObjectOptions::PointerDepth m_ptr_depth;
-        uint32_t m_curr_depth;
-        LazyBool m_should_print;
-        LazyBool m_is_nil;
-        LazyBool m_is_ptr;
-        LazyBool m_is_ref;
-        LazyBool m_is_aggregate;
-        LazyBool m_is_instance_ptr;
-        std::pair<TypeSummaryImpl*,bool> m_summary_formatter;
-        std::string m_value;
-        std::string m_summary;
-        std::string m_error;
-        bool m_val_summary_ok;
-        std::pair<TypeValidatorResult,std::string> m_validation;
-        
-        friend struct StringSummaryFormat;
-        
-        DISALLOW_COPY_AND_ASSIGN(ValueObjectPrinter);
-    };
+    DISALLOW_COPY_AND_ASSIGN(ValueObjectPrinter);
+};
     
 } // namespace lldb_private
 

Modified: lldb/trunk/include/lldb/Target/Language.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Target/Language.h?rev=252663&r1=252662&r2=252663&view=diff
==============================================================================
--- lldb/trunk/include/lldb/Target/Language.h (original)
+++ lldb/trunk/include/lldb/Target/Language.h Tue Nov 10 16:39:15 2015
@@ -123,6 +123,17 @@ public:
     IsLogicalTrue (ValueObject& valobj,
                    Error& error);
     
+    // for a ValueObject of some "reference type", if the value points to the
+    // nil/null object, this method returns true
+    virtual bool
+    IsNilReference (ValueObject& valobj);
+    
+    // for a ValueObject of some "reference type", if the language provides a technique
+    // to decide whether the reference has ever been assigned to some object, this method
+    // will return true if such detection is possible, and if the reference has never been assigned
+    virtual bool
+    IsUninitializedReference (ValueObject& valobj);
+    
     // These are accessors for general information about the Languages lldb knows about:
     
     static lldb::LanguageType

Modified: lldb/trunk/source/Core/ValueObject.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Core/ValueObject.cpp?rev=252663&r1=252662&r2=252663&view=diff
==============================================================================
--- lldb/trunk/source/Core/ValueObject.cpp (original)
+++ lldb/trunk/source/Core/ValueObject.cpp Tue Nov 10 16:39:15 2015
@@ -2145,15 +2145,23 @@ ValueObject::IsRuntimeSupportValue ()
 }
 
 bool
-ValueObject::IsObjCNil ()
+ValueObject::IsNilReference ()
 {
-    const uint32_t mask = eTypeIsObjC | eTypeIsPointer;
-    bool isObjCpointer = (((GetCompilerType().GetTypeInfo(NULL)) & mask) == mask);
-    if (!isObjCpointer)
-        return false;
-    bool canReadValue = true;
-    bool isZero = GetValueAsUnsigned(0,&canReadValue) == 0;
-    return canReadValue && isZero;
+    if (Language *language = Language::FindPlugin(GetObjectRuntimeLanguage()))
+    {
+        return language->IsNilReference(*this);
+    }
+    return false;
+}
+
+bool
+ValueObject::IsUninitializedReference ()
+{
+    if (Language *language = Language::FindPlugin(GetObjectRuntimeLanguage()))
+    {
+        return language->IsUninitializedReference(*this);
+    }
+    return false;
 }
 
 // This allows you to create an array member using and index

Modified: lldb/trunk/source/DataFormatters/ValueObjectPrinter.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/DataFormatters/ValueObjectPrinter.cpp?rev=252663&r1=252662&r2=252663&view=diff
==============================================================================
--- lldb/trunk/source/DataFormatters/ValueObjectPrinter.cpp (original)
+++ lldb/trunk/source/DataFormatters/ValueObjectPrinter.cpp Tue Nov 10 16:39:15 2015
@@ -73,6 +73,7 @@ ValueObjectPrinter::Init (ValueObject* v
     assert (m_stream && "cannot print to a NULL Stream");
     m_should_print = eLazyBoolCalculate;
     m_is_nil = eLazyBoolCalculate;
+    m_is_uninit = eLazyBoolCalculate;
     m_is_ptr = eLazyBoolCalculate;
     m_is_ref = eLazyBoolCalculate;
     m_is_aggregate = eLazyBoolCalculate;
@@ -100,12 +101,12 @@ ValueObjectPrinter::PrintValueObject ()
         
         PrintDecl();
     }
-    
+
     bool value_printed = false;
     bool summary_printed = false;
     
     m_val_summary_ok = PrintValueAndSummaryIfNeeded (value_printed,summary_printed);
-    
+
     if (m_val_summary_ok)
         PrintChildrenIfNeeded (value_printed, summary_printed);
     else
@@ -194,8 +195,8 @@ const char*
 ValueObjectPrinter::GetRootNameForDisplay (const char* if_fail)
 {
     const char *root_valobj_name = m_options.m_root_valobj_name.empty() ?
-    m_valobj->GetName().AsCString() :
-    m_options.m_root_valobj_name.c_str();
+        m_valobj->GetName().AsCString() :
+        m_options.m_root_valobj_name.c_str();
     return root_valobj_name ? root_valobj_name : if_fail;
 }
 
@@ -211,11 +212,19 @@ bool
 ValueObjectPrinter::IsNil ()
 {
     if (m_is_nil == eLazyBoolCalculate)
-        m_is_nil = m_valobj->IsObjCNil() ? eLazyBoolYes : eLazyBoolNo;
+        m_is_nil = m_valobj->IsNilReference() ? eLazyBoolYes : eLazyBoolNo;
     return m_is_nil == eLazyBoolYes;
 }
 
 bool
+ValueObjectPrinter::IsUninitialized ()
+{
+    if (m_is_uninit == eLazyBoolCalculate)
+        m_is_uninit = m_valobj->IsUninitializedReference() ? eLazyBoolYes : eLazyBoolNo;
+    return m_is_uninit == eLazyBoolYes;
+}
+
+bool
 ValueObjectPrinter::IsPtr ()
 {
     if (m_is_ptr == eLazyBoolCalculate)
@@ -426,6 +435,8 @@ ValueObjectPrinter::GetValueSummaryError
     {
         if (IsNil())
             summary.assign("nil");
+        else if (IsUninitialized())
+            summary.assign("<uninitialized>");
         else if (m_options.m_omit_summary_depth == 0)
         {
             TypeSummaryImpl* entry = GetSummaryFormatter();
@@ -476,7 +487,7 @@ ValueObjectPrinter::PrintValueAndSummary
             // the value if this thing is nil
             // (but show the value if the user passes a format explicitly)
             TypeSummaryImpl* entry = GetSummaryFormatter();
-            if (!IsNil() && !m_value.empty() && (entry == NULL || (entry->DoesPrintValue(m_valobj) || m_options.m_format != eFormatDefault) || m_summary.empty()) && !m_options.m_hide_value)
+            if (!IsNil() && !IsUninitialized() && !m_value.empty() && (entry == NULL || (entry->DoesPrintValue(m_valobj) || m_options.m_format != eFormatDefault) || m_summary.empty()) && !m_options.m_hide_value)
             {
                 if (m_options.m_hide_pointer_value && IsPointerValue(m_valobj->GetCompilerType())) {}
                 else
@@ -503,7 +514,7 @@ ValueObjectPrinter::PrintObjectDescripti
     if (ShouldPrintValueObject())
     {
         // let's avoid the overly verbose no description error for a nil thing
-        if (m_options.m_use_objc && !IsNil())
+        if (m_options.m_use_objc && !IsNil() && !IsUninitialized())
         {
             if (!m_options.m_hide_value || !m_options.m_hide_name)
                 m_stream->Printf(" ");
@@ -571,6 +582,10 @@ ValueObjectPrinter::ShouldPrintChildren
 {
     const bool is_ref = IsRef ();
     const bool is_ptr = IsPtr ();
+    const bool is_uninit = IsUninitialized();
+    
+    if (is_uninit)
+        return false;
     
     TypeSummaryImpl* entry = GetSummaryFormatter();
     

Modified: lldb/trunk/source/Plugins/Language/ObjC/ObjCLanguage.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Plugins/Language/ObjC/ObjCLanguage.cpp?rev=252663&r1=252662&r2=252663&view=diff
==============================================================================
--- lldb/trunk/source/Plugins/Language/ObjC/ObjCLanguage.cpp (original)
+++ lldb/trunk/source/Plugins/Language/ObjC/ObjCLanguage.cpp Tue Nov 10 16:39:15 2015
@@ -863,3 +863,15 @@ ObjCLanguage::GetFormatterPrefixSuffix (
     
     return false;
 }
+
+bool
+ObjCLanguage::IsNilReference (ValueObject& valobj)
+{
+    const uint32_t mask = eTypeIsObjC | eTypeIsPointer;
+    bool isObjCpointer = (((valobj.GetCompilerType().GetTypeInfo(nullptr)) & mask) == mask);
+    if (!isObjCpointer)
+        return false;
+    bool canReadValue = true;
+    bool isZero = valobj.GetValueAsUnsigned(0,&canReadValue) == 0;
+    return canReadValue && isZero;
+}

Modified: lldb/trunk/source/Plugins/Language/ObjC/ObjCLanguage.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Plugins/Language/ObjC/ObjCLanguage.h?rev=252663&r1=252662&r2=252663&view=diff
==============================================================================
--- lldb/trunk/source/Plugins/Language/ObjC/ObjCLanguage.h (original)
+++ lldb/trunk/source/Plugins/Language/ObjC/ObjCLanguage.h Tue Nov 10 16:39:15 2015
@@ -153,6 +153,9 @@ public:
     GetFormatterPrefixSuffix (ValueObject& valobj, ConstString type_hint,
                               std::string& prefix, std::string& suffix) override;
     
+    bool
+    IsNilReference (ValueObject& valobj) override;
+    
     //------------------------------------------------------------------
     // Static Functions
     //------------------------------------------------------------------

Modified: lldb/trunk/source/Target/Language.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Target/Language.cpp?rev=252663&r1=252662&r2=252663&view=diff
==============================================================================
--- lldb/trunk/source/Target/Language.cpp (original)
+++ lldb/trunk/source/Target/Language.cpp Tue Nov 10 16:39:15 2015
@@ -358,6 +358,18 @@ Language::IsLogicalTrue (ValueObject& va
     return eLazyBoolCalculate;
 }
 
+bool
+Language::IsNilReference (ValueObject& valobj)
+{
+    return false;
+}
+
+bool
+Language::IsUninitializedReference (ValueObject& valobj)
+{
+    return false;
+}
+
 //----------------------------------------------------------------------
 // Constructor
 //----------------------------------------------------------------------




More information about the lldb-commits mailing list