2
* Copyright (C) 1998, 1989 Transarc Corporation - All rights reserved
4
* (C) COPYRIGHT IBM CORPORATION 1987, 1988
5
* LICENSED MATERIALS - PROPERTY OF IBM
9
/* Copyright (C) 1994 Cazamar Systems, Inc. */
12
#include <afs/param.h>
21
#define OSI_MOD1LOOPS 15000
22
#define OSI_MOD2LOOPS 10000
24
/* global variables for the test */
25
osi_mutex_t main_aMutex; /* mutex controlling access to a */
26
long a; /* variable a */
28
osi_rwlock_t main_bRWLock; /* rwlock controlling access to b */
29
long b; /* variable b itself */
31
osi_rwlock_t main_doneRWLock; /* lock for done */
32
int done; /* count of done dudes */
34
osi_log_t *main_logp; /* global log */
36
/* unlocked stat counters */
43
unsigned long main_Mod1(void *parm)
46
for(i=0; i<OSI_MOD1LOOPS; i++) {
47
lock_ObtainMutex(&main_aMutex);
48
osi_Log0(main_logp, "mod1");
49
lock_ObtainWrite(&main_bRWLock);
53
osi_assert(a+b == 100);
55
lock_ReleaseWrite(&main_bRWLock);
57
lock_ReleaseMutex(&main_aMutex);
60
osi_Log1(main_logp, "mod1 done, %d", m1Loops);
62
lock_ObtainWrite(&main_doneRWLock);
65
lock_ReleaseWrite(&main_doneRWLock);
69
unsigned long main_Mod2(void *parm)
72
for(i=0; i<OSI_MOD2LOOPS; i++) {
73
osi_Log0(main_logp, "mod2");
74
lock_ObtainMutex(&main_aMutex);
75
lock_ObtainWrite(&main_bRWLock);
79
osi_assert(a+b == 100);
81
lock_ReleaseWrite(&main_bRWLock);
83
lock_ReleaseMutex(&main_aMutex);
86
osi_Log4(main_logp, "mod2 done, %d %d %d %d", m2Loops, 2, 3, 4);
88
lock_ObtainWrite(&main_doneRWLock);
91
lock_ReleaseWrite(&main_doneRWLock);
95
unsigned long main_Scan1(unsigned long parm)
98
osi_Log0(main_logp, "scan1");
99
/* check to see if we're done */
100
lock_ObtainRead(&main_doneRWLock);
101
lock_AssertRead(&main_doneRWLock);
102
if (done >= 2) break;
103
lock_ReleaseRead(&main_doneRWLock);
105
/* check state for consistency */
106
lock_ObtainMutex(&main_aMutex);
107
lock_AssertMutex(&main_aMutex);
109
lock_ObtainRead(&main_bRWLock);
111
osi_assert(a+b == 100);
112
lock_ReleaseRead(&main_bRWLock);
114
lock_ReleaseMutex(&main_aMutex);
116
/* get a read lock here to test people getting stuck on RW lock alone */
117
lock_ObtainRead(&main_bRWLock);
119
lock_ReleaseRead(&main_bRWLock);
123
osi_Log2(main_logp, "scan1 done %d %d", s1Loops, 2);
125
lock_ReleaseRead(&main_doneRWLock);
126
lock_ObtainWrite(&main_doneRWLock);
127
lock_AssertWrite(&main_doneRWLock);
129
lock_ReleaseWrite(&main_doneRWLock);
133
unsigned long main_Scan2(unsigned long parm)
136
osi_Log0(main_logp, "scan2");
137
/* check to see if we're done */
138
lock_ObtainRead(&main_doneRWLock);
139
lock_AssertAny(&main_doneRWLock);
140
if (done >= 2) break;
141
lock_ReleaseRead(&main_doneRWLock);
143
/* check state for consistency without locks */
144
if (a+b != 100) s2Events++;
146
/* and record that we went around again */
149
/* give others a chance */
151
osi_Log3(main_logp, "scan2 done %d %d %d", s2Loops, 2, 3);
153
lock_ReleaseRead(&main_doneRWLock);
154
lock_ObtainWrite(&main_doneRWLock);
155
lock_AssertAny(&main_doneRWLock);
157
lock_ReleaseWrite(&main_doneRWLock);
161
main_BasicTest(HANDLE hWnd)
175
if (main_logp == NULL) {
176
main_logp = osi_LogCreate("basic", 0);
177
osi_LogEnable(main_logp);
178
osi_SetStatLog(main_logp);
181
/* create three processes, two modifiers and one scanner. The scanner
182
* checks that the basic invariants are being maintained, while the
183
* modifiers modify the global variables, maintaining certain invariants
186
* The invariant is that global variables a and b total 100.
192
lock_InitializeRWLock(&main_doneRWLock, "done lock");
193
lock_InitializeRWLock(&main_bRWLock, "b lock");
194
lock_InitializeMutex(&main_aMutex, "a mutex");
196
mod1Handle = CreateThread((SECURITY_ATTRIBUTES *) 0, 0,
197
(LPTHREAD_START_ROUTINE) main_Mod1, 0, 0, &mod1ID);
198
if (mod1Handle == NULL) return -1;
200
mod2Handle = CreateThread((SECURITY_ATTRIBUTES *) 0, 0,
201
(LPTHREAD_START_ROUTINE) main_Mod2, 0, 0, &mod2ID);
202
if (mod2Handle == NULL) return -2;
204
scan1Handle = CreateThread((SECURITY_ATTRIBUTES *) 0, 0,
205
(LPTHREAD_START_ROUTINE) main_Scan1, 0, 0, &scan1ID);
206
if (scan1Handle== NULL) return -2;
208
scan2Handle = CreateThread((SECURITY_ATTRIBUTES *) 0, 0,
209
(LPTHREAD_START_ROUTINE) main_Scan2, 0, 0, &scan2ID);
210
if (scan2Handle== NULL) return -2;
212
/* start running check daemon */
215
wsprintf(main_screenText[1], "Mod1 iteration %d", m1Loops);
216
wsprintf(main_screenText[2], "Mod2 iteration %d", m2Loops);
217
wsprintf(main_screenText[3], "Scan1 iteration %d", s1Loops);
218
wsprintf(main_screenText[4], "Scan2 iteration %d, %d opportunites seen",
220
main_ForceDisplay(hWnd);
222
/* copy out count of # of dudes finished */
223
lock_ObtainRead(&main_doneRWLock);
225
lock_ReleaseRead(&main_doneRWLock);
227
/* right now, we're waiting for 4 threads */
228
if (localDone == 4) break;
231
wsprintf(main_screenText[0], "Test done.");
232
main_ForceDisplay(hWnd);
234
/* done, release and finalize all locks */
235
lock_FinalizeRWLock(&main_doneRWLock);
236
lock_FinalizeRWLock(&main_bRWLock);
237
lock_FinalizeMutex(&main_aMutex);
239
/* finally clean up thread handles */
240
CloseHandle(mod1Handle);
241
CloseHandle(mod2Handle);
242
CloseHandle(scan1Handle);
243
CloseHandle(scan2Handle);