r205659 - Objective-C arc [Sema]. Allow bridge cast of a qualified-id expression

Fariborz Jahanian fjahanian at apple.com
Fri Apr 4 16:53:46 PDT 2014


Author: fjahanian
Date: Fri Apr  4 18:53:45 2014
New Revision: 205659

URL: http://llvm.org/viewvc/llvm-project?rev=205659&view=rev
Log:
Objective-C arc [Sema]. Allow bridge cast of a qualified-id expression
when bridged Objective-C type conforms to the protocols in CF types's
Objective-C class. // rdar://16393330

Modified:
    cfe/trunk/lib/AST/ASTContext.cpp
    cfe/trunk/test/SemaObjC/objcbridge-attribute-arc.m
    cfe/trunk/test/SemaObjC/objcbridge-attribute.m
    cfe/trunk/test/SemaObjCXX/objcbridge-attribute-arc.mm
    cfe/trunk/test/SemaObjCXX/objcbridge-attribute.mm

Modified: cfe/trunk/lib/AST/ASTContext.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/ASTContext.cpp?rev=205659&r1=205658&r2=205659&view=diff
==============================================================================
--- cfe/trunk/lib/AST/ASTContext.cpp (original)
+++ cfe/trunk/lib/AST/ASTContext.cpp Fri Apr  4 18:53:45 2014
@@ -3559,12 +3559,28 @@ bool ASTContext::QIdProtocolsAdoptObjCOb
   CollectInheritedProtocols(IDecl, InheritedProtocols);
   if (InheritedProtocols.empty())
     return false;
-      
+  // Check that if every protocol in list of id<plist> conforms to a protcol
+  // of IDecl's, then bridge casting is ok.
+  bool Conforms = false;
+  for (auto *Proto : OPT->quals()) {
+    Conforms = false;
+    for (auto *PI : InheritedProtocols) {
+      if (ProtocolCompatibleWithProtocol(Proto, PI)) {
+        Conforms = true;
+        break;
+      }
+    }
+    if (!Conforms)
+      break;
+  }
+  if (Conforms)
+    return true;
+  
   for (auto *PI : InheritedProtocols) {
     // If both the right and left sides have qualifiers.
     bool Adopts = false;
     for (auto *Proto : OPT->quals()) {
-      // return 'true' if '*PI' is in the inheritance hierarchy of Proto
+      // return 'true' if 'PI' is in the inheritance hierarchy of Proto
       if ((Adopts = ProtocolCompatibleWithProtocol(PI, Proto)))
         break;
     }

Modified: cfe/trunk/test/SemaObjC/objcbridge-attribute-arc.m
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/SemaObjC/objcbridge-attribute-arc.m?rev=205659&r1=205658&r2=205659&view=diff
==============================================================================
--- cfe/trunk/test/SemaObjC/objcbridge-attribute-arc.m (original)
+++ cfe/trunk/test/SemaObjC/objcbridge-attribute-arc.m Fri Apr  4 18:53:45 2014
@@ -1,9 +1,9 @@
 // RUN: %clang_cc1 -fsyntax-only -x objective-c -fobjc-arc -verify -Wno-objc-root-class %s
 // rdar://15454846
 
-typedef struct __attribute__ ((objc_bridge(NSError))) __CFErrorRef * CFErrorRef; // expected-note 7 {{declared here}}
+typedef struct __attribute__ ((objc_bridge(NSError))) __CFErrorRef * CFErrorRef; // expected-note 5 {{declared here}}
 
-typedef struct __attribute__ ((objc_bridge(MyError))) __CFMyErrorRef * CFMyErrorRef; // expected-note 3 {{declared here}}
+typedef struct __attribute__ ((objc_bridge(MyError))) __CFMyErrorRef * CFMyErrorRef; // expected-note 1 {{declared here}}
 
 typedef struct __attribute__((objc_bridge(12))) __CFMyColor  *CFMyColorRef; // expected-error {{parameter of 'objc_bridge' attribute must be a single name of an Objective-C class}}
 
@@ -53,9 +53,9 @@ typedef CFErrorRef1 CFErrorRef2; // expe
 @protocol P4 @end
 @protocol P5 @end
 
- at interface NSError<P1, P2, P3> @end // expected-note 7 {{declared here}}
+ at interface NSError<P1, P2, P3> @end // expected-note 5 {{declared here}}
 
- at interface MyError : NSError // expected-note 3 {{declared here}}
+ at interface MyError : NSError // expected-note 1 {{declared here}}
 @end
 
 @interface NSUColor @end
@@ -92,8 +92,8 @@ void Test5(id<P1, P2, P3> P123, id ID, i
  (void)(CFErrorRef)ID; // ok
  (void)(CFErrorRef)P123; // ok
  (void)(CFErrorRef)P1234; // ok
- (void)(CFErrorRef)P12; // expected-warning {{'id<P1,P2>' cannot bridge to 'CFErrorRef' (aka 'struct __CFErrorRef *')}}
- (void)(CFErrorRef)P23; // expected-warning {{'id<P2,P3>' cannot bridge to 'CFErrorRef' (aka 'struct __CFErrorRef *')}}
+ (void)(CFErrorRef)P12;
+ (void)(CFErrorRef)P23;
 }
 
 void Test6(id<P1, P2, P3> P123, id ID, id<P1, P2, P3, P4> P1234, id<P1, P2> P12, id<P2, P3> P23) {
@@ -101,21 +101,21 @@ void Test6(id<P1, P2, P3> P123, id ID, i
  (void)(CFMyErrorRef)ID; // ok
  (void)(CFMyErrorRef)P123; // ok
  (void)(CFMyErrorRef)P1234; // ok
- (void)(CFMyErrorRef)P12; // expected-warning {{'id<P1,P2>' cannot bridge to 'CFMyErrorRef' (aka 'struct __CFMyErrorRef *')}}
- (void)(CFMyErrorRef)P23; // expected-warning {{'id<P2,P3>' cannot bridge to 'CFMyErrorRef' (aka 'struct __CFMyErrorRef *')}}
+ (void)(CFMyErrorRef)P12; // ok
+ (void)(CFMyErrorRef)P23; // ok
 }
 
-typedef struct __attribute__ ((objc_bridge(MyPersonalError))) __CFMyPersonalErrorRef * CFMyPersonalErrorRef;  // expected-note 4 {{declared here}}
+typedef struct __attribute__ ((objc_bridge(MyPersonalError))) __CFMyPersonalErrorRef * CFMyPersonalErrorRef;  // expected-note 1 {{declared here}}
 
- at interface MyPersonalError : NSError <P4> // expected-note 4 {{declared here}}
+ at interface MyPersonalError : NSError <P4> // expected-note 1 {{declared here}}
 @end
 
 void Test7(id<P1, P2, P3> P123, id ID, id<P1, P2, P3, P4> P1234, id<P1, P2> P12, id<P2, P3> P23) {
  (void)(CFMyPersonalErrorRef)ID; // ok
- (void)(CFMyPersonalErrorRef)P123; // expected-warning {{'id<P1,P2,P3>' cannot bridge to 'CFMyPersonalErrorRef' (aka 'struct __CFMyPersonalErrorRef *')}}
+ (void)(CFMyPersonalErrorRef)P123; // ok
  (void)(CFMyPersonalErrorRef)P1234; // ok
- (void)(CFMyPersonalErrorRef)P12; //  expected-warning {{'id<P1,P2>' cannot bridge to 'CFMyPersonalErrorRef' (aka 'struct __CFMyPersonalErrorRef *')}}
- (void)(CFMyPersonalErrorRef)P23; //  expected-warning {{'id<P2,P3>' cannot bridge to 'CFMyPersonalErrorRef' (aka 'struct __CFMyPersonalErrorRef *')}}
+ (void)(CFMyPersonalErrorRef)P12; // ok
+ (void)(CFMyPersonalErrorRef)P23; // ok
 }
 
 void Test8(CFMyPersonalErrorRef cf) {

Modified: cfe/trunk/test/SemaObjC/objcbridge-attribute.m
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/SemaObjC/objcbridge-attribute.m?rev=205659&r1=205658&r2=205659&view=diff
==============================================================================
--- cfe/trunk/test/SemaObjC/objcbridge-attribute.m (original)
+++ cfe/trunk/test/SemaObjC/objcbridge-attribute.m Fri Apr  4 18:53:45 2014
@@ -1,9 +1,9 @@
 // RUN: %clang_cc1 -fsyntax-only -verify -Wno-objc-root-class %s
 // rdar://15454846
 
-typedef struct __attribute__ ((objc_bridge(NSError))) __CFErrorRef * CFErrorRef; // expected-note 5 {{declared here}}
+typedef struct __attribute__ ((objc_bridge(NSError))) __CFErrorRef * CFErrorRef; // expected-note 3 {{declared here}}
 
-typedef struct __attribute__ ((objc_bridge(MyError))) __CFMyErrorRef * CFMyErrorRef; // expected-note 3 {{declared here}}
+typedef struct __attribute__ ((objc_bridge(MyError))) __CFMyErrorRef * CFMyErrorRef; // expected-note 1 {{declared here}}
 
 typedef struct __attribute__((objc_bridge(12))) __CFMyColor  *CFMyColorRef; // expected-error {{parameter of 'objc_bridge' attribute must be a single name of an Objective-C class}}
 
@@ -53,9 +53,9 @@ typedef CFErrorRef1 CFErrorRef2; // expe
 @protocol P4 @end
 @protocol P5 @end
 
- at interface NSError<P1, P2, P3> @end // expected-note 5 {{declared here}}
+ at interface NSError<P1, P2, P3> @end // expected-note 3 {{declared here}}
 
- at interface MyError : NSError // expected-note 3 {{declared here}}
+ at interface MyError : NSError // expected-note 1 {{declared here}}
 @end
 
 @interface NSUColor @end
@@ -92,8 +92,8 @@ void Test5(id<P1, P2, P3> P123, id ID, i
  (void)(CFErrorRef)ID; // ok
  (void)(CFErrorRef)P123; // ok
  (void)(CFErrorRef)P1234; // ok
- (void)(CFErrorRef)P12; // expected-warning {{'id<P1,P2>' cannot bridge to 'CFErrorRef' (aka 'struct __CFErrorRef *')}}
- (void)(CFErrorRef)P23; // expected-warning {{'id<P2,P3>' cannot bridge to 'CFErrorRef' (aka 'struct __CFErrorRef *')}}
+ (void)(CFErrorRef)P12; // ok 
+ (void)(CFErrorRef)P23; // ok
 }
 
 void Test6(id<P1, P2, P3> P123, id ID, id<P1, P2, P3, P4> P1234, id<P1, P2> P12, id<P2, P3> P23) {
@@ -101,21 +101,21 @@ void Test6(id<P1, P2, P3> P123, id ID, i
  (void)(CFMyErrorRef)ID; // ok
  (void)(CFMyErrorRef)P123; // ok
  (void)(CFMyErrorRef)P1234; // ok
- (void)(CFMyErrorRef)P12; // expected-warning {{'id<P1,P2>' cannot bridge to 'CFMyErrorRef' (aka 'struct __CFMyErrorRef *')}}
- (void)(CFMyErrorRef)P23; // expected-warning {{'id<P2,P3>' cannot bridge to 'CFMyErrorRef' (aka 'struct __CFMyErrorRef *')}}
+ (void)(CFMyErrorRef)P12; // ok
+ (void)(CFMyErrorRef)P23; // ok
 }
 
-typedef struct __attribute__ ((objc_bridge(MyPersonalError))) __CFMyPersonalErrorRef * CFMyPersonalErrorRef;  // expected-note 4 {{declared here}}
+typedef struct __attribute__ ((objc_bridge(MyPersonalError))) __CFMyPersonalErrorRef * CFMyPersonalErrorRef;  // expected-note 1 {{declared here}}
 
- at interface MyPersonalError : NSError <P4> // expected-note 4 {{declared here}}
+ at interface MyPersonalError : NSError <P4> // expected-note 1 {{declared here}}
 @end
 
 void Test7(id<P1, P2, P3> P123, id ID, id<P1, P2, P3, P4> P1234, id<P1, P2> P12, id<P2, P3> P23) {
  (void)(CFMyPersonalErrorRef)ID; // ok
- (void)(CFMyPersonalErrorRef)P123; // expected-warning {{'id<P1,P2,P3>' cannot bridge to 'CFMyPersonalErrorRef' (aka 'struct __CFMyPersonalErrorRef *')}}
+ (void)(CFMyPersonalErrorRef)P123; // ok
  (void)(CFMyPersonalErrorRef)P1234; // ok
- (void)(CFMyPersonalErrorRef)P12; //  expected-warning {{'id<P1,P2>' cannot bridge to 'CFMyPersonalErrorRef' (aka 'struct __CFMyPersonalErrorRef *')}}
- (void)(CFMyPersonalErrorRef)P23; //  expected-warning {{'id<P2,P3>' cannot bridge to 'CFMyPersonalErrorRef' (aka 'struct __CFMyPersonalErrorRef *')}}
+ (void)(CFMyPersonalErrorRef)P12; // ok
+ (void)(CFMyPersonalErrorRef)P23; // ok
 }
 
 void Test8(CFMyPersonalErrorRef cf) {

Modified: cfe/trunk/test/SemaObjCXX/objcbridge-attribute-arc.mm
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/SemaObjCXX/objcbridge-attribute-arc.mm?rev=205659&r1=205658&r2=205659&view=diff
==============================================================================
--- cfe/trunk/test/SemaObjCXX/objcbridge-attribute-arc.mm (original)
+++ cfe/trunk/test/SemaObjCXX/objcbridge-attribute-arc.mm Fri Apr  4 18:53:45 2014
@@ -1,9 +1,9 @@
 // RUN: %clang_cc1 -fsyntax-only -x objective-c++ -fobjc-arc -verify -Wno-objc-root-class %s
 // rdar://15454846
 
-typedef struct __attribute__ ((objc_bridge(NSError))) __CFErrorRef * CFErrorRef; // expected-note 7 {{declared here}}
+typedef struct __attribute__ ((objc_bridge(NSError))) __CFErrorRef * CFErrorRef; // expected-note 5 {{declared here}}
 
-typedef struct __attribute__ ((objc_bridge(MyError))) __CFMyErrorRef * CFMyErrorRef; // expected-note 3 {{declared here}}
+typedef struct __attribute__ ((objc_bridge(MyError))) __CFMyErrorRef * CFMyErrorRef; // expected-note 1 {{declared here}}
 
 typedef struct __attribute__((objc_bridge(12))) __CFMyColor  *CFMyColorRef; // expected-error {{parameter of 'objc_bridge' attribute must be a single name of an Objective-C class}}
 
@@ -53,9 +53,9 @@ typedef CFErrorRef1 CFErrorRef2; // expe
 @protocol P4 @end
 @protocol P5 @end
 
- at interface NSError<P1, P2, P3> @end // expected-note 7 {{declared here}}
+ at interface NSError<P1, P2, P3> @end // expected-note 5 {{declared here}}
 
- at interface MyError : NSError // expected-note 3 {{declared here}}
+ at interface MyError : NSError // expected-note 1 {{declared here}}
 @end
 
 @interface NSUColor @end
@@ -92,8 +92,8 @@ void Test5(id<P1, P2, P3> P123, id ID, i
  (void)(CFErrorRef)ID; // ok
  (void)(CFErrorRef)P123; // ok
  (void)(CFErrorRef)P1234; // ok
- (void)(CFErrorRef)P12; // expected-warning {{'id<P1,P2>' cannot bridge to 'CFErrorRef' (aka '__CFErrorRef *')}}
- (void)(CFErrorRef)P23; // expected-warning {{'id<P2,P3>' cannot bridge to 'CFErrorRef' (aka '__CFErrorRef *')}}
+ (void)(CFErrorRef)P12;
+ (void)(CFErrorRef)P23;
 }
 
 void Test6(id<P1, P2, P3> P123, id ID, id<P1, P2, P3, P4> P1234, id<P1, P2> P12, id<P2, P3> P23) {
@@ -101,21 +101,21 @@ void Test6(id<P1, P2, P3> P123, id ID, i
  (void)(CFMyErrorRef)ID; // ok
  (void)(CFMyErrorRef)P123; // ok
  (void)(CFMyErrorRef)P1234; // ok
- (void)(CFMyErrorRef)P12; // expected-warning {{'id<P1,P2>' cannot bridge to 'CFMyErrorRef' (aka '__CFMyErrorRef *')}}
- (void)(CFMyErrorRef)P23; // expected-warning {{'id<P2,P3>' cannot bridge to 'CFMyErrorRef' (aka '__CFMyErrorRef *')}}
+ (void)(CFMyErrorRef)P12; // ok
+ (void)(CFMyErrorRef)P23; // ok
 }
 
-typedef struct __attribute__ ((objc_bridge(MyPersonalError))) __CFMyPersonalErrorRef * CFMyPersonalErrorRef;  // expected-note 4 {{declared here}}
+typedef struct __attribute__ ((objc_bridge(MyPersonalError))) __CFMyPersonalErrorRef * CFMyPersonalErrorRef;  // expected-note 1 {{declared here}}
 
- at interface MyPersonalError : NSError <P4> // expected-note 4 {{declared here}}
+ at interface MyPersonalError : NSError <P4> // expected-note 1 {{declared here}}
 @end
 
 void Test7(id<P1, P2, P3> P123, id ID, id<P1, P2, P3, P4> P1234, id<P1, P2> P12, id<P2, P3> P23) {
  (void)(CFMyPersonalErrorRef)ID; // ok
- (void)(CFMyPersonalErrorRef)P123; // expected-warning {{'id<P1,P2,P3>' cannot bridge to 'CFMyPersonalErrorRef' (aka '__CFMyPersonalErrorRef *')}}
+ (void)(CFMyPersonalErrorRef)P123; // ok
  (void)(CFMyPersonalErrorRef)P1234; // ok
- (void)(CFMyPersonalErrorRef)P12; //  expected-warning {{'id<P1,P2>' cannot bridge to 'CFMyPersonalErrorRef' (aka '__CFMyPersonalErrorRef *')}}
- (void)(CFMyPersonalErrorRef)P23; //  expected-warning {{'id<P2,P3>' cannot bridge to 'CFMyPersonalErrorRef' (aka '__CFMyPersonalErrorRef *')}}
+ (void)(CFMyPersonalErrorRef)P12; // ok
+ (void)(CFMyPersonalErrorRef)P23; // ok
 }
 
 void Test8(CFMyPersonalErrorRef cf) {

Modified: cfe/trunk/test/SemaObjCXX/objcbridge-attribute.mm
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/SemaObjCXX/objcbridge-attribute.mm?rev=205659&r1=205658&r2=205659&view=diff
==============================================================================
--- cfe/trunk/test/SemaObjCXX/objcbridge-attribute.mm (original)
+++ cfe/trunk/test/SemaObjCXX/objcbridge-attribute.mm Fri Apr  4 18:53:45 2014
@@ -1,9 +1,9 @@
 // RUN: %clang_cc1 -fsyntax-only -x objective-c++ -verify -Wno-objc-root-class %s
 // rdar://15454846
 
-typedef struct __attribute__ ((objc_bridge(NSError))) __CFErrorRef * CFErrorRef; // expected-note 5 {{declared here}}
+typedef struct __attribute__ ((objc_bridge(NSError))) __CFErrorRef * CFErrorRef; // expected-note 3 {{declared here}}
 
-typedef struct __attribute__ ((objc_bridge(MyError))) __CFMyErrorRef * CFMyErrorRef; // expected-note 3 {{declared here}}
+typedef struct __attribute__ ((objc_bridge(MyError))) __CFMyErrorRef * CFMyErrorRef; // expected-note 1 {{declared here}}
 
 typedef struct __attribute__((objc_bridge(12))) __CFMyColor  *CFMyColorRef; // expected-error {{parameter of 'objc_bridge' attribute must be a single name of an Objective-C class}}
 
@@ -53,9 +53,9 @@ typedef CFErrorRef1 CFErrorRef2; // expe
 @protocol P4 @end
 @protocol P5 @end
 
- at interface NSError<P1, P2, P3> @end // expected-note 5 {{declared here}}
+ at interface NSError<P1, P2, P3> @end // expected-note 3 {{declared here}}
 
- at interface MyError : NSError // expected-note 3 {{declared here}}
+ at interface MyError : NSError // expected-note 1 {{declared here}}
 @end
 
 @interface NSUColor @end
@@ -92,8 +92,8 @@ void Test5(id<P1, P2, P3> P123, id ID, i
  (void)(CFErrorRef)ID; // ok
  (void)(CFErrorRef)P123; // ok
  (void)(CFErrorRef)P1234; // ok
- (void)(CFErrorRef)P12; // expected-warning {{'id<P1,P2>' cannot bridge to 'CFErrorRef' (aka '__CFErrorRef *')}}
- (void)(CFErrorRef)P23; // expected-warning {{'id<P2,P3>' cannot bridge to 'CFErrorRef' (aka '__CFErrorRef *')}}
+ (void)(CFErrorRef)P12; // ok 
+ (void)(CFErrorRef)P23; // ok
 }
 
 void Test6(id<P1, P2, P3> P123, id ID, id<P1, P2, P3, P4> P1234, id<P1, P2> P12, id<P2, P3> P23) {
@@ -101,21 +101,21 @@ void Test6(id<P1, P2, P3> P123, id ID, i
  (void)(CFMyErrorRef)ID; // ok
  (void)(CFMyErrorRef)P123; // ok
  (void)(CFMyErrorRef)P1234; // ok
- (void)(CFMyErrorRef)P12; // expected-warning {{'id<P1,P2>' cannot bridge to 'CFMyErrorRef' (aka '__CFMyErrorRef *')}}
- (void)(CFMyErrorRef)P23; // expected-warning {{'id<P2,P3>' cannot bridge to 'CFMyErrorRef' (aka '__CFMyErrorRef *')}}
+ (void)(CFMyErrorRef)P12; // ok
+ (void)(CFMyErrorRef)P23; // ok
 }
 
-typedef struct __attribute__ ((objc_bridge(MyPersonalError))) __CFMyPersonalErrorRef * CFMyPersonalErrorRef;  // expected-note 4 {{declared here}}
+typedef struct __attribute__ ((objc_bridge(MyPersonalError))) __CFMyPersonalErrorRef * CFMyPersonalErrorRef;  // expected-note 1 {{declared here}}
 
- at interface MyPersonalError : NSError <P4> // expected-note 4 {{declared here}}
+ at interface MyPersonalError : NSError <P4> // expected-note 1 {{declared here}}
 @end
 
 void Test7(id<P1, P2, P3> P123, id ID, id<P1, P2, P3, P4> P1234, id<P1, P2> P12, id<P2, P3> P23) {
  (void)(CFMyPersonalErrorRef)ID; // ok
- (void)(CFMyPersonalErrorRef)P123; // expected-warning {{'id<P1,P2,P3>' cannot bridge to 'CFMyPersonalErrorRef' (aka '__CFMyPersonalErrorRef *')}}
+ (void)(CFMyPersonalErrorRef)P123; // ok
  (void)(CFMyPersonalErrorRef)P1234; // ok
- (void)(CFMyPersonalErrorRef)P12; //  expected-warning {{'id<P1,P2>' cannot bridge to 'CFMyPersonalErrorRef' (aka '__CFMyPersonalErrorRef *')}}
- (void)(CFMyPersonalErrorRef)P23; //  expected-warning {{'id<P2,P3>' cannot bridge to 'CFMyPersonalErrorRef' (aka '__CFMyPersonalErrorRef *')}}
+ (void)(CFMyPersonalErrorRef)P12; // ok
+ (void)(CFMyPersonalErrorRef)P23; // ok
 }
 
 void Test8(CFMyPersonalErrorRef cf) {





More information about the cfe-commits mailing list