[Lldb-commits] [lldb] r153624 - in /lldb/trunk: examples/summaries/cocoa/CFString.py source/Core/ValueObject.cpp test/functionalities/data-formatter/data-formatter-objc/TestDataFormatterObjC.py test/functionalities/data-formatter/data-formatter-objc/main.m

Enrico Granata egranata at apple.com
Wed Mar 28 18:34:34 PDT 2012


Author: enrico
Date: Wed Mar 28 20:34:34 2012
New Revision: 153624

URL: http://llvm.org/viewvc/llvm-project?rev=153624&view=rev
Log:
Fixing an issue where Unicode characters in an NSString were printed as escape sequences by the summary provider shipping with LLDB - Added relevant test case code. Bonus points for identifying the source of the quotes :-)

Modified:
    lldb/trunk/examples/summaries/cocoa/CFString.py
    lldb/trunk/source/Core/ValueObject.cpp
    lldb/trunk/test/functionalities/data-formatter/data-formatter-objc/TestDataFormatterObjC.py
    lldb/trunk/test/functionalities/data-formatter/data-formatter-objc/main.m

Modified: lldb/trunk/examples/summaries/cocoa/CFString.py
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/examples/summaries/cocoa/CFString.py?rev=153624&r1=153623&r2=153624&view=diff
==============================================================================
--- lldb/trunk/examples/summaries/cocoa/CFString.py (original)
+++ lldb/trunk/examples/summaries/cocoa/CFString.py Wed Mar 28 20:34:34 2012
@@ -14,7 +14,11 @@
 	provider = CFStringSynthProvider(valobj,dict);
 	if provider.invalid == False:
 		try:
-			summary = provider.get_child_at_index(provider.get_child_index("content")).GetSummary();
+			summary = provider.get_child_at_index(provider.get_child_index("content"))
+			if type(summary) == lldb.SBValue:
+				summary = summary.GetSummary()
+			else:
+				summary = '"' + summary + '"'
 		except:
 			summary = None
 		if summary == None:
@@ -111,20 +115,19 @@
 				# a full pointer is skipped here before getting to the live data
 				pointer = pointer + self.pointer_size
 		else:
-			pointer = self.valobj.GetValueAsUnsigned(0) + self.size_of_cfruntime_base();
+			pointer = self.valobj.GetValueAsUnsigned(0) + self.size_of_cfruntime_base()
 			# read 8 bytes here and make an address out of them
 			try:
-			    vopointer = self.valobj.CreateChildAtOffset("dummy",
-				pointer,self.valobj.GetType().GetBasicType(lldb.eBasicTypeChar).GetPointerType());
-			    pointer = vopointer.GetValueAsUnsigned(0)
+				char_type = self.valobj.GetType().GetBasicType(lldb.eBasicTypeChar).GetPointerType()
+				vopointer = self.valobj.CreateValueFromAddress("dummy",pointer,char_type);
+				pointer = vopointer.GetValueAsUnsigned(0)
 			except:
-			    return self.valobj.CreateValueFromExpression("content",
+				return self.valobj.CreateValueFromExpression("content",
                                                              '(char*)"@\"invalid NSString\""')
 		# step 2: read Unicode data at pointer
 		pystr = self.read_unicode(pointer)
 		# step 3: return it
-		return self.valobj.CreateValueFromExpression("content",
-			"(char*)\"" + pystr.encode('utf-8') + "\"")
+		return pystr.encode('utf-8')
 
 	def handle_inline_explicit(self):
 		offset = 3*self.pointer_size
@@ -177,6 +180,11 @@
 			# if this is not possible, a new flag might have to be made up (like the "special" flag
 			# below, which is not a real flag in CFString), or alternatively one might need to use
 			# the ObjC runtime helper to detect the new class and deal with it accordingly
+			#print 'mutable = ' + str(self.mutable)
+			#print 'inline = ' + str(self.inline)
+			#print 'explicit = ' + str(self.explicit)
+			#print 'unicode = ' + str(self.unicode)
+			#print 'special = ' + str(self.special)
 			if self.mutable == True:
 				return self.handle_mutable_string()
 			elif self.inline == True and self.explicit == True and \

Modified: lldb/trunk/source/Core/ValueObject.cpp
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Core/ValueObject.cpp?rev=153624&r1=153623&r2=153624&view=diff
==============================================================================
--- lldb/trunk/source/Core/ValueObject.cpp (original)
+++ lldb/trunk/source/Core/ValueObject.cpp Wed Mar 28 20:34:34 2012
@@ -2322,7 +2322,7 @@
     if (!ret_val.get()) // if there are errors, I add nothing to the list
         return 0;
     
-    if (*reason_to_stop != eExpressionPathScanEndReasonArrayRangeOperatorMet)
+    if ( (reason_to_stop ? *reason_to_stop : dummy_reason_to_stop) != eExpressionPathScanEndReasonArrayRangeOperatorMet)
     {
         // I need not expand a range, just post-process the final value and return
         if (!final_task_on_target || *final_task_on_target == ValueObject::eExpressionPathAftermathNothing)
@@ -2330,7 +2330,7 @@
             list->Append(ret_val);
             return 1;
         }
-        if (ret_val.get() && *final_value_type == eExpressionPathEndResultTypePlain) // I can only deref and takeaddress of plain objects
+        if (ret_val.get() && (final_value_type ? *final_value_type : dummy_final_value_type) == eExpressionPathEndResultTypePlain) // I can only deref and takeaddress of plain objects
         {
             if (*final_task_on_target == ValueObject::eExpressionPathAftermathDereference)
             {

Modified: lldb/trunk/test/functionalities/data-formatter/data-formatter-objc/TestDataFormatterObjC.py
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/test/functionalities/data-formatter/data-formatter-objc/TestDataFormatterObjC.py?rev=153624&r1=153623&r2=153624&view=diff
==============================================================================
--- lldb/trunk/test/functionalities/data-formatter/data-formatter-objc/TestDataFormatterObjC.py (original)
+++ lldb/trunk/test/functionalities/data-formatter/data-formatter-objc/TestDataFormatterObjC.py Wed Mar 28 20:34:34 2012
@@ -1,3 +1,4 @@
+# encoding: utf-8
 """
 Test lldb data formatter subsystem.
 """
@@ -61,6 +62,18 @@
         self.kvo_data_formatter_commands()
 
     @unittest2.skipUnless(sys.platform.startswith("darwin"), "requires Darwin")
+    def test_rdar11106605_with_dsym_and_run_command(self):
+        """Check that Unicode characters come out of CFString summary correctly."""
+        self.buildDsym()
+        self.rdar11106605_commands()
+
+    @unittest2.skipUnless(sys.platform.startswith("darwin"), "requires Darwin")
+    def test_rdar11106605_with_dwarf_and_run_command(self):
+        """Check that Unicode characters come out of CFString summary correctly."""
+        self.buildDwarf()
+        self.rdar11106605_commands()
+
+    @unittest2.skipUnless(sys.platform.startswith("darwin"), "requires Darwin")
     @expectedFailurei386
     def test_expr_with_dsym_and_run_command(self):
         """Test common cases of expression parser <--> formatters interaction."""
@@ -80,6 +93,44 @@
         # Find the line number to break at.
         self.line = line_number('main.m', '// Set break point at this line.')
 
+    def rdar11106605_commands(self):
+        """Check that Unicode characters come out of CFString summary correctly."""
+        self.runCmd("file a.out", CURRENT_EXECUTABLE_SET)
+
+        self.expect("breakpoint set -f main.m -l %d" % self.line,
+                    BREAKPOINT_CREATED,
+            startstr = "Breakpoint created: 1: file ='main.m', line = %d, locations = 1" %
+                        self.line)
+
+        self.runCmd("run", RUN_SUCCEEDED)
+
+        # The stop reason of the thread should be breakpoint.
+        self.expect("thread list", STOPPED_DUE_TO_BREAKPOINT,
+            substrs = ['stopped',
+                       'stop reason = breakpoint'])
+
+        # This is the function to remove the custom formats in order to have a
+        # clean slate for the next test case.
+        def cleanup():
+            self.runCmd('type format clear', check=False)
+            self.runCmd('type summary clear', check=False)
+            self.runCmd('type synth clear', check=False)
+            self.runCmd('type category disable CoreFoundation', check=False)
+            self.runCmd('type category disable CoreGraphics', check=False)
+            self.runCmd('type category disable CoreServices', check=False)
+            self.runCmd('type category disable AppKit', check=False)
+
+
+        # Execute the cleanup function during test case tear down.
+        self.addTearDownHook(cleanup)
+
+        self.runCmd("type category enable AppKit")
+
+        self.expect('frame variable italian', substrs = ['L\'Italia è una Repubblica democratica, fondata sul lavoro. La sovranità appartiene al popolo, che la esercita nelle forme e nei limiti della Costituzione.'])
+        self.expect('frame variable french', substrs = ['Que veut cette horde d\'esclaves, De traîtres, de rois conjurés?'])
+        self.expect('frame variable german', substrs = ['Über-Ich und aus den Ansprüchen der sozialen Umwelt'])
+        self.expect('frame variable japanese', substrs = ['色は匂へど散りぬるを'])
+
     def plain_data_formatter_commands(self):
         """Test basic ObjC formatting behavior."""
         self.runCmd("file a.out", CURRENT_EXECUTABLE_SET)
@@ -197,7 +248,7 @@
                     '(NSString *) str6 = ',' @"1ST"',
                     '(NSString *) str8 = ',' @"hasVeryLongExtensionThisTimehasVeryLongExtensionThisTimehasVeryLongExtensionThisTimehasVeryLongExtensionThisTimehasVeryLongExtensionThisTimehasVeryLongExtensionThisTimehasVeryLongExtensionThisTimehasVeryLongExtensionThisTimehasVeryLongExtensionThisTime',
                     '(NSString *) str9 = ',' @"a very much boring task to write a string this way!!',
-                    '(NSString *) str10 = ',' @"This is a Unicode string',
+                    '(NSString *) str10 = ',' @"This is a Unicode string σ number 4 right here"',
                     '(NSString *) str11 = ',' @"__NSCFString"',
                     '(NSString *) label1 = ',' @"Process Name: "',
                     '(NSString *) label2 = ',' @"Process Id: "',

Modified: lldb/trunk/test/functionalities/data-formatter/data-formatter-objc/main.m
URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/test/functionalities/data-formatter/data-formatter-objc/main.m?rev=153624&r1=153623&r2=153624&view=diff
==============================================================================
--- lldb/trunk/test/functionalities/data-formatter/data-formatter-objc/main.m (original)
+++ lldb/trunk/test/functionalities/data-formatter/data-formatter-objc/main.m Wed Mar 28 20:34:34 2012
@@ -277,6 +277,13 @@
 
 	    NSString *strD12 = [NSString stringWithFormat:@"%@ %@ %@ %@", label1, processName, label2, processID];
 
+	    NSString *eAcute = [NSString stringWithFormat: @"%C", 0x00E9];
+	    NSString *randomHaziChar = [NSString stringWithFormat: @"%C", 0x9DC5];
+	    NSString *japanese = @"色は匂へど散りぬるを";
+	    NSString *italian = @"L'Italia è una Repubblica democratica, fondata sul lavoro. La sovranità appartiene al popolo, che la esercita nelle forme e nei limiti della Costituzione.";
+	    NSString* french = @"Que veut cette horde d'esclaves, De traîtres, de rois conjurés?";
+	    NSString* german = @"Über-Ich und aus den Ansprüchen der sozialen Umwelt";
+
 	    void* data_set[3] = {str1,str2,str3};
 
 	    NSArray* newArray = [[NSMutableArray alloc] init];





More information about the lldb-commits mailing list