[cfe-commits] r69041 - in /cfe/trunk: lib/AST/ASTContext.cpp test/SemaObjC/class-method-self.m test/SemaObjC/comptypes-1.m

Steve Naroff snaroff at apple.com
Tue Apr 14 08:11:48 PDT 2009


Author: snaroff
Date: Tue Apr 14 10:11:46 2009
New Revision: 69041

URL: http://llvm.org/viewvc/llvm-project?rev=69041&view=rev
Log:
ASTContext::mergeTypes(): Loosen up the type checking for 'Class' (treating it like 'id').

This fixes <rdar://problem/6782722> XCDataTipsManager.m registers, observes notifications in class methods.

The radar above is the result of clang typing 'self' in a class method as 'Class', which results in some spurious warnings (GCC types 'self' in a class method as 'id').

I considered changing the type of 'self' to 'id' (to conform to GCC), however this resulted in *many* test cases breaking. In addition, I really prefer a more strongly typed 'self'.

All in all, this is the least obtrusive fix I could find for removing the spurious warnings (though we do loose some valid warnings).

Added:
    cfe/trunk/test/SemaObjC/class-method-self.m
Modified:
    cfe/trunk/lib/AST/ASTContext.cpp
    cfe/trunk/test/SemaObjC/comptypes-1.m

Modified: cfe/trunk/lib/AST/ASTContext.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/ASTContext.cpp?rev=69041&r1=69040&r2=69041&view=diff

==============================================================================
--- cfe/trunk/lib/AST/ASTContext.cpp (original)
+++ cfe/trunk/lib/AST/ASTContext.cpp Tue Apr 14 10:11:46 2009
@@ -2964,17 +2964,17 @@
     const ObjCInterfaceType* LHSIface = LHS->getAsObjCInterfaceType();
     const ObjCInterfaceType* RHSIface = RHS->getAsObjCInterfaceType();
 
-    // ID acts sort of like void* for ObjC interfaces
-    if (LHSIface && isObjCIdStructType(RHS))
+    // 'id' and 'Class' act sort of like void* for ObjC interfaces
+    if (LHSIface && (isObjCIdStructType(RHS) || isObjCClassStructType(RHS)))
       return LHS;
-    if (RHSIface && isObjCIdStructType(LHS))
+    if (RHSIface && (isObjCIdStructType(LHS) || isObjCClassStructType(LHS)))
       return RHS;
     
     // ID is compatible with all qualified id types.
     if (LHS->isObjCQualifiedIdType()) {
       if (const PointerType *PT = RHS->getAsPointerType()) {
         QualType pType = PT->getPointeeType();
-        if (isObjCIdStructType(pType))
+        if (isObjCIdStructType(pType) || isObjCClassStructType(pType))
           return LHS;
         // FIXME: need to use ObjCQualifiedIdTypesAreCompatible(LHS, RHS, true).
         // Unfortunately, this API is part of Sema (which we don't have access
@@ -2987,7 +2987,7 @@
     if (RHS->isObjCQualifiedIdType()) {
       if (const PointerType *PT = LHS->getAsPointerType()) {
         QualType pType = PT->getPointeeType();
-        if (isObjCIdStructType(pType))
+        if (isObjCIdStructType(pType) || isObjCClassStructType(pType))
           return RHS;
         // FIXME: need to use ObjCQualifiedIdTypesAreCompatible(LHS, RHS, true).
         // Unfortunately, this API is part of Sema (which we don't have access

Added: cfe/trunk/test/SemaObjC/class-method-self.m
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/SemaObjC/class-method-self.m?rev=69041&view=auto

==============================================================================
--- cfe/trunk/test/SemaObjC/class-method-self.m (added)
+++ cfe/trunk/test/SemaObjC/class-method-self.m Tue Apr 14 10:11:46 2009
@@ -0,0 +1,26 @@
+// RUN: clang-cc -verify %s 
+
+typedef struct objc_class *Class;
+ at interface XX
+
+- (void)addObserver:(XX*)o;
+
+ at end
+
+ at interface YY
+
++ (void)classMethod;
+
+ at end
+
+ at implementation YY
+
+static XX *obj;
+
++ (void)classMethod {
+  [obj addObserver:self];
+  Class whatever;
+  [obj addObserver:whatever]; // GCC warns about this.
+}
+ at end
+

Modified: cfe/trunk/test/SemaObjC/comptypes-1.m
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/SemaObjC/comptypes-1.m?rev=69041&r1=69040&r2=69041&view=diff

==============================================================================
--- cfe/trunk/test/SemaObjC/comptypes-1.m (original)
+++ cfe/trunk/test/SemaObjC/comptypes-1.m Tue Apr 14 10:11:46 2009
@@ -35,7 +35,7 @@
      warning, unless done from an 'id'.  */
   obj_c = obj;    /* Ok */
   obj_c = obj_cp; // // expected-warning {{incompatible pointer types assigning 'MyOtherClass *', expected 'MyClass *'}}
-  obj_c = obj_C;  // expected-warning {{incompatible pointer types assigning 'Class', expected 'MyClass *'}}
+  obj_c = obj_C;
 
   /* Assigning to an 'id<MyProtocol>' variable should generate a
      warning if done from a 'MyClass *' (which doesn't implement
@@ -52,7 +52,7 @@
   obj_cp = obj;    /* Ok */
   obj_cp = obj_c;  // expected-warning {{incompatible pointer types assigning 'MyClass *', expected 'MyOtherClass *'}}
   obj_cp = obj_p;  /* Ok */
-  obj_cp = obj_C;  // expected-warning {{incompatible pointer types assigning 'Class', expected 'MyOtherClass *'}}
+  obj_cp = obj_C;
 
   /* Any comparison involving an 'id' must be without warnings.  */
   if (obj == obj_p) foo() ;  /* Ok  */ /*Bogus warning here in 2.95.4*/
@@ -73,8 +73,8 @@
   if (obj_c == obj_cp) foo() ; // expected-warning {{comparison of distinct pointer types ('MyClass *' and 'MyOtherClass *')}} 
   if (obj_cp == obj_c) foo() ; // expected-warning {{comparison of distinct pointer types ('MyOtherClass *' and 'MyClass *')}}
 
-  if (obj_c == obj_C) foo() ;  // expected-warning {{comparison of distinct pointer types ('MyClass *' and 'Class')}}
-  if (obj_C == obj_c) foo() ;  // expected-warning {{comparison of distinct pointer types ('Class' and 'MyClass *')}} 
+  if (obj_c == obj_C) foo() ;
+  if (obj_C == obj_c) foo() ;
 
   /* Any comparison between 'MyOtherClass *' (which implements
      MyProtocol) and an 'id' implementing MyProtocol are Ok.  */
@@ -82,10 +82,10 @@
   if (obj_p == obj_cp) foo() ; /* Ok */
 
 
-  if (obj_p == obj_C) foo() ; // expected-warning {{comparison of distinct pointer types ('id<MyProtocol>' and 'Class')}} 
-  if (obj_C == obj_p) foo() ; // expected-warning {{comparison of distinct pointer types ('Class' and 'id<MyProtocol>')}} 
-  if (obj_cp == obj_C) foo() ; // expected-warning {{comparison of distinct pointer types ('MyOtherClass *' and 'Class')}} 
-  if (obj_C == obj_cp) foo() ; // expected-warning {{comparison of distinct pointer types ('Class' and 'MyOtherClass *')}}
+  if (obj_p == obj_C) foo() ;  
+  if (obj_C == obj_p) foo() ;
+  if (obj_cp == obj_C) foo() ;  
+  if (obj_C == obj_cp) foo() ;
 
   return 0;
 }





More information about the cfe-commits mailing list