diff options
author | dim <dim@FreeBSD.org> | 2013-04-08 18:45:10 +0000 |
---|---|---|
committer | dim <dim@FreeBSD.org> | 2013-04-08 18:45:10 +0000 |
commit | c72c57c9e9b69944e3e009cd5e209634839581d3 (patch) | |
tree | 4fc2f184c499d106f29a386c452b49e5197bf63d /test/SemaObjCXX | |
parent | 5b20025c30d23d521e12c1f33ec8fa6b821952cd (diff) | |
download | FreeBSD-src-c72c57c9e9b69944e3e009cd5e209634839581d3.zip FreeBSD-src-c72c57c9e9b69944e3e009cd5e209634839581d3.tar.gz |
Vendor import of clang trunk r178860:
http://llvm.org/svn/llvm-project/cfe/trunk@178860
Diffstat (limited to 'test/SemaObjCXX')
-rw-r--r-- | test/SemaObjCXX/arc-0x.mm | 8 | ||||
-rw-r--r-- | test/SemaObjCXX/arc-nsconsumed-errors.mm | 32 | ||||
-rw-r--r-- | test/SemaObjCXX/arc-templates.mm | 9 | ||||
-rw-r--r-- | test/SemaObjCXX/arc-unbridged-cast.mm | 9 | ||||
-rw-r--r-- | test/SemaObjCXX/capturing-flexible-array-in-block.mm | 8 | ||||
-rw-r--r-- | test/SemaObjCXX/debugger-cast-result-to-id.mm | 34 | ||||
-rw-r--r-- | test/SemaObjCXX/instancetype.mm | 216 | ||||
-rw-r--r-- | test/SemaObjCXX/instantiate-expr.mm | 4 | ||||
-rw-r--r-- | test/SemaObjCXX/parameters.mm | 3 | ||||
-rw-r--r-- | test/SemaObjCXX/properties.mm | 37 | ||||
-rw-r--r-- | test/SemaObjCXX/unknown-anytype.mm | 45 |
11 files changed, 398 insertions, 7 deletions
diff --git a/test/SemaObjCXX/arc-0x.mm b/test/SemaObjCXX/arc-0x.mm index 43f6671..391fc47 100644 --- a/test/SemaObjCXX/arc-0x.mm +++ b/test/SemaObjCXX/arc-0x.mm @@ -93,3 +93,11 @@ typedef __builtin_va_list va_list; __builtin_va_arg(args, id); } @end + +namespace rdar12078752 { + void f() { + NSObject* o =0; + __autoreleasing decltype(o) o2 = o; + __autoreleasing auto o3 = o; + } +} diff --git a/test/SemaObjCXX/arc-nsconsumed-errors.mm b/test/SemaObjCXX/arc-nsconsumed-errors.mm index 93f5d99..10ae10d 100644 --- a/test/SemaObjCXX/arc-nsconsumed-errors.mm +++ b/test/SemaObjCXX/arc-nsconsumed-errors.mm @@ -18,3 +18,35 @@ blk1 b2 = ^void (id, __attribute((ns_consumed)) id){}; // expected-error {{canno blk1 c3 = ^void (__attribute((ns_consumed)) id, __attribute((ns_consumed)) id){}; blk1 d4 = ^void (id, id) {}; // expected-error {{cannot initialize a variable of type '__strong blk1'}} + + +typedef void (*releaser_t)(__attribute__((ns_consumed)) id); + +void normalFunction(id); +releaser_t r1 = normalFunction; // expected-error {{cannot initialize a variable of type 'releaser_t'}} + +void releaser(__attribute__((ns_consumed)) id); +releaser_t r2 = releaser; // no-warning + +template <typename T> +void templateFunction(T) {} // expected-note {{candidate function}} +releaser_t r3 = templateFunction<id>; // expected-error {{address of overloaded function 'templateFunction' does not match required type 'void (id)'}} + +template <typename T> +void templateReleaser(__attribute__((ns_consumed)) T) {} +releaser_t r4 = templateReleaser<id>; // no-warning + + +@class AntiRelease, ExplicitAntiRelease, ProRelease; + +template<> +void templateFunction(__attribute__((ns_consumed)) AntiRelease *); // expected-error {{no function template matches function template specialization 'templateFunction'}} + +template<> +void templateReleaser(AntiRelease *); // expected-error {{no function template matches function template specialization 'templateReleaser'}} + +template<> +void templateReleaser(ExplicitAntiRelease *) {} // expected-error {{no function template matches function template specialization 'templateReleaser'}} + +template<> +void templateReleaser(__attribute__((ns_consumed)) ProRelease *); // no-warning diff --git a/test/SemaObjCXX/arc-templates.mm b/test/SemaObjCXX/arc-templates.mm index 8009272..ef68b94 100644 --- a/test/SemaObjCXX/arc-templates.mm +++ b/test/SemaObjCXX/arc-templates.mm @@ -283,3 +283,12 @@ namespace rdar10862386 { testing(@"hi"); } } + +namespace rdar12367446 { + template <class T> class A; + template <class R> class A<R()> {}; + + void test() { + A<id()> value; + } +} diff --git a/test/SemaObjCXX/arc-unbridged-cast.mm b/test/SemaObjCXX/arc-unbridged-cast.mm index f7d2391..3f7f76d 100644 --- a/test/SemaObjCXX/arc-unbridged-cast.mm +++ b/test/SemaObjCXX/arc-unbridged-cast.mm @@ -108,3 +108,12 @@ void testTakerFunctions(id string) { takeCFVariadicAudited(1, (CFStringRef) string); takeCFConsumedAudited((CFStringRef) string); // expected-error {{cast of Objective-C pointer type 'id' to C pointer type 'CFStringRef'}} expected-note {{use __bridge to}} expected-note {{use CFBridgingRetain call to}} } + +// rdar://12788838 +id obj; + +void rdar12788838() { + void *foo = reinterpret_cast<void *>(obj); // expected-error {{cast of Objective-C pointer type 'id' to C pointer type 'void *' requires a bridged cast}} \ + // expected-note {{use __bridge with C-style cast to convert directly}} \ + // expected-note {{use CFBridgingRetain call to make an ARC object available as a +1 'void *'}} +} diff --git a/test/SemaObjCXX/capturing-flexible-array-in-block.mm b/test/SemaObjCXX/capturing-flexible-array-in-block.mm new file mode 100644 index 0000000..d7d8885 --- /dev/null +++ b/test/SemaObjCXX/capturing-flexible-array-in-block.mm @@ -0,0 +1,8 @@ +// RUN: %clang_cc1 -fsyntax-only -fblocks -verify -std=c++11 %s +// rdar://12655829 + +void f() { + struct { int x; int y[]; } a; // expected-note 2 {{'a' declared here}} + ^{return a.x;}(); // expected-error {{cannot refer to declaration of structure variable with flexible array member inside block}} + [] {return a.x;}(); // expected-error {{variable 'a' with flexible array member cannot be captured in a lambda expression}} +} diff --git a/test/SemaObjCXX/debugger-cast-result-to-id.mm b/test/SemaObjCXX/debugger-cast-result-to-id.mm index cd7aa7b..815ae38 100644 --- a/test/SemaObjCXX/debugger-cast-result-to-id.mm +++ b/test/SemaObjCXX/debugger-cast-result-to-id.mm @@ -1,7 +1,21 @@ -// RUN: %clang_cc1 -fdebugger-support -fdebugger-cast-result-to-id -funknown-anytype -fsyntax-only -verify %s +// RUN: %clang_cc1 -std=c++11 -fdebugger-support -fdebugger-cast-result-to-id -funknown-anytype -fsyntax-only -verify %s + +extern __unknown_anytype test0a; +extern __unknown_anytype test1a(); +extern __unknown_anytype test0b; +extern __unknown_anytype test1b(); +extern __unknown_anytype test0c; +extern __unknown_anytype test1c(); +extern __unknown_anytype test0d; +extern __unknown_anytype test1d(); +extern __unknown_anytype test0d; +extern __unknown_anytype test1d(); + +@interface A +@end // rdar://problem/9416370 -namespace test0 { +namespace rdar9416370 { void test(id x) { if ([x foo]) {} // expected-error {{no known method '-foo'; cast the message send to the method's return type}} [x foo]; @@ -10,8 +24,20 @@ namespace test0 { // rdar://10988847 @class NSString; // expected-note {{forward declaration of class here}} -namespace test1 { - void rdar10988847() { +namespace rdar10988847 { + void test() { id s = [NSString stringWithUTF8String:"foo"]; // expected-warning {{receiver 'NSString' is a forward class and corresponding @interface may not exist}} } } + +// rdar://13338107 +namespace rdar13338107 { + void test() { + id x1 = test0a; + id x2 = test1a(); + A *x3 = test0b; + A *x4 = test1b(); + auto x5 = test0c; + auto x6 = test1c(); + } +} diff --git a/test/SemaObjCXX/instancetype.mm b/test/SemaObjCXX/instancetype.mm new file mode 100644 index 0000000..bbf100e --- /dev/null +++ b/test/SemaObjCXX/instancetype.mm @@ -0,0 +1,216 @@ +// RUN: %clang_cc1 -fsyntax-only -verify %s + +#if !__has_feature(objc_instancetype) +# error Missing 'instancetype' feature macro. +#endif + +@interface Root ++ (instancetype)alloc; +- (instancetype)init; // expected-note{{overridden method is part of the 'init' method family}} +- (instancetype)self; // expected-note {{explicitly declared 'instancetype'}} +- (Class)class; + +@property (assign) Root *selfProp; +- (instancetype)selfProp; +@end + +@protocol Proto1 +@optional +- (instancetype)methodInProto1; +@end + +@protocol Proto2 +@optional +- (instancetype)methodInProto2; // expected-note{{overridden method returns an instance of its class type}} +- (instancetype)otherMethodInProto2; // expected-note{{overridden method returns an instance of its class type}} +@end + +@interface Subclass1 : Root +- (instancetype)initSubclass1; +- (void)methodOnSubclass1; ++ (instancetype)allocSubclass1; +@end + +@interface Subclass2 : Root +- (instancetype)initSubclass2; +- (void)methodOnSubclass2; +@end + +// Sanity check: the basic initialization pattern. +void test_instancetype_alloc_init_simple() { + Root *r1 = [[Root alloc] init]; + Subclass1 *sc1 = [[Subclass1 alloc] init]; +} + +// Test that message sends to instancetype methods have the right type. +void test_instancetype_narrow_method_search() { + // instancetype on class methods + Subclass1 *sc1 = [[Subclass1 alloc] initSubclass2]; // expected-warning{{'Subclass1' may not respond to 'initSubclass2'}} + Subclass2 *sc2 = [[Subclass2 alloc] initSubclass2]; // okay + + // instancetype on instance methods + [[[Subclass1 alloc] init] methodOnSubclass2]; // expected-warning{{'Subclass1' may not respond to 'methodOnSubclass2'}} + [[[Subclass2 alloc] init] methodOnSubclass2]; + + // instancetype on class methods using protocols + typedef Subclass1<Proto1> SC1Proto1; + typedef Subclass1<Proto2> SC1Proto2; + [[SC1Proto1 alloc] methodInProto2]; // expected-warning{{method '-methodInProto2' not found (return type defaults to 'id')}} + [[SC1Proto2 alloc] methodInProto2]; + + // instancetype on instance methods + Subclass1<Proto1> *sc1proto1 = 0; + [[sc1proto1 self] methodInProto2]; // expected-warning{{method '-methodInProto2' not found (return type defaults to 'id')}} + Subclass1<Proto2> *sc1proto2 = 0; + [[sc1proto2 self] methodInProto2]; + + // Exact type checks + typeof([[Subclass1 alloc] init]) *ptr1 = (Subclass1 **)0; + typeof([[Subclass2 alloc] init]) *ptr2 = (Subclass2 **)0; + + // Message sends to Class. + Subclass1<Proto1> *sc1proto1_2 = [[[sc1proto1 class] alloc] init]; + + // Property access + [sc1proto1.self methodInProto2]; // expected-warning{{method '-methodInProto2' not found (return type defaults to 'id')}} + [sc1proto2.self methodInProto2]; + [Subclass1.alloc initSubclass2]; // expected-warning{{'Subclass1' may not respond to 'initSubclass2'}} + [Subclass2.alloc initSubclass2]; + + [sc1proto1.selfProp methodInProto2]; // expected-warning{{method '-methodInProto2' not found (return type defaults to 'id')}} + [sc1proto2.selfProp methodInProto2]; +} + +// Test that message sends to super methods have the right type. +@interface Subsubclass1 : Subclass1 +- (instancetype)initSubclass1; ++ (instancetype)allocSubclass1; + +- (void)onlyInSubsubclass1; +@end + +@implementation Subsubclass1 +- (instancetype)initSubclass1 { + // Check based on method search. + [[super initSubclass1] methodOnSubclass2]; // expected-warning{{'Subsubclass1' may not respond to 'methodOnSubclass2'}} + [super.initSubclass1 methodOnSubclass2]; // expected-warning{{'Subsubclass1' may not respond to 'methodOnSubclass2'}} + + self = [super init]; // common pattern + + // Exact type check. + typeof([super initSubclass1]) *ptr1 = (Subsubclass1**)0; + + return self; +} + ++ (instancetype)allocSubclass1 { + // Check based on method search. + [[super allocSubclass1] methodOnSubclass2]; // expected-warning{{'Subsubclass1' may not respond to 'methodOnSubclass2'}} + + // The ASTs don't model super property accesses well enough to get this right + [super.allocSubclass1 methodOnSubclass2]; // expected-warning{{'Subsubclass1' may not respond to 'methodOnSubclass2'}} + + // Exact type check. + typeof([super allocSubclass1]) *ptr1 = (Subsubclass1**)0; + + return [super allocSubclass1]; +} + +- (void)onlyInSubsubclass1 {} +@end + +// Check compatibility rules for inheritance of related return types. +@class Subclass4; + +@interface Subclass3 <Proto1, Proto2> +- (Subclass3 *)methodInProto1; +- (Subclass4 *)methodInProto2; // expected-warning{{method is expected to return an instance of its class type 'Subclass3', but is declared to return 'Subclass4 *'}} +@end + +@interface Subclass4 : Root ++ (Subclass4 *)alloc; // okay +- (Subclass3 *)init; // expected-warning{{method is expected to return an instance of its class type 'Subclass4', but is declared to return 'Subclass3 *'}} +- (id)self; // expected-note{{overridden method is part of the 'self' method family}} +- (instancetype)initOther; +@end + +@protocol Proto3 <Proto1, Proto2> +@optional +- (id)methodInProto1; +- (Subclass1 *)methodInProto2; +- (int)otherMethodInProto2; // expected-warning{{protocol method is expected to return an instance of the implementing class, but is declared to return 'int'}} +@end + +@implementation Subclass4 ++ (id)alloc { + return self; // FIXME: we accept this in ObjC++ but not ObjC? +} + +- (Subclass3 *)init { return 0; } // don't complain: we lost the related return type + +- (Subclass3 *)self { return 0; } // expected-warning{{method is expected to return an instance of its class type 'Subclass4', but is declared to return 'Subclass3 *'}} + +- (Subclass4 *)initOther { return 0; } + +@end + +// Check that inherited related return types influence the types of +// message sends. +void test_instancetype_inherited() { + [[Subclass4 alloc] initSubclass1]; // expected-warning{{'Subclass4' may not respond to 'initSubclass1'}} + [[Subclass4 alloc] initOther]; +} + +// Check that related return types tighten up the semantics of +// Objective-C method implementations. +@implementation Subclass2 +- (instancetype)initSubclass2 { // expected-note {{explicitly declared 'instancetype'}} + Subclass1 *sc1 = [[Subclass1 alloc] init]; + return sc1; // expected-error{{cannot initialize return object of type 'Subclass2 *' with an lvalue of type 'Subclass1 *'}} +} +- (void)methodOnSubclass2 {} +- (id)self { + Subclass1 *sc1 = [[Subclass1 alloc] init]; + return sc1; // expected-error{{cannot initialize return object of type 'Subclass2 *' with an lvalue of type 'Subclass1 *'}} +} +@end + +@interface MyClass : Root ++ (int)myClassMethod; +@end + +@implementation MyClass ++ (int)myClassMethod { return 0; } + +- (void)blah { + int i = [[MyClass self] myClassMethod]; +} + +@end + +// rdar://12493140 +@protocol P4 +- (instancetype) foo; // expected-note {{current method is explicitly declared 'instancetype' and is expected to return an instance of its class type}} +@end +@interface A4 : Root <P4> +- (instancetype) bar; // expected-note {{current method is explicitly declared 'instancetype' and is expected to return an instance of its class type}} +- (instancetype) baz; // expected-note {{overridden method returns an instance of its class type}} expected-note {{previous definition is here}} +@end +@interface B4 : Root @end + +@implementation A4 { + B4 *_b; +} +- (id) foo { + return _b; // expected-error {{cannot initialize return object of type 'A4 *' with an lvalue of type 'B4 *'}} +} +- (id) bar { + return _b; // expected-error {{cannot initialize return object of type 'A4 *' with an lvalue of type 'B4 *'}} +} + +// This is really just to ensure that we don't crash. +// FIXME: only one diagnostic, please +- (float) baz { // expected-warning {{method is expected to return an instance of its class type 'A4', but is declared to return 'float'}} expected-warning {{conflicting return type in implementation}} + return 0; +} +@end diff --git a/test/SemaObjCXX/instantiate-expr.mm b/test/SemaObjCXX/instantiate-expr.mm index 75a5b7e..e9d296d 100644 --- a/test/SemaObjCXX/instantiate-expr.mm +++ b/test/SemaObjCXX/instantiate-expr.mm @@ -21,7 +21,7 @@ void f(U value, V value2) { get_an_A(N)->ivar = value; // expected-error{{assigning to 'int' from incompatible type 'int *'}} get_an_A(N).prop = value2; // expected-error{{assigning to 'int' from incompatible type 'double *'}} T c = get_an_id(N)->isa; // expected-error{{cannot initialize a variable of type 'int' with an lvalue of type 'Class'}} \ - // expected-warning 5 {{direct access to objective-c's isa is deprecated in favor of object_setClass() and object_getClass()}} + // expected-warning 3 {{direct access to Objective-C's isa is deprecated in favor of object_getClass()}} } template void f<6, Class>(int, int); // expected-note{{in instantiation of}} @@ -46,7 +46,7 @@ template void f2(A*, int, double*); // expected-note{{instantiation of}} template<typename T, typename U> void f3(U ptr) { T c = ptr->isa; // expected-error{{cannot initialize a variable of type 'int' with an lvalue of type 'Class'}} \ - // expected-warning 2 {{direct access to objective-c's isa is deprecated in favor of object_setClass() and object_getClass()}} + // expected-warning 1 {{direct access to Objective-C's isa is deprecated in favor of object_getClass()}} } template void f3<Class>(id); // expected-note{{in instantiation of}} diff --git a/test/SemaObjCXX/parameters.mm b/test/SemaObjCXX/parameters.mm index 1a7869d..363675a 100644 --- a/test/SemaObjCXX/parameters.mm +++ b/test/SemaObjCXX/parameters.mm @@ -15,3 +15,6 @@ struct test2 { virtual void foo() = 0; }; // expected-note {{unimplemented}} @interface Test2 - (void) foo: (test2) foo; // expected-error {{parameter type 'test2' is an abstract class}} @end + +template<typename T> void r1(__restrict T); +void r2(__restrict id x) { r1(x); } diff --git a/test/SemaObjCXX/properties.mm b/test/SemaObjCXX/properties.mm index 0783eeb..abd4db9 100644 --- a/test/SemaObjCXX/properties.mm +++ b/test/SemaObjCXX/properties.mm @@ -28,7 +28,7 @@ struct X { - (int) z; @end void test2(Test2 *a) { - auto y = a.y; // expected-error {{expected getter method not found on object of type 'Test2 *'}} + auto y = a.y; // expected-error {{no getter method for read from property}} auto z = a.z; } @@ -129,3 +129,38 @@ extern void* VoidType; extern decltype(TestNonTrivialObj.p1 = NonTrivial1())* VoidType; extern decltype(TestNonTrivialObj.p2 = NonTrivial2())* VoidType; +// rdar://13332183 +namespace test9 { + struct CString { + const char *_data; + char operator[](int i) const { return _data[i]; } + }; +} +@interface Test9 +@property test9::CString name; +@end +namespace test9 { + char test(Test9 *t) { + return t.name[0]; + } +} + +namespace test10 { + struct A { operator const char*(); }; + struct B { operator const char*(); }; +} +@interface Test10 +@property test10::A a; +@property test10::B b; +@property int index; +@end +namespace test10 { + void test(Test10 *t) { + (void) t.a[6]; + (void) 6[t.b]; + (void) "help"[t.index]; + (void) t.index["help"]; + (void) t.a[t.index]; + (void) t.index[t.b]; + } +} diff --git a/test/SemaObjCXX/unknown-anytype.mm b/test/SemaObjCXX/unknown-anytype.mm index b28b135..e89dee1 100644 --- a/test/SemaObjCXX/unknown-anytype.mm +++ b/test/SemaObjCXX/unknown-anytype.mm @@ -7,3 +7,48 @@ namespace test0 { [x foo]; // expected-error {{no known method '-foo'; cast the message send to the method's return type}} } } + +// rdar://problem/12565338 +@interface Test1 +- (void) test_a: (__unknown_anytype)foo; +- (void) test_b: (__unknown_anytype)foo; +- (void) test_c: (__unknown_anytype)foo; +@end +namespace test1 { + struct POD { + int x; + }; + + void a(Test1 *obj) { + POD v; + [obj test_a: v]; + } + + struct Uncopyable { + Uncopyable(); + private: + Uncopyable(const Uncopyable &); // expected-note {{declared private here}} + }; + + void b(Test1 *obj) { + Uncopyable v; + [obj test_b: v]; // expected-error {{calling a private constructor}} + } + + void c(Test1 *obj) { + Uncopyable v; + [obj test_c: (const Uncopyable&) v]; + } +} + +// Just test that we can declare a function taking __unknown_anytype. +// For now, we don't actually need to make calling something like this +// work; if that changes, here's what's required: +// - get this call through overload resolution somehow, +// - update the function-call argument-passing code like the +// message-send code, and +// - rewrite the function expression to have a type that doesn't +// involving __unknown_anytype. +namespace test2 { + void foo(__unknown_anytype x); +} |