This patch fixes two errors in the gnu-api-2-objc.m testcase for libobjc's 
Modern Objective-C API.

One of them is that class_addIvar() was called with the alignment, instead of 
the log2 of the alignment,
being passed as argument.  The error slipped in because a previous, buggy 
version of libobjc's class_addIvar()
didn't use the log2, and when fixing libobjc it seems I forgot to update this 
testcase.  It's important to fix this
in case people look at the testcase as an example of how to use the API. ;-)

The other one is that a root class was created, and an instance of it 
instantiated, without the required "isa" instance
variable to hold the Class.  This error slipped in because the instantiation 
was added later without realizing
the root class was a test, fake class without the required variable.  This is 
more serious and could cause the
testcase to fail under some conditions, depending on how the memory is 
allocated.  This patch fixes it. :-)

Committed to trunk.

Thanks

PS: I noticed that these testcases, and the gnu-api-2-class.m[m] ones, are 
failing on Apple m64.  That's a separate
issue and I'll submit a separate patch.

Index: ChangeLog
===================================================================
--- ChangeLog   (revision 174655)
+++ ChangeLog   (working copy)
@@ -1,3 +1,10 @@
+2011-06-04  Nicola Pero  <nicola.p...@meta-innovation.com>
+
+       * objc.dg/gnu-api-2-objc.m: Fixed testcase.  Use log2 of the
+       alignment, not the alignment, when calling class_addIvar().  Add
+       an 'isa' instance variable to the test root class.
+       * obj-c++.dg/gnu-api-2-objc.mm: Likewise.
+       
 2011-06-04  Jan Hubicka  <j...@suse.cz>
 
        PR tree-optimization/48893
Index: objc.dg/gnu-api-2-objc.m
===================================================================
--- objc.dg/gnu-api-2-objc.m    (revision 174655)
+++ objc.dg/gnu-api-2-objc.m    (working copy)
@@ -45,7 +45,24 @@
 - (id) variable { return variable_ivar; }
 @end
 
+/* Hack to calculate the log2 of a byte alignment.  */
+unsigned char
+log_2_of (unsigned int x)
+{
+  unsigned char result = 0;
 
+  /* We count how many times we need to divide by 2 before we reach 1.
+     This algorithm is good enough for the small numbers (such as 8,
+     16 or 64) that we have to deal with.  */
+  while (x > 1)
+    {
+      x = x / 2;
+      result++;
+    }
+
+  return result;
+}
+
 int main(int argc, void **args)
 {
   /* Functions are tested in alphabetical order.  */
@@ -56,8 +73,9 @@ int main(int argc, void **args)
     Class new_class = objc_allocateClassPair (objc_getClass ("MyRootClass"), 
"MyNewSubClass", 0);
 
     /* A new root class would obviously need at least an 'isa'
-       instance variable.  We don't add it so we never actually
-       instantiate an instance of the class, which wouldn't work.  */
+       instance variable.  */
+    class_addIvar (new_root_class, "isa", sizeof (Class), log_2_of 
(__alignof__ (Class)),
+                  @encode (Class));
 
     objc_registerClassPair (new_root_class);
     objc_registerClassPair (new_class);
@@ -114,7 +132,7 @@ int main(int argc, void **args)
     /* Add a bit of everything to the class to exercise undoing all these 
changes.  */
 
     /* Instance variable.  */
-    class_addIvar (new_class, "my_variable", sizeof (float), __alignof__ 
(float), @encode (float));
+    class_addIvar (new_class, "my_variable", sizeof (float), log_2_of 
(__alignof__ (float)), @encode (float));
 
     /* Instance method.  */
     class_addMethod (new_class, @selector (setVariable:), 
method_getImplementation (method),
Index: obj-c++.dg/gnu-api-2-objc.mm
===================================================================
--- obj-c++.dg/gnu-api-2-objc.mm        (revision 174655)
+++ obj-c++.dg/gnu-api-2-objc.mm        (working copy)
@@ -45,7 +45,24 @@
 - (id) variable { return variable_ivar; }
 @end
 
+/* Hack to calculate the log2 of a byte alignment.  */
+unsigned char
+log_2_of (unsigned int x)
+{
+  unsigned char result = 0;
 
+  /* We count how many times we need to divide by 2 before we reach 1.
+     This algorithm is good enough for the small numbers (such as 8,
+     16 or 64) that we have to deal with.  */
+  while (x > 1)
+    {
+      x = x / 2;
+      result++;
+    }
+
+  return result;
+}
+
 int main ()
 {
   /* Functions are tested in alphabetical order.  */
@@ -56,8 +73,9 @@ int main ()
     Class new_class = objc_allocateClassPair (objc_getClass ("MyRootClass"), 
"MyNewSubClass", 0);
 
     /* A new root class would obviously need at least an 'isa'
-       instance variable.  We don't add it so we never actually
-       instantiate an instance of the class, which wouldn't work.  */
+       instance variable.  */
+    class_addIvar (new_root_class, "isa", sizeof (Class), log_2_of 
(__alignof__ (Class)),
+                  @encode (Class));
 
     objc_registerClassPair (new_root_class);
     objc_registerClassPair (new_class);
@@ -114,7 +132,7 @@ int main ()
     /* Add a bit of everything to the class to exercise undoing all these 
changes.  */
 
     /* Instance variable.  */
-    class_addIvar (new_class, "my_variable", sizeof (float), __alignof__ 
(float), @encode (float));
+    class_addIvar (new_class, "my_variable", sizeof (float), log_2_of 
(__alignof__ (float)), @encode (float));
 
     /* Instance method.  */
     class_addMethod (new_class, @selector (setVariable:), 
method_getImplementation (method),

Reply via email to