1// RUN: %clang_cc1 -triple x86_64-apple-macosx10.9 -Wunguarded-availability -fblocks -fsyntax-only -verify %s 2// RUN: %clang_cc1 -xobjective-c++ -std=c++11 -DOBJCPP -triple x86_64-apple-macosx10.9 -Wunguarded-availability -fblocks -fsyntax-only -verify %s 3 4#define AVAILABLE_10_0 __attribute__((availability(macos, introduced = 10.0))) 5#define AVAILABLE_10_11 __attribute__((availability(macos, introduced = 10.11))) 6#define AVAILABLE_10_12 __attribute__((availability(macos, introduced = 10.12))) 7 8typedef int AVAILABLE_10_12 new_int; // expected-note + {{'new_int' has been marked as being introduced in macOS 10.12 here, but the deployment target is macOS 10.9}} 9 10int func_10_11(void) AVAILABLE_10_11; // expected-note 8 {{'func_10_11' has been marked as being introduced in macOS 10.11 here, but the deployment target is macOS 10.9}} 11 12#ifdef OBJCPP 13// expected-note@+2 6 {{'func_10_12' has been marked as being introduced in macOS 10.12 here, but the deployment target is macOS 10.9}} 14#endif 15int func_10_12(void) AVAILABLE_10_12; // expected-note 7 {{'func_10_12' has been marked as being introduced in macOS 10.12 here, but the deployment target is macOS 10.9}} 16 17int func_10_0(void) AVAILABLE_10_0; 18 19void use_func(void) { 20 func_10_11(); // expected-warning{{'func_10_11' is only available on macOS 10.11 or newer}} expected-note{{enclose 'func_10_11' in an @available check to silence this warning}} 21 22 if (@available(macos 10.11, *)) 23 func_10_11(); 24 else 25 func_10_11(); // expected-warning{{'func_10_11' is only available on macOS 10.11 or newer}} expected-note{{enclose 'func_10_11' in an @available check to silence this warning}} 26} 27 28void defn_10_11(void) AVAILABLE_10_11; 29 30void defn_10_11(void) { 31 func_10_11(); 32} 33 34void nested_ifs(void) { 35 if (@available(macos 10.12, *)) { 36 if (@available(macos 10.10, *)) { 37 func_10_12(); 38 } else { 39 func_10_12(); 40 } 41 } else { 42 func_10_12(); // expected-warning{{'func_10_12' is only available on macOS 10.12 or newer}} expected-note{{enclose 'func_10_12' in an @available check to silence this warning}} 43 } 44} 45 46void star_case(void) { 47 if (@available(ios 9, *)) { 48 func_10_11(); // expected-warning{{'func_10_11' is only available on macOS 10.11 or newer}} expected-note{{enclose 'func_10_11' in an @available check to silence this warning}} 49 func_10_0(); 50 } else 51 func_10_11(); // expected-warning{{'func_10_11' is only available on macOS 10.11 or newer}} expected-note{{enclose 'func_10_11' in an @available check to silence this warning}} 52 53 if (@available(macOS 10.11, *)) { 54 if (@available(ios 8, *)) { 55 func_10_11(); 56 func_10_12(); // expected-warning{{'func_10_12' is only available on macOS 10.12 or newer}} expected-note{{enclose}} 57 } else { 58 func_10_11(); 59 func_10_12(); // expected-warning{{'func_10_12' is only available on macOS 10.12 or newer}} expected-note{{enclose}} 60 } 61 } 62} 63 64typedef int int_10_11 AVAILABLE_10_11; // expected-note {{'int_10_11' has been marked as being introduced in macOS 10.11 here, but the deployment target is macOS 10.9}} 65#ifdef OBJCPP 66// expected-note@+2 {{'int_10_12' has been marked as being introduced in macOS 10.12 here, but the deployment target is macOS 10.9}} 67#endif 68typedef int int_10_12 AVAILABLE_10_12; // expected-note 2 {{'int_10_12' has been marked as being introduced in macOS 10.12 here, but the deployment target is macOS 10.9}} 69 70void use_typedef(void) { 71 int_10_11 x; // expected-warning{{'int_10_11' is only available on macOS 10.11 or newer}} expected-note{{enclose 'int_10_11' in an @available check to silence this warning}} 72} 73 74__attribute__((objc_root_class)) 75AVAILABLE_10_11 @interface Class_10_11 { // expected-note{{annotate 'Class_10_11' with an availability attribute to silence}} 76 int_10_11 foo; 77 int_10_12 bar; // expected-warning {{'int_10_12' is only available on macOS 10.12 or newer}} 78} 79- (void)method1; 80- (void)method2; 81@end 82 83@implementation Class_10_11 84- (void) method1 { 85 func_10_11(); 86 func_10_12(); // expected-warning{{'func_10_12' is only available on macOS 10.12 or newer}} expected-note{{enclose 'func_10_12' in an @available check to silence this warning}} 87} 88 89- (void)method2 AVAILABLE_10_12 { 90 func_10_12(); 91} 92 93@end 94 95int protected_scope(void) { 96 if (@available(macos 10.20, *)) { // expected-note 2 {{jump enters controlled statement of if available}} 97 label1: 98 return 0; 99 } else { 100 label2: 101 goto label1; // expected-error{{cannot jump from this goto statement to its label}} 102 } 103 104 goto label2; // expected-error{{cannot jump from this goto statement to its label}} 105} 106 107struct S { 108 int m1; 109 int m2 __attribute__((availability(macos, introduced = 10.12))); // expected-note{{has been marked as being introduced in macOS 10.12 here, but the deployment target is macOS 10.9}} 110 111 struct Nested { 112 int nested_member __attribute__((availability(macos, introduced = 10.12))); // expected-note{{'nested_member' has been marked as being introduced in macOS 10.12 here, but the deployment target is macOS 10.9}} 113 } n; 114}; 115 116int test_members(void) { 117 struct S s; 118 (void)s.m1; 119 (void)s.m2; // expected-warning{{'m2' is only available on macOS 10.12 or newer}} expected-note{{@available}} 120 121 (void)s.n.nested_member; // expected-warning{{'nested_member' is only available on macOS 10.12 or newer}} expected-note{{@available}} 122} 123 124void test_blocks(void) { 125 (void) ^{ 126 func_10_12(); // expected-warning{{'func_10_12' is only available on macOS 10.12 or newer}} expected-note{{@available}} 127 }; 128 129 if (@available(macos 10.12, *)) 130 (void) ^{ 131 func_10_12(); 132 (void) ^{ 133 func_10_12(); 134 }; 135 }; 136} 137 138void test_params(int_10_12 x); // expected-warning {{'int_10_12' is only available on macOS 10.12 or newer}} expected-note{{annotate 'test_params' with an availability attribute to silence this warning}} 139 140void test_params2(int_10_12 x) AVAILABLE_10_12; // no warn 141 142void (^topLevelBlockDecl)(void) = ^ { 143 func_10_12(); // expected-warning{{'func_10_12' is only available on macOS 10.12 or newer}} expected-note{{@available}} 144 if (@available(macos 10.12, *)) 145 func_10_12(); 146}; 147 148AVAILABLE_10_12 149__attribute__((objc_root_class)) 150@interface InterWithProp // expected-note 2 {{'InterWithProp' has been marked as being introduced in macOS 10.12 here, but the deployment target is macOS 10.9}} 151@property(class) int x; 152+ (void) setX: (int)newX AVAILABLE_10_12; // expected-note{{'setX:' has been marked as being introduced in macOS 10.12 here, but the deployment target is macOS 10.9}} 153@end 154void test_property(void) { 155 int y = InterWithProp.x; // expected-warning{{'InterWithProp' is only available on macOS 10.12 or newer}} expected-note{{@available}} 156 InterWithProp.x = y; // expected-warning{{'InterWithProp' is only available on macOS 10.12 or newer}} expected-note{{@available}} expected-warning{{'setX:' is only available on macOS 10.12 or newer}} expected-note{{@available}} 157} 158 159__attribute__((objc_root_class)) 160@interface Subscriptable 161- (id)objectAtIndexedSubscript:(int)sub AVAILABLE_10_12; // expected-note{{'objectAtIndexedSubscript:' has been marked as being introduced in macOS 10.12 here, but the deployment target is macOS 10.9}} 162@end 163 164void test_at(Subscriptable *x) { 165 id y = x[42]; // expected-warning{{'objectAtIndexedSubscript:' is only available on macOS 10.12 or newer}} expected-note{{@available}} 166} 167 168void uncheckAtAvailable(void) { 169 if (@available(macOS 10.12, *) || 0) // expected-warning {{@available does not guard availability here; use if (@available) instead}} 170 func_10_12(); // expected-warning {{'func_10_12' is only available on macOS 10.12 or newer}} 171 // expected-note@-1 {{enclose 'func_10_12' in an @available check to silence this warning}} 172} 173 174void justAtAvailable(void) { 175 int availability = @available(macOS 10.12, *); // expected-warning {{@available does not guard availability here; use if (@available) instead}} 176} 177 178#ifdef OBJCPP 179 180int f(char) AVAILABLE_10_12; // #f_char_def 181int f(int); 182 183template <class T> int use_f() { 184 if (@available(macos 10.12, *)) { 185 return f(T()); // no warning expected 186 } else { 187 // expected-warning@#f_call {{'f' is only available on macOS 10.12 or newer}} 188 // expected-note@#f_char_inst {{in instantiation of function template specialization 'use_f<char>' requested here}} 189 // expected-note@#f_char_def {{'f' has been marked as being introduced in macOS 10.12 here, but the deployment target is macOS 10.9}} 190 // expected-note@#f_call {{enclose 'f' in an @available check to silence this warning}} 191 return f(T()); // #f_call 192 } 193} 194 195int a = use_f<int>(); 196int b = use_f<char>(); // #f_char_inst 197 198int use_f2() AVAILABLE_10_12 { 199 int c = use_f<int>(); 200 int d = use_f<char>(); // no warning expected 201} 202 203template <class> int use_at_available() { 204 if (@available(macos 10.12, *)) 205 return func_10_12(); 206 else 207 return func_10_12(); // expected-warning {{'func_10_12' is only available on macOS 10.12 or newer}} expected-note{{enclose}} 208} 209 210int instantiate_template() { 211 if (@available(macos 10.12, *)) { 212 use_at_available<char>(); 213 } else { 214 use_at_available<float>(); 215 } 216} 217 218template <class> 219int with_availability_attr() AVAILABLE_10_11 { // expected-note 2 {{'with_availability_attr<int>' has been marked as being introduced in macOS 10.11 here, but the deployment target is macOS 10.9}} 220 return 0; 221} 222 223int instantiate_with_availability_attr() { 224 if (@available(macos 10.12, *)) 225 with_availability_attr<char>(); 226 else 227 with_availability_attr<int>(); // expected-warning {{'with_availability_attr<int>' is only available on macOS 10.11 or newer}} expected-note {{enclose}} 228} 229 230int instantiate_availability() { 231 if (@available(macOS 10.12, *)) 232 with_availability_attr<int_10_12>(); 233 else 234 with_availability_attr<int_10_12>(); // expected-warning{{'with_availability_attr<int>' is only available on macOS 10.11 or newer}} expected-warning{{'int_10_12' is only available on macOS 10.12 or newer}} expected-note 2 {{enclose}} 235} 236 237auto topLevelLambda = [] () { 238 func_10_12(); // expected-warning{{'func_10_12' is only available on macOS 10.12 or newer}} expected-note{{@available}} 239 if (@available(macos 10.12, *)) 240 func_10_12(); 241}; 242 243void functionInFunction() { 244 func_10_12(); // expected-warning{{'func_10_12' is only available on macOS 10.12 or newer}} expected-note{{@available}} 245 struct DontWarnTwice { 246 void f() { 247 func_10_12(); // expected-warning{{'func_10_12' is only available on macOS 10.12 or newer}} expected-note{{@available}} 248 } 249 }; 250 void([] () { 251 func_10_12(); // expected-warning{{'func_10_12' is only available on macOS 10.12 or newer}} expected-note{{@available}} 252 }); 253 (void)(^ { 254 func_10_12(); // expected-warning{{'func_10_12' is only available on macOS 10.12 or newer}} expected-note{{@available}} 255 }); 256 257 if (@available(macos 10.12, *)) { 258 void([]() { 259 func_10_12(); 260 void([] () { 261 func_10_12(); 262 }); 263 struct DontWarn { 264 void f() { 265 func_10_12(); 266 } 267 }; 268 }); 269 } 270 271 if (@available(macos 10.12, *)) { 272 struct DontWarn { 273 void f() { 274 func_10_12(); 275 void([] () { 276 func_10_12(); 277 }); 278 struct DontWarn2 { 279 void f() { 280 func_10_12(); 281 } 282 }; 283 } 284 }; 285 } 286} 287 288#endif 289 290struct InStruct { // expected-note{{annotate 'InStruct' with an availability attribute to silence}} 291 new_int mem; // expected-warning{{'new_int' is only available on macOS 10.12 or newer}} 292 293 struct { new_int mem; } anon; // expected-warning{{'new_int' is only available on macOS 10.12 or newer}} expected-note{{annotate anonymous struct with an availability attribute to silence}} 294}; 295 296#ifdef OBJCPP 297static constexpr int AVAILABLE_10_12 SomeConstexprValue = 2; // expected-note{{'SomeConstexprValue' has been marked as being introduced in macOS 10.12 here, but the deployment target is macOS 10.9}} 298typedef enum { // expected-note{{annotate anonymous enum with an availability attribute}} 299 SomeValue = SomeConstexprValue // expected-warning{{'SomeConstexprValue' is only available on macOS 10.12 or newer}} 300} SomeEnum; 301#endif 302 303@interface InInterface 304-(new_int)meth; // expected-warning{{'new_int' is only available on macOS 10.12 or newer}} expected-note{{annotate 'meth' with an availability attribute}} 305@end 306 307@interface Proper // expected-note{{annotate 'Proper' with an availability attribute}} 308@property (class) new_int x; // expected-warning{{'new_int' is only available}} 309@end 310 311void with_local_struct(void) { 312 struct local { 313 new_int x; // expected-warning{{'new_int' is only available}} expected-note{{enclose 'new_int' in an @available check}} 314 }; 315 if (@available(macos 10.12, *)) { 316 struct DontWarn { 317 new_int x; 318 }; 319 } 320} 321 322// Avoid the warning on protocol requirements. 323 324AVAILABLE_10_12 325@protocol NewProtocol // expected-note {{'NewProtocol' has been marked as being introduced in macOS 10.12 here, but the deployment target is macOS 10.9}} 326@end 327 328@protocol ProtocolWithNewProtocolRequirement <NewProtocol> // expected-note {{annotate 'ProtocolWithNewProtocolRequirement' with an availability attribute to silence}} 329 330@property(copy) id<NewProtocol> prop; // expected-warning {{'NewProtocol' is only available on macOS 10.12 or newer}} 331 332@end 333 334@interface BaseClass 335@end 336 337@interface ClassWithNewProtocolRequirement : BaseClass <NewProtocol> 338 339@end 340 341@interface BaseClass (CategoryWithNewProtocolRequirement) <NewProtocol> 342 343@end 344 345typedef enum { 346 AK_Dodo __attribute__((availability(macos, deprecated=10.3))), // expected-note 3 {{marked deprecated here}} 347 AK_Cat __attribute__((availability(macos, introduced=10.4))), 348 AK_CyborgCat __attribute__((availability(macos, introduced=10.12))), // expected-note {{'AK_CyborgCat' has been marked as being introduced in macOS 10.12 here, but the deployment target is macOS 10.9}} 349} Animals; 350 351void switchAnimals(Animals a) { 352 switch (a) { 353 case AK_Dodo: break; // expected-warning{{'AK_Dodo' is deprecated}} 354 case AK_Cat: break; 355 case AK_Cat|AK_CyborgCat: break; // expected-warning{{case value not in enum}} 356 case AK_CyborgCat: break; // no warn 357 } 358 359 switch (a) { 360 case AK_Dodo...AK_CyborgCat: // expected-warning {{'AK_Dodo' is depr}} 361 break; 362 } 363 364 (void)AK_Dodo; // expected-warning{{'AK_Dodo' is deprecated}} 365 (void)AK_Cat; // no warning 366 (void)AK_CyborgCat; // expected-warning{{'AK_CyborgCat' is only available on macOS 10.12 or newer}} expected-note {{@available}} 367} 368 369 370// test static initializers has the same availability as the deployment target and it cannot be overwritten. 371@interface HasStaticInitializer : BaseClass 372+ (void)load AVAILABLE_10_11; // expected-warning{{ignoring availability attribute on '+load' method}} 373@end 374 375@implementation HasStaticInitializer 376+ (void)load { 377 func_10_11(); // expected-warning{{'func_10_11' is only available on macOS 10.11 or newer}} expected-note{{enclose 'func_10_11' in an @available check to silence this warning}} 378} 379@end 380 381// test availability from interface is ignored when checking the unguarded availability in +load method. 382AVAILABLE_10_11 383@interface HasStaticInitializer1 : BaseClass 384+ (void)load; 385+ (void)load: (int)x; // no warning. 386@end 387 388@implementation HasStaticInitializer1 389+ (void)load { 390 func_10_11(); // expected-warning{{'func_10_11' is only available on macOS 10.11 or newer}} expected-note{{enclose 'func_10_11' in an @available check to silence this warning}} 391} 392+ (void)load: (int)x { 393 func_10_11(); // no warning. 394} 395@end 396 397__attribute__((constructor)) 398void is_constructor(void); 399 400AVAILABLE_10_11 // expected-warning{{ignoring availability attribute with constructor attribute}} 401void is_constructor(void) { 402 func_10_11(); // expected-warning{{'func_10_11' is only available on macOS 10.11 or newer}} expected-note{{enclose 'func_10_11' in an @available check to silence this warning}} 403} 404 405AVAILABLE_10_11 // expected-warning{{ignoring availability attribute with destructor attribute}} 406__attribute__((destructor)) 407void is_destructor(void) { 408 func_10_11(); // expected-warning{{'func_10_11' is only available on macOS 10.11 or newer}} expected-note{{enclose 'func_10_11' in an @available check to silence this warning}} 409} 410