source: src/tests/concurrent/signal/wait.c @ e8db295

ADTaaron-thesisarm-ehast-experimentalcleanup-dtorsdeferred_resndemanglerenumforall-pointer-decayjacob/cs343-translationjenkins-sandboxnew-astnew-ast-unique-exprnew-envno_listpersistent-indexerpthread-emulationqualifiedEnumwith_gc
Last change on this file since e8db295 was b9da9585, checked in by Thierry Delisle <tdelisle@…>, 6 years ago

Fixed long run tests

  • Property mode set to 100644
File size: 3.2 KB
Line 
1//---------------------------------------------------------
2// Multi wait test
3// Ensures that no deadlock from waiting/signalling conditions
4//---------------------------------------------------------
5
6
7#include <fstream>
8#include <kernel>
9#include <monitor>
10#include <stdlib>
11#include <thread>
12#include <time>
13
14#ifndef PREEMPTION_RATE
15#define PREEMPTION_RATE 10`ms
16#endif
17
18Duration default_preemption() {
19        return PREEMPTION_RATE;
20}
21
22#ifdef LONG_TEST
23static const unsigned long N = 375_000ul;
24#else
25static const unsigned long N = 2_500ul;
26#endif
27
28monitor global_t {};
29
30global_t globalA;
31global_t globalB;
32global_t globalC;
33
34condition condAB, condAC, condBC, condABC;
35
36thread Signaler {};
37thread WaiterAB {};
38thread WaiterAC {};
39thread WaiterBC {};
40thread WaiterABC{};
41
42volatile int waiter_left;
43
44//----------------------------------------------------------------------------------------------------
45// Tools
46void signal( condition & cond, global_t & mutex a, global_t & mutex b ) {
47        signal( cond );
48}
49
50void signal( condition & cond, global_t & mutex a, global_t & mutex b, global_t & mutex c ) {
51        signal( cond );
52}
53
54void wait( condition & cond, global_t & mutex a, global_t & mutex b ) {
55        wait( cond );
56}
57
58void wait( condition & cond, global_t & mutex a, global_t & mutex b, global_t & mutex c ) {
59        wait( cond );
60}
61
62//----------------------------------------------------------------------------------------------------
63// Signaler
64void main( Signaler & this ) {
65
66        while( waiter_left != 0 ) {
67                unsigned action = random( 4 );
68                switch( action ) {
69                        case 0:
70                                signal( condABC, globalA, globalB, globalC );
71                                break;
72                        case 1:
73                                signal( condAB , globalA, globalB );
74                                break;
75                        case 2:
76                                signal( condBC , globalB, globalC );
77                                break;
78                        case 3:
79                                signal( condAC , globalA, globalC );
80                                break;
81                        default:
82                                sout | "Something went wrong" | endl;
83                                abort();
84                }
85                yield();
86        }
87}
88
89//----------------------------------------------------------------------------------------------------
90// Waiter ABC
91void main( WaiterABC & this ) {
92        for( int i = 0; i < N; i++ ) {
93                wait( condABC, globalA, globalB, globalC );
94        }
95
96        __sync_fetch_and_sub_4( &waiter_left, 1);
97}
98
99//----------------------------------------------------------------------------------------------------
100// Waiter AB
101void main( WaiterAB & this ) {
102        for( int i = 0; i < N; i++ ) {
103                wait( condAB , globalA, globalB );
104        }
105
106        __sync_fetch_and_sub_4( &waiter_left, 1);
107}
108
109//----------------------------------------------------------------------------------------------------
110// Waiter AC
111void main( WaiterAC & this ) {
112        for( int i = 0; i < N; i++ ) {
113                wait( condAC , globalA, globalC );
114        }
115
116        __sync_fetch_and_sub_4( &waiter_left, 1);
117}
118
119//----------------------------------------------------------------------------------------------------
120// Waiter BC
121void main( WaiterBC & this ) {
122        for( int i = 0; i < N; i++ ) {
123                wait( condBC , globalB, globalC );
124        }
125
126        __sync_fetch_and_sub_4( &waiter_left, 1);
127}
128
129//----------------------------------------------------------------------------------------------------
130// Main
131int main(int argc, char* argv[]) {
132        srandom( time( NULL ) );
133        waiter_left = 4;
134        processor p[2];
135        sout | "Starting" | endl;
136        {
137                Signaler  e;
138                {
139                        WaiterABC a;
140                        WaiterAB  b;
141                        WaiterBC  c;
142                        WaiterAC  d;
143                }
144        }
145        sout | "Done" | endl;
146}
Note: See TracBrowser for help on using the repository browser.