зеркало из https://github.com/microsoft/clang-1.git
Diagnose conversion of 'Class' to/from objective-c
object pointer types. Fixes radar 7634850. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@98970 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Родитель
b9e1b75772
Коммит
d4c60909ae
|
@ -4592,8 +4592,18 @@ Sema::CheckBlockPointerTypesForAssignment(QualType lhsType,
|
|||
/// for assignment compatibility.
|
||||
Sema::AssignConvertType
|
||||
Sema::CheckObjCPointerTypesForAssignment(QualType lhsType, QualType rhsType) {
|
||||
if (lhsType->isObjCBuiltinType() || rhsType->isObjCBuiltinType())
|
||||
if (lhsType->isObjCBuiltinType()) {
|
||||
// Class is not compatible with ObjC object pointers.
|
||||
if (lhsType->isObjCClassType() && !rhsType->isObjCBuiltinType())
|
||||
return IncompatiblePointer;
|
||||
return Compatible;
|
||||
}
|
||||
if (rhsType->isObjCBuiltinType()) {
|
||||
// Class is not compatible with ObjC object pointers.
|
||||
if (rhsType->isObjCClassType() && !lhsType->isObjCBuiltinType())
|
||||
return IncompatiblePointer;
|
||||
return Compatible;
|
||||
}
|
||||
QualType lhptee =
|
||||
lhsType->getAs<ObjCObjectPointerType>()->getPointeeType();
|
||||
QualType rhptee =
|
||||
|
|
|
@ -18,9 +18,9 @@ typedef struct objc_class *Class;
|
|||
static XX *obj;
|
||||
|
||||
+ (void)classMethod {
|
||||
[obj addObserver:self];
|
||||
[obj addObserver:self]; // expected-warning {{incompatible pointer types sending 'Class', expected 'XX *'}}
|
||||
Class whatever;
|
||||
[obj addObserver:whatever]; // GCC warns about this.
|
||||
[obj addObserver:whatever]; // expected-warning {{incompatible pointer types sending 'Class', expected 'XX *'}}
|
||||
}
|
||||
@end
|
||||
|
||||
|
|
|
@ -35,7 +35,7 @@ int main()
|
|||
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;
|
||||
obj_c = obj_C; // expected-warning {{incompatible pointer types assigning 'Class', expected 'MyClass *'}}
|
||||
|
||||
/* Assigning to an 'id<MyProtocol>' variable should generate a
|
||||
warning if done from a 'MyClass *' (which doesn't implement
|
||||
|
@ -44,7 +44,7 @@ int main()
|
|||
obj_p = obj; /* Ok */
|
||||
obj_p = obj_c; // expected-warning {{incompatible type assigning 'MyClass *', expected 'id<MyProtocol>'}}
|
||||
obj_p = obj_cp; /* Ok */
|
||||
obj_p = obj_C; // Ok
|
||||
obj_p = obj_C; // expected-warning {{incompatible pointer types assigning 'Class', expected 'id<MyProtocol>'}}
|
||||
|
||||
/* Assigning to a 'MyOtherClass *' variable should always generate
|
||||
a warning, unless done from an 'id' or an 'id<MyProtocol>' (since
|
||||
|
@ -52,7 +52,7 @@ int main()
|
|||
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;
|
||||
obj_cp = obj_C; // expected-warning {{incompatible pointer types assigning 'Class', expected 'MyOtherClass *'}}
|
||||
|
||||
/* Any comparison involving an 'id' must be without warnings. */
|
||||
if (obj == obj_p) foo() ; /* Ok */ /*Bogus warning here in 2.95.4*/
|
||||
|
|
|
@ -9,7 +9,8 @@ void foo() {
|
|||
// Test assignment compatibility of Class and id. No warning should be
|
||||
// produced.
|
||||
// rdar://6770142 - Class and id<foo> are compatible.
|
||||
S = T; T = S;
|
||||
S = T; // expected-warning {{incompatible pointer types assigning 'Class', expected 'id<Foo>'}}
|
||||
T = S; // expected-warning {{incompatible pointer types assigning 'id<Foo>', expected 'Class'}}
|
||||
R = T; T = R;
|
||||
R = S; S = R;
|
||||
}
|
||||
|
|
|
@ -0,0 +1,42 @@
|
|||
// RUN: %clang_cc1 -fsyntax-only -verify %s
|
||||
// rdar 7634850
|
||||
|
||||
@interface Foo
|
||||
- (void)foo:(Class)class;
|
||||
@end
|
||||
|
||||
void FUNC() {
|
||||
Class c, c1;
|
||||
SEL s1, s2;
|
||||
id i, i1;
|
||||
Foo *f;
|
||||
[f foo:f]; // expected-warning {{incompatible pointer types sending 'Foo *', expected 'Class'}}
|
||||
c = f; // expected-warning {{incompatible pointer types assigning 'Foo *', expected 'Class'}}
|
||||
|
||||
c = i;
|
||||
|
||||
i = c;
|
||||
|
||||
c = c1;
|
||||
|
||||
i = i1;
|
||||
|
||||
s1 = i; // expected-warning {{incompatible pointer types assigning 'id', expected 'SEL'}}
|
||||
i = s1; // expected-warning {{incompatible pointer types assigning 'SEL', expected 'id'}}
|
||||
|
||||
s1 = s2;
|
||||
|
||||
s1 = c; // expected-warning {{incompatible pointer types assigning 'Class', expected 'SEL'}}
|
||||
|
||||
c = s1; // expected-warning {{incompatible pointer types assigning 'SEL', expected 'Class'}}
|
||||
|
||||
f = i;
|
||||
|
||||
f = c; // expected-warning {{incompatible pointer types assigning 'Class', expected 'Foo *'}}
|
||||
|
||||
f = s1; // expected-warning {{incompatible pointer types assigning 'SEL', expected 'Foo *'}}
|
||||
|
||||
i = f;
|
||||
|
||||
s1 = f; // expected-warning {{incompatible pointer types assigning 'Foo *', expected 'SEL'}}
|
||||
}
|
Загрузка…
Ссылка в новой задаче