• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // RUN: %clang_cc1 -fsyntax-only -verify -Wthread-safety -std=c++11 %s
2 
3 // FIXME: should also run  %clang_cc1 -fsyntax-only -verify -Wthread-safety -std=c++11 -Wc++98-compat %s
4 // FIXME: should also run  %clang_cc1 -fsyntax-only -verify -Wthread-safety %s
5 
6 #define LOCKABLE            __attribute__ ((lockable))
7 #define SCOPED_LOCKABLE     __attribute__ ((scoped_lockable))
8 #define GUARDED_BY(x)       __attribute__ ((guarded_by(x)))
9 #define GUARDED_VAR         __attribute__ ((guarded_var))
10 #define PT_GUARDED_BY(x)    __attribute__ ((pt_guarded_by(x)))
11 #define PT_GUARDED_VAR      __attribute__ ((pt_guarded_var))
12 #define ACQUIRED_AFTER(...) __attribute__ ((acquired_after(__VA_ARGS__)))
13 #define ACQUIRED_BEFORE(...) __attribute__ ((acquired_before(__VA_ARGS__)))
14 #define EXCLUSIVE_LOCK_FUNCTION(...)   __attribute__ ((exclusive_lock_function(__VA_ARGS__)))
15 #define SHARED_LOCK_FUNCTION(...)      __attribute__ ((shared_lock_function(__VA_ARGS__)))
16 #define EXCLUSIVE_TRYLOCK_FUNCTION(...) __attribute__ ((exclusive_trylock_function(__VA_ARGS__)))
17 #define SHARED_TRYLOCK_FUNCTION(...)    __attribute__ ((shared_trylock_function(__VA_ARGS__)))
18 #define UNLOCK_FUNCTION(...)            __attribute__ ((unlock_function(__VA_ARGS__)))
19 #define LOCK_RETURNED(x)    __attribute__ ((lock_returned(x)))
20 #define LOCKS_EXCLUDED(...) __attribute__ ((locks_excluded(__VA_ARGS__)))
21 #define EXCLUSIVE_LOCKS_REQUIRED(...) \
22   __attribute__ ((exclusive_locks_required(__VA_ARGS__)))
23 #define SHARED_LOCKS_REQUIRED(...) \
24   __attribute__ ((shared_locks_required(__VA_ARGS__)))
25 #define NO_THREAD_SAFETY_ANALYSIS  __attribute__ ((no_thread_safety_analysis))
26 
27 
28 class  __attribute__((lockable)) Mutex {
29  public:
30   void Lock() __attribute__((exclusive_lock_function));
31   void ReaderLock() __attribute__((shared_lock_function));
32   void Unlock() __attribute__((unlock_function));
33   bool TryLock() __attribute__((exclusive_trylock_function(true)));
34   bool ReaderTryLock() __attribute__((shared_trylock_function(true)));
35   void LockWhen(const int &cond) __attribute__((exclusive_lock_function));
36 };
37 
38 class __attribute__((scoped_lockable)) MutexLock {
39  public:
40   MutexLock(Mutex *mu) __attribute__((exclusive_lock_function(mu)));
41   ~MutexLock() __attribute__((unlock_function));
42 };
43 
44 class __attribute__((scoped_lockable)) ReaderMutexLock {
45  public:
46   ReaderMutexLock(Mutex *mu) __attribute__((exclusive_lock_function(mu)));
47   ~ReaderMutexLock() __attribute__((unlock_function));
48 };
49 
50 class SCOPED_LOCKABLE ReleasableMutexLock {
51  public:
52   ReleasableMutexLock(Mutex *mu) EXCLUSIVE_LOCK_FUNCTION(mu);
53   ~ReleasableMutexLock() UNLOCK_FUNCTION();
54 
55   void Release() UNLOCK_FUNCTION();
56 };
57 
58 
59 // The universal lock, written "*", allows checking to be selectively turned
60 // off for a particular piece of code.
61 void beginNoWarnOnReads()  SHARED_LOCK_FUNCTION("*");
62 void endNoWarnOnReads()    UNLOCK_FUNCTION("*");
63 void beginNoWarnOnWrites() EXCLUSIVE_LOCK_FUNCTION("*");
64 void endNoWarnOnWrites()   UNLOCK_FUNCTION("*");
65 
66 
67 template<class T>
68 class SmartPtr {
69 public:
SmartPtr(T * p)70   SmartPtr(T* p) : ptr_(p) { }
SmartPtr(const SmartPtr<T> & p)71   SmartPtr(const SmartPtr<T>& p) : ptr_(p.ptr_) { }
72   ~SmartPtr();
73 
get() const74   T* get()        const { return ptr_; }
operator ->() const75   T* operator->() const { return ptr_; }
operator *() const76   T& operator*()  const { return *ptr_; }
77 
78 private:
79   T* ptr_;
80 };
81 
82 
83 Mutex sls_mu;
84 
85 Mutex sls_mu2 __attribute__((acquired_after(sls_mu)));
86 int sls_guard_var __attribute__((guarded_var)) = 0;
87 int sls_guardby_var __attribute__((guarded_by(sls_mu))) = 0;
88 
89 bool getBool();
90 
91 class MutexWrapper {
92 public:
93    Mutex mu;
94    int x __attribute__((guarded_by(mu)));
95    void MyLock() __attribute__((exclusive_lock_function(mu)));
96 };
97 
98 MutexWrapper sls_mw;
99 
sls_fun_0()100 void sls_fun_0() {
101   sls_mw.mu.Lock();
102   sls_mw.x = 5;
103   sls_mw.mu.Unlock();
104 }
105 
sls_fun_2()106 void sls_fun_2() {
107   sls_mu.Lock();
108   int x = sls_guard_var;
109   sls_mu.Unlock();
110 }
111 
sls_fun_3()112 void sls_fun_3() {
113   sls_mu.Lock();
114   sls_guard_var = 2;
115   sls_mu.Unlock();
116 }
117 
sls_fun_4()118 void sls_fun_4() {
119   sls_mu2.Lock();
120   sls_guard_var = 2;
121   sls_mu2.Unlock();
122 }
123 
sls_fun_5()124 void sls_fun_5() {
125   sls_mu.Lock();
126   int x = sls_guardby_var;
127   sls_mu.Unlock();
128 }
129 
sls_fun_6()130 void sls_fun_6() {
131   sls_mu.Lock();
132   sls_guardby_var = 2;
133   sls_mu.Unlock();
134 }
135 
sls_fun_7()136 void sls_fun_7() {
137   sls_mu.Lock();
138   sls_mu2.Lock();
139   sls_mu2.Unlock();
140   sls_mu.Unlock();
141 }
142 
sls_fun_8()143 void sls_fun_8() {
144   sls_mu.Lock();
145   if (getBool())
146     sls_mu.Unlock();
147   else
148     sls_mu.Unlock();
149 }
150 
sls_fun_9()151 void sls_fun_9() {
152   if (getBool())
153     sls_mu.Lock();
154   else
155     sls_mu.Lock();
156   sls_mu.Unlock();
157 }
158 
sls_fun_good_6()159 void sls_fun_good_6() {
160   if (getBool()) {
161     sls_mu.Lock();
162   } else {
163     if (getBool()) {
164       getBool(); // EMPTY
165     } else {
166       getBool(); // EMPTY
167     }
168     sls_mu.Lock();
169   }
170   sls_mu.Unlock();
171 }
172 
sls_fun_good_7()173 void sls_fun_good_7() {
174   sls_mu.Lock();
175   while (getBool()) {
176     sls_mu.Unlock();
177     if (getBool()) {
178       if (getBool()) {
179         sls_mu.Lock();
180         continue;
181       }
182     }
183     sls_mu.Lock();
184   }
185   sls_mu.Unlock();
186 }
187 
sls_fun_good_8()188 void sls_fun_good_8() {
189   sls_mw.MyLock();
190   sls_mw.mu.Unlock();
191 }
192 
sls_fun_bad_1()193 void sls_fun_bad_1() {
194   sls_mu.Unlock(); // \
195     // expected-warning{{unlocking 'sls_mu' that was not locked}}
196 }
197 
sls_fun_bad_2()198 void sls_fun_bad_2() {
199   sls_mu.Lock();
200   sls_mu.Lock(); // \
201     // expected-warning{{locking 'sls_mu' that is already locked}}
202   sls_mu.Unlock();
203 }
204 
sls_fun_bad_3()205 void sls_fun_bad_3() {
206   sls_mu.Lock(); // expected-note {{mutex acquired here}}
207 } // expected-warning{{mutex 'sls_mu' is still locked at the end of function}}
208 
sls_fun_bad_4()209 void sls_fun_bad_4() {
210   if (getBool())
211     sls_mu.Lock();  // expected-note{{mutex acquired here}}
212   else
213     sls_mu2.Lock(); // expected-note{{mutex acquired here}}
214 } // expected-warning{{mutex 'sls_mu' is not locked on every path through here}}  \
215   // expected-warning{{mutex 'sls_mu2' is not locked on every path through here}}
216 
sls_fun_bad_5()217 void sls_fun_bad_5() {
218   sls_mu.Lock(); // expected-note {{mutex acquired here}}
219   if (getBool())
220     sls_mu.Unlock();
221 } // expected-warning{{mutex 'sls_mu' is not locked on every path through here}}
222 
sls_fun_bad_6()223 void sls_fun_bad_6() {
224   if (getBool()) {
225     sls_mu.Lock(); // expected-note {{mutex acquired here}}
226   } else {
227     if (getBool()) {
228       getBool(); // EMPTY
229     } else {
230       getBool(); // EMPTY
231     }
232   }
233   sls_mu.Unlock(); // \
234     expected-warning{{mutex 'sls_mu' is not locked on every path through here}}\
235     expected-warning{{unlocking 'sls_mu' that was not locked}}
236 }
237 
sls_fun_bad_7()238 void sls_fun_bad_7() {
239   sls_mu.Lock();
240   while (getBool()) {
241     sls_mu.Unlock();
242     if (getBool()) {
243       if (getBool()) {
244         continue; // \
245         expected-warning{{expecting mutex 'sls_mu' to be locked at start of each loop}}
246       }
247     }
248     sls_mu.Lock(); // expected-note {{mutex acquired here}}
249   }
250   sls_mu.Unlock();
251 }
252 
sls_fun_bad_8()253 void sls_fun_bad_8() {
254   sls_mu.Lock(); // expected-note{{mutex acquired here}}
255 
256   do {
257     sls_mu.Unlock(); // expected-warning{{expecting mutex 'sls_mu' to be locked at start of each loop}}
258   } while (getBool());
259 }
260 
sls_fun_bad_9()261 void sls_fun_bad_9() {
262   do {
263     sls_mu.Lock();  // \
264       // expected-warning{{expecting mutex 'sls_mu' to be locked at start of each loop}} \
265       // expected-note{{mutex acquired here}}
266   } while (getBool());
267   sls_mu.Unlock();
268 }
269 
sls_fun_bad_10()270 void sls_fun_bad_10() {
271   sls_mu.Lock();  // expected-note 2{{mutex acquired here}}
272   while(getBool()) {  // expected-warning{{expecting mutex 'sls_mu' to be locked at start of each loop}}
273     sls_mu.Unlock();
274   }
275 } // expected-warning{{mutex 'sls_mu' is still locked at the end of function}}
276 
sls_fun_bad_11()277 void sls_fun_bad_11() {
278   while (getBool()) { // \
279       expected-warning{{expecting mutex 'sls_mu' to be locked at start of each loop}}
280     sls_mu.Lock(); // expected-note {{mutex acquired here}}
281   }
282   sls_mu.Unlock(); // \
283     // expected-warning{{unlocking 'sls_mu' that was not locked}}
284 }
285 
sls_fun_bad_12()286 void sls_fun_bad_12() {
287   sls_mu.Lock(); // expected-note {{mutex acquired here}}
288   while (getBool()) {
289     sls_mu.Unlock();
290     if (getBool()) {
291       if (getBool()) {
292         break; // expected-warning{{mutex 'sls_mu' is not locked on every path through here}}
293       }
294     }
295     sls_mu.Lock();
296   }
297   sls_mu.Unlock();
298 }
299 
300 //-----------------------------------------//
301 // Handling lock expressions in attribute args
302 // -------------------------------------------//
303 
304 Mutex aa_mu;
305 
306 class GlobalLocker {
307 public:
308   void globalLock() __attribute__((exclusive_lock_function(aa_mu)));
309   void globalUnlock() __attribute__((unlock_function(aa_mu)));
310 };
311 
312 GlobalLocker glock;
313 
aa_fun_1()314 void aa_fun_1() {
315   glock.globalLock();
316   glock.globalUnlock();
317 }
318 
aa_fun_bad_1()319 void aa_fun_bad_1() {
320   glock.globalUnlock(); // \
321     // expected-warning{{unlocking 'aa_mu' that was not locked}}
322 }
323 
aa_fun_bad_2()324 void aa_fun_bad_2() {
325   glock.globalLock();
326   glock.globalLock(); // \
327     // expected-warning{{locking 'aa_mu' that is already locked}}
328   glock.globalUnlock();
329 }
330 
aa_fun_bad_3()331 void aa_fun_bad_3() {
332   glock.globalLock(); // expected-note{{mutex acquired here}}
333 } // expected-warning{{mutex 'aa_mu' is still locked at the end of function}}
334 
335 //--------------------------------------------------//
336 // Regression tests for unusual method names
337 //--------------------------------------------------//
338 
339 Mutex wmu;
340 
341 // Test diagnostics for other method names.
342 class WeirdMethods {
343   // FIXME: can't currently check inside constructors and destructors.
WeirdMethods()344   WeirdMethods() {
345     wmu.Lock(); // EXPECTED-NOTE {{mutex acquired here}}
346   } // EXPECTED-WARNING {{mutex 'wmu' is still locked at the end of function}}
~WeirdMethods()347   ~WeirdMethods() {
348     wmu.Lock(); // EXPECTED-NOTE {{mutex acquired here}}
349   } // EXPECTED-WARNING {{mutex 'wmu' is still locked at the end of function}}
operator ++()350   void operator++() {
351     wmu.Lock(); // expected-note {{mutex acquired here}}
352   } // expected-warning {{mutex 'wmu' is still locked at the end of function}}
operator int*()353   operator int*() {
354     wmu.Lock(); // expected-note {{mutex acquired here}}
355     return 0;
356   } // expected-warning {{mutex 'wmu' is still locked at the end of function}}
357 };
358 
359 //-----------------------------------------------//
360 // Errors for guarded by or guarded var variables
361 // ----------------------------------------------//
362 
363 int *pgb_gvar __attribute__((pt_guarded_var));
364 int *pgb_var __attribute__((pt_guarded_by(sls_mu)));
365 
366 class PGBFoo {
367  public:
368   int x;
369   int *pgb_field __attribute__((guarded_by(sls_mu2)))
370                  __attribute__((pt_guarded_by(sls_mu)));
testFoo()371   void testFoo() {
372     pgb_field = &x; // \
373       // expected-warning {{writing variable 'pgb_field' requires locking 'sls_mu2' exclusively}}
374     *pgb_field = x; // expected-warning {{reading variable 'pgb_field' requires locking 'sls_mu2'}} \
375       // expected-warning {{writing the value pointed to by 'pgb_field' requires locking 'sls_mu' exclusively}}
376     x = *pgb_field; // expected-warning {{reading variable 'pgb_field' requires locking 'sls_mu2'}} \
377       // expected-warning {{reading the value pointed to by 'pgb_field' requires locking 'sls_mu'}}
378     (*pgb_field)++; // expected-warning {{reading variable 'pgb_field' requires locking 'sls_mu2'}} \
379       // expected-warning {{writing the value pointed to by 'pgb_field' requires locking 'sls_mu' exclusively}}
380   }
381 };
382 
383 class GBFoo {
384  public:
385   int gb_field __attribute__((guarded_by(sls_mu)));
386 
testFoo()387   void testFoo() {
388     gb_field = 0; // \
389       // expected-warning {{writing variable 'gb_field' requires locking 'sls_mu' exclusively}}
390   }
391 
testNoAnal()392   void testNoAnal() __attribute__((no_thread_safety_analysis)) {
393     gb_field = 0;
394   }
395 };
396 
397 GBFoo GlobalGBFoo __attribute__((guarded_by(sls_mu)));
398 
gb_fun_0()399 void gb_fun_0() {
400   sls_mu.Lock();
401   int x = *pgb_var;
402   sls_mu.Unlock();
403 }
404 
gb_fun_1()405 void gb_fun_1() {
406   sls_mu.Lock();
407   *pgb_var = 2;
408   sls_mu.Unlock();
409 }
410 
gb_fun_2()411 void gb_fun_2() {
412   int x;
413   pgb_var = &x;
414 }
415 
gb_fun_3()416 void gb_fun_3() {
417   int *x = pgb_var;
418 }
419 
gb_bad_0()420 void gb_bad_0() {
421   sls_guard_var = 1; // \
422     // expected-warning{{writing variable 'sls_guard_var' requires locking any mutex exclusively}}
423 }
424 
gb_bad_1()425 void gb_bad_1() {
426   int x = sls_guard_var; // \
427     // expected-warning{{reading variable 'sls_guard_var' requires locking any mutex}}
428 }
429 
gb_bad_2()430 void gb_bad_2() {
431   sls_guardby_var = 1; // \
432     // expected-warning {{writing variable 'sls_guardby_var' requires locking 'sls_mu' exclusively}}
433 }
434 
gb_bad_3()435 void gb_bad_3() {
436   int x = sls_guardby_var; // \
437     // expected-warning {{reading variable 'sls_guardby_var' requires locking 'sls_mu'}}
438 }
439 
gb_bad_4()440 void gb_bad_4() {
441   *pgb_gvar = 1; // \
442     // expected-warning {{writing the value pointed to by 'pgb_gvar' requires locking any mutex exclusively}}
443 }
444 
gb_bad_5()445 void gb_bad_5() {
446   int x = *pgb_gvar; // \
447     // expected-warning {{reading the value pointed to by 'pgb_gvar' requires locking any mutex}}
448 }
449 
gb_bad_6()450 void gb_bad_6() {
451   *pgb_var = 1; // \
452     // expected-warning {{writing the value pointed to by 'pgb_var' requires locking 'sls_mu' exclusively}}
453 }
454 
gb_bad_7()455 void gb_bad_7() {
456   int x = *pgb_var; // \
457     // expected-warning {{reading the value pointed to by 'pgb_var' requires locking 'sls_mu'}}
458 }
459 
gb_bad_8()460 void gb_bad_8() {
461   GBFoo G;
462   G.gb_field = 0; // \
463     // expected-warning {{writing variable 'gb_field' requires locking 'sls_mu'}}
464 }
465 
gb_bad_9()466 void gb_bad_9() {
467   sls_guard_var++; // \
468     // expected-warning{{writing variable 'sls_guard_var' requires locking any mutex exclusively}}
469   sls_guard_var--; // \
470     // expected-warning{{writing variable 'sls_guard_var' requires locking any mutex exclusively}}
471   ++sls_guard_var; // \
472     // expected-warning{{writing variable 'sls_guard_var' requires locking any mutex exclusively}}
473   --sls_guard_var;// \
474     // expected-warning{{writing variable 'sls_guard_var' requires locking any mutex exclusively}}
475 }
476 
477 //-----------------------------------------------//
478 // Warnings on variables with late parsed attributes
479 // ----------------------------------------------//
480 
481 class LateFoo {
482 public:
483   int a __attribute__((guarded_by(mu)));
484   int b;
485 
foo()486   void foo() __attribute__((exclusive_locks_required(mu))) { }
487 
test()488   void test() {
489     a = 0; // \
490       // expected-warning{{writing variable 'a' requires locking 'mu' exclusively}}
491     b = a; // \
492       // expected-warning {{reading variable 'a' requires locking 'mu'}}
493     c = 0; // \
494       // expected-warning {{writing variable 'c' requires locking 'mu' exclusively}}
495   }
496 
497   int c __attribute__((guarded_by(mu)));
498 
499   Mutex mu;
500 };
501 
502 class LateBar {
503  public:
504   int a_ __attribute__((guarded_by(mu1_)));
505   int b_;
506   int *q __attribute__((pt_guarded_by(mu)));
507   Mutex mu1_;
508   Mutex mu;
509   LateFoo Foo;
510   LateFoo Foo2;
511   LateFoo *FooPointer;
512 };
513 
514 LateBar b1, *b3;
515 
late_0()516 void late_0() {
517   LateFoo FooA;
518   LateFoo FooB;
519   FooA.mu.Lock();
520   FooA.a = 5;
521   FooA.mu.Unlock();
522 }
523 
late_1()524 void late_1() {
525   LateBar BarA;
526   BarA.FooPointer->mu.Lock();
527   BarA.FooPointer->a = 2;
528   BarA.FooPointer->mu.Unlock();
529 }
530 
late_bad_0()531 void late_bad_0() {
532   LateFoo fooA;
533   LateFoo fooB;
534   fooA.mu.Lock();
535   fooB.a = 5; // \
536     // expected-warning{{writing variable 'a' requires locking 'fooB.mu' exclusively}} \
537     // expected-note{{found near match 'fooA.mu'}}
538   fooA.mu.Unlock();
539 }
540 
late_bad_1()541 void late_bad_1() {
542   Mutex mu;
543   mu.Lock();
544   b1.mu1_.Lock();
545   int res = b1.a_ + b3->b_;
546   b3->b_ = *b1.q; // \
547     // expected-warning{{reading the value pointed to by 'q' requires locking 'b1.mu'}}
548   b1.mu1_.Unlock();
549   b1.b_ = res;
550   mu.Unlock();
551 }
552 
late_bad_2()553 void late_bad_2() {
554   LateBar BarA;
555   BarA.FooPointer->mu.Lock();
556   BarA.Foo.a = 2; // \
557     // expected-warning{{writing variable 'a' requires locking 'BarA.Foo.mu' exclusively}} \
558     // expected-note{{found near match 'BarA.FooPointer->mu'}}
559   BarA.FooPointer->mu.Unlock();
560 }
561 
late_bad_3()562 void late_bad_3() {
563   LateBar BarA;
564   BarA.Foo.mu.Lock();
565   BarA.FooPointer->a = 2; // \
566     // expected-warning{{writing variable 'a' requires locking 'BarA.FooPointer->mu' exclusively}} \
567     // expected-note{{found near match 'BarA.Foo.mu'}}
568   BarA.Foo.mu.Unlock();
569 }
570 
late_bad_4()571 void late_bad_4() {
572   LateBar BarA;
573   BarA.Foo.mu.Lock();
574   BarA.Foo2.a = 2; // \
575     // expected-warning{{writing variable 'a' requires locking 'BarA.Foo2.mu' exclusively}} \
576     // expected-note{{found near match 'BarA.Foo.mu'}}
577   BarA.Foo.mu.Unlock();
578 }
579 
580 //-----------------------------------------------//
581 // Extra warnings for shared vs. exclusive locks
582 // ----------------------------------------------//
583 
shared_fun_0()584 void shared_fun_0() {
585   sls_mu.Lock();
586   do {
587     sls_mu.Unlock();
588     sls_mu.Lock();
589   } while (getBool());
590   sls_mu.Unlock();
591 }
592 
shared_fun_1()593 void shared_fun_1() {
594   sls_mu.ReaderLock(); // \
595     // expected-warning {{mutex 'sls_mu' is locked exclusively and shared in the same scope}}
596   do {
597     sls_mu.Unlock();
598     sls_mu.Lock();  // \
599       // expected-note {{the other lock of mutex 'sls_mu' is here}}
600   } while (getBool());
601   sls_mu.Unlock();
602 }
603 
shared_fun_3()604 void shared_fun_3() {
605   if (getBool())
606     sls_mu.Lock();
607   else
608     sls_mu.Lock();
609   *pgb_var = 1;
610   sls_mu.Unlock();
611 }
612 
shared_fun_4()613 void shared_fun_4() {
614   if (getBool())
615     sls_mu.ReaderLock();
616   else
617     sls_mu.ReaderLock();
618   int x = sls_guardby_var;
619   sls_mu.Unlock();
620 }
621 
shared_fun_8()622 void shared_fun_8() {
623   if (getBool())
624     sls_mu.Lock(); // \
625       // expected-warning {{mutex 'sls_mu' is locked exclusively and shared in the same scope}}
626   else
627     sls_mu.ReaderLock(); // \
628       // expected-note {{the other lock of mutex 'sls_mu' is here}}
629   sls_mu.Unlock();
630 }
631 
shared_bad_0()632 void shared_bad_0() {
633   sls_mu.Lock();  // \
634     // expected-warning {{mutex 'sls_mu' is locked exclusively and shared in the same scope}}
635   do {
636     sls_mu.Unlock();
637     sls_mu.ReaderLock();  // \
638       // expected-note {{the other lock of mutex 'sls_mu' is here}}
639   } while (getBool());
640   sls_mu.Unlock();
641 }
642 
shared_bad_1()643 void shared_bad_1() {
644   if (getBool())
645     sls_mu.Lock(); // \
646       // expected-warning {{mutex 'sls_mu' is locked exclusively and shared in the same scope}}
647   else
648     sls_mu.ReaderLock(); // \
649       // expected-note {{the other lock of mutex 'sls_mu' is here}}
650   *pgb_var = 1;
651   sls_mu.Unlock();
652 }
653 
shared_bad_2()654 void shared_bad_2() {
655   if (getBool())
656     sls_mu.ReaderLock(); // \
657       // expected-warning {{mutex 'sls_mu' is locked exclusively and shared in the same scope}}
658   else
659     sls_mu.Lock(); // \
660       // expected-note {{the other lock of mutex 'sls_mu' is here}}
661   *pgb_var = 1;
662   sls_mu.Unlock();
663 }
664 
665 // FIXME: Add support for functions (not only methods)
666 class LRBar {
667  public:
668   void aa_elr_fun() __attribute__((exclusive_locks_required(aa_mu)));
669   void aa_elr_fun_s() __attribute__((shared_locks_required(aa_mu)));
670   void le_fun() __attribute__((locks_excluded(sls_mu)));
671 };
672 
673 class LRFoo {
674  public:
675   void test() __attribute__((exclusive_locks_required(sls_mu)));
676   void testShared() __attribute__((shared_locks_required(sls_mu2)));
677 };
678 
679 void elr_fun() __attribute__((exclusive_locks_required(sls_mu)));
elr_fun()680 void elr_fun() {}
681 
682 LRFoo MyLRFoo;
683 LRBar Bar;
684 
es_fun_0()685 void es_fun_0() {
686   aa_mu.Lock();
687   Bar.aa_elr_fun();
688   aa_mu.Unlock();
689 }
690 
es_fun_1()691 void es_fun_1() {
692   aa_mu.Lock();
693   Bar.aa_elr_fun_s();
694   aa_mu.Unlock();
695 }
696 
es_fun_2()697 void es_fun_2() {
698   aa_mu.ReaderLock();
699   Bar.aa_elr_fun_s();
700   aa_mu.Unlock();
701 }
702 
es_fun_3()703 void es_fun_3() {
704   sls_mu.Lock();
705   MyLRFoo.test();
706   sls_mu.Unlock();
707 }
708 
es_fun_4()709 void es_fun_4() {
710   sls_mu2.Lock();
711   MyLRFoo.testShared();
712   sls_mu2.Unlock();
713 }
714 
es_fun_5()715 void es_fun_5() {
716   sls_mu2.ReaderLock();
717   MyLRFoo.testShared();
718   sls_mu2.Unlock();
719 }
720 
es_fun_6()721 void es_fun_6() {
722   Bar.le_fun();
723 }
724 
es_fun_7()725 void es_fun_7() {
726   sls_mu.Lock();
727   elr_fun();
728   sls_mu.Unlock();
729 }
730 
731 void es_fun_8() __attribute__((no_thread_safety_analysis));
732 
es_fun_8()733 void es_fun_8() {
734   Bar.aa_elr_fun_s();
735 }
736 
737 void es_fun_9() __attribute__((shared_locks_required(aa_mu)));
es_fun_9()738 void es_fun_9() {
739   Bar.aa_elr_fun_s();
740 }
741 
742 void es_fun_10() __attribute__((exclusive_locks_required(aa_mu)));
es_fun_10()743 void es_fun_10() {
744   Bar.aa_elr_fun_s();
745 }
746 
es_bad_0()747 void es_bad_0() {
748   Bar.aa_elr_fun(); // \
749     // expected-warning {{calling function 'aa_elr_fun' requires exclusive lock on 'aa_mu'}}
750 }
751 
es_bad_1()752 void es_bad_1() {
753   aa_mu.ReaderLock();
754   Bar.aa_elr_fun(); // \
755     // expected-warning {{calling function 'aa_elr_fun' requires exclusive lock on 'aa_mu'}}
756   aa_mu.Unlock();
757 }
758 
es_bad_2()759 void es_bad_2() {
760   Bar.aa_elr_fun_s(); // \
761     // expected-warning {{calling function 'aa_elr_fun_s' requires shared lock on 'aa_mu'}}
762 }
763 
es_bad_3()764 void es_bad_3() {
765   MyLRFoo.test(); // \
766     // expected-warning {{calling function 'test' requires exclusive lock on 'sls_mu'}}
767 }
768 
es_bad_4()769 void es_bad_4() {
770   MyLRFoo.testShared(); // \
771     // expected-warning {{calling function 'testShared' requires shared lock on 'sls_mu2'}}
772 }
773 
es_bad_5()774 void es_bad_5() {
775   sls_mu.ReaderLock();
776   MyLRFoo.test(); // \
777     // expected-warning {{calling function 'test' requires exclusive lock on 'sls_mu'}}
778   sls_mu.Unlock();
779 }
780 
es_bad_6()781 void es_bad_6() {
782   sls_mu.Lock();
783   Bar.le_fun(); // \
784     // expected-warning {{cannot call function 'le_fun' while mutex 'sls_mu' is locked}}
785   sls_mu.Unlock();
786 }
787 
es_bad_7()788 void es_bad_7() {
789   sls_mu.ReaderLock();
790   Bar.le_fun(); // \
791     // expected-warning {{cannot call function 'le_fun' while mutex 'sls_mu' is locked}}
792   sls_mu.Unlock();
793 }
794 
795 
796 //-----------------------------------------------//
797 // Unparseable lock expressions
798 // ----------------------------------------------//
799 
800 // FIXME -- derive new tests for unhandled expressions
801 
802 
803 //----------------------------------------------------------------------------//
804 // The following test cases are ported from the gcc thread safety implementation
805 // They are each wrapped inside a namespace with the test number of the gcc test
806 //
807 // FIXME: add all the gcc tests, once this analysis passes them.
808 //----------------------------------------------------------------------------//
809 
810 //-----------------------------------------//
811 // Good testcases (no errors)
812 //-----------------------------------------//
813 
814 namespace thread_annot_lock_20 {
815 class Bar {
816  public:
817   static int func1() EXCLUSIVE_LOCKS_REQUIRED(mu1_);
818   static int b_ GUARDED_BY(mu1_);
819   static Mutex mu1_;
820   static int a_ GUARDED_BY(mu1_);
821 };
822 
823 Bar b1;
824 
func1()825 int Bar::func1()
826 {
827   int res = 5;
828 
829   if (a_ == 4)
830     res = b_;
831   return res;
832 }
833 } // end namespace thread_annot_lock_20
834 
835 namespace thread_annot_lock_22 {
836 // Test various usage of GUARDED_BY and PT_GUARDED_BY annotations, especially
837 // uses in class definitions.
838 Mutex mu;
839 
840 class Bar {
841  public:
842   int a_ GUARDED_BY(mu1_);
843   int b_;
844   int *q PT_GUARDED_BY(mu);
845   Mutex mu1_ ACQUIRED_AFTER(mu);
846 };
847 
848 Bar b1, *b3;
849 int *p GUARDED_BY(mu) PT_GUARDED_BY(mu);
850 int res GUARDED_BY(mu) = 5;
851 
func(int i)852 int func(int i)
853 {
854   int x;
855   mu.Lock();
856   b1.mu1_.Lock();
857   res = b1.a_ + b3->b_;
858   *p = i;
859   b1.a_ = res + b3->b_;
860   b3->b_ = *b1.q;
861   b1.mu1_.Unlock();
862   b1.b_ = res;
863   x = res;
864   mu.Unlock();
865   return x;
866 }
867 } // end namespace thread_annot_lock_22
868 
869 namespace thread_annot_lock_27_modified {
870 // test lock annotations applied to function definitions
871 // Modified: applied annotations only to function declarations
872 Mutex mu1;
873 Mutex mu2 ACQUIRED_AFTER(mu1);
874 
875 class Foo {
876  public:
877   int method1(int i) SHARED_LOCKS_REQUIRED(mu2) EXCLUSIVE_LOCKS_REQUIRED(mu1);
878 };
879 
method1(int i)880 int Foo::method1(int i) {
881   return i;
882 }
883 
884 
885 int foo(int i) EXCLUSIVE_LOCKS_REQUIRED(mu2) SHARED_LOCKS_REQUIRED(mu1);
foo(int i)886 int foo(int i) {
887   return i;
888 }
889 
890 static int bar(int i) EXCLUSIVE_LOCKS_REQUIRED(mu1);
bar(int i)891 static int bar(int i) {
892   return i;
893 }
894 
main()895 void main() {
896   Foo a;
897 
898   mu1.Lock();
899   mu2.Lock();
900   a.method1(1);
901   foo(2);
902   mu2.Unlock();
903   bar(3);
904   mu1.Unlock();
905 }
906 } // end namespace thread_annot_lock_27_modified
907 
908 
909 namespace thread_annot_lock_38 {
910 // Test the case where a template member function is annotated with lock
911 // attributes in a non-template class.
912 class Foo {
913  public:
914   void func1(int y) LOCKS_EXCLUDED(mu_);
915   template <typename T> void func2(T x) LOCKS_EXCLUDED(mu_);
916  private:
917   Mutex mu_;
918 };
919 
920 Foo *foo;
921 
main()922 void main()
923 {
924   foo->func1(5);
925   foo->func2(5);
926 }
927 } // end namespace thread_annot_lock_38
928 
929 namespace thread_annot_lock_43 {
930 // Tests lock canonicalization
931 class Foo {
932  public:
933   Mutex *mu_;
934 };
935 
936 class FooBar {
937  public:
938   Foo *foo_;
GetA()939   int GetA() EXCLUSIVE_LOCKS_REQUIRED(foo_->mu_) { return a_; }
940   int a_ GUARDED_BY(foo_->mu_);
941 };
942 
943 FooBar *fb;
944 
main()945 void main()
946 {
947   int x;
948   fb->foo_->mu_->Lock();
949   x = fb->GetA();
950   fb->foo_->mu_->Unlock();
951 }
952 } // end namespace thread_annot_lock_43
953 
954 namespace thread_annot_lock_49 {
955 // Test the support for use of lock expression in the annotations
956 class Foo {
957  public:
958   Mutex foo_mu_;
959 };
960 
961 class Bar {
962  private:
963   Foo *foo;
964   Mutex bar_mu_ ACQUIRED_AFTER(foo->foo_mu_);
965 
966  public:
Test1()967   void Test1() {
968     foo->foo_mu_.Lock();
969     bar_mu_.Lock();
970     bar_mu_.Unlock();
971     foo->foo_mu_.Unlock();
972   }
973 };
974 
main()975 void main() {
976   Bar bar;
977   bar.Test1();
978 }
979 } // end namespace thread_annot_lock_49
980 
981 namespace thread_annot_lock_61_modified {
982   // Modified to fix the compiler errors
983   // Test the fix for a bug introduced by the support of pass-by-reference
984   // paramters.
operator <<thread_annot_lock_61_modified::Foo985   struct Foo { Foo &operator<< (bool) {return *this;} };
986   Foo &getFoo();
functhread_annot_lock_61_modified::Bar987   struct Bar { Foo &func () {return getFoo();} };
operator &thread_annot_lock_61_modified::Bas988   struct Bas { void operator& (Foo &) {} };
mumble()989   void mumble()
990   {
991     Bas() & Bar().func() << "" << "";
992     Bas() & Bar().func() << "";
993   }
994 } // end namespace thread_annot_lock_61_modified
995 
996 
997 namespace thread_annot_lock_65 {
998 // Test the fix for a bug in the support of allowing reader locks for
999 // non-const, non-modifying overload functions. (We didn't handle the builtin
1000 // properly.)
1001 enum MyFlags {
1002   Zero,
1003   One,
1004   Two,
1005   Three,
1006   Four,
1007   Five,
1008   Six,
1009   Seven,
1010   Eight,
1011   Nine
1012 };
1013 
1014 inline MyFlags
operator |(MyFlags a,MyFlags b)1015 operator|(MyFlags a, MyFlags b)
1016 {
1017   return MyFlags(static_cast<int>(a) | static_cast<int>(b));
1018 }
1019 
1020 inline MyFlags&
operator |=(MyFlags & a,MyFlags b)1021 operator|=(MyFlags& a, MyFlags b)
1022 {
1023     return a = a | b;
1024 }
1025 } // end namespace thread_annot_lock_65
1026 
1027 namespace thread_annot_lock_66_modified {
1028 // Modified: Moved annotation to function defn
1029 // Test annotations on out-of-line definitions of member functions where the
1030 // annotations refer to locks that are also data members in the class.
1031 Mutex mu;
1032 
1033 class Foo {
1034  public:
1035   int method1(int i) SHARED_LOCKS_REQUIRED(mu1, mu, mu2);
1036   int data GUARDED_BY(mu1);
1037   Mutex *mu1;
1038   Mutex *mu2;
1039 };
1040 
method1(int i)1041 int Foo::method1(int i)
1042 {
1043   return data + i;
1044 }
1045 
main()1046 void main()
1047 {
1048   Foo a;
1049 
1050   a.mu2->Lock();
1051   a.mu1->Lock();
1052   mu.Lock();
1053   a.method1(1);
1054   mu.Unlock();
1055   a.mu1->Unlock();
1056   a.mu2->Unlock();
1057 }
1058 } // end namespace thread_annot_lock_66_modified
1059 
1060 namespace thread_annot_lock_68_modified {
1061 // Test a fix to a bug in the delayed name binding with nested template
1062 // instantiation. We use a stack to make sure a name is not resolved to an
1063 // inner context.
1064 template <typename T>
1065 class Bar {
1066   Mutex mu_;
1067 };
1068 
1069 template <typename T>
1070 class Foo {
1071  public:
func(T x)1072   void func(T x) {
1073     mu_.Lock();
1074     count_ = x;
1075     mu_.Unlock();
1076   }
1077 
1078  private:
1079   T count_ GUARDED_BY(mu_);
1080   Bar<T> bar_;
1081   Mutex mu_;
1082 };
1083 
main()1084 void main()
1085 {
1086   Foo<int> *foo;
1087   foo->func(5);
1088 }
1089 } // end namespace thread_annot_lock_68_modified
1090 
1091 namespace thread_annot_lock_30_modified {
1092 // Test delay parsing of lock attribute arguments with nested classes.
1093 // Modified: trylocks replaced with exclusive_lock_fun
1094 int a = 0;
1095 
1096 class Bar {
1097   struct Foo;
1098 
1099  public:
1100   void MyLock() EXCLUSIVE_LOCK_FUNCTION(mu);
1101 
func()1102   int func() {
1103     MyLock();
1104 //    if (foo == 0) {
1105 //      return 0;
1106 //    }
1107     a = 5;
1108     mu.Unlock();
1109     return 1;
1110   }
1111 
1112   class FooBar {
1113     int x;
1114     int y;
1115   };
1116 
1117  private:
1118   Mutex mu;
1119 };
1120 
1121 Bar *bar;
1122 
main()1123 void main()
1124 {
1125   bar->func();
1126 }
1127 } // end namespace thread_annot_lock_30_modified
1128 
1129 namespace thread_annot_lock_47 {
1130 // Test the support for annotations on virtual functions.
1131 // This is a good test case. (i.e. There should be no warning emitted by the
1132 // compiler.)
1133 class Base {
1134  public:
1135   virtual void func1() EXCLUSIVE_LOCKS_REQUIRED(mu_);
1136   virtual void func2() LOCKS_EXCLUDED(mu_);
1137   Mutex mu_;
1138 };
1139 
1140 class Child : public Base {
1141  public:
1142   virtual void func1() EXCLUSIVE_LOCKS_REQUIRED(mu_);
1143   virtual void func2() LOCKS_EXCLUDED(mu_);
1144 };
1145 
main()1146 void main() {
1147   Child *c;
1148   Base *b = c;
1149 
1150   b->mu_.Lock();
1151   b->func1();
1152   b->mu_.Unlock();
1153   b->func2();
1154 
1155   c->mu_.Lock();
1156   c->func1();
1157   c->mu_.Unlock();
1158   c->func2();
1159 }
1160 } // end namespace thread_annot_lock_47
1161 
1162 //-----------------------------------------//
1163 // Tests which produce errors
1164 //-----------------------------------------//
1165 
1166 namespace thread_annot_lock_13 {
1167 Mutex mu1;
1168 Mutex mu2;
1169 
1170 int g GUARDED_BY(mu1);
1171 int w GUARDED_BY(mu2);
1172 
1173 class Foo {
1174  public:
1175   void bar() LOCKS_EXCLUDED(mu_, mu1);
1176   int foo() SHARED_LOCKS_REQUIRED(mu_) EXCLUSIVE_LOCKS_REQUIRED(mu2);
1177 
1178  private:
1179   int a_ GUARDED_BY(mu_);
1180  public:
1181   Mutex mu_ ACQUIRED_AFTER(mu1);
1182 };
1183 
foo()1184 int Foo::foo()
1185 {
1186   int res;
1187   w = 5;
1188   res = a_ + 5;
1189   return res;
1190 }
1191 
bar()1192 void Foo::bar()
1193 {
1194   int x;
1195   mu_.Lock();
1196   x = foo(); // expected-warning {{calling function 'foo' requires exclusive lock on 'mu2'}}
1197   a_ = x + 1;
1198   mu_.Unlock();
1199   if (x > 5) {
1200     mu1.Lock();
1201     g = 2;
1202     mu1.Unlock();
1203   }
1204 }
1205 
main()1206 void main()
1207 {
1208   Foo f1, *f2;
1209   f1.mu_.Lock();
1210   f1.bar(); // expected-warning {{cannot call function 'bar' while mutex 'f1.mu_' is locked}}
1211   mu2.Lock();
1212   f1.foo();
1213   mu2.Unlock();
1214   f1.mu_.Unlock();
1215   f2->mu_.Lock();
1216   f2->bar(); // expected-warning {{cannot call function 'bar' while mutex 'f2->mu_' is locked}}
1217   f2->mu_.Unlock();
1218   mu2.Lock();
1219   w = 2;
1220   mu2.Unlock();
1221 }
1222 } // end namespace thread_annot_lock_13
1223 
1224 namespace thread_annot_lock_18_modified {
1225 // Modified: Trylocks removed
1226 // Test the ability to distnguish between the same lock field of
1227 // different objects of a class.
1228   class Bar {
1229  public:
1230   bool MyLock() EXCLUSIVE_LOCK_FUNCTION(mu1_);
1231   void MyUnlock() UNLOCK_FUNCTION(mu1_);
1232   int a_ GUARDED_BY(mu1_);
1233 
1234  private:
1235   Mutex mu1_;
1236 };
1237 
1238 Bar *b1, *b2;
1239 
func()1240 void func()
1241 {
1242   b1->MyLock();
1243   b1->a_ = 5;
1244   b2->a_ = 3; // \
1245     // expected-warning {{writing variable 'a_' requires locking 'b2->mu1_' exclusively}} \
1246     // expected-note {{found near match 'b1->mu1_'}}
1247   b2->MyLock();
1248   b2->MyUnlock();
1249   b1->MyUnlock();
1250 }
1251 } // end namespace thread_annot_lock_18_modified
1252 
1253 namespace thread_annot_lock_21 {
1254 // Test various usage of GUARDED_BY and PT_GUARDED_BY annotations, especially
1255 // uses in class definitions.
1256 Mutex mu;
1257 
1258 class Bar {
1259  public:
1260   int a_ GUARDED_BY(mu1_);
1261   int b_;
1262   int *q PT_GUARDED_BY(mu);
1263   Mutex mu1_ ACQUIRED_AFTER(mu);
1264 };
1265 
1266 Bar b1, *b3;
1267 int *p GUARDED_BY(mu) PT_GUARDED_BY(mu);
1268 
1269 int res GUARDED_BY(mu) = 5;
1270 
func(int i)1271 int func(int i)
1272 {
1273   int x;
1274   b3->mu1_.Lock();
1275   res = b1.a_ + b3->b_; // expected-warning {{reading variable 'a_' requires locking 'b1.mu1_'}} \
1276     // expected-warning {{writing variable 'res' requires locking 'mu' exclusively}} \
1277     // expected-note {{found near match 'b3->mu1_'}}
1278   *p = i; // expected-warning {{reading variable 'p' requires locking 'mu'}} \
1279     // expected-warning {{writing the value pointed to by 'p' requires locking 'mu' exclusively}}
1280   b1.a_ = res + b3->b_; // expected-warning {{reading variable 'res' requires locking 'mu'}} \
1281     // expected-warning {{writing variable 'a_' requires locking 'b1.mu1_' exclusively}} \
1282     // expected-note {{found near match 'b3->mu1_'}}
1283   b3->b_ = *b1.q; // expected-warning {{reading the value pointed to by 'q' requires locking 'mu'}}
1284   b3->mu1_.Unlock();
1285   b1.b_ = res; // expected-warning {{reading variable 'res' requires locking 'mu'}}
1286   x = res; // expected-warning {{reading variable 'res' requires locking 'mu'}}
1287   return x;
1288 }
1289 } // end namespace thread_annot_lock_21
1290 
1291 namespace thread_annot_lock_35_modified {
1292 // Test the analyzer's ability to distinguish the lock field of different
1293 // objects.
1294 class Foo {
1295  private:
1296   Mutex lock_;
1297   int a_ GUARDED_BY(lock_);
1298 
1299  public:
Func(Foo * child)1300   void Func(Foo* child) LOCKS_EXCLUDED(lock_) {
1301      Foo *new_foo = new Foo;
1302 
1303      lock_.Lock();
1304 
1305      child->Func(new_foo); // There shouldn't be any warning here as the
1306                            // acquired lock is not in child.
1307      child->bar(7); // \
1308        // expected-warning {{calling function 'bar' requires exclusive lock on 'child->lock_'}} \
1309        // expected-note {{found near match 'lock_'}}
1310      child->a_ = 5; // \
1311        // expected-warning {{writing variable 'a_' requires locking 'child->lock_' exclusively}} \
1312        // expected-note {{found near match 'lock_'}}
1313      lock_.Unlock();
1314   }
1315 
bar(int y)1316   void bar(int y) EXCLUSIVE_LOCKS_REQUIRED(lock_) {
1317     a_ = y;
1318   }
1319 };
1320 
1321 Foo *x;
1322 
main()1323 void main() {
1324   Foo *child = new Foo;
1325   x->Func(child);
1326 }
1327 } // end namespace thread_annot_lock_35_modified
1328 
1329 namespace thread_annot_lock_36_modified {
1330 // Modified to move the annotations to function defns.
1331 // Test the analyzer's ability to distinguish the lock field of different
1332 // objects
1333 class Foo {
1334  private:
1335   Mutex lock_;
1336   int a_ GUARDED_BY(lock_);
1337 
1338  public:
1339   void Func(Foo* child) LOCKS_EXCLUDED(lock_);
1340   void bar(int y) EXCLUSIVE_LOCKS_REQUIRED(lock_);
1341 };
1342 
Func(Foo * child)1343 void Foo::Func(Foo* child) {
1344   Foo *new_foo = new Foo;
1345 
1346   lock_.Lock();
1347 
1348   child->lock_.Lock();
1349   child->Func(new_foo); // expected-warning {{cannot call function 'Func' while mutex 'child->lock_' is locked}}
1350   child->bar(7);
1351   child->a_ = 5;
1352   child->lock_.Unlock();
1353 
1354   lock_.Unlock();
1355 }
1356 
bar(int y)1357 void Foo::bar(int y) {
1358   a_ = y;
1359 }
1360 
1361 
1362 Foo *x;
1363 
main()1364 void main() {
1365   Foo *child = new Foo;
1366   x->Func(child);
1367 }
1368 } // end namespace thread_annot_lock_36_modified
1369 
1370 
1371 namespace thread_annot_lock_42 {
1372 // Test support of multiple lock attributes of the same kind on a decl.
1373 class Foo {
1374  private:
1375   Mutex mu1, mu2, mu3;
1376   int x GUARDED_BY(mu1) GUARDED_BY(mu2);
1377   int y GUARDED_BY(mu2);
1378 
f2()1379   void f2() LOCKS_EXCLUDED(mu1) LOCKS_EXCLUDED(mu2) LOCKS_EXCLUDED(mu3) {
1380     mu2.Lock();
1381     y = 2;
1382     mu2.Unlock();
1383   }
1384 
1385  public:
f1()1386   void f1() EXCLUSIVE_LOCKS_REQUIRED(mu2) EXCLUSIVE_LOCKS_REQUIRED(mu1) {
1387     x = 5;
1388     f2(); // expected-warning {{cannot call function 'f2' while mutex 'mu1' is locked}} \
1389       // expected-warning {{cannot call function 'f2' while mutex 'mu2' is locked}}
1390   }
1391 };
1392 
1393 Foo *foo;
1394 
func()1395 void func()
1396 {
1397   foo->f1(); // expected-warning {{calling function 'f1' requires exclusive lock on 'foo->mu2'}} \
1398              // expected-warning {{calling function 'f1' requires exclusive lock on 'foo->mu1'}}
1399 }
1400 } // end namespace thread_annot_lock_42
1401 
1402 namespace thread_annot_lock_46 {
1403 // Test the support for annotations on virtual functions.
1404 class Base {
1405  public:
1406   virtual void func1() EXCLUSIVE_LOCKS_REQUIRED(mu_);
1407   virtual void func2() LOCKS_EXCLUDED(mu_);
1408   Mutex mu_;
1409 };
1410 
1411 class Child : public Base {
1412  public:
1413   virtual void func1() EXCLUSIVE_LOCKS_REQUIRED(mu_);
1414   virtual void func2() LOCKS_EXCLUDED(mu_);
1415 };
1416 
main()1417 void main() {
1418   Child *c;
1419   Base *b = c;
1420 
1421   b->func1(); // expected-warning {{calling function 'func1' requires exclusive lock on 'b->mu_'}}
1422   b->mu_.Lock();
1423   b->func2(); // expected-warning {{cannot call function 'func2' while mutex 'b->mu_' is locked}}
1424   b->mu_.Unlock();
1425 
1426   c->func1(); // expected-warning {{calling function 'func1' requires exclusive lock on 'c->mu_'}}
1427   c->mu_.Lock();
1428   c->func2(); // expected-warning {{cannot call function 'func2' while mutex 'c->mu_' is locked}}
1429   c->mu_.Unlock();
1430 }
1431 } // end namespace thread_annot_lock_46
1432 
1433 namespace thread_annot_lock_67_modified {
1434 // Modified: attributes on definitions moved to declarations
1435 // Test annotations on out-of-line definitions of member functions where the
1436 // annotations refer to locks that are also data members in the class.
1437 Mutex mu;
1438 Mutex mu3;
1439 
1440 class Foo {
1441  public:
1442   int method1(int i) SHARED_LOCKS_REQUIRED(mu1, mu, mu2, mu3);
1443   int data GUARDED_BY(mu1);
1444   Mutex *mu1;
1445   Mutex *mu2;
1446 };
1447 
method1(int i)1448 int Foo::method1(int i) {
1449   return data + i;
1450 }
1451 
main()1452 void main()
1453 {
1454   Foo a;
1455   a.method1(1); // expected-warning {{calling function 'method1' requires shared lock on 'a.mu1'}} \
1456     // expected-warning {{calling function 'method1' requires shared lock on 'mu'}} \
1457     // expected-warning {{calling function 'method1' requires shared lock on 'a.mu2'}} \
1458     // expected-warning {{calling function 'method1' requires shared lock on 'mu3'}}
1459 }
1460 } // end namespace thread_annot_lock_67_modified
1461 
1462 
1463 namespace substitution_test {
1464   class MyData  {
1465   public:
1466     Mutex mu;
1467 
lockData()1468     void lockData()    __attribute__((exclusive_lock_function(mu)))   { }
unlockData()1469     void unlockData()  __attribute__((unlock_function(mu)))           { }
1470 
doSomething()1471     void doSomething() __attribute__((exclusive_locks_required(mu)))  { }
1472   };
1473 
1474 
1475   class DataLocker {
1476   public:
lockData(MyData * d)1477     void lockData  (MyData *d) __attribute__((exclusive_lock_function(d->mu))) { }
unlockData(MyData * d)1478     void unlockData(MyData *d) __attribute__((unlock_function(d->mu)))         { }
1479   };
1480 
1481 
1482   class Foo {
1483   public:
foo(MyData * d)1484     void foo(MyData* d) __attribute__((exclusive_locks_required(d->mu))) { }
1485 
bar1(MyData * d)1486     void bar1(MyData* d) {
1487       d->lockData();
1488       foo(d);
1489       d->unlockData();
1490     }
1491 
bar2(MyData * d)1492     void bar2(MyData* d) {
1493       DataLocker dlr;
1494       dlr.lockData(d);
1495       foo(d);
1496       dlr.unlockData(d);
1497     }
1498 
bar3(MyData * d1,MyData * d2)1499     void bar3(MyData* d1, MyData* d2) {
1500       DataLocker dlr;
1501       dlr.lockData(d1);   // expected-note {{mutex acquired here}}
1502       dlr.unlockData(d2); // \
1503         // expected-warning {{unlocking 'd2->mu' that was not locked}}
1504     } // expected-warning {{mutex 'd1->mu' is still locked at the end of function}}
1505 
bar4(MyData * d1,MyData * d2)1506     void bar4(MyData* d1, MyData* d2) {
1507       DataLocker dlr;
1508       dlr.lockData(d1);
1509       foo(d2); // \
1510         // expected-warning {{calling function 'foo' requires exclusive lock on 'd2->mu'}} \
1511         // expected-note {{found near match 'd1->mu'}}
1512       dlr.unlockData(d1);
1513     }
1514   };
1515 } // end namespace substituation_test
1516 
1517 
1518 
1519 namespace constructor_destructor_tests {
1520   Mutex fooMu;
1521   int myVar GUARDED_BY(fooMu);
1522 
1523   class Foo {
1524   public:
Foo()1525     Foo()  __attribute__((exclusive_lock_function(fooMu))) { }
~Foo()1526     ~Foo() __attribute__((unlock_function(fooMu))) { }
1527   };
1528 
fooTest()1529   void fooTest() {
1530     Foo foo;
1531     myVar = 0;
1532   }
1533 }
1534 
1535 
1536 namespace invalid_lock_expression_test {
1537 
1538 class LOCKABLE MyLockable {
1539 public:
MyLockable()1540   MyLockable() __attribute__((exclusive_lock_function)) { }
~MyLockable()1541   ~MyLockable() { }
1542 };
1543 
1544 // create an empty lock expression
foo()1545 void foo() {
1546   MyLockable lock;  // \
1547     // expected-warning {{cannot resolve lock expression}}
1548 }
1549 
1550 } // end namespace invalid_lock_expression_test
1551 
1552 namespace template_member_test {
1553 
1554   struct S { int n; };
1555   struct T {
1556     Mutex m;
1557     S *s GUARDED_BY(this->m);
1558   };
1559   Mutex m;
1560   struct U {
1561     union {
1562       int n;
1563     };
1564   } *u GUARDED_BY(m);
1565 
1566   template<typename U>
1567   struct IndirectLock {
DoNaughtyThingstemplate_member_test::IndirectLock1568     int DoNaughtyThings(T *t) {
1569       u->n = 0; // expected-warning {{reading variable 'u' requires locking 'm'}}
1570       return t->s->n; // expected-warning {{reading variable 's' requires locking 't->m'}}
1571     }
1572   };
1573 
1574   template struct IndirectLock<int>; // expected-note {{here}}
1575 
1576   struct V {
1577     void f(int);
1578     void f(double);
1579 
1580     Mutex m;
1581     V *p GUARDED_BY(this->m);
1582   };
1583   template<typename U> struct W {
1584     V v;
ftemplate_member_test::W1585     void f(U u) {
1586       v.p->f(u); // expected-warning {{reading variable 'p' requires locking 'v.m'}}
1587     }
1588   };
1589   template struct W<int>; // expected-note {{here}}
1590 
1591 }
1592 
1593 namespace test_scoped_lockable {
1594 
1595 struct TestScopedLockable {
1596   Mutex mu1;
1597   Mutex mu2;
1598   int a __attribute__((guarded_by(mu1)));
1599   int b __attribute__((guarded_by(mu2)));
1600 
1601   bool getBool();
1602 
foo1test_scoped_lockable::TestScopedLockable1603   void foo1() {
1604     MutexLock mulock(&mu1);
1605     a = 5;
1606   }
1607 
foo2test_scoped_lockable::TestScopedLockable1608   void foo2() {
1609     ReaderMutexLock mulock1(&mu1);
1610     if (getBool()) {
1611       MutexLock mulock2a(&mu2);
1612       b = a + 1;
1613     }
1614     else {
1615       MutexLock mulock2b(&mu2);
1616       b = a + 2;
1617     }
1618   }
1619 
foo3test_scoped_lockable::TestScopedLockable1620   void foo3() {
1621     MutexLock mulock_a(&mu1);
1622     MutexLock mulock_b(&mu1); // \
1623       // expected-warning {{locking 'mu1' that is already locked}}
1624   }
1625 
foo4test_scoped_lockable::TestScopedLockable1626   void foo4() {
1627     MutexLock mulock1(&mu1), mulock2(&mu2);
1628     a = b+1;
1629     b = a+1;
1630   }
1631 };
1632 
1633 } // end namespace test_scoped_lockable
1634 
1635 
1636 namespace FunctionAttrTest {
1637 
1638 class Foo {
1639 public:
1640   Mutex mu_;
1641   int a GUARDED_BY(mu_);
1642 };
1643 
1644 Foo fooObj;
1645 
1646 void foo() EXCLUSIVE_LOCKS_REQUIRED(fooObj.mu_);
1647 
bar()1648 void bar() {
1649   foo();  // expected-warning {{calling function 'foo' requires exclusive lock on 'fooObj.mu_'}}
1650   fooObj.mu_.Lock();
1651   foo();
1652   fooObj.mu_.Unlock();
1653 }
1654 
1655 };  // end namespace FunctionAttrTest
1656 
1657 
1658 struct TestTryLock {
1659   Mutex mu;
1660   int a GUARDED_BY(mu);
1661   bool cond;
1662 
foo1TestTryLock1663   void foo1() {
1664     if (mu.TryLock()) {
1665       a = 1;
1666       mu.Unlock();
1667     }
1668   }
1669 
foo2TestTryLock1670   void foo2() {
1671     if (!mu.TryLock()) return;
1672     a = 2;
1673     mu.Unlock();
1674   }
1675 
foo3TestTryLock1676   void foo3() {
1677     bool b = mu.TryLock();
1678     if (b) {
1679       a = 3;
1680       mu.Unlock();
1681     }
1682   }
1683 
foo4TestTryLock1684   void foo4() {
1685     bool b = mu.TryLock();
1686     if (!b) return;
1687     a = 4;
1688     mu.Unlock();
1689   }
1690 
foo5TestTryLock1691   void foo5() {
1692     while (mu.TryLock()) {
1693       a = a + 1;
1694       mu.Unlock();
1695     }
1696   }
1697 
foo6TestTryLock1698   void foo6() {
1699     bool b = mu.TryLock();
1700     b = !b;
1701     if (b) return;
1702     a = 6;
1703     mu.Unlock();
1704   }
1705 
foo7TestTryLock1706   void foo7() {
1707     bool b1 = mu.TryLock();
1708     bool b2 = !b1;
1709     bool b3 = !b2;
1710     if (b3) {
1711       a = 7;
1712       mu.Unlock();
1713     }
1714   }
1715 
1716   // Test use-def chains: join points
foo8TestTryLock1717   void foo8() {
1718     bool b  = mu.TryLock();
1719     bool b2 = b;
1720     if (cond)
1721       b = true;
1722     if (b) {    // b should be unknown at this point, because of the join point
1723       a = 8;    // expected-warning {{writing variable 'a' requires locking 'mu' exclusively}}
1724     }
1725     if (b2) {   // b2 should be known at this point.
1726       a = 8;
1727       mu.Unlock();
1728     }
1729   }
1730 
1731   // Test use-def-chains: back edges
foo9TestTryLock1732   void foo9() {
1733     bool b = mu.TryLock();
1734 
1735     for (int i = 0; i < 10; ++i);
1736 
1737     if (b) {  // b is still known, because the loop doesn't alter it
1738       a = 9;
1739       mu.Unlock();
1740     }
1741   }
1742 
1743   // Test use-def chains: back edges
foo10TestTryLock1744   void foo10() {
1745     bool b = mu.TryLock();
1746 
1747     while (cond) {
1748       if (b) {   // b should be uknown at this point b/c of the loop
1749         a = 10;  // expected-warning {{writing variable 'a' requires locking 'mu' exclusively}}
1750       }
1751       b = !b;
1752     }
1753   }
1754 };  // end TestTrylock
1755 
1756 
1757 namespace TestTemplateAttributeInstantiation {
1758 
1759 class Foo1 {
1760 public:
1761   Mutex mu_;
1762   int a GUARDED_BY(mu_);
1763 };
1764 
1765 class Foo2 {
1766 public:
1767   int a GUARDED_BY(mu_);
1768   Mutex mu_;
1769 };
1770 
1771 
1772 class Bar {
1773 public:
1774   // Test non-dependent expressions in attributes on template functions
1775   template <class T>
barND(Foo1 * foo,T * fooT)1776   void barND(Foo1 *foo, T *fooT) EXCLUSIVE_LOCKS_REQUIRED(foo->mu_) {
1777     foo->a = 0;
1778   }
1779 
1780   // Test dependent expressions in attributes on template functions
1781   template <class T>
barD(Foo1 * foo,T * fooT)1782   void barD(Foo1 *foo, T *fooT) EXCLUSIVE_LOCKS_REQUIRED(fooT->mu_) {
1783     fooT->a = 0;
1784   }
1785 };
1786 
1787 
1788 template <class T>
1789 class BarT {
1790 public:
1791   Foo1 fooBase;
1792   T    fooBaseT;
1793 
1794   // Test non-dependent expression in ordinary method on template class
barND()1795   void barND() EXCLUSIVE_LOCKS_REQUIRED(fooBase.mu_) {
1796     fooBase.a = 0;
1797   }
1798 
1799   // Test dependent expressions in ordinary methods on template class
barD()1800   void barD() EXCLUSIVE_LOCKS_REQUIRED(fooBaseT.mu_) {
1801     fooBaseT.a = 0;
1802   }
1803 
1804   // Test dependent expressions in template method in template class
1805   template <class T2>
barTD(T2 * fooT)1806   void barTD(T2 *fooT) EXCLUSIVE_LOCKS_REQUIRED(fooBaseT.mu_, fooT->mu_) {
1807     fooBaseT.a = 0;
1808     fooT->a = 0;
1809   }
1810 };
1811 
1812 template <class T>
1813 class Cell {
1814 public:
1815   Mutex mu_;
1816   // Test dependent guarded_by
1817   T data GUARDED_BY(mu_);
1818 
fooEx()1819   void fooEx() EXCLUSIVE_LOCKS_REQUIRED(mu_) {
1820     data = 0;
1821   }
1822 
foo()1823   void foo() {
1824     mu_.Lock();
1825     data = 0;
1826     mu_.Unlock();
1827   }
1828 };
1829 
test()1830 void test() {
1831   Bar b;
1832   BarT<Foo2> bt;
1833   Foo1 f1;
1834   Foo2 f2;
1835 
1836   f1.mu_.Lock();
1837   f2.mu_.Lock();
1838   bt.fooBase.mu_.Lock();
1839   bt.fooBaseT.mu_.Lock();
1840 
1841   b.barND(&f1, &f2);
1842   b.barD(&f1, &f2);
1843   bt.barND();
1844   bt.barD();
1845   bt.barTD(&f2);
1846 
1847   f1.mu_.Unlock();
1848   bt.barTD(&f1);  // \
1849     // expected-warning {{calling function 'barTD' requires exclusive lock on 'f1.mu_'}} \
1850     // expected-note {{found near match 'bt.fooBase.mu_'}}
1851 
1852   bt.fooBase.mu_.Unlock();
1853   bt.fooBaseT.mu_.Unlock();
1854   f2.mu_.Unlock();
1855 
1856   Cell<int> cell;
1857   cell.data = 0; // \
1858     // expected-warning {{writing variable 'data' requires locking 'cell.mu_' exclusively}}
1859   cell.foo();
1860   cell.mu_.Lock();
1861   cell.fooEx();
1862   cell.mu_.Unlock();
1863 }
1864 
1865 
1866 template <class T>
1867 class CellDelayed {
1868 public:
1869   // Test dependent guarded_by
1870   T data GUARDED_BY(mu_);
1871   static T static_data GUARDED_BY(static_mu_);
1872 
fooEx(CellDelayed<T> * other)1873   void fooEx(CellDelayed<T> *other) EXCLUSIVE_LOCKS_REQUIRED(mu_, other->mu_) {
1874     this->data = other->data;
1875   }
1876 
1877   template <class T2>
fooExT(CellDelayed<T2> * otherT)1878   void fooExT(CellDelayed<T2> *otherT) EXCLUSIVE_LOCKS_REQUIRED(mu_, otherT->mu_) {
1879     this->data = otherT->data;
1880   }
1881 
foo()1882   void foo() {
1883     mu_.Lock();
1884     data = 0;
1885     mu_.Unlock();
1886   }
1887 
1888   Mutex mu_;
1889   static Mutex static_mu_;
1890 };
1891 
testDelayed()1892 void testDelayed() {
1893   CellDelayed<int> celld;
1894   CellDelayed<int> celld2;
1895   celld.foo();
1896   celld.mu_.Lock();
1897   celld2.mu_.Lock();
1898 
1899   celld.fooEx(&celld2);
1900   celld.fooExT(&celld2);
1901 
1902   celld2.mu_.Unlock();
1903   celld.mu_.Unlock();
1904 }
1905 
1906 };  // end namespace TestTemplateAttributeInstantiation
1907 
1908 
1909 namespace FunctionDeclDefTest {
1910 
1911 class Foo {
1912 public:
1913   Mutex mu_;
1914   int a GUARDED_BY(mu_);
1915 
1916   virtual void foo1(Foo *f_declared) EXCLUSIVE_LOCKS_REQUIRED(f_declared->mu_);
1917 };
1918 
1919 // EXCLUSIVE_LOCKS_REQUIRED should be applied, and rewritten to f_defined->mu_
foo1(Foo * f_defined)1920 void Foo::foo1(Foo *f_defined) {
1921   f_defined->a = 0;
1922 };
1923 
test()1924 void test() {
1925   Foo myfoo;
1926   myfoo.foo1(&myfoo);  // \
1927     // expected-warning {{calling function 'foo1' requires exclusive lock on 'myfoo.mu_'}}
1928   myfoo.mu_.Lock();
1929   myfoo.foo1(&myfoo);
1930   myfoo.mu_.Unlock();
1931 }
1932 
1933 };
1934 
1935 namespace GoingNative {
1936 
1937   struct __attribute__((lockable)) mutex {
1938     void lock() __attribute__((exclusive_lock_function));
1939     void unlock() __attribute__((unlock_function));
1940     // ...
1941   };
1942   bool foo();
1943   bool bar();
1944   mutex m;
test()1945   void test() {
1946     m.lock();
1947     while (foo()) {
1948       m.unlock();
1949       // ...
1950       if (bar()) {
1951         // ...
1952         if (foo())
1953           continue; // expected-warning {{expecting mutex 'm' to be locked at start of each loop}}
1954         //...
1955       }
1956       // ...
1957       m.lock(); // expected-note {{mutex acquired here}}
1958     }
1959     m.unlock();
1960   }
1961 
1962 }
1963 
1964 
1965 
1966 namespace FunctionDefinitionTest {
1967 
1968 class Foo {
1969 public:
1970   void foo1();
1971   void foo2();
1972   void foo3(Foo *other);
1973 
1974   template<class T>
1975   void fooT1(const T& dummy1);
1976 
1977   template<class T>
1978   void fooT2(const T& dummy2) EXCLUSIVE_LOCKS_REQUIRED(mu_);
1979 
1980   Mutex mu_;
1981   int a GUARDED_BY(mu_);
1982 };
1983 
1984 template<class T>
1985 class FooT {
1986 public:
1987   void foo();
1988 
1989   Mutex mu_;
1990   T a GUARDED_BY(mu_);
1991 };
1992 
1993 
foo1()1994 void Foo::foo1() NO_THREAD_SAFETY_ANALYSIS {
1995   a = 1;
1996 }
1997 
foo2()1998 void Foo::foo2() EXCLUSIVE_LOCKS_REQUIRED(mu_) {
1999   a = 2;
2000 }
2001 
foo3(Foo * other)2002 void Foo::foo3(Foo *other) EXCLUSIVE_LOCKS_REQUIRED(other->mu_) {
2003   other->a = 3;
2004 }
2005 
2006 template<class T>
fooT1(const T & dummy1)2007 void Foo::fooT1(const T& dummy1) EXCLUSIVE_LOCKS_REQUIRED(mu_) {
2008   a = dummy1;
2009 }
2010 
2011 /* TODO -- uncomment with template instantiation of attributes.
2012 template<class T>
2013 void Foo::fooT2(const T& dummy2) {
2014   a = dummy2;
2015 }
2016 */
2017 
fooF1(Foo * f)2018 void fooF1(Foo *f) EXCLUSIVE_LOCKS_REQUIRED(f->mu_) {
2019   f->a = 1;
2020 }
2021 
2022 void fooF2(Foo *f);
fooF2(Foo * f)2023 void fooF2(Foo *f) EXCLUSIVE_LOCKS_REQUIRED(f->mu_) {
2024   f->a = 2;
2025 }
2026 
2027 void fooF3(Foo *f) EXCLUSIVE_LOCKS_REQUIRED(f->mu_);
fooF3(Foo * f)2028 void fooF3(Foo *f) {
2029   f->a = 3;
2030 }
2031 
2032 template<class T>
foo()2033 void FooT<T>::foo() EXCLUSIVE_LOCKS_REQUIRED(mu_) {
2034   a = 0;
2035 }
2036 
test()2037 void test() {
2038   int dummy = 0;
2039   Foo myFoo;
2040 
2041   myFoo.foo2();        // \
2042     // expected-warning {{calling function 'foo2' requires exclusive lock on 'myFoo.mu_'}}
2043   myFoo.foo3(&myFoo);  // \
2044     // expected-warning {{calling function 'foo3' requires exclusive lock on 'myFoo.mu_'}}
2045   myFoo.fooT1(dummy);  // \
2046     // expected-warning {{calling function 'fooT1' requires exclusive lock on 'myFoo.mu_'}}
2047 
2048   myFoo.fooT2(dummy);  // \
2049     // expected-warning {{calling function 'fooT2' requires exclusive lock on 'myFoo.mu_'}}
2050 
2051   fooF1(&myFoo);  // \
2052     // expected-warning {{calling function 'fooF1' requires exclusive lock on 'myFoo.mu_'}}
2053   fooF2(&myFoo);  // \
2054     // expected-warning {{calling function 'fooF2' requires exclusive lock on 'myFoo.mu_'}}
2055   fooF3(&myFoo);  // \
2056     // expected-warning {{calling function 'fooF3' requires exclusive lock on 'myFoo.mu_'}}
2057 
2058   myFoo.mu_.Lock();
2059   myFoo.foo2();
2060   myFoo.foo3(&myFoo);
2061   myFoo.fooT1(dummy);
2062 
2063   myFoo.fooT2(dummy);
2064 
2065   fooF1(&myFoo);
2066   fooF2(&myFoo);
2067   fooF3(&myFoo);
2068   myFoo.mu_.Unlock();
2069 
2070   FooT<int> myFooT;
2071   myFooT.foo();  // \
2072     // expected-warning {{calling function 'foo' requires exclusive lock on 'myFooT.mu_'}}
2073 }
2074 
2075 } // end namespace FunctionDefinitionTest
2076 
2077 
2078 namespace SelfLockingTest {
2079 
2080 class LOCKABLE MyLock {
2081 public:
2082   int foo GUARDED_BY(this);
2083 
2084   void lock()   EXCLUSIVE_LOCK_FUNCTION();
2085   void unlock() UNLOCK_FUNCTION();
2086 
doSomething()2087   void doSomething() {
2088     this->lock();  // allow 'this' as a lock expression
2089     foo = 0;
2090     doSomethingElse();
2091     this->unlock();
2092   }
2093 
doSomethingElse()2094   void doSomethingElse() EXCLUSIVE_LOCKS_REQUIRED(this) {
2095     foo = 1;
2096   };
2097 
test()2098   void test() {
2099     foo = 2;  // \
2100       // expected-warning {{writing variable 'foo' requires locking 'this' exclusively}}
2101   }
2102 };
2103 
2104 
2105 class LOCKABLE MyLock2 {
2106 public:
2107   Mutex mu_;
2108   int foo GUARDED_BY(this);
2109 
2110   // don't check inside lock and unlock functions
lock()2111   void lock()   EXCLUSIVE_LOCK_FUNCTION() { mu_.Lock();   }
unlock()2112   void unlock() UNLOCK_FUNCTION()         { mu_.Unlock(); }
2113 
2114   // don't check inside constructors and destructors
MyLock2()2115   MyLock2()  { foo = 1; }
~MyLock2()2116   ~MyLock2() { foo = 0; }
2117 };
2118 
2119 
2120 } // end namespace SelfLockingTest
2121 
2122 
2123 namespace InvalidNonstatic {
2124 
2125 // Forward decl here causes bogus "invalid use of non-static data member"
2126 // on reference to mutex_ in guarded_by attribute.
2127 class Foo;
2128 
2129 class Foo {
2130   Mutex* mutex_;
2131 
2132   int foo __attribute__((guarded_by(mutex_)));
2133 };
2134 
2135 }  // end namespace InvalidNonStatic
2136 
2137 
2138 namespace NoReturnTest {
2139 
2140 bool condition();
2141 void fatal() __attribute__((noreturn));
2142 
2143 Mutex mu_;
2144 
test1()2145 void test1() {
2146   MutexLock lock(&mu_);
2147   if (condition()) {
2148     fatal();
2149     return;
2150   }
2151 }
2152 
2153 } // end namespace NoReturnTest
2154 
2155 
2156 namespace TestMultiDecl {
2157 
2158 class Foo {
2159 public:
2160   int GUARDED_BY(mu_) a;
2161   int GUARDED_BY(mu_) b, c;
2162 
foo()2163   void foo() {
2164     a = 0; // \
2165       // expected-warning {{writing variable 'a' requires locking 'mu_' exclusively}}
2166     b = 0; // \
2167       // expected-warning {{writing variable 'b' requires locking 'mu_' exclusively}}
2168     c = 0; // \
2169       // expected-warning {{writing variable 'c' requires locking 'mu_' exclusively}}
2170   }
2171 
2172 private:
2173   Mutex mu_;
2174 };
2175 
2176 } // end namespace TestMultiDecl
2177 
2178 
2179 namespace WarnNoDecl {
2180 
2181 class Foo {
2182   void foo(int a);  __attribute__(( // \
2183     // expected-warning {{declaration does not declare anything}}
2184     exclusive_locks_required(a))); // \
2185     // expected-warning {{attribute exclusive_locks_required ignored}}
2186 };
2187 
2188 } // end namespace WarnNoDecl
2189 
2190 
2191 
2192 namespace MoreLockExpressions {
2193 
2194 class Foo {
2195 public:
2196   Mutex mu_;
2197   int a GUARDED_BY(mu_);
2198 };
2199 
2200 class Bar {
2201 public:
2202   int b;
2203   Foo* f;
2204 
getFoo()2205   Foo& getFoo()              { return *f; }
getFoo2(int c)2206   Foo& getFoo2(int c)        { return *f; }
getFoo3(int c,int d)2207   Foo& getFoo3(int c, int d) { return *f; }
2208 
getFooey()2209   Foo& getFooey() { return *f; }
2210 };
2211 
getBarFoo(Bar & bar,int c)2212 Foo& getBarFoo(Bar &bar, int c) { return bar.getFoo2(c); }
2213 
test()2214 void test() {
2215   Foo foo;
2216   Foo *fooArray;
2217   Bar bar;
2218   int a;
2219   int b;
2220   int c;
2221 
2222   bar.getFoo().mu_.Lock();
2223   bar.getFoo().a = 0;
2224   bar.getFoo().mu_.Unlock();
2225 
2226   (bar.getFoo().mu_).Lock();   // test parenthesis
2227   bar.getFoo().a = 0;
2228   (bar.getFoo().mu_).Unlock();
2229 
2230   bar.getFoo2(a).mu_.Lock();
2231   bar.getFoo2(a).a = 0;
2232   bar.getFoo2(a).mu_.Unlock();
2233 
2234   bar.getFoo3(a, b).mu_.Lock();
2235   bar.getFoo3(a, b).a = 0;
2236   bar.getFoo3(a, b).mu_.Unlock();
2237 
2238   getBarFoo(bar, a).mu_.Lock();
2239   getBarFoo(bar, a).a = 0;
2240   getBarFoo(bar, a).mu_.Unlock();
2241 
2242   bar.getFoo2(10).mu_.Lock();
2243   bar.getFoo2(10).a = 0;
2244   bar.getFoo2(10).mu_.Unlock();
2245 
2246   bar.getFoo2(a + 1).mu_.Lock();
2247   bar.getFoo2(a + 1).a = 0;
2248   bar.getFoo2(a + 1).mu_.Unlock();
2249 
2250   (a > 0 ? fooArray[1] : fooArray[b]).mu_.Lock();
2251   (a > 0 ? fooArray[1] : fooArray[b]).a = 0;
2252   (a > 0 ? fooArray[1] : fooArray[b]).mu_.Unlock();
2253 
2254   bar.getFoo().mu_.Lock();
2255   bar.getFooey().a = 0; // \
2256     // expected-warning {{writing variable 'a' requires locking 'bar.getFooey().mu_' exclusively}} \
2257     // expected-note {{found near match 'bar.getFoo().mu_'}}
2258   bar.getFoo().mu_.Unlock();
2259 
2260   bar.getFoo2(a).mu_.Lock();
2261   bar.getFoo2(b).a = 0; // \
2262     // expected-warning {{writing variable 'a' requires locking 'bar.getFoo2(b).mu_' exclusively}} \
2263     // expected-note {{found near match 'bar.getFoo2(a).mu_'}}
2264   bar.getFoo2(a).mu_.Unlock();
2265 
2266   bar.getFoo3(a, b).mu_.Lock();
2267   bar.getFoo3(a, c).a = 0;  // \
2268     // expected-warning {{writing variable 'a' requires locking 'bar.getFoo3(a,c).mu_' exclusively}} \
2269     // expected-note {{'bar.getFoo3(a,b).mu_'}}
2270   bar.getFoo3(a, b).mu_.Unlock();
2271 
2272   getBarFoo(bar, a).mu_.Lock();
2273   getBarFoo(bar, b).a = 0;  // \
2274     // expected-warning {{writing variable 'a' requires locking 'getBarFoo(bar,b).mu_' exclusively}} \
2275     // expected-note {{'getBarFoo(bar,a).mu_'}}
2276   getBarFoo(bar, a).mu_.Unlock();
2277 
2278   (a > 0 ? fooArray[1] : fooArray[b]).mu_.Lock();
2279   (a > 0 ? fooArray[b] : fooArray[c]).a = 0; // \
2280     // expected-warning {{writing variable 'a' requires locking '((a#_)#_#fooArray[b]).mu_' exclusively}} \
2281     // expected-note {{'((a#_)#_#fooArray[_]).mu_'}}
2282   (a > 0 ? fooArray[1] : fooArray[b]).mu_.Unlock();
2283 }
2284 
2285 
2286 } // end namespace MoreLockExpressions
2287 
2288 
2289 namespace TrylockJoinPoint {
2290 
2291 class Foo {
2292   Mutex mu;
2293   bool c;
2294 
foo()2295   void foo() {
2296     if (c) {
2297       if (!mu.TryLock())
2298         return;
2299     } else {
2300       mu.Lock();
2301     }
2302     mu.Unlock();
2303   }
2304 };
2305 
2306 } // end namespace TrylockJoinPoint
2307 
2308 
2309 namespace LockReturned {
2310 
2311 class Foo {
2312 public:
2313   int a             GUARDED_BY(mu_);
2314   void foo()        EXCLUSIVE_LOCKS_REQUIRED(mu_);
2315   void foo2(Foo* f) EXCLUSIVE_LOCKS_REQUIRED(mu_, f->mu_);
2316 
2317   static void sfoo(Foo* f) EXCLUSIVE_LOCKS_REQUIRED(f->mu_);
2318 
2319   Mutex* getMu() LOCK_RETURNED(mu_);
2320 
2321   Mutex mu_;
2322 
2323   static Mutex* getMu(Foo* f) LOCK_RETURNED(f->mu_);
2324 };
2325 
2326 
2327 // Calls getMu() directly to lock and unlock
test1(Foo * f1,Foo * f2)2328 void test1(Foo* f1, Foo* f2) {
2329   f1->a = 0;       // expected-warning {{writing variable 'a' requires locking 'f1->mu_' exclusively}}
2330   f1->foo();       // expected-warning {{calling function 'foo' requires exclusive lock on 'f1->mu_'}}
2331 
2332   f1->foo2(f2);    // expected-warning {{calling function 'foo2' requires exclusive lock on 'f1->mu_'}} \
2333                    // expected-warning {{calling function 'foo2' requires exclusive lock on 'f2->mu_'}}
2334   Foo::sfoo(f1);   // expected-warning {{calling function 'sfoo' requires exclusive lock on 'f1->mu_'}}
2335 
2336   f1->getMu()->Lock();
2337 
2338   f1->a = 0;
2339   f1->foo();
2340   f1->foo2(f2); // \
2341     // expected-warning {{calling function 'foo2' requires exclusive lock on 'f2->mu_'}} \
2342     // expected-note {{found near match 'f1->mu_'}}
2343 
2344   Foo::getMu(f2)->Lock();
2345   f1->foo2(f2);
2346   Foo::getMu(f2)->Unlock();
2347 
2348   Foo::sfoo(f1);
2349 
2350   f1->getMu()->Unlock();
2351 }
2352 
2353 
2354 Mutex* getFooMu(Foo* f) LOCK_RETURNED(Foo::getMu(f));
2355 
2356 class Bar : public Foo {
2357 public:
2358   int  b            GUARDED_BY(getMu());
2359   void bar()        EXCLUSIVE_LOCKS_REQUIRED(getMu());
2360   void bar2(Bar* g) EXCLUSIVE_LOCKS_REQUIRED(getMu(this), g->getMu());
2361 
2362   static void sbar(Bar* g)  EXCLUSIVE_LOCKS_REQUIRED(g->getMu());
2363   static void sbar2(Bar* g) EXCLUSIVE_LOCKS_REQUIRED(getFooMu(g));
2364 };
2365 
2366 
2367 
2368 // Use getMu() within other attributes.
2369 // This requires at lest levels of substitution, more in the case of
test2(Bar * b1,Bar * b2)2370 void test2(Bar* b1, Bar* b2) {
2371   b1->b = 0;       // expected-warning {{writing variable 'b' requires locking 'b1->mu_' exclusively}}
2372   b1->bar();       // expected-warning {{calling function 'bar' requires exclusive lock on 'b1->mu_'}}
2373   b1->bar2(b2);    // expected-warning {{calling function 'bar2' requires exclusive lock on 'b1->mu_'}} \
2374                    // expected-warning {{calling function 'bar2' requires exclusive lock on 'b2->mu_'}}
2375   Bar::sbar(b1);   // expected-warning {{calling function 'sbar' requires exclusive lock on 'b1->mu_'}}
2376   Bar::sbar2(b1);  // expected-warning {{calling function 'sbar2' requires exclusive lock on 'b1->mu_'}}
2377 
2378   b1->getMu()->Lock();
2379 
2380   b1->b = 0;
2381   b1->bar();
2382   b1->bar2(b2);  // \
2383     // expected-warning {{calling function 'bar2' requires exclusive lock on 'b2->mu_'}} \
2384     // // expected-note {{found near match 'b1->mu_'}}
2385 
2386   b2->getMu()->Lock();
2387   b1->bar2(b2);
2388 
2389   b2->getMu()->Unlock();
2390 
2391   Bar::sbar(b1);
2392   Bar::sbar2(b1);
2393 
2394   b1->getMu()->Unlock();
2395 }
2396 
2397 
2398 // Sanity check -- lock the mutex directly, but use attributes that call getMu()
2399 // Also lock the mutex using getFooMu, which calls a lock_returned function.
test3(Bar * b1,Bar * b2)2400 void test3(Bar* b1, Bar* b2) {
2401   b1->mu_.Lock();
2402   b1->b = 0;
2403   b1->bar();
2404 
2405   getFooMu(b2)->Lock();
2406   b1->bar2(b2);
2407   getFooMu(b2)->Unlock();
2408 
2409   Bar::sbar(b1);
2410   Bar::sbar2(b1);
2411 
2412   b1->mu_.Unlock();
2413 }
2414 
2415 } // end namespace LockReturned
2416 
2417 
2418 namespace ReleasableScopedLock {
2419 
2420 class Foo {
2421   Mutex mu_;
2422   bool c;
2423   int a GUARDED_BY(mu_);
2424 
2425   void test1();
2426   void test2();
2427   void test3();
2428   void test4();
2429   void test5();
2430 };
2431 
2432 
test1()2433 void Foo::test1() {
2434   ReleasableMutexLock rlock(&mu_);
2435   rlock.Release();
2436 }
2437 
test2()2438 void Foo::test2() {
2439   ReleasableMutexLock rlock(&mu_);
2440   if (c) {            // test join point -- held/not held during release
2441     rlock.Release();
2442   }
2443 }
2444 
test3()2445 void Foo::test3() {
2446   ReleasableMutexLock rlock(&mu_);
2447   a = 0;
2448   rlock.Release();
2449   a = 1;  // expected-warning {{writing variable 'a' requires locking 'mu_' exclusively}}
2450 }
2451 
test4()2452 void Foo::test4() {
2453   ReleasableMutexLock rlock(&mu_);
2454   rlock.Release();
2455   rlock.Release();  // expected-warning {{unlocking 'mu_' that was not locked}}
2456 }
2457 
test5()2458 void Foo::test5() {
2459   ReleasableMutexLock rlock(&mu_);
2460   if (c) {
2461     rlock.Release();
2462   }
2463   // no warning on join point for managed lock.
2464   rlock.Release();  // expected-warning {{unlocking 'mu_' that was not locked}}
2465 }
2466 
2467 
2468 } // end namespace ReleasableScopedLock
2469 
2470 
2471 namespace TrylockFunctionTest {
2472 
2473 class Foo {
2474 public:
2475   Mutex mu1_;
2476   Mutex mu2_;
2477   bool c;
2478 
2479   bool lockBoth() EXCLUSIVE_TRYLOCK_FUNCTION(true, mu1_, mu2_);
2480 };
2481 
lockBoth()2482 bool Foo::lockBoth() {
2483   if (!mu1_.TryLock())
2484     return false;
2485 
2486   mu2_.Lock();
2487   if (!c) {
2488     mu1_.Unlock();
2489     mu2_.Unlock();
2490     return false;
2491   }
2492 
2493   return true;
2494 }
2495 
2496 
2497 }  // end namespace TrylockFunctionTest
2498 
2499 
2500 
2501 namespace DoubleLockBug {
2502 
2503 class Foo {
2504 public:
2505   Mutex mu_;
2506   int a GUARDED_BY(mu_);
2507 
2508   void foo1() EXCLUSIVE_LOCKS_REQUIRED(mu_);
2509   int  foo2() SHARED_LOCKS_REQUIRED(mu_);
2510 };
2511 
2512 
foo1()2513 void Foo::foo1() EXCLUSIVE_LOCKS_REQUIRED(mu_) {
2514   a = 0;
2515 }
2516 
foo2()2517 int Foo::foo2() SHARED_LOCKS_REQUIRED(mu_) {
2518   return a;
2519 }
2520 
2521 }
2522 
2523 
2524 
2525 namespace UnlockBug {
2526 
2527 class Foo {
2528 public:
2529   Mutex mutex_;
2530 
foo1()2531   void foo1() EXCLUSIVE_LOCKS_REQUIRED(mutex_) {  // expected-note {{mutex acquired here}}
2532     mutex_.Unlock();
2533   }  // expected-warning {{expecting mutex 'mutex_' to be locked at the end of function}}
2534 
2535 
foo2()2536   void foo2() SHARED_LOCKS_REQUIRED(mutex_) {   // expected-note {{mutex acquired here}}
2537     mutex_.Unlock();
2538   }  // expected-warning {{expecting mutex 'mutex_' to be locked at the end of function}}
2539 };
2540 
2541 } // end namespace UnlockBug
2542 
2543 
2544 
2545 namespace FoolishScopedLockableBug {
2546 
2547 class SCOPED_LOCKABLE WTF_ScopedLockable {
2548 public:
2549   WTF_ScopedLockable(Mutex* mu) EXCLUSIVE_LOCK_FUNCTION(mu);
2550 
2551   // have to call release() manually;
2552   ~WTF_ScopedLockable();
2553 
2554   void release() UNLOCK_FUNCTION();
2555 };
2556 
2557 
2558 class Foo {
2559   Mutex mu_;
2560   int a GUARDED_BY(mu_);
2561   bool c;
2562 
2563   void doSomething();
2564 
test1()2565   void test1() {
2566     WTF_ScopedLockable wtf(&mu_);
2567     wtf.release();
2568   }
2569 
test2()2570   void test2() {
2571     WTF_ScopedLockable wtf(&mu_);  // expected-note {{mutex acquired here}}
2572   }  // expected-warning {{mutex 'mu_' is still locked at the end of function}}
2573 
test3()2574   void test3() {
2575     if (c) {
2576       WTF_ScopedLockable wtf(&mu_);
2577       wtf.release();
2578     }
2579   }
2580 
test4()2581   void test4() {
2582     if (c) {
2583       doSomething();
2584     }
2585     else {
2586       WTF_ScopedLockable wtf(&mu_);
2587       wtf.release();
2588     }
2589   }
2590 
test5()2591   void test5() {
2592     if (c) {
2593       WTF_ScopedLockable wtf(&mu_);  // expected-note {{mutex acquired here}}
2594     }
2595   } // expected-warning {{mutex 'mu_' is not locked on every path through here}}
2596 
test6()2597   void test6() {
2598     if (c) {
2599       doSomething();
2600     }
2601     else {
2602       WTF_ScopedLockable wtf(&mu_);  // expected-note {{mutex acquired here}}
2603     }
2604   } // expected-warning {{mutex 'mu_' is not locked on every path through here}}
2605 };
2606 
2607 
2608 } // end namespace FoolishScopedLockableBug
2609 
2610 
2611 
2612 namespace TemporaryCleanupExpr {
2613 
2614 class Foo {
2615   int a GUARDED_BY(getMutexPtr().get());
2616 
2617   SmartPtr<Mutex> getMutexPtr();
2618 
2619   void test();
2620 };
2621 
2622 
test()2623 void Foo::test() {
2624   {
2625     ReaderMutexLock lock(getMutexPtr().get());
2626     int b = a;
2627   }
2628   int b = a;  // expected-warning {{reading variable 'a' requires locking 'getMutexPtr()'}}
2629 }
2630 
2631 } // end namespace TemporaryCleanupExpr
2632 
2633 
2634 
2635 namespace SmartPointerTests {
2636 
2637 class Foo {
2638 public:
2639   SmartPtr<Mutex> mu_;
2640   int a GUARDED_BY(mu_);
2641   int b GUARDED_BY(mu_.get());
2642   int c GUARDED_BY(*mu_);
2643 
2644   void Lock()   EXCLUSIVE_LOCK_FUNCTION(mu_);
2645   void Unlock() UNLOCK_FUNCTION(mu_);
2646 
2647   void test0();
2648   void test1();
2649   void test2();
2650   void test3();
2651   void test4();
2652   void test5();
2653   void test6();
2654   void test7();
2655   void test8();
2656 };
2657 
test0()2658 void Foo::test0() {
2659   a = 0;  // expected-warning {{writing variable 'a' requires locking 'mu_' exclusively}}
2660   b = 0;  // expected-warning {{writing variable 'b' requires locking 'mu_' exclusively}}
2661   c = 0;  // expected-warning {{writing variable 'c' requires locking 'mu_' exclusively}}
2662 }
2663 
test1()2664 void Foo::test1() {
2665   mu_->Lock();
2666   a = 0;
2667   b = 0;
2668   c = 0;
2669   mu_->Unlock();
2670 }
2671 
test2()2672 void Foo::test2() {
2673   (*mu_).Lock();
2674   a = 0;
2675   b = 0;
2676   c = 0;
2677   (*mu_).Unlock();
2678 }
2679 
2680 
test3()2681 void Foo::test3() {
2682   mu_.get()->Lock();
2683   a = 0;
2684   b = 0;
2685   c = 0;
2686   mu_.get()->Unlock();
2687 }
2688 
2689 
test4()2690 void Foo::test4() {
2691   MutexLock lock(mu_.get());
2692   a = 0;
2693   b = 0;
2694   c = 0;
2695 }
2696 
2697 
test5()2698 void Foo::test5() {
2699   MutexLock lock(&(*mu_));
2700   a = 0;
2701   b = 0;
2702   c = 0;
2703 }
2704 
2705 
test6()2706 void Foo::test6() {
2707   Lock();
2708   a = 0;
2709   b = 0;
2710   c = 0;
2711   Unlock();
2712 }
2713 
2714 
test7()2715 void Foo::test7() {
2716   {
2717     Lock();
2718     mu_->Unlock();
2719   }
2720   {
2721     mu_->Lock();
2722     Unlock();
2723   }
2724   {
2725     mu_.get()->Lock();
2726     mu_->Unlock();
2727   }
2728   {
2729     mu_->Lock();
2730     mu_.get()->Unlock();
2731   }
2732   {
2733     mu_.get()->Lock();
2734     (*mu_).Unlock();
2735   }
2736   {
2737     (*mu_).Lock();
2738     mu_->Unlock();
2739   }
2740 }
2741 
2742 
test8()2743 void Foo::test8() {
2744   mu_->Lock();
2745   mu_.get()->Lock();    // expected-warning {{locking 'mu_' that is already locked}}
2746   (*mu_).Lock();        // expected-warning {{locking 'mu_' that is already locked}}
2747   mu_.get()->Unlock();
2748   Unlock();             // expected-warning {{unlocking 'mu_' that was not locked}}
2749 }
2750 
2751 
2752 class Bar {
2753   SmartPtr<Foo> foo;
2754 
2755   void test0();
2756   void test1();
2757   void test2();
2758   void test3();
2759 };
2760 
2761 
test0()2762 void Bar::test0() {
2763   foo->a = 0;         // expected-warning {{writing variable 'a' requires locking 'foo->mu_' exclusively}}
2764   (*foo).b = 0;       // expected-warning {{writing variable 'b' requires locking 'foo->mu_' exclusively}}
2765   foo.get()->c = 0;   // expected-warning {{writing variable 'c' requires locking 'foo->mu_' exclusively}}
2766 }
2767 
2768 
test1()2769 void Bar::test1() {
2770   foo->mu_->Lock();
2771   foo->a = 0;
2772   (*foo).b = 0;
2773   foo.get()->c = 0;
2774   foo->mu_->Unlock();
2775 }
2776 
2777 
test2()2778 void Bar::test2() {
2779   (*foo).mu_->Lock();
2780   foo->a = 0;
2781   (*foo).b = 0;
2782   foo.get()->c = 0;
2783   foo.get()->mu_->Unlock();
2784 }
2785 
2786 
test3()2787 void Bar::test3() {
2788   MutexLock lock(foo->mu_.get());
2789   foo->a = 0;
2790   (*foo).b = 0;
2791   foo.get()->c = 0;
2792 }
2793 
2794 }  // end namespace SmartPointerTests
2795 
2796 
2797 
2798 namespace DuplicateAttributeTest {
2799 
2800 class LOCKABLE Foo {
2801 public:
2802   Mutex mu1_;
2803   Mutex mu2_;
2804   Mutex mu3_;
2805   int a GUARDED_BY(mu1_);
2806   int b GUARDED_BY(mu2_);
2807   int c GUARDED_BY(mu3_);
2808 
2809   void lock()   EXCLUSIVE_LOCK_FUNCTION();
2810   void unlock() UNLOCK_FUNCTION();
2811 
2812   void lock1()  EXCLUSIVE_LOCK_FUNCTION(mu1_);
2813   void slock1() SHARED_LOCK_FUNCTION(mu1_);
2814   void lock3()  EXCLUSIVE_LOCK_FUNCTION(mu1_, mu2_, mu3_);
2815   void locklots()
2816     EXCLUSIVE_LOCK_FUNCTION(mu1_)
2817     EXCLUSIVE_LOCK_FUNCTION(mu2_)
2818     EXCLUSIVE_LOCK_FUNCTION(mu1_, mu2_, mu3_);
2819 
2820   void unlock1() UNLOCK_FUNCTION(mu1_);
2821   void unlock3() UNLOCK_FUNCTION(mu1_, mu2_, mu3_);
2822   void unlocklots()
2823     UNLOCK_FUNCTION(mu1_)
2824     UNLOCK_FUNCTION(mu2_)
2825     UNLOCK_FUNCTION(mu1_, mu2_, mu3_);
2826 };
2827 
2828 
lock()2829 void Foo::lock()   EXCLUSIVE_LOCK_FUNCTION() { }
unlock()2830 void Foo::unlock() UNLOCK_FUNCTION()         { }
2831 
lock1()2832 void Foo::lock1()  EXCLUSIVE_LOCK_FUNCTION(mu1_) {
2833   mu1_.Lock();
2834 }
2835 
slock1()2836 void Foo::slock1() SHARED_LOCK_FUNCTION(mu1_) {
2837   mu1_.Lock();
2838 }
2839 
lock3()2840 void Foo::lock3()  EXCLUSIVE_LOCK_FUNCTION(mu1_, mu2_, mu3_) {
2841   mu1_.Lock();
2842   mu2_.Lock();
2843   mu3_.Lock();
2844 }
2845 
locklots()2846 void Foo::locklots()
2847     EXCLUSIVE_LOCK_FUNCTION(mu1_, mu2_)
2848     EXCLUSIVE_LOCK_FUNCTION(mu2_, mu3_) {
2849   mu1_.Lock();
2850   mu2_.Lock();
2851   mu3_.Lock();
2852 }
2853 
unlock1()2854 void Foo::unlock1() UNLOCK_FUNCTION(mu1_) {
2855   mu1_.Unlock();
2856 }
2857 
unlock3()2858 void Foo::unlock3() UNLOCK_FUNCTION(mu1_, mu2_, mu3_) {
2859   mu1_.Unlock();
2860   mu2_.Unlock();
2861   mu3_.Unlock();
2862 }
2863 
unlocklots()2864 void Foo::unlocklots()
2865     UNLOCK_FUNCTION(mu1_, mu2_)
2866     UNLOCK_FUNCTION(mu2_, mu3_) {
2867   mu1_.Unlock();
2868   mu2_.Unlock();
2869   mu3_.Unlock();
2870 }
2871 
2872 
test0()2873 void test0() {
2874   Foo foo;
2875   foo.lock();
2876   foo.unlock();
2877 
2878   foo.lock();
2879   foo.lock();     // expected-warning {{locking 'foo' that is already locked}}
2880   foo.unlock();
2881   foo.unlock();   // expected-warning {{unlocking 'foo' that was not locked}}
2882 }
2883 
2884 
test1()2885 void test1() {
2886   Foo foo;
2887   foo.lock1();
2888   foo.a = 0;
2889   foo.unlock1();
2890 
2891   foo.lock1();
2892   foo.lock1();    // expected-warning {{locking 'foo.mu1_' that is already locked}}
2893   foo.a = 0;
2894   foo.unlock1();
2895   foo.unlock1();  // expected-warning {{unlocking 'foo.mu1_' that was not locked}}
2896 }
2897 
2898 
test2()2899 int test2() {
2900   Foo foo;
2901   foo.slock1();
2902   int d1 = foo.a;
2903   foo.unlock1();
2904 
2905   foo.slock1();
2906   foo.slock1();    // expected-warning {{locking 'foo.mu1_' that is already locked}}
2907   int d2 = foo.a;
2908   foo.unlock1();
2909   foo.unlock1();   // expected-warning {{unlocking 'foo.mu1_' that was not locked}}
2910   return d1 + d2;
2911 }
2912 
2913 
test3()2914 void test3() {
2915   Foo foo;
2916   foo.lock3();
2917   foo.a = 0;
2918   foo.b = 0;
2919   foo.c = 0;
2920   foo.unlock3();
2921 
2922   foo.lock3();
2923   foo.lock3(); // \
2924     // expected-warning {{locking 'foo.mu1_' that is already locked}} \
2925     // expected-warning {{locking 'foo.mu2_' that is already locked}} \
2926     // expected-warning {{locking 'foo.mu3_' that is already locked}}
2927   foo.a = 0;
2928   foo.b = 0;
2929   foo.c = 0;
2930   foo.unlock3();
2931   foo.unlock3(); // \
2932     // expected-warning {{unlocking 'foo.mu1_' that was not locked}} \
2933     // expected-warning {{unlocking 'foo.mu2_' that was not locked}} \
2934     // expected-warning {{unlocking 'foo.mu3_' that was not locked}}
2935 }
2936 
2937 
testlots()2938 void testlots() {
2939   Foo foo;
2940   foo.locklots();
2941   foo.a = 0;
2942   foo.b = 0;
2943   foo.c = 0;
2944   foo.unlocklots();
2945 
2946   foo.locklots();
2947   foo.locklots(); // \
2948     // expected-warning {{locking 'foo.mu1_' that is already locked}} \
2949     // expected-warning {{locking 'foo.mu2_' that is already locked}} \
2950     // expected-warning {{locking 'foo.mu3_' that is already locked}}
2951   foo.a = 0;
2952   foo.b = 0;
2953   foo.c = 0;
2954   foo.unlocklots();
2955   foo.unlocklots(); // \
2956     // expected-warning {{unlocking 'foo.mu1_' that was not locked}} \
2957     // expected-warning {{unlocking 'foo.mu2_' that was not locked}} \
2958     // expected-warning {{unlocking 'foo.mu3_' that was not locked}}
2959 }
2960 
2961 }  // end namespace DuplicateAttributeTest
2962 
2963 
2964 
2965 namespace TryLockEqTest {
2966 
2967 class Foo {
2968   Mutex mu_;
2969   int a GUARDED_BY(mu_);
2970   bool c;
2971 
2972   int    tryLockMutexI() EXCLUSIVE_TRYLOCK_FUNCTION(1, mu_);
2973   Mutex* tryLockMutexP() EXCLUSIVE_TRYLOCK_FUNCTION(1, mu_);
2974   void unlock() UNLOCK_FUNCTION(mu_);
2975 
2976   void test1();
2977   void test2();
2978 };
2979 
2980 
test1()2981 void Foo::test1() {
2982   if (tryLockMutexP() == 0) {
2983     a = 0;  // expected-warning {{writing variable 'a' requires locking 'mu_' exclusively}}
2984     return;
2985   }
2986   a = 0;
2987   unlock();
2988 
2989   if (tryLockMutexP() != 0) {
2990     a = 0;
2991     unlock();
2992   }
2993 
2994   if (0 != tryLockMutexP()) {
2995     a = 0;
2996     unlock();
2997   }
2998 
2999   if (!(tryLockMutexP() == 0)) {
3000     a = 0;
3001     unlock();
3002   }
3003 
3004   if (tryLockMutexI() == 0) {
3005     a = 0;   // expected-warning {{writing variable 'a' requires locking 'mu_' exclusively}}
3006     return;
3007   }
3008   a = 0;
3009   unlock();
3010 
3011   if (0 == tryLockMutexI()) {
3012     a = 0;   // expected-warning {{writing variable 'a' requires locking 'mu_' exclusively}}
3013     return;
3014   }
3015   a = 0;
3016   unlock();
3017 
3018   if (tryLockMutexI() == 1) {
3019     a = 0;
3020     unlock();
3021   }
3022 
3023   if (mu_.TryLock() == false) {
3024     a = 0;   // expected-warning {{writing variable 'a' requires locking 'mu_' exclusively}}
3025     return;
3026   }
3027   a = 0;
3028   unlock();
3029 
3030   if (mu_.TryLock() == true) {
3031     a = 0;
3032     unlock();
3033   }
3034   else {
3035     a = 0;  // expected-warning {{writing variable 'a' requires locking 'mu_' exclusively}}
3036   }
3037 
3038 #if __has_feature(cxx_nullptr)
3039   if (tryLockMutexP() == nullptr) {
3040     a = 0;  // expected-warning {{writing variable 'a' requires locking 'mu_' exclusively}}
3041     return;
3042   }
3043   a = 0;
3044   unlock();
3045 #endif
3046 }
3047 
3048 
test2()3049 void Foo::test2() {
3050 /* FIXME: these tests depend on changes to the CFG.
3051  *
3052   if (mu_.TryLock() && c) {
3053     a = 0;
3054     unlock();
3055   }
3056   else return;
3057 
3058   if (c && mu_.TryLock()) {
3059     a = 0;
3060     unlock();
3061   }
3062   else return;
3063 
3064   if (!(mu_.TryLock() && c))
3065     return;
3066   a = 0;
3067   unlock();
3068 
3069   if (!(c && mu_.TryLock()))
3070     return;
3071   a = 0;
3072   unlock();
3073 
3074   if (!(mu_.TryLock() == 0) && c) {
3075     a = 0;
3076     unlock();
3077   }
3078 
3079   if (!mu_.TryLock() || c)
3080     return;
3081   a = 0;
3082   unlock();
3083 */
3084 }
3085 
3086 } // end namespace TryLockEqTest
3087 
3088 
3089 namespace ExistentialPatternMatching {
3090 
3091 class Graph {
3092 public:
3093   Mutex mu_;
3094 };
3095 
3096 void LockAllGraphs()   EXCLUSIVE_LOCK_FUNCTION(&Graph::mu_);
3097 void UnlockAllGraphs() UNLOCK_FUNCTION(&Graph::mu_);
3098 
3099 class Node {
3100 public:
3101   int a GUARDED_BY(&Graph::mu_);
3102 
foo()3103   void foo()  EXCLUSIVE_LOCKS_REQUIRED(&Graph::mu_) {
3104     a = 0;
3105   }
3106   void foo2() LOCKS_EXCLUDED(&Graph::mu_);
3107 };
3108 
test()3109 void test() {
3110   Graph g1;
3111   Graph g2;
3112   Node n1;
3113 
3114   n1.a = 0;   // expected-warning {{writing variable 'a' requires locking '&ExistentialPatternMatching::Graph::mu_' exclusively}}
3115   n1.foo();   // expected-warning {{calling function 'foo' requires exclusive lock on '&ExistentialPatternMatching::Graph::mu_'}}
3116   n1.foo2();
3117 
3118   g1.mu_.Lock();
3119   n1.a = 0;
3120   n1.foo();
3121   n1.foo2();  // expected-warning {{cannot call function 'foo2' while mutex '&ExistentialPatternMatching::Graph::mu_' is locked}}
3122   g1.mu_.Unlock();
3123 
3124   g2.mu_.Lock();
3125   n1.a = 0;
3126   n1.foo();
3127   n1.foo2();  // expected-warning {{cannot call function 'foo2' while mutex '&ExistentialPatternMatching::Graph::mu_' is locked}}
3128   g2.mu_.Unlock();
3129 
3130   LockAllGraphs();
3131   n1.a = 0;
3132   n1.foo();
3133   n1.foo2();  // expected-warning {{cannot call function 'foo2' while mutex '&ExistentialPatternMatching::Graph::mu_' is locked}}
3134   UnlockAllGraphs();
3135 
3136   LockAllGraphs();
3137   g1.mu_.Unlock();
3138 
3139   LockAllGraphs();
3140   g2.mu_.Unlock();
3141 
3142   LockAllGraphs();
3143   g1.mu_.Lock();  // expected-warning {{locking 'g1.mu_' that is already locked}}
3144   g1.mu_.Unlock();
3145 }
3146 
3147 } // end namespace ExistentialPatternMatching
3148 
3149 
3150 namespace StringIgnoreTest {
3151 
3152 class Foo {
3153 public:
3154   Mutex mu_;
3155   void lock()   EXCLUSIVE_LOCK_FUNCTION("");
3156   void unlock() UNLOCK_FUNCTION("");
3157   void goober() EXCLUSIVE_LOCKS_REQUIRED("");
3158   void roober() SHARED_LOCKS_REQUIRED("");
3159 };
3160 
3161 
3162 class Bar : public Foo {
3163 public:
bar(Foo * f)3164   void bar(Foo* f) {
3165     f->unlock();
3166     f->goober();
3167     f->roober();
3168     f->lock();
3169   };
3170 };
3171 
3172 } // end namespace StringIgnoreTest
3173 
3174 
3175 namespace LockReturnedScopeFix {
3176 
3177 class Base {
3178 protected:
3179   struct Inner;
3180   bool c;
3181 
3182   const Mutex& getLock(const Inner* i);
3183 
3184   void lockInner  (Inner* i) EXCLUSIVE_LOCK_FUNCTION(getLock(i));
3185   void unlockInner(Inner* i) UNLOCK_FUNCTION(getLock(i));
3186   void foo(Inner* i) EXCLUSIVE_LOCKS_REQUIRED(getLock(i));
3187 
3188   void bar(Inner* i);
3189 };
3190 
3191 
3192 struct Base::Inner {
3193   Mutex lock_;
3194   void doSomething() EXCLUSIVE_LOCKS_REQUIRED(lock_);
3195 };
3196 
3197 
getLock(const Inner * i)3198 const Mutex& Base::getLock(const Inner* i) LOCK_RETURNED(i->lock_) {
3199   return i->lock_;
3200 }
3201 
3202 
foo(Inner * i)3203 void Base::foo(Inner* i) {
3204   i->doSomething();
3205 }
3206 
bar(Inner * i)3207 void Base::bar(Inner* i) {
3208   if (c) {
3209     i->lock_.Lock();
3210     unlockInner(i);
3211   }
3212   else {
3213     lockInner(i);
3214     i->lock_.Unlock();
3215   }
3216 }
3217 
3218 } // end namespace LockReturnedScopeFix
3219 
3220 
3221 namespace TrylockWithCleanups {
3222 
3223 class MyString {
3224 public:
3225   MyString(const char* s);
3226   ~MyString();
3227 };
3228 
3229 struct Foo {
3230   Mutex mu_;
3231   int a GUARDED_BY(mu_);
3232 };
3233 
3234 Foo* GetAndLockFoo(const MyString& s)
3235     EXCLUSIVE_TRYLOCK_FUNCTION(true, &Foo::mu_);
3236 
test()3237 static void test() {
3238   Foo* lt = GetAndLockFoo("foo");
3239   if (!lt) return;
3240   int a = lt->a;
3241   lt->mu_.Unlock();
3242 }
3243 
3244 }
3245 
3246 
3247 namespace UniversalLock {
3248 
3249 class Foo {
3250   Mutex mu_;
3251   bool c;
3252 
3253   int a        GUARDED_BY(mu_);
3254   void r_foo() SHARED_LOCKS_REQUIRED(mu_);
3255   void w_foo() EXCLUSIVE_LOCKS_REQUIRED(mu_);
3256 
test1()3257   void test1() {
3258     int b;
3259 
3260     beginNoWarnOnReads();
3261     b = a;
3262     r_foo();
3263     endNoWarnOnReads();
3264 
3265     beginNoWarnOnWrites();
3266     a = 0;
3267     w_foo();
3268     endNoWarnOnWrites();
3269   }
3270 
3271   // don't warn on joins with universal lock
test2()3272   void test2() {
3273     if (c) {
3274       beginNoWarnOnWrites();
3275     }
3276     a = 0; // \
3277       // expected-warning {{writing variable 'a' requires locking 'mu_' exclusively}}
3278     endNoWarnOnWrites();  // \
3279       // expected-warning {{unlocking '*' that was not locked}}
3280   }
3281 
3282 
3283   // make sure the universal lock joins properly
test3()3284   void test3() {
3285     if (c) {
3286       mu_.Lock();
3287       beginNoWarnOnWrites();
3288     }
3289     else {
3290       beginNoWarnOnWrites();
3291       mu_.Lock();
3292     }
3293     a = 0;
3294     endNoWarnOnWrites();
3295     mu_.Unlock();
3296   }
3297 
3298 
3299   // combine universal lock with other locks
test4()3300   void test4() {
3301     beginNoWarnOnWrites();
3302     mu_.Lock();
3303     mu_.Unlock();
3304     endNoWarnOnWrites();
3305 
3306     mu_.Lock();
3307     beginNoWarnOnWrites();
3308     endNoWarnOnWrites();
3309     mu_.Unlock();
3310 
3311     mu_.Lock();
3312     beginNoWarnOnWrites();
3313     mu_.Unlock();
3314     endNoWarnOnWrites();
3315   }
3316 };
3317 
3318 }
3319