blob: c65cc612cf735d0aea028519dcf059ec2dbfa64e [file] [log] [blame]
Dominic Chen184c6242017-03-03 18:02:02 +00001// RUN: %clang_analyze_cc1 -analyzer-checker=alpha.unix.BlockInCriticalSection -std=c++11 -verify %s
Anna Zaksc154f7b2016-09-20 20:28:50 +00002
3void sleep(int x) {}
4
5namespace std {
6struct mutex {
7 void lock() {}
8 void unlock() {}
9};
10}
11
Gabor Horvath829c6bc2017-03-10 14:50:12 +000012void getc() {}
13void fgets() {}
14void read() {}
15void recv() {}
16
17void pthread_mutex_lock() {}
18void pthread_mutex_trylock() {}
19void pthread_mutex_unlock() {}
20
21void mtx_lock() {}
22void mtx_timedlock() {}
23void mtx_trylock() {}
24void mtx_unlock() {}
25
26void testBlockInCriticalSectionWithStdMutex() {
Anna Zaksc154f7b2016-09-20 20:28:50 +000027 std::mutex m;
28 m.lock();
Gabor Horvath829c6bc2017-03-10 14:50:12 +000029 sleep(3); // expected-warning {{Call to blocking function 'sleep' inside of critical section}}
30 getc(); // expected-warning {{Call to blocking function 'getc' inside of critical section}}
31 fgets(); // expected-warning {{Call to blocking function 'fgets' inside of critical section}}
32 read(); // expected-warning {{Call to blocking function 'read' inside of critical section}}
33 recv(); // expected-warning {{Call to blocking function 'recv' inside of critical section}}
Anna Zaksc154f7b2016-09-20 20:28:50 +000034 m.unlock();
35}
36
Gabor Horvath829c6bc2017-03-10 14:50:12 +000037void testBlockInCriticalSectionWithPthreadMutex() {
38 pthread_mutex_lock();
39 sleep(3); // expected-warning {{Call to blocking function 'sleep' inside of critical section}}
40 getc(); // expected-warning {{Call to blocking function 'getc' inside of critical section}}
41 fgets(); // expected-warning {{Call to blocking function 'fgets' inside of critical section}}
42 read(); // expected-warning {{Call to blocking function 'read' inside of critical section}}
43 recv(); // expected-warning {{Call to blocking function 'recv' inside of critical section}}
44 pthread_mutex_unlock();
45
46 pthread_mutex_trylock();
47 sleep(3); // expected-warning {{Call to blocking function 'sleep' inside of critical section}}
48 getc(); // expected-warning {{Call to blocking function 'getc' inside of critical section}}
49 fgets(); // expected-warning {{Call to blocking function 'fgets' inside of critical section}}
50 read(); // expected-warning {{Call to blocking function 'read' inside of critical section}}
51 recv(); // expected-warning {{Call to blocking function 'recv' inside of critical section}}
52 pthread_mutex_unlock();
53}
54
55void testBlockInCriticalSectionC11Locks() {
56 mtx_lock();
57 sleep(3); // expected-warning {{Call to blocking function 'sleep' inside of critical section}}
58 getc(); // expected-warning {{Call to blocking function 'getc' inside of critical section}}
59 fgets(); // expected-warning {{Call to blocking function 'fgets' inside of critical section}}
60 read(); // expected-warning {{Call to blocking function 'read' inside of critical section}}
61 recv(); // expected-warning {{Call to blocking function 'recv' inside of critical section}}
62 mtx_unlock();
63
64 mtx_timedlock();
65 sleep(3); // expected-warning {{Call to blocking function 'sleep' inside of critical section}}
66 getc(); // expected-warning {{Call to blocking function 'getc' inside of critical section}}
67 fgets(); // expected-warning {{Call to blocking function 'fgets' inside of critical section}}
68 read(); // expected-warning {{Call to blocking function 'read' inside of critical section}}
69 recv(); // expected-warning {{Call to blocking function 'recv' inside of critical section}}
70 mtx_unlock();
71
72 mtx_trylock();
73 sleep(3); // expected-warning {{Call to blocking function 'sleep' inside of critical section}}
74 getc(); // expected-warning {{Call to blocking function 'getc' inside of critical section}}
75 fgets(); // expected-warning {{Call to blocking function 'fgets' inside of critical section}}
76 read(); // expected-warning {{Call to blocking function 'read' inside of critical section}}
77 recv(); // expected-warning {{Call to blocking function 'recv' inside of critical section}}
78 mtx_unlock();
79}
80
Anna Zaksc154f7b2016-09-20 20:28:50 +000081void testBlockInCriticalSectionWithNestedMutexes() {
82 std::mutex m, n, k;
83 m.lock();
84 n.lock();
85 k.lock();
Gabor Horvath829c6bc2017-03-10 14:50:12 +000086 sleep(3); // expected-warning {{Call to blocking function 'sleep' inside of critical section}}
Anna Zaksc154f7b2016-09-20 20:28:50 +000087 k.unlock();
Gabor Horvath829c6bc2017-03-10 14:50:12 +000088 sleep(5); // expected-warning {{Call to blocking function 'sleep' inside of critical section}}
Anna Zaksc154f7b2016-09-20 20:28:50 +000089 n.unlock();
Gabor Horvath829c6bc2017-03-10 14:50:12 +000090 sleep(3); // expected-warning {{Call to blocking function 'sleep' inside of critical section}}
Anna Zaksc154f7b2016-09-20 20:28:50 +000091 m.unlock();
92 sleep(3); // no-warning
93}
94
95void f() {
Gabor Horvath829c6bc2017-03-10 14:50:12 +000096 sleep(1000); // expected-warning {{Call to blocking function 'sleep' inside of critical section}}
Anna Zaksc154f7b2016-09-20 20:28:50 +000097}
98
99void testBlockInCriticalSectionInterProcedural() {
100 std::mutex m;
101 m.lock();
102 f();
103 m.unlock();
104}
105
106void testBlockInCriticalSectionUnexpectedUnlock() {
107 std::mutex m;
108 m.unlock();
109 sleep(1); // no-warning
110 m.lock();
Gabor Horvath829c6bc2017-03-10 14:50:12 +0000111 sleep(1); // expected-warning {{Call to blocking function 'sleep' inside of critical section}}
Anna Zaksc154f7b2016-09-20 20:28:50 +0000112}