[Lldb-commits] [lldb] r147838 - /lldb/trunk/include/lldb/Core/FormatNavigator.h

Jim Ingham jingham at apple.com
Mon Jan 9 19:58:23 PST 2012


Author: jingham
Date: Mon Jan  9 21:58:23 2012
New Revision: 147838

URL: http://llvm.org/viewvc/llvm-project?rev=147838&view=rev
Log:
As we are grubbing through memory chasing down the hierarchy of an ObjC object, protect against the possibility that that object might be just random memory with loops.

Modified:
    lldb/trunk/include/lldb/Core/FormatNavigator.h

Modified: lldb/trunk/include/lldb/Core/FormatNavigator.h
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Core/FormatNavigator.h?rev=147838&r1=147837&r2=147838&view=diff
==============================================================================
--- lldb/trunk/include/lldb/Core/FormatNavigator.h (original)
+++ lldb/trunk/include/lldb/Core/FormatNavigator.h Mon Jan  9 21:58:23 2012
@@ -375,8 +375,11 @@
         return Get_Impl(type, entry, Types<KeyType,ValueType>());
     }
     
+    #define LLDB_MAX_REASONABLE_OBJC_CLASS_DEPTH 100
+    
     bool Get_ObjC(ValueObject& valobj,
              ObjCLanguageRuntime::ObjCISA isa,
+             std::set<ObjCLanguageRuntime::ObjCISA> &found_values,
              MapValueType& entry,
              uint32_t& reason)
     {
@@ -397,6 +400,7 @@
                 log->Printf("invalid ISA, bailing out");
             return false;
         }
+        
         ConstString name = runtime->GetActualTypeName(isa);
         if (log)
             log->Printf("looking for formatter for %s", name.GetCString());
@@ -415,13 +419,29 @@
                 log->Printf("invalid parent ISA, bailing out");
             return false;
         }
-        if (parent == isa)
+        
+        // Put the isa value in our map.  Then check the new_value, if it was already there, we've got a 
+        // loop in the inheritance hierarchy, and should bag out.
+        std::pair<std::set<ObjCLanguageRuntime::ObjCISA>::iterator, bool> new_value = found_values.insert (isa);
+        if (new_value.second == false)
+        {
+            //Our value already existed in the map.
+            if (log)
+                log->Printf ("ISA: 0x%llx already found in inheritance chain.", isa);
+            return false;
+        }
+        
+        if (found_values.size() > LLDB_MAX_REASONABLE_OBJC_CLASS_DEPTH)
         {
+            // ObjC hierarchies are usually pretty shallow, if we've gone this far, we are probably chasing
+            // uninitialized memory.
             if (log)
-                log->Printf("parent-child loop, bailing out");
+                log->Printf("Parent-child depth of %d, we are probably off in the weeds, bailing out.",
+                            LLDB_MAX_REASONABLE_OBJC_CLASS_DEPTH);
             return false;
         }
-        if (Get_ObjC(valobj, parent, entry, reason))
+                
+        if (Get_ObjC(valobj, parent, found_values, entry, reason))
         {
             reason |= lldb_private::eFormatterChoiceCriterionNavigatedBaseClasses;
             return true;
@@ -512,7 +532,8 @@
             }
             else
             {
-                if (Get_ObjC(valobj, runtime->GetISA(valobj), entry, reason))
+                std::set<ObjCLanguageRuntime::ObjCISA> found_values;
+                if (Get_ObjC(valobj, runtime->GetISA(valobj), found_values, entry, reason))
                 {
                     reason |= lldb_private::eFormatterChoiceCriterionDynamicObjCHierarchy;
                     return true;
@@ -555,7 +576,8 @@
                 }
                 else
                 {
-                    if (Get_ObjC(valobj, runtime->GetISA(valobj), entry, reason))
+                    std::set<ObjCLanguageRuntime::ObjCISA> found_values;
+                    if (Get_ObjC(valobj, runtime->GetISA(valobj), found_values, entry, reason))
                     {
                         reason |= lldb_private::eFormatterChoiceCriterionDynamicObjCHierarchy;
                         return true;





More information about the lldb-commits mailing list