Home | History | Annotate | Download | only in SemaCXX
      1 // RUN: %clang_cc1 -fsyntax-only -verify -Wthread-safety %s
      2 
      3 #define LOCKABLE            __attribute__ ((lockable))
      4 #define SCOPED_LOCKABLE     __attribute__ ((scoped_lockable))
      5 #define GUARDED_BY(x)       __attribute__ ((guarded_by(x)))
      6 #define GUARDED_VAR         __attribute__ ((guarded_var))
      7 #define PT_GUARDED_BY(x)    __attribute__ ((pt_guarded_by(x)))
      8 #define PT_GUARDED_VAR      __attribute__ ((pt_guarded_var))
      9 #define ACQUIRED_AFTER(...) __attribute__ ((acquired_after(__VA_ARGS__)))
     10 #define ACQUIRED_BEFORE(...) __attribute__ ((acquired_before(__VA_ARGS__)))
     11 #define EXCLUSIVE_LOCK_FUNCTION(...)    __attribute__ ((exclusive_lock_function(__VA_ARGS__)))
     12 #define SHARED_LOCK_FUNCTION(...)       __attribute__ ((shared_lock_function(__VA_ARGS__)))
     13 #define ASSERT_EXCLUSIVE_LOCK(...)      __attribute__ ((assert_exclusive_lock(__VA_ARGS__)))
     14 #define ASSERT_SHARED_LOCK(...)         __attribute__ ((assert_shared_lock(__VA_ARGS__)))
     15 #define EXCLUSIVE_TRYLOCK_FUNCTION(...) __attribute__ ((exclusive_trylock_function(__VA_ARGS__)))
     16 #define SHARED_TRYLOCK_FUNCTION(...)    __attribute__ ((shared_trylock_function(__VA_ARGS__)))
     17 #define UNLOCK_FUNCTION(...)            __attribute__ ((unlock_function(__VA_ARGS__)))
     18 #define LOCK_RETURNED(x)    __attribute__ ((lock_returned(x)))
     19 #define LOCKS_EXCLUDED(...) __attribute__ ((locks_excluded(__VA_ARGS__)))
     20 #define EXCLUSIVE_LOCKS_REQUIRED(...) \
     21   __attribute__ ((exclusive_locks_required(__VA_ARGS__)))
     22 #define SHARED_LOCKS_REQUIRED(...) \
     23   __attribute__ ((shared_locks_required(__VA_ARGS__)))
     24 #define NO_THREAD_SAFETY_ANALYSIS  __attribute__ ((no_thread_safety_analysis))
     25 
     26 
     27 class LOCKABLE Mutex {
     28   public:
     29   void Lock()          EXCLUSIVE_LOCK_FUNCTION();
     30   void ReaderLock()    SHARED_LOCK_FUNCTION();
     31   void Unlock()        UNLOCK_FUNCTION();
     32 
     33   bool TryLock()       EXCLUSIVE_TRYLOCK_FUNCTION(true);
     34   bool ReaderTryLock() SHARED_TRYLOCK_FUNCTION(true);
     35 
     36   void AssertHeld()       ASSERT_EXCLUSIVE_LOCK();
     37   void AssertReaderHeld() ASSERT_SHARED_LOCK();
     38 };
     39 
     40 class UnlockableMu{
     41 };
     42 
     43 class MuWrapper {
     44   public:
     45   Mutex mu;
     46   Mutex getMu() {
     47     return mu;
     48   }
     49   Mutex * getMuPointer() {
     50     return μ
     51   }
     52 };
     53 
     54 
     55 class MuDoubleWrapper {
     56   public:
     57   MuWrapper* muWrapper;
     58   MuWrapper* getWrapper() {
     59     return muWrapper;
     60   }
     61 };
     62 
     63 Mutex mu1;
     64 UnlockableMu umu;
     65 Mutex mu2;
     66 MuWrapper muWrapper;
     67 MuDoubleWrapper muDoubleWrapper;
     68 Mutex* muPointer;
     69 Mutex** muDoublePointer = & muPointer;
     70 Mutex& muRef = mu1;
     71 
     72 //---------------------------------------//
     73 // Scoping tests
     74 //--------------------------------------//
     75 
     76 class Foo {
     77   Mutex foomu;
     78   void needLock() EXCLUSIVE_LOCK_FUNCTION(foomu);
     79 };
     80 
     81 class Foo2 {
     82   void needLock() EXCLUSIVE_LOCK_FUNCTION(foomu);
     83   Mutex foomu;
     84 };
     85 
     86 class Bar {
     87  Mutex barmu;
     88  Mutex barmu2 ACQUIRED_AFTER(barmu);
     89 };
     90 
     91 
     92 //-----------------------------------------//
     93 //   No Thread Safety Analysis (noanal)    //
     94 //-----------------------------------------//
     95 
     96 // FIXME: Right now we cannot parse attributes put on function definitions
     97 // We would like to patch this at some point.
     98 
     99 #if !__has_attribute(no_thread_safety_analysis)
    100 #error "Should support no_thread_safety_analysis attribute"
    101 #endif
    102 
    103 void noanal_fun() NO_THREAD_SAFETY_ANALYSIS;
    104 
    105 void noanal_fun_args() __attribute__((no_thread_safety_analysis(1))); // \
    106   // expected-error {{'no_thread_safety_analysis' attribute takes no arguments}}
    107 
    108 int noanal_testfn(int y) NO_THREAD_SAFETY_ANALYSIS;
    109 
    110 int noanal_testfn(int y) {
    111   int x NO_THREAD_SAFETY_ANALYSIS = y; // \
    112     // expected-warning {{'no_thread_safety_analysis' attribute only applies to functions}}
    113   return x;
    114 };
    115 
    116 int noanal_test_var NO_THREAD_SAFETY_ANALYSIS; // \
    117   // expected-warning {{'no_thread_safety_analysis' attribute only applies to functions}}
    118 
    119 class NoanalFoo {
    120  private:
    121   int test_field NO_THREAD_SAFETY_ANALYSIS; // \
    122     // expected-warning {{'no_thread_safety_analysis' attribute only applies to functions}}
    123   void test_method() NO_THREAD_SAFETY_ANALYSIS;
    124 };
    125 
    126 class NO_THREAD_SAFETY_ANALYSIS NoanalTestClass { // \
    127   // expected-warning {{'no_thread_safety_analysis' attribute only applies to functions}}
    128 };
    129 
    130 void noanal_fun_params(int lvar NO_THREAD_SAFETY_ANALYSIS); // \
    131   // expected-warning {{'no_thread_safety_analysis' attribute only applies to functions}}
    132 
    133 
    134 //-----------------------------------------//
    135 //  Guarded Var Attribute (gv)
    136 //-----------------------------------------//
    137 
    138 #if !__has_attribute(guarded_var)
    139 #error "Should support guarded_var attribute"
    140 #endif
    141 
    142 int gv_var_noargs GUARDED_VAR;
    143 
    144 int gv_var_args __attribute__((guarded_var(1))); // \
    145   // expected-error {{'guarded_var' attribute takes no arguments}}
    146 
    147 class GVFoo {
    148  private:
    149   int gv_field_noargs GUARDED_VAR;
    150   int gv_field_args __attribute__((guarded_var(1))); // \
    151     // expected-error {{'guarded_var' attribute takes no arguments}}
    152 };
    153 
    154 class GUARDED_VAR GV { // \
    155   // expected-warning {{'guarded_var' attribute only applies to fields and global variables}}
    156 };
    157 
    158 void gv_function() GUARDED_VAR; // \
    159   // expected-warning {{'guarded_var' attribute only applies to fields and global variables}}
    160 
    161 void gv_function_params(int gv_lvar GUARDED_VAR); // \
    162   // expected-warning {{'guarded_var' attribute only applies to fields and global variables}}
    163 
    164 int gv_testfn(int y){
    165   int x GUARDED_VAR = y; // \
    166     // expected-warning {{'guarded_var' attribute only applies to fields and global variables}}
    167   return x;
    168 }
    169 
    170 //-----------------------------------------//
    171 //   Pt Guarded Var Attribute (pgv)
    172 //-----------------------------------------//
    173 
    174 //FIXME: add support for boost::scoped_ptr<int> fancyptr  and references
    175 
    176 #if !__has_attribute(pt_guarded_var)
    177 #error "Should support pt_guarded_var attribute"
    178 #endif
    179 
    180 int *pgv_pt_var_noargs PT_GUARDED_VAR;
    181 
    182 int pgv_var_noargs PT_GUARDED_VAR; // \
    183     // expected-warning {{'pt_guarded_var' only applies to pointer types; type here is 'int'}}
    184 
    185 class PGVFoo {
    186  private:
    187   int *pt_field_noargs PT_GUARDED_VAR;
    188   int field_noargs PT_GUARDED_VAR; // \
    189     // expected-warning {{'pt_guarded_var' only applies to pointer types; type here is 'int'}}
    190   int *gv_field_args __attribute__((pt_guarded_var(1))); // \
    191     // expected-error {{'pt_guarded_var' attribute takes no arguments}}
    192 };
    193 
    194 class PT_GUARDED_VAR PGV { // \
    195   // expected-warning {{'pt_guarded_var' attribute only applies to fields and global variables}}
    196 };
    197 
    198 int *pgv_var_args __attribute__((pt_guarded_var(1))); // \
    199   // expected-error {{'pt_guarded_var' attribute takes no arguments}}
    200 
    201 
    202 void pgv_function() PT_GUARDED_VAR; // \
    203   // expected-warning {{'pt_guarded_var' attribute only applies to fields and global variables}}
    204 
    205 void pgv_function_params(int *gv_lvar PT_GUARDED_VAR); // \
    206   // expected-warning {{'pt_guarded_var' attribute only applies to fields and global variables}}
    207 
    208 void pgv_testfn(int y){
    209   int *x PT_GUARDED_VAR = new int(0); // \
    210     // expected-warning {{'pt_guarded_var' attribute only applies to fields and global variables}}
    211   delete x;
    212 }
    213 
    214 //-----------------------------------------//
    215 //  Lockable Attribute (l)
    216 //-----------------------------------------//
    217 
    218 //FIXME: In future we may want to add support for structs, ObjC classes, etc.
    219 
    220 #if !__has_attribute(lockable)
    221 #error "Should support lockable attribute"
    222 #endif
    223 
    224 class LOCKABLE LTestClass {
    225 };
    226 
    227 class __attribute__((lockable (1))) LTestClass_args { // \
    228     // expected-error {{'lockable' attribute takes no arguments}}
    229 };
    230 
    231 void l_test_function() LOCKABLE;  // \
    232   // expected-warning {{'lockable' attribute only applies to struct, union or class}}
    233 
    234 int l_testfn(int y) {
    235   int x LOCKABLE = y; // \
    236     // expected-warning {{'lockable' attribute only applies to struct, union or class}}
    237   return x;
    238 }
    239 
    240 int l_test_var LOCKABLE; // \
    241   // expected-warning {{'lockable' attribute only applies to struct, union or class}}
    242 
    243 class LFoo {
    244  private:
    245   int test_field LOCKABLE; // \
    246     // expected-warning {{'lockable' attribute only applies to struct, union or class}}
    247   void test_method() LOCKABLE; // \
    248     // expected-warning {{'lockable' attribute only applies to struct, union or class}}
    249 };
    250 
    251 
    252 void l_function_params(int lvar LOCKABLE); // \
    253   // expected-warning {{'lockable' attribute only applies to struct, union or class}}
    254 
    255 
    256 //-----------------------------------------//
    257 //  Scoped Lockable Attribute (sl)
    258 //-----------------------------------------//
    259 
    260 #if !__has_attribute(scoped_lockable)
    261 #error "Should support scoped_lockable attribute"
    262 #endif
    263 
    264 class SCOPED_LOCKABLE SLTestClass {
    265 };
    266 
    267 class __attribute__((scoped_lockable (1))) SLTestClass_args { // \
    268   // expected-error {{'scoped_lockable' attribute takes no arguments}}
    269 };
    270 
    271 void sl_test_function() SCOPED_LOCKABLE;  // \
    272   // expected-warning {{'scoped_lockable' attribute only applies to struct, union or class}}
    273 
    274 int sl_testfn(int y) {
    275   int x SCOPED_LOCKABLE = y; // \
    276     // expected-warning {{'scoped_lockable' attribute only applies to struct, union or class}}
    277   return x;
    278 }
    279 
    280 int sl_test_var SCOPED_LOCKABLE; // \
    281   // expected-warning {{'scoped_lockable' attribute only applies to struct, union or class}}
    282 
    283 class SLFoo {
    284  private:
    285   int test_field SCOPED_LOCKABLE; // \
    286     // expected-warning {{'scoped_lockable' attribute only applies to struct, union or class}}
    287   void test_method() SCOPED_LOCKABLE; // \
    288     // expected-warning {{'scoped_lockable' attribute only applies to struct, union or class}}
    289 };
    290 
    291 
    292 void sl_function_params(int lvar SCOPED_LOCKABLE); // \
    293   // expected-warning {{'scoped_lockable' attribute only applies to struct, union or class}}
    294 
    295 
    296 //-----------------------------------------//
    297 //  Guarded By Attribute (gb)
    298 //-----------------------------------------//
    299 
    300 // FIXME: Eventually, would we like this attribute to take more than 1 arg?
    301 
    302 #if !__has_attribute(guarded_by)
    303 #error "Should support guarded_by attribute"
    304 #endif
    305 
    306 //1. Check applied to the right types & argument number
    307 
    308 int gb_var_arg GUARDED_BY(mu1);
    309 
    310 int gb_non_ascii GUARDED_BY(L"wide"); // expected-warning {{ignoring 'guarded_by' attribute because its argument is invalid}}
    311 
    312 int gb_var_args __attribute__((guarded_by(mu1, mu2))); // \
    313   // expected-error {{'guarded_by' attribute takes one argument}}
    314 
    315 int gb_var_noargs __attribute__((guarded_by)); // \
    316   // expected-error {{'guarded_by' attribute takes one argument}}
    317 
    318 class GBFoo {
    319  private:
    320   int gb_field_noargs __attribute__((guarded_by)); // \
    321     // expected-error {{'guarded_by' attribute takes one argument}}
    322   int gb_field_args GUARDED_BY(mu1);
    323 };
    324 
    325 class GUARDED_BY(mu1) GB { // \
    326   // expected-warning {{'guarded_by' attribute only applies to fields and global variables}}
    327 };
    328 
    329 void gb_function() GUARDED_BY(mu1); // \
    330   // expected-warning {{'guarded_by' attribute only applies to fields and global variables}}
    331 
    332 void gb_function_params(int gv_lvar GUARDED_BY(mu1)); // \
    333   // expected-warning {{'guarded_by' attribute only applies to fields and global variables}}
    334 
    335 int gb_testfn(int y){
    336   int x GUARDED_BY(mu1) = y; // \
    337     // expected-warning {{'guarded_by' attribute only applies to fields and global variables}}
    338   return x;
    339 }
    340 
    341 //2. Check argument parsing.
    342 
    343 // legal attribute arguments
    344 int gb_var_arg_1 GUARDED_BY(muWrapper.mu);
    345 int gb_var_arg_2 GUARDED_BY(muDoubleWrapper.muWrapper->mu);
    346 int gb_var_arg_3 GUARDED_BY(muWrapper.getMu());
    347 int gb_var_arg_4 GUARDED_BY(*muWrapper.getMuPointer());
    348 int gb_var_arg_5 GUARDED_BY(&mu1);
    349 int gb_var_arg_6 GUARDED_BY(muRef);
    350 int gb_var_arg_7 GUARDED_BY(muDoubleWrapper.getWrapper()->getMu());
    351 int gb_var_arg_8 GUARDED_BY(muPointer);
    352 
    353 
    354 // illegal attribute arguments
    355 int gb_var_arg_bad_1 GUARDED_BY(1); // \
    356   // expected-warning {{'guarded_by' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'int'}}
    357 int gb_var_arg_bad_2 GUARDED_BY("mu"); // \
    358   // expected-warning {{ignoring 'guarded_by' attribute because its argument is invalid}}
    359 int gb_var_arg_bad_3 GUARDED_BY(muDoublePointer); // \
    360   // expected-warning {{'guarded_by' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'Mutex **'}}
    361 int gb_var_arg_bad_4 GUARDED_BY(umu); // \
    362   // expected-warning {{'guarded_by' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'UnlockableMu'}}
    363 
    364 //3.
    365 // Thread Safety analysis tests
    366 
    367 
    368 //-----------------------------------------//
    369 //  Pt Guarded By Attribute (pgb)
    370 //-----------------------------------------//
    371 
    372 #if !__has_attribute(pt_guarded_by)
    373 #error "Should support pt_guarded_by attribute"
    374 #endif
    375 
    376 //1. Check applied to the right types & argument number
    377 
    378 int *pgb_var_noargs __attribute__((pt_guarded_by)); // \
    379   // expected-error {{'pt_guarded_by' attribute takes one argument}}
    380 
    381 int *pgb_ptr_var_arg PT_GUARDED_BY(mu1);
    382 
    383 int *pgb_ptr_var_args __attribute__((pt_guarded_by(mu1, mu2))); // \
    384   // expected-error {{'pt_guarded_by' attribute takes one argument}}
    385 
    386 int pgb_var_args PT_GUARDED_BY(mu1); // \
    387   // expected-warning {{'pt_guarded_by' only applies to pointer types; type here is 'int'}}
    388 
    389 class PGBFoo {
    390  private:
    391   int *pgb_field_noargs __attribute__((pt_guarded_by)); // \
    392     // expected-error {{'pt_guarded_by' attribute takes one argument}}
    393   int *pgb_field_args PT_GUARDED_BY(mu1);
    394 };
    395 
    396 class PT_GUARDED_BY(mu1) PGB { // \
    397   // expected-warning {{'pt_guarded_by' attribute only applies to fields and global variables}}
    398 };
    399 
    400 void pgb_function() PT_GUARDED_BY(mu1); // \
    401   // expected-warning {{'pt_guarded_by' attribute only applies to fields and global variables}}
    402 
    403 void pgb_function_params(int gv_lvar PT_GUARDED_BY(mu1)); // \
    404   // expected-warning {{'pt_guarded_by' attribute only applies to fields and global variables}}
    405 
    406 void pgb_testfn(int y){
    407   int *x PT_GUARDED_BY(mu1) = new int(0); // \
    408     // expected-warning {{'pt_guarded_by' attribute only applies to fields and global variables}}
    409   delete x;
    410 }
    411 
    412 //2. Check argument parsing.
    413 
    414 // legal attribute arguments
    415 int * pgb_var_arg_1 PT_GUARDED_BY(muWrapper.mu);
    416 int * pgb_var_arg_2 PT_GUARDED_BY(muDoubleWrapper.muWrapper->mu);
    417 int * pgb_var_arg_3 PT_GUARDED_BY(muWrapper.getMu());
    418 int * pgb_var_arg_4 PT_GUARDED_BY(*muWrapper.getMuPointer());
    419 int * pgb_var_arg_5 PT_GUARDED_BY(&mu1);
    420 int * pgb_var_arg_6 PT_GUARDED_BY(muRef);
    421 int * pgb_var_arg_7 PT_GUARDED_BY(muDoubleWrapper.getWrapper()->getMu());
    422 int * pgb_var_arg_8 PT_GUARDED_BY(muPointer);
    423 
    424 
    425 // illegal attribute arguments
    426 int * pgb_var_arg_bad_1 PT_GUARDED_BY(1); // \
    427   // expected-warning {{'pt_guarded_by' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'int'}}
    428 int * pgb_var_arg_bad_2 PT_GUARDED_BY("mu"); // \
    429   // expected-warning {{ignoring 'pt_guarded_by' attribute because its argument is invalid}}
    430 int * pgb_var_arg_bad_3 PT_GUARDED_BY(muDoublePointer); // \
    431   // expected-warning {{'pt_guarded_by' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'Mutex **'}}
    432 int * pgb_var_arg_bad_4 PT_GUARDED_BY(umu); // \
    433   // expected-warning {{'pt_guarded_by' attribute requires arguments whose type is annotated with 'capability' attribute}}
    434 
    435 
    436 //-----------------------------------------//
    437 //  Acquired After (aa)
    438 //-----------------------------------------//
    439 
    440 // FIXME: Would we like this attribute to take more than 1 arg?
    441 
    442 #if !__has_attribute(acquired_after)
    443 #error "Should support acquired_after attribute"
    444 #endif
    445 
    446 Mutex mu_aa ACQUIRED_AFTER(mu1);
    447 
    448 Mutex aa_var_noargs __attribute__((acquired_after)); // \
    449   // expected-error {{'acquired_after' attribute takes at least 1 argument}}
    450 
    451 class AAFoo {
    452  private:
    453   Mutex aa_field_noargs __attribute__((acquired_after)); // \
    454     // expected-error {{'acquired_after' attribute takes at least 1 argument}}
    455   Mutex aa_field_args ACQUIRED_AFTER(mu1);
    456 };
    457 
    458 class ACQUIRED_AFTER(mu1) AA { // \
    459   // expected-warning {{'acquired_after' attribute only applies to fields and global variables}}
    460 };
    461 
    462 void aa_function() ACQUIRED_AFTER(mu1); // \
    463   // expected-warning {{'acquired_after' attribute only applies to fields and global variables}}
    464 
    465 void aa_function_params(int gv_lvar ACQUIRED_AFTER(mu1)); // \
    466   // expected-warning {{'acquired_after' attribute only applies to fields and global variables}}
    467 
    468 void aa_testfn(int y){
    469   Mutex x ACQUIRED_AFTER(mu1) = Mutex(); // \
    470     // expected-warning {{'acquired_after' attribute only applies to fields and global variables}}
    471 }
    472 
    473 //Check argument parsing.
    474 
    475 // legal attribute arguments
    476 Mutex aa_var_arg_1 ACQUIRED_AFTER(muWrapper.mu);
    477 Mutex aa_var_arg_2 ACQUIRED_AFTER(muDoubleWrapper.muWrapper->mu);
    478 Mutex aa_var_arg_3 ACQUIRED_AFTER(muWrapper.getMu());
    479 Mutex aa_var_arg_4 ACQUIRED_AFTER(*muWrapper.getMuPointer());
    480 Mutex aa_var_arg_5 ACQUIRED_AFTER(&mu1);
    481 Mutex aa_var_arg_6 ACQUIRED_AFTER(muRef);
    482 Mutex aa_var_arg_7 ACQUIRED_AFTER(muDoubleWrapper.getWrapper()->getMu());
    483 Mutex aa_var_arg_8 ACQUIRED_AFTER(muPointer);
    484 
    485 
    486 // illegal attribute arguments
    487 Mutex aa_var_arg_bad_1 ACQUIRED_AFTER(1); // \
    488   // expected-warning {{'acquired_after' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'int'}}
    489 Mutex aa_var_arg_bad_2 ACQUIRED_AFTER("mu"); // \
    490   // expected-warning {{ignoring 'acquired_after' attribute because its argument is invalid}}
    491 Mutex aa_var_arg_bad_3 ACQUIRED_AFTER(muDoublePointer); // \
    492   // expected-warning {{'acquired_after' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'Mutex **'}}
    493 Mutex aa_var_arg_bad_4 ACQUIRED_AFTER(umu); // \
    494   // expected-warning {{'acquired_after' attribute requires arguments whose type is annotated with 'capability' attribute}}
    495 UnlockableMu aa_var_arg_bad_5 ACQUIRED_AFTER(mu_aa); // \
    496   // expected-warning {{'acquired_after' attribute can only be applied in a context annotated with 'capability("mutex")' attribute}}
    497 
    498 //-----------------------------------------//
    499 //  Acquired Before (ab)
    500 //-----------------------------------------//
    501 
    502 #if !__has_attribute(acquired_before)
    503 #error "Should support acquired_before attribute"
    504 #endif
    505 
    506 Mutex mu_ab ACQUIRED_BEFORE(mu1);
    507 
    508 Mutex ab_var_noargs __attribute__((acquired_before)); // \
    509   // expected-error {{'acquired_before' attribute takes at least 1 argument}}
    510 
    511 class ABFoo {
    512  private:
    513   Mutex ab_field_noargs __attribute__((acquired_before)); // \
    514     // expected-error {{'acquired_before' attribute takes at least 1 argument}}
    515   Mutex ab_field_args ACQUIRED_BEFORE(mu1);
    516 };
    517 
    518 class ACQUIRED_BEFORE(mu1) AB { // \
    519   // expected-warning {{'acquired_before' attribute only applies to fields and global variables}}
    520 };
    521 
    522 void ab_function() ACQUIRED_BEFORE(mu1); // \
    523   // expected-warning {{'acquired_before' attribute only applies to fields and global variables}}
    524 
    525 void ab_function_params(int gv_lvar ACQUIRED_BEFORE(mu1)); // \
    526   // expected-warning {{'acquired_before' attribute only applies to fields and global variables}}
    527 
    528 void ab_testfn(int y){
    529   Mutex x ACQUIRED_BEFORE(mu1) = Mutex(); // \
    530     // expected-warning {{'acquired_before' attribute only applies to fields and global variables}}
    531 }
    532 
    533 // Note: illegal int ab_int ACQUIRED_BEFORE(mu1) will
    534 // be taken care of by warnings that ab__int is not lockable.
    535 
    536 //Check argument parsing.
    537 
    538 // legal attribute arguments
    539 Mutex ab_var_arg_1 ACQUIRED_BEFORE(muWrapper.mu);
    540 Mutex ab_var_arg_2 ACQUIRED_BEFORE(muDoubleWrapper.muWrapper->mu);
    541 Mutex ab_var_arg_3 ACQUIRED_BEFORE(muWrapper.getMu());
    542 Mutex ab_var_arg_4 ACQUIRED_BEFORE(*muWrapper.getMuPointer());
    543 Mutex ab_var_arg_5 ACQUIRED_BEFORE(&mu1);
    544 Mutex ab_var_arg_6 ACQUIRED_BEFORE(muRef);
    545 Mutex ab_var_arg_7 ACQUIRED_BEFORE(muDoubleWrapper.getWrapper()->getMu());
    546 Mutex ab_var_arg_8 ACQUIRED_BEFORE(muPointer);
    547 
    548 
    549 // illegal attribute arguments
    550 Mutex ab_var_arg_bad_1 ACQUIRED_BEFORE(1); // \
    551   // expected-warning {{'acquired_before' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'int'}}
    552 Mutex ab_var_arg_bad_2 ACQUIRED_BEFORE("mu"); // \
    553   // expected-warning {{ignoring 'acquired_before' attribute because its argument is invalid}}
    554 Mutex ab_var_arg_bad_3 ACQUIRED_BEFORE(muDoublePointer); // \
    555   // expected-warning {{'acquired_before' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'Mutex **'}}
    556 Mutex ab_var_arg_bad_4 ACQUIRED_BEFORE(umu); // \
    557   // expected-warning {{'acquired_before' attribute requires arguments whose type is annotated with 'capability' attribute}}
    558 UnlockableMu ab_var_arg_bad_5 ACQUIRED_BEFORE(mu_ab); // \
    559   // expected-warning {{'acquired_before' attribute can only be applied in a context annotated with 'capability("mutex")' attribute}}
    560 
    561 
    562 //-----------------------------------------//
    563 //  Exclusive Lock Function (elf)
    564 //-----------------------------------------//
    565 
    566 #if !__has_attribute(exclusive_lock_function)
    567 #error "Should support exclusive_lock_function attribute"
    568 #endif
    569 
    570 // takes zero or more arguments, all locks (vars/fields)
    571 
    572 void elf_function() EXCLUSIVE_LOCK_FUNCTION();
    573 
    574 void elf_function_args() EXCLUSIVE_LOCK_FUNCTION(mu1, mu2);
    575 
    576 int elf_testfn(int y) EXCLUSIVE_LOCK_FUNCTION();
    577 
    578 int elf_testfn(int y) {
    579   int x EXCLUSIVE_LOCK_FUNCTION() = y; // \
    580     // expected-warning {{'exclusive_lock_function' attribute only applies to functions}}
    581   return x;
    582 };
    583 
    584 int elf_test_var EXCLUSIVE_LOCK_FUNCTION(); // \
    585   // expected-warning {{'exclusive_lock_function' attribute only applies to functions}}
    586 
    587 class ElfFoo {
    588  private:
    589   int test_field EXCLUSIVE_LOCK_FUNCTION(); // \
    590     // expected-warning {{'exclusive_lock_function' attribute only applies to functions}}
    591   void test_method() EXCLUSIVE_LOCK_FUNCTION();
    592 };
    593 
    594 class EXCLUSIVE_LOCK_FUNCTION() ElfTestClass { // \
    595   // expected-warning {{'exclusive_lock_function' attribute only applies to functions}}
    596 };
    597 
    598 void elf_fun_params(int lvar EXCLUSIVE_LOCK_FUNCTION()); // \
    599   // expected-warning {{'exclusive_lock_function' attribute only applies to functions}}
    600 
    601 // Check argument parsing.
    602 
    603 // legal attribute arguments
    604 int elf_function_1() EXCLUSIVE_LOCK_FUNCTION(muWrapper.mu);
    605 int elf_function_2() EXCLUSIVE_LOCK_FUNCTION(muDoubleWrapper.muWrapper->mu);
    606 int elf_function_3() EXCLUSIVE_LOCK_FUNCTION(muWrapper.getMu());
    607 int elf_function_4() EXCLUSIVE_LOCK_FUNCTION(*muWrapper.getMuPointer());
    608 int elf_function_5() EXCLUSIVE_LOCK_FUNCTION(&mu1);
    609 int elf_function_6() EXCLUSIVE_LOCK_FUNCTION(muRef);
    610 int elf_function_7() EXCLUSIVE_LOCK_FUNCTION(muDoubleWrapper.getWrapper()->getMu());
    611 int elf_function_8() EXCLUSIVE_LOCK_FUNCTION(muPointer);
    612 int elf_function_9(Mutex x) EXCLUSIVE_LOCK_FUNCTION(1);
    613 int elf_function_9(Mutex x, Mutex y) EXCLUSIVE_LOCK_FUNCTION(1,2);
    614 
    615 
    616 // illegal attribute arguments
    617 int elf_function_bad_2() EXCLUSIVE_LOCK_FUNCTION("mu"); // \
    618   // expected-warning {{ignoring 'exclusive_lock_function' attribute because its argument is invalid}}
    619 int elf_function_bad_3() EXCLUSIVE_LOCK_FUNCTION(muDoublePointer); // \
    620   // expected-warning {{'exclusive_lock_function' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'Mutex **'}}
    621 int elf_function_bad_4() EXCLUSIVE_LOCK_FUNCTION(umu); // \
    622   // expected-warning {{'exclusive_lock_function' attribute requires arguments whose type is annotated with 'capability' attribute}}
    623 
    624 int elf_function_bad_1() EXCLUSIVE_LOCK_FUNCTION(1); // \
    625   // expected-error {{'exclusive_lock_function' attribute parameter 1 is out of bounds: no parameters to index into}}
    626 int elf_function_bad_5(Mutex x) EXCLUSIVE_LOCK_FUNCTION(0); // \
    627   // expected-error {{'exclusive_lock_function' attribute parameter 1 is out of bounds: can only be 1, since there is one parameter}}
    628 int elf_function_bad_6(Mutex x, Mutex y) EXCLUSIVE_LOCK_FUNCTION(0); // \
    629   // expected-error {{'exclusive_lock_function' attribute parameter 1 is out of bounds: must be between 1 and 2}}
    630 int elf_function_bad_7() EXCLUSIVE_LOCK_FUNCTION(0); // \
    631   // expected-error {{'exclusive_lock_function' attribute parameter 1 is out of bounds: no parameters to index into}}
    632 
    633 
    634 //-----------------------------------------//
    635 //  Shared Lock Function (slf)
    636 //-----------------------------------------//
    637 
    638 #if !__has_attribute(shared_lock_function)
    639 #error "Should support shared_lock_function attribute"
    640 #endif
    641 
    642 // takes zero or more arguments, all locks (vars/fields)
    643 
    644 void slf_function() SHARED_LOCK_FUNCTION();
    645 
    646 void slf_function_args() SHARED_LOCK_FUNCTION(mu1, mu2);
    647 
    648 int slf_testfn(int y) SHARED_LOCK_FUNCTION();
    649 
    650 int slf_testfn(int y) {
    651   int x SHARED_LOCK_FUNCTION() = y; // \
    652     // expected-warning {{'shared_lock_function' attribute only applies to functions}}
    653   return x;
    654 };
    655 
    656 int slf_test_var SHARED_LOCK_FUNCTION(); // \
    657   // expected-warning {{'shared_lock_function' attribute only applies to functions}}
    658 
    659 void slf_fun_params(int lvar SHARED_LOCK_FUNCTION()); // \
    660   // expected-warning {{'shared_lock_function' attribute only applies to functions}}
    661 
    662 class SlfFoo {
    663  private:
    664   int test_field SHARED_LOCK_FUNCTION(); // \
    665     // expected-warning {{'shared_lock_function' attribute only applies to functions}}
    666   void test_method() SHARED_LOCK_FUNCTION();
    667 };
    668 
    669 class SHARED_LOCK_FUNCTION() SlfTestClass { // \
    670   // expected-warning {{'shared_lock_function' attribute only applies to functions}}
    671 };
    672 
    673 // Check argument parsing.
    674 
    675 // legal attribute arguments
    676 int slf_function_1() SHARED_LOCK_FUNCTION(muWrapper.mu);
    677 int slf_function_2() SHARED_LOCK_FUNCTION(muDoubleWrapper.muWrapper->mu);
    678 int slf_function_3() SHARED_LOCK_FUNCTION(muWrapper.getMu());
    679 int slf_function_4() SHARED_LOCK_FUNCTION(*muWrapper.getMuPointer());
    680 int slf_function_5() SHARED_LOCK_FUNCTION(&mu1);
    681 int slf_function_6() SHARED_LOCK_FUNCTION(muRef);
    682 int slf_function_7() SHARED_LOCK_FUNCTION(muDoubleWrapper.getWrapper()->getMu());
    683 int slf_function_8() SHARED_LOCK_FUNCTION(muPointer);
    684 int slf_function_9(Mutex x) SHARED_LOCK_FUNCTION(1);
    685 int slf_function_9(Mutex x, Mutex y) SHARED_LOCK_FUNCTION(1,2);
    686 
    687 
    688 // illegal attribute arguments
    689 int slf_function_bad_2() SHARED_LOCK_FUNCTION("mu"); // \
    690   // expected-warning {{ignoring 'shared_lock_function' attribute because its argument is invalid}}
    691 int slf_function_bad_3() SHARED_LOCK_FUNCTION(muDoublePointer); // \
    692   // expected-warning {{'shared_lock_function' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'Mutex **'}}
    693 int slf_function_bad_4() SHARED_LOCK_FUNCTION(umu); // \
    694   // expected-warning {{'shared_lock_function' attribute requires arguments whose type is annotated with 'capability' attribute}}
    695 
    696 int slf_function_bad_1() SHARED_LOCK_FUNCTION(1); // \
    697   // expected-error {{'shared_lock_function' attribute parameter 1 is out of bounds: no parameters to index into}}
    698 int slf_function_bad_5(Mutex x) SHARED_LOCK_FUNCTION(0); // \
    699   // expected-error {{'shared_lock_function' attribute parameter 1 is out of bounds: can only be 1, since there is one parameter}}
    700 int slf_function_bad_6(Mutex x, Mutex y) SHARED_LOCK_FUNCTION(0); // \
    701   // expected-error {{'shared_lock_function' attribute parameter 1 is out of bounds: must be between 1 and 2}}
    702 int slf_function_bad_7() SHARED_LOCK_FUNCTION(0); // \
    703   // expected-error {{'shared_lock_function' attribute parameter 1 is out of bounds: no parameters to index into}}
    704 
    705 
    706 //-----------------------------------------//
    707 //  Exclusive TryLock Function (etf)
    708 //-----------------------------------------//
    709 
    710 #if !__has_attribute(exclusive_trylock_function)
    711 #error "Should support exclusive_trylock_function attribute"
    712 #endif
    713 
    714 // takes a mandatory boolean or integer argument specifying the retval
    715 // plus an optional list of locks (vars/fields)
    716 
    717 void etf_function() __attribute__((exclusive_trylock_function));  // \
    718   // expected-error {{'exclusive_trylock_function' attribute takes at least 1 argument}}
    719 
    720 void etf_function_args() EXCLUSIVE_TRYLOCK_FUNCTION(1, mu2);
    721 
    722 void etf_function_arg() EXCLUSIVE_TRYLOCK_FUNCTION(1);
    723 
    724 int etf_testfn(int y) EXCLUSIVE_TRYLOCK_FUNCTION(1);
    725 
    726 int etf_testfn(int y) {
    727   int x EXCLUSIVE_TRYLOCK_FUNCTION(1) = y; // \
    728     // expected-warning {{'exclusive_trylock_function' attribute only applies to functions}}
    729   return x;
    730 };
    731 
    732 int etf_test_var EXCLUSIVE_TRYLOCK_FUNCTION(1); // \
    733   // expected-warning {{'exclusive_trylock_function' attribute only applies to functions}}
    734 
    735 class EtfFoo {
    736  private:
    737   int test_field EXCLUSIVE_TRYLOCK_FUNCTION(1); // \
    738     // expected-warning {{'exclusive_trylock_function' attribute only applies to functions}}
    739   void test_method() EXCLUSIVE_TRYLOCK_FUNCTION(1);
    740 };
    741 
    742 class EXCLUSIVE_TRYLOCK_FUNCTION(1) EtfTestClass { // \
    743   // expected-warning {{'exclusive_trylock_function' attribute only applies to functions}}
    744 };
    745 
    746 void etf_fun_params(int lvar EXCLUSIVE_TRYLOCK_FUNCTION(1)); // \
    747   // expected-warning {{'exclusive_trylock_function' attribute only applies to functions}}
    748 
    749 // Check argument parsing.
    750 
    751 // legal attribute arguments
    752 int etf_function_1() EXCLUSIVE_TRYLOCK_FUNCTION(1, muWrapper.mu);
    753 int etf_function_2() EXCLUSIVE_TRYLOCK_FUNCTION(1, muDoubleWrapper.muWrapper->mu);
    754 int etf_function_3() EXCLUSIVE_TRYLOCK_FUNCTION(1, muWrapper.getMu());
    755 int etf_function_4() EXCLUSIVE_TRYLOCK_FUNCTION(1, *muWrapper.getMuPointer());
    756 int etf_function_5() EXCLUSIVE_TRYLOCK_FUNCTION(1, &mu1);
    757 int etf_function_6() EXCLUSIVE_TRYLOCK_FUNCTION(1, muRef);
    758 int etf_function_7() EXCLUSIVE_TRYLOCK_FUNCTION(1, muDoubleWrapper.getWrapper()->getMu());
    759 int etf_functetfn_8() EXCLUSIVE_TRYLOCK_FUNCTION(1, muPointer);
    760 int etf_function_9() EXCLUSIVE_TRYLOCK_FUNCTION(true);
    761 
    762 
    763 // illegal attribute arguments
    764 int etf_function_bad_1() EXCLUSIVE_TRYLOCK_FUNCTION(mu1); // \
    765   // expected-error {{'exclusive_trylock_function' attribute requires parameter 1 to be int or bool}}
    766 int etf_function_bad_2() EXCLUSIVE_TRYLOCK_FUNCTION("mu"); // \
    767   // expected-error {{'exclusive_trylock_function' attribute requires parameter 1 to be int or bool}}
    768 int etf_function_bad_3() EXCLUSIVE_TRYLOCK_FUNCTION(muDoublePointer); // \
    769   // expected-error {{'exclusive_trylock_function' attribute requires parameter 1 to be int or bool}}
    770 
    771 int etf_function_bad_4() EXCLUSIVE_TRYLOCK_FUNCTION(1, "mu"); // \
    772   // expected-warning {{ignoring 'exclusive_trylock_function' attribute because its argument is invalid}}
    773 int etf_function_bad_5() EXCLUSIVE_TRYLOCK_FUNCTION(1, muDoublePointer); // \
    774   // expected-warning {{'exclusive_trylock_function' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'Mutex **'}}
    775 int etf_function_bad_6() EXCLUSIVE_TRYLOCK_FUNCTION(1, umu); // \
    776   // expected-warning {{'exclusive_trylock_function' attribute requires arguments whose type is annotated with 'capability' attribute}}
    777 
    778 
    779 //-----------------------------------------//
    780 //  Shared TryLock Function (stf)
    781 //-----------------------------------------//
    782 
    783 #if !__has_attribute(shared_trylock_function)
    784 #error "Should support shared_trylock_function attribute"
    785 #endif
    786 
    787 // takes a mandatory boolean or integer argument specifying the retval
    788 // plus an optional list of locks (vars/fields)
    789 
    790 void stf_function() __attribute__((shared_trylock_function));  // \
    791   // expected-error {{'shared_trylock_function' attribute takes at least 1 argument}}
    792 
    793 void stf_function_args() SHARED_TRYLOCK_FUNCTION(1, mu2);
    794 
    795 void stf_function_arg() SHARED_TRYLOCK_FUNCTION(1);
    796 
    797 int stf_testfn(int y) SHARED_TRYLOCK_FUNCTION(1);
    798 
    799 int stf_testfn(int y) {
    800   int x SHARED_TRYLOCK_FUNCTION(1) = y; // \
    801     // expected-warning {{'shared_trylock_function' attribute only applies to functions}}
    802   return x;
    803 };
    804 
    805 int stf_test_var SHARED_TRYLOCK_FUNCTION(1); // \
    806   // expected-warning {{'shared_trylock_function' attribute only applies to functions}}
    807 
    808 void stf_fun_params(int lvar SHARED_TRYLOCK_FUNCTION(1)); // \
    809   // expected-warning {{'shared_trylock_function' attribute only applies to functions}}
    810 
    811 
    812 class StfFoo {
    813  private:
    814   int test_field SHARED_TRYLOCK_FUNCTION(1); // \
    815     // expected-warning {{'shared_trylock_function' attribute only applies to functions}}
    816   void test_method() SHARED_TRYLOCK_FUNCTION(1);
    817 };
    818 
    819 class SHARED_TRYLOCK_FUNCTION(1) StfTestClass { // \
    820     // expected-warning {{'shared_trylock_function' attribute only applies to functions}}
    821 };
    822 
    823 // Check argument parsing.
    824 
    825 // legal attribute arguments
    826 int stf_function_1() SHARED_TRYLOCK_FUNCTION(1, muWrapper.mu);
    827 int stf_function_2() SHARED_TRYLOCK_FUNCTION(1, muDoubleWrapper.muWrapper->mu);
    828 int stf_function_3() SHARED_TRYLOCK_FUNCTION(1, muWrapper.getMu());
    829 int stf_function_4() SHARED_TRYLOCK_FUNCTION(1, *muWrapper.getMuPointer());
    830 int stf_function_5() SHARED_TRYLOCK_FUNCTION(1, &mu1);
    831 int stf_function_6() SHARED_TRYLOCK_FUNCTION(1, muRef);
    832 int stf_function_7() SHARED_TRYLOCK_FUNCTION(1, muDoubleWrapper.getWrapper()->getMu());
    833 int stf_function_8() SHARED_TRYLOCK_FUNCTION(1, muPointer);
    834 int stf_function_9() SHARED_TRYLOCK_FUNCTION(true);
    835 
    836 
    837 // illegal attribute arguments
    838 int stf_function_bad_1() SHARED_TRYLOCK_FUNCTION(mu1); // \
    839   // expected-error {{'shared_trylock_function' attribute requires parameter 1 to be int or bool}}
    840 int stf_function_bad_2() SHARED_TRYLOCK_FUNCTION("mu"); // \
    841   // expected-error {{'shared_trylock_function' attribute requires parameter 1 to be int or bool}}
    842 int stf_function_bad_3() SHARED_TRYLOCK_FUNCTION(muDoublePointer); // \
    843   // expected-error {{'shared_trylock_function' attribute requires parameter 1 to be int or bool}}
    844 
    845 int stf_function_bad_4() SHARED_TRYLOCK_FUNCTION(1, "mu"); // \
    846   // expected-warning {{ignoring 'shared_trylock_function' attribute because its argument is invalid}}
    847 int stf_function_bad_5() SHARED_TRYLOCK_FUNCTION(1, muDoublePointer); // \
    848   // expected-warning {{'shared_trylock_function' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'Mutex **'}}
    849 int stf_function_bad_6() SHARED_TRYLOCK_FUNCTION(1, umu); // \
    850   // expected-warning {{'shared_trylock_function' attribute requires arguments whose type is annotated with 'capability' attribute}}
    851 
    852 
    853 //-----------------------------------------//
    854 //  Unlock Function (uf)
    855 //-----------------------------------------//
    856 
    857 #if !__has_attribute(unlock_function)
    858 #error "Should support unlock_function attribute"
    859 #endif
    860 
    861 // takes zero or more arguments, all locks (vars/fields)
    862 
    863 void uf_function() UNLOCK_FUNCTION();
    864 
    865 void uf_function_args() UNLOCK_FUNCTION(mu1, mu2);
    866 
    867 int uf_testfn(int y) UNLOCK_FUNCTION();
    868 
    869 int uf_testfn(int y) {
    870   int x UNLOCK_FUNCTION() = y; // \
    871     // expected-warning {{'unlock_function' attribute only applies to functions}}
    872   return x;
    873 };
    874 
    875 int uf_test_var UNLOCK_FUNCTION(); // \
    876   // expected-warning {{'unlock_function' attribute only applies to functions}}
    877 
    878 class UfFoo {
    879  private:
    880   int test_field UNLOCK_FUNCTION(); // \
    881     // expected-warning {{'unlock_function' attribute only applies to functions}}
    882   void test_method() UNLOCK_FUNCTION();
    883 };
    884 
    885 class NO_THREAD_SAFETY_ANALYSIS UfTestClass { // \
    886   // expected-warning {{'no_thread_safety_analysis' attribute only applies to functions}}
    887 };
    888 
    889 void uf_fun_params(int lvar UNLOCK_FUNCTION()); // \
    890   // expected-warning {{'unlock_function' attribute only applies to functions}}
    891 
    892 // Check argument parsing.
    893 
    894 // legal attribute arguments
    895 int uf_function_1() UNLOCK_FUNCTION(muWrapper.mu);
    896 int uf_function_2() UNLOCK_FUNCTION(muDoubleWrapper.muWrapper->mu);
    897 int uf_function_3() UNLOCK_FUNCTION(muWrapper.getMu());
    898 int uf_function_4() UNLOCK_FUNCTION(*muWrapper.getMuPointer());
    899 int uf_function_5() UNLOCK_FUNCTION(&mu1);
    900 int uf_function_6() UNLOCK_FUNCTION(muRef);
    901 int uf_function_7() UNLOCK_FUNCTION(muDoubleWrapper.getWrapper()->getMu());
    902 int uf_function_8() UNLOCK_FUNCTION(muPointer);
    903 int uf_function_9(Mutex x) UNLOCK_FUNCTION(1);
    904 int uf_function_9(Mutex x, Mutex y) UNLOCK_FUNCTION(1,2);
    905 
    906 
    907 // illegal attribute arguments
    908 int uf_function_bad_2() UNLOCK_FUNCTION("mu"); // \
    909   // expected-warning {{ignoring 'unlock_function' attribute because its argument is invalid}}
    910 int uf_function_bad_3() UNLOCK_FUNCTION(muDoublePointer); // \
    911   // expected-warning {{'unlock_function' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'Mutex **'}}
    912 int uf_function_bad_4() UNLOCK_FUNCTION(umu); // \
    913   // expected-warning {{'unlock_function' attribute requires arguments whose type is annotated with 'capability' attribute}}
    914 
    915 int uf_function_bad_1() UNLOCK_FUNCTION(1); // \
    916   // expected-error {{'unlock_function' attribute parameter 1 is out of bounds: no parameters to index into}}
    917 int uf_function_bad_5(Mutex x) UNLOCK_FUNCTION(0); // \
    918   // expected-error {{'unlock_function' attribute parameter 1 is out of bounds: can only be 1, since there is one parameter}}
    919 int uf_function_bad_6(Mutex x, Mutex y) UNLOCK_FUNCTION(0); // \
    920   // expected-error {{'unlock_function' attribute parameter 1 is out of bounds: must be between 1 and 2}}
    921 int uf_function_bad_7() UNLOCK_FUNCTION(0); // \
    922   // expected-error {{'unlock_function' attribute parameter 1 is out of bounds: no parameters to index into}}
    923 
    924 
    925 //-----------------------------------------//
    926 //  Lock Returned (lr)
    927 //-----------------------------------------//
    928 
    929 #if !__has_attribute(lock_returned)
    930 #error "Should support lock_returned attribute"
    931 #endif
    932 
    933 // Takes exactly one argument, a var/field
    934 
    935 void lr_function() __attribute__((lock_returned)); // \
    936   // expected-error {{'lock_returned' attribute takes one argument}}
    937 
    938 void lr_function_arg() LOCK_RETURNED(mu1);
    939 
    940 void lr_function_args() __attribute__((lock_returned(mu1, mu2))); // \
    941   // expected-error {{'lock_returned' attribute takes one argument}}
    942 
    943 int lr_testfn(int y) LOCK_RETURNED(mu1);
    944 
    945 int lr_testfn(int y) {
    946   int x LOCK_RETURNED(mu1) = y; // \
    947     // expected-warning {{'lock_returned' attribute only applies to functions}}
    948   return x;
    949 };
    950 
    951 int lr_test_var LOCK_RETURNED(mu1); // \
    952   // expected-warning {{'lock_returned' attribute only applies to functions}}
    953 
    954 void lr_fun_params(int lvar LOCK_RETURNED(mu1)); // \
    955   // expected-warning {{'lock_returned' attribute only applies to functions}}
    956 
    957 class LrFoo {
    958  private:
    959   int test_field LOCK_RETURNED(mu1); // \
    960     // expected-warning {{'lock_returned' attribute only applies to functions}}
    961   void test_method() LOCK_RETURNED(mu1);
    962 };
    963 
    964 class LOCK_RETURNED(mu1) LrTestClass { // \
    965     // expected-warning {{'lock_returned' attribute only applies to functions}}
    966 };
    967 
    968 // Check argument parsing.
    969 
    970 // legal attribute arguments
    971 int lr_function_1() LOCK_RETURNED(muWrapper.mu);
    972 int lr_function_2() LOCK_RETURNED(muDoubleWrapper.muWrapper->mu);
    973 int lr_function_3() LOCK_RETURNED(muWrapper.getMu());
    974 int lr_function_4() LOCK_RETURNED(*muWrapper.getMuPointer());
    975 int lr_function_5() LOCK_RETURNED(&mu1);
    976 int lr_function_6() LOCK_RETURNED(muRef);
    977 int lr_function_7() LOCK_RETURNED(muDoubleWrapper.getWrapper()->getMu());
    978 int lr_function_8() LOCK_RETURNED(muPointer);
    979 
    980 
    981 // illegal attribute arguments
    982 int lr_function_bad_1() LOCK_RETURNED(1); // \
    983   // expected-warning {{'lock_returned' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'int'}}
    984 int lr_function_bad_2() LOCK_RETURNED("mu"); // \
    985   // expected-warning {{ignoring 'lock_returned' attribute because its argument is invalid}}
    986 int lr_function_bad_3() LOCK_RETURNED(muDoublePointer); // \
    987   // expected-warning {{'lock_returned' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'Mutex **'}}
    988 int lr_function_bad_4() LOCK_RETURNED(umu); // \
    989   // expected-warning {{'lock_returned' attribute requires arguments whose type is annotated with 'capability' attribute}}
    990 
    991 
    992 
    993 //-----------------------------------------//
    994 //  Locks Excluded (le)
    995 //-----------------------------------------//
    996 
    997 #if !__has_attribute(locks_excluded)
    998 #error "Should support locks_excluded attribute"
    999 #endif
   1000 
   1001 // takes one or more arguments, all locks (vars/fields)
   1002 
   1003 void le_function() __attribute__((locks_excluded)); // \
   1004   // expected-error {{'locks_excluded' attribute takes at least 1 argument}}
   1005 
   1006 void le_function_arg() LOCKS_EXCLUDED(mu1);
   1007 
   1008 void le_function_args() LOCKS_EXCLUDED(mu1, mu2);
   1009 
   1010 int le_testfn(int y) LOCKS_EXCLUDED(mu1);
   1011 
   1012 int le_testfn(int y) {
   1013   int x LOCKS_EXCLUDED(mu1) = y; // \
   1014     // expected-warning {{'locks_excluded' attribute only applies to functions}}
   1015   return x;
   1016 };
   1017 
   1018 int le_test_var LOCKS_EXCLUDED(mu1); // \
   1019   // expected-warning {{'locks_excluded' attribute only applies to functions}}
   1020 
   1021 void le_fun_params(int lvar LOCKS_EXCLUDED(mu1)); // \
   1022   // expected-warning {{'locks_excluded' attribute only applies to functions}}
   1023 
   1024 class LeFoo {
   1025  private:
   1026   int test_field LOCKS_EXCLUDED(mu1); // \
   1027     // expected-warning {{'locks_excluded' attribute only applies to functions}}
   1028   void test_method() LOCKS_EXCLUDED(mu1);
   1029 };
   1030 
   1031 class LOCKS_EXCLUDED(mu1) LeTestClass { // \
   1032   // expected-warning {{'locks_excluded' attribute only applies to functions}}
   1033 };
   1034 
   1035 // Check argument parsing.
   1036 
   1037 // legal attribute arguments
   1038 int le_function_1() LOCKS_EXCLUDED(muWrapper.mu);
   1039 int le_function_2() LOCKS_EXCLUDED(muDoubleWrapper.muWrapper->mu);
   1040 int le_function_3() LOCKS_EXCLUDED(muWrapper.getMu());
   1041 int le_function_4() LOCKS_EXCLUDED(*muWrapper.getMuPointer());
   1042 int le_function_5() LOCKS_EXCLUDED(&mu1);
   1043 int le_function_6() LOCKS_EXCLUDED(muRef);
   1044 int le_function_7() LOCKS_EXCLUDED(muDoubleWrapper.getWrapper()->getMu());
   1045 int le_function_8() LOCKS_EXCLUDED(muPointer);
   1046 
   1047 
   1048 // illegal attribute arguments
   1049 int le_function_bad_1() LOCKS_EXCLUDED(1); // \
   1050   // expected-warning {{'locks_excluded' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'int'}}
   1051 int le_function_bad_2() LOCKS_EXCLUDED("mu"); // \
   1052   // expected-warning {{ignoring 'locks_excluded' attribute because its argument is invalid}}
   1053 int le_function_bad_3() LOCKS_EXCLUDED(muDoublePointer); // \
   1054   // expected-warning {{'locks_excluded' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'Mutex **'}}
   1055 int le_function_bad_4() LOCKS_EXCLUDED(umu); // \
   1056   // expected-warning {{'locks_excluded' attribute requires arguments whose type is annotated with 'capability' attribute}}
   1057 
   1058 
   1059 
   1060 //-----------------------------------------//
   1061 //  Exclusive Locks Required (elr)
   1062 //-----------------------------------------//
   1063 
   1064 #if !__has_attribute(exclusive_locks_required)
   1065 #error "Should support exclusive_locks_required attribute"
   1066 #endif
   1067 
   1068 // takes one or more arguments, all locks (vars/fields)
   1069 
   1070 void elr_function() __attribute__((exclusive_locks_required)); // \
   1071   // expected-error {{'exclusive_locks_required' attribute takes at least 1 argument}}
   1072 
   1073 void elr_function_arg() EXCLUSIVE_LOCKS_REQUIRED(mu1);
   1074 
   1075 void elr_function_args() EXCLUSIVE_LOCKS_REQUIRED(mu1, mu2);
   1076 
   1077 int elr_testfn(int y) EXCLUSIVE_LOCKS_REQUIRED(mu1);
   1078 
   1079 int elr_testfn(int y) {
   1080   int x EXCLUSIVE_LOCKS_REQUIRED(mu1) = y; // \
   1081     // expected-warning {{'exclusive_locks_required' attribute only applies to functions}}
   1082   return x;
   1083 };
   1084 
   1085 int elr_test_var EXCLUSIVE_LOCKS_REQUIRED(mu1); // \
   1086   // expected-warning {{'exclusive_locks_required' attribute only applies to functions}}
   1087 
   1088 void elr_fun_params(int lvar EXCLUSIVE_LOCKS_REQUIRED(mu1)); // \
   1089   // expected-warning {{'exclusive_locks_required' attribute only applies to functions}}
   1090 
   1091 class ElrFoo {
   1092  private:
   1093   int test_field EXCLUSIVE_LOCKS_REQUIRED(mu1); // \
   1094     // expected-warning {{'exclusive_locks_required' attribute only applies to functions}}
   1095   void test_method() EXCLUSIVE_LOCKS_REQUIRED(mu1);
   1096 };
   1097 
   1098 class EXCLUSIVE_LOCKS_REQUIRED(mu1) ElrTestClass { // \
   1099   // expected-warning {{'exclusive_locks_required' attribute only applies to functions}}
   1100 };
   1101 
   1102 // Check argument parsing.
   1103 
   1104 // legal attribute arguments
   1105 int elr_function_1() EXCLUSIVE_LOCKS_REQUIRED(muWrapper.mu);
   1106 int elr_function_2() EXCLUSIVE_LOCKS_REQUIRED(muDoubleWrapper.muWrapper->mu);
   1107 int elr_function_3() EXCLUSIVE_LOCKS_REQUIRED(muWrapper.getMu());
   1108 int elr_function_4() EXCLUSIVE_LOCKS_REQUIRED(*muWrapper.getMuPointer());
   1109 int elr_function_5() EXCLUSIVE_LOCKS_REQUIRED(&mu1);
   1110 int elr_function_6() EXCLUSIVE_LOCKS_REQUIRED(muRef);
   1111 int elr_function_7() EXCLUSIVE_LOCKS_REQUIRED(muDoubleWrapper.getWrapper()->getMu());
   1112 int elr_function_8() EXCLUSIVE_LOCKS_REQUIRED(muPointer);
   1113 
   1114 
   1115 // illegal attribute arguments
   1116 int elr_function_bad_1() EXCLUSIVE_LOCKS_REQUIRED(1); // \
   1117   // expected-warning {{'exclusive_locks_required' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'int'}}
   1118 int elr_function_bad_2() EXCLUSIVE_LOCKS_REQUIRED("mu"); // \
   1119   // expected-warning {{ignoring 'exclusive_locks_required' attribute because its argument is invalid}}
   1120 int elr_function_bad_3() EXCLUSIVE_LOCKS_REQUIRED(muDoublePointer); // \
   1121   // expected-warning {{'exclusive_locks_required' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'Mutex **'}}
   1122 int elr_function_bad_4() EXCLUSIVE_LOCKS_REQUIRED(umu); // \
   1123   // expected-warning {{'exclusive_locks_required' attribute requires arguments whose type is annotated with 'capability' attribute}}
   1124 
   1125 
   1126 
   1127 
   1128 //-----------------------------------------//
   1129 //  Shared Locks Required (slr)
   1130 //-----------------------------------------//
   1131 
   1132 #if !__has_attribute(shared_locks_required)
   1133 #error "Should support shared_locks_required attribute"
   1134 #endif
   1135 
   1136 // takes one or more arguments, all locks (vars/fields)
   1137 
   1138 void slr_function() __attribute__((shared_locks_required)); // \
   1139   // expected-error {{'shared_locks_required' attribute takes at least 1 argument}}
   1140 
   1141 void slr_function_arg() SHARED_LOCKS_REQUIRED(mu1);
   1142 
   1143 void slr_function_args() SHARED_LOCKS_REQUIRED(mu1, mu2);
   1144 
   1145 int slr_testfn(int y) SHARED_LOCKS_REQUIRED(mu1);
   1146 
   1147 int slr_testfn(int y) {
   1148   int x SHARED_LOCKS_REQUIRED(mu1) = y; // \
   1149     // expected-warning {{'shared_locks_required' attribute only applies to functions}}
   1150   return x;
   1151 };
   1152 
   1153 int slr_test_var SHARED_LOCKS_REQUIRED(mu1); // \
   1154   // expected-warning {{'shared_locks_required' attribute only applies to functions}}
   1155 
   1156 void slr_fun_params(int lvar SHARED_LOCKS_REQUIRED(mu1)); // \
   1157   // expected-warning {{'shared_locks_required' attribute only applies to functions}}
   1158 
   1159 class SlrFoo {
   1160  private:
   1161   int test_field SHARED_LOCKS_REQUIRED(mu1); // \
   1162     // expected-warning {{'shared_locks_required' attribute only applies to functions}}
   1163   void test_method() SHARED_LOCKS_REQUIRED(mu1);
   1164 };
   1165 
   1166 class SHARED_LOCKS_REQUIRED(mu1) SlrTestClass { // \
   1167   // expected-warning {{'shared_locks_required' attribute only applies to functions}}
   1168 };
   1169 
   1170 // Check argument parsing.
   1171 
   1172 // legal attribute arguments
   1173 int slr_function_1() SHARED_LOCKS_REQUIRED(muWrapper.mu);
   1174 int slr_function_2() SHARED_LOCKS_REQUIRED(muDoubleWrapper.muWrapper->mu);
   1175 int slr_function_3() SHARED_LOCKS_REQUIRED(muWrapper.getMu());
   1176 int slr_function_4() SHARED_LOCKS_REQUIRED(*muWrapper.getMuPointer());
   1177 int slr_function_5() SHARED_LOCKS_REQUIRED(&mu1);
   1178 int slr_function_6() SHARED_LOCKS_REQUIRED(muRef);
   1179 int slr_function_7() SHARED_LOCKS_REQUIRED(muDoubleWrapper.getWrapper()->getMu());
   1180 int slr_function_8() SHARED_LOCKS_REQUIRED(muPointer);
   1181 
   1182 
   1183 // illegal attribute arguments
   1184 int slr_function_bad_1() SHARED_LOCKS_REQUIRED(1); // \
   1185   // expected-warning {{'shared_locks_required' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'int'}}
   1186 int slr_function_bad_2() SHARED_LOCKS_REQUIRED("mu"); // \
   1187   // expected-warning {{ignoring 'shared_locks_required' attribute because its argument is invalid}}
   1188 int slr_function_bad_3() SHARED_LOCKS_REQUIRED(muDoublePointer); // \
   1189   // expected-warning {{'shared_locks_required' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'Mutex **'}}
   1190 int slr_function_bad_4() SHARED_LOCKS_REQUIRED(umu); // \
   1191   // expected-warning {{'shared_locks_required' attribute requires arguments whose type is annotated with 'capability' attribute}}
   1192 
   1193 
   1194 //-----------------------------------------//
   1195 //  Regression tests for unusual cases.
   1196 //-----------------------------------------//
   1197 
   1198 int trivially_false_edges(bool b) {
   1199   // Create NULL (never taken) edges in CFG
   1200   if (false) return 1;
   1201   else       return 2;
   1202 }
   1203 
   1204 // Possible Clang bug -- method pointer in template parameter
   1205 class UnFoo {
   1206 public:
   1207   void foo();
   1208 };
   1209 
   1210 template<void (UnFoo::*methptr)()>
   1211 class MCaller {
   1212 public:
   1213   static void call_method_ptr(UnFoo *f) {
   1214     // FIXME: Possible Clang bug:
   1215     // getCalleeDecl() returns NULL in the following case:
   1216     (f->*methptr)();
   1217   }
   1218 };
   1219 
   1220 void call_method_ptr_inst(UnFoo* f) {
   1221   MCaller<&UnFoo::foo>::call_method_ptr(f);
   1222 }
   1223 
   1224 int temp;
   1225 void empty_back_edge() {
   1226   // Create a back edge to a block with with no statements
   1227   for (;;) {
   1228     ++temp;
   1229     if (temp > 10) break;
   1230   }
   1231 }
   1232 
   1233 struct Foomger {
   1234   void operator++();
   1235 };
   1236 
   1237 struct Foomgoper {
   1238   Foomger f;
   1239 
   1240   bool done();
   1241   void invalid_back_edge() {
   1242     do {
   1243       // FIXME: Possible Clang bug:
   1244       // The first statement in this basic block has no source location
   1245       ++f;
   1246     } while (!done());
   1247   }
   1248 };
   1249 
   1250 
   1251 //-----------------------------------------------------
   1252 // Parsing of member variables and function parameters
   1253 //------------------------------------------------------
   1254 
   1255 Mutex gmu;
   1256 
   1257 class StaticMu {
   1258   static Mutex statmu;
   1259 };
   1260 
   1261 class FooLate {
   1262 public:
   1263   void foo1()           EXCLUSIVE_LOCKS_REQUIRED(gmu)   { }
   1264   void foo2()           EXCLUSIVE_LOCKS_REQUIRED(mu)    { }
   1265   void foo3(Mutex *m)   EXCLUSIVE_LOCKS_REQUIRED(m)     { }
   1266   void foo3(FooLate *f) EXCLUSIVE_LOCKS_REQUIRED(f->mu) { }
   1267   void foo4(FooLate *f) EXCLUSIVE_LOCKS_REQUIRED(f->mu);
   1268 
   1269   static void foo5()    EXCLUSIVE_LOCKS_REQUIRED(mu); // \
   1270     // expected-error {{invalid use of member 'mu' in static member function}}
   1271 
   1272   template <class T>
   1273   void foo6() EXCLUSIVE_LOCKS_REQUIRED(T::statmu) { }
   1274 
   1275   template <class T>
   1276   void foo7(T* f) EXCLUSIVE_LOCKS_REQUIRED(f->mu) { }
   1277 
   1278   int a GUARDED_BY(gmu);
   1279   int b GUARDED_BY(mu);
   1280   int c GUARDED_BY(this->mu);
   1281 
   1282   Mutex mu;
   1283 };
   1284 
   1285 //-------------------------
   1286 // Empty argument lists
   1287 //-------------------------
   1288 
   1289 class LOCKABLE EmptyArgListsTest {
   1290   void lock() EXCLUSIVE_LOCK_FUNCTION() { }
   1291   void unlock() UNLOCK_FUNCTION() { }
   1292 };
   1293 
   1294 
   1295 namespace FunctionDefinitionParseTest {
   1296 // Test parsing of attributes on function definitions.
   1297 
   1298 class Foo {
   1299 public:
   1300   Mutex mu_;
   1301   void foo1();
   1302   void foo2(Foo *f);
   1303 };
   1304 
   1305 template <class T>
   1306 class Bar {
   1307 public:
   1308   Mutex mu_;
   1309   void bar();
   1310 };
   1311 
   1312 void Foo::foo1()       EXCLUSIVE_LOCKS_REQUIRED(mu_) { }
   1313 void Foo::foo2(Foo *f) EXCLUSIVE_LOCKS_REQUIRED(f->mu_) { }
   1314 
   1315 template <class T>
   1316 void Bar<T>::bar() EXCLUSIVE_LOCKS_REQUIRED(mu_) { }
   1317 
   1318 void baz(Foo *f) EXCLUSIVE_LOCKS_REQUIRED(f->mu_) { }
   1319 
   1320 } // end namespace
   1321 
   1322 
   1323 namespace TestMultiDecl {
   1324 
   1325 class Foo {
   1326 public:
   1327   int GUARDED_BY(mu_) a;
   1328   int GUARDED_BY(mu_) b, c;
   1329 
   1330 private:
   1331   Mutex mu_;
   1332 };
   1333 
   1334 } // end namespace TestMultiDecl
   1335 
   1336 
   1337 namespace NestedClassLateDecl {
   1338 
   1339 class Foo {
   1340   class Bar {
   1341     int a GUARDED_BY(mu);
   1342     int b GUARDED_BY(fooMuStatic);
   1343 
   1344     void bar()        EXCLUSIVE_LOCKS_REQUIRED(mu)       { a = 0;    }
   1345     void bar2(Bar* b) EXCLUSIVE_LOCKS_REQUIRED(b->mu)    { b->a = 0; }
   1346     void bar3(Foo* f) EXCLUSIVE_LOCKS_REQUIRED(f->fooMu) { f->a = 0; }
   1347 
   1348     Mutex mu;
   1349   };
   1350 
   1351   int a GUARDED_BY(fooMu);
   1352   Mutex fooMu;
   1353   static Mutex fooMuStatic;
   1354 };
   1355 
   1356 }
   1357 
   1358 namespace PointerToMemberTest {
   1359 
   1360 // Empty string should be ignored.
   1361 int  testEmptyAttribute GUARDED_BY("");
   1362 void testEmptyAttributeFunction() EXCLUSIVE_LOCKS_REQUIRED("");
   1363 
   1364 class Graph {
   1365 public:
   1366   Mutex mu_;
   1367 
   1368   static Mutex* get_static_mu() LOCK_RETURNED(&Graph::mu_);
   1369 };
   1370 
   1371 class Node {
   1372 public:
   1373   void foo() EXCLUSIVE_LOCKS_REQUIRED(&Graph::mu_);
   1374   int a GUARDED_BY(&Graph::mu_);
   1375 };
   1376 
   1377 }
   1378 
   1379 
   1380 namespace SmartPointerTest {
   1381 
   1382 template<class T>
   1383 class smart_ptr {
   1384  public:
   1385   T* operator->() { return ptr_; }
   1386   T& operator*()  { return ptr_; }
   1387 
   1388  private:
   1389   T* ptr_;
   1390 };
   1391 
   1392 
   1393 Mutex gmu;
   1394 smart_ptr<int> gdat PT_GUARDED_BY(gmu);
   1395 
   1396 
   1397 class MyClass {
   1398 public:
   1399   Mutex mu_;
   1400   smart_ptr<Mutex> smu_;
   1401 
   1402 
   1403   smart_ptr<int> a PT_GUARDED_BY(mu_);
   1404   int b            GUARDED_BY(smu_);
   1405 };
   1406 
   1407 }
   1408 
   1409 
   1410 namespace InheritanceTest {
   1411 
   1412 class LOCKABLE Base {
   1413  public:
   1414   void lock()   EXCLUSIVE_LOCK_FUNCTION();
   1415   void unlock() UNLOCK_FUNCTION();
   1416 };
   1417 
   1418 class Base2 { };
   1419 
   1420 class Derived1 : public Base { };
   1421 
   1422 class Derived2 : public Base2, public Derived1 { };
   1423 
   1424 class Derived3 : public Base2 { };
   1425 
   1426 class Foo {
   1427   Derived1 mu1_;
   1428   Derived2 mu2_;
   1429   Derived3 mu3_;
   1430   int a GUARDED_BY(mu1_);
   1431   int b GUARDED_BY(mu2_);
   1432   int c GUARDED_BY(mu3_);  // \
   1433     // expected-warning {{'guarded_by' attribute requires arguments whose type is annotated with 'capability' attribute; type here is 'InheritanceTest::Derived3'}}
   1434 
   1435   void foo() EXCLUSIVE_LOCKS_REQUIRED(mu1_, mu2_) {
   1436     a = 0;
   1437     b = 0;
   1438   }
   1439 };
   1440 
   1441 }
   1442 
   1443 
   1444 namespace InvalidDeclTest {
   1445 
   1446 class Foo { };
   1447 namespace {
   1448 void Foo::bar(Mutex* mu) LOCKS_EXCLUDED(mu) { } // \
   1449    // expected-error   {{cannot define or redeclare 'bar' here because namespace '' does not enclose namespace 'Foo'}} \
   1450    // expected-warning {{attribute locks_excluded ignored, because it is not attached to a declaration}}
   1451 }
   1452 
   1453 } // end namespace InvalidDeclTest
   1454 
   1455 
   1456 namespace StaticScopeTest {
   1457 
   1458 class FooStream;
   1459 
   1460 class Foo {
   1461   mutable Mutex mu;
   1462   int a GUARDED_BY(mu);
   1463 
   1464   static int si GUARDED_BY(mu); // \
   1465     // expected-error {{invalid use of non-static data member 'mu'}}
   1466 
   1467   static void foo() EXCLUSIVE_LOCKS_REQUIRED(mu); // \
   1468     // expected-error {{invalid use of member 'mu' in static member function}}
   1469 
   1470   friend FooStream& operator<<(FooStream& s, const Foo& f)
   1471     EXCLUSIVE_LOCKS_REQUIRED(mu); // \
   1472     // expected-error {{invalid use of non-static data member 'mu'}}
   1473 };
   1474 
   1475 
   1476 } // end namespace StaticScopeTest
   1477 
   1478 
   1479 namespace FunctionAttributesInsideClass_ICE_Test {
   1480 
   1481 class Foo {
   1482 public:
   1483   /*  Originally found when parsing foo() as an ordinary method after the
   1484    *  the following:
   1485 
   1486   template <class T>
   1487   void syntaxErrorMethod(int i) {
   1488     if (i) {
   1489       foo(
   1490     }
   1491   }
   1492   */
   1493 
   1494   void method() {
   1495     void foo() EXCLUSIVE_LOCKS_REQUIRED(mu); // \
   1496       // expected-error {{use of undeclared identifier 'mu'}}
   1497   }
   1498 };
   1499 
   1500 }  // end namespace FunctionAttributesInsideClass_ICE_Test
   1501 
   1502