modified: SpatialOmicsCoord.py
[GalaxyCodeBases.git] / c_cpp / pthreadtest / 11locktest.c
blob94efaf7dad9bdef577a56935b3c7e57550ab4cad
1 /* mutexex.c */
2 /* Simple pthread example using pthread_mutex to ensure mutual exclusion */
3 /* This corrects the bug from raceexample.c */
4 /* To compile me for Linux, type: gcc -o filename filename.c -lpthread */
5 /* To execute, type: filename */
6 #define _GNU_SOURCE
7 #include <pthread.h>
8 #include <stdio.h>
9 #include <stdlib.h>
10 #include <sys/time.h> //getrusage, gettimeofday
11 #include <sys/resource.h>
13 void * simplemux1(void *);
14 void * simplemux2(void *);
15 void * simplemux3(void *);
16 void * simplemux4(void *);
17 void * simplemux5(void *);
18 void * simplespin(void *);
19 void * simplespins(void *);
20 void * simplecas1(void *);
21 void * simplecas2(void *);
22 void * simplecas3(void *);
23 void * simplecas4(void *);
24 void * simplecas5(void *);
25 void * simplena(void *);
27 int NumThreads,SumCount;
28 volatile int bignum;
29 pthread_mutex_t mut1=PTHREAD_MUTEX_INITIALIZER;
30 pthread_mutex_t mut2=PTHREAD_RECURSIVE_MUTEX_INITIALIZER_NP;
31 pthread_mutex_t mut3=PTHREAD_ERRORCHECK_MUTEX_INITIALIZER_NP;
32 pthread_mutex_t mut4=PTHREAD_ADAPTIVE_MUTEX_INITIALIZER_NP;
33 pthread_mutex_t mut5={ { 0, 0, 0, 0, PTHREAD_MUTEX_FAST_NP, 0, { 0, 0 } } };
34 pthread_spinlock_t spin,spins;
36 struct timeval __g_timeofday_start, __g_timeofday_end, __g_timeofday_diff,\
37 __g_resource_usage_tmp,__g_resource_usage_other_time;
38 struct rusage __g_resource_usage;
40 #define G_TIMER_START \
41 gettimeofday(&__g_timeofday_start,NULL)
43 #define G_TIMER_END \
44 do {\
45 getrusage(RUSAGE_SELF, &__g_resource_usage);\
46 gettimeofday(&__g_timeofday_end,NULL);\
47 timersub(&__g_timeofday_end,&__g_timeofday_start,&__g_timeofday_diff);\
48 } while (0)
50 #define G_TIMER_PRINT \
51 fprintf(stderr,\
52 "U: %ld.%06ld, S: %ld.%06ld, R: %ld.%06ld (s)\n",\
53 __g_resource_usage.ru_utime.tv_sec, __g_resource_usage.ru_utime.tv_usec,\
54 __g_resource_usage.ru_stime.tv_sec, __g_resource_usage.ru_stime.tv_usec,\
55 __g_timeofday_diff.tv_sec, __g_timeofday_diff.tv_usec);
57 int main( int argc, char *argv[] ) {
58 int i;
60 if (argc != 3) {
61 printf("Usage: %s threads to_count\n",argv[0]);
62 exit(1);
63 } else {
64 SumCount=atoi(argv[2]);
65 NumThreads=atoi(argv[1]);
66 fprintf(stderr, "Threads:%d, To_Count:%d\n\n",NumThreads,SumCount);
68 pthread_t *tid=malloc(NumThreads*sizeof(pthread_t)); /* array of thread IDs */
69 //pthread_mutex_init(&mut1, NULL);
70 pthread_spin_init(&spin, PTHREAD_PROCESS_PRIVATE);
71 pthread_spin_init(&spins, PTHREAD_PROCESS_SHARED);
73 G_TIMER_START;
74 bignum = 0;
75 for (i=0; i<NumThreads; i++) {
76 pthread_create(&tid[i], NULL, simplena, NULL);
78 for ( i = 0; i < NumThreads; i++)
79 pthread_join(tid[i], NULL);
80 fprintf(stderr, "Non-lock:\n[%d]%d ", i, bignum);
81 G_TIMER_END;
82 G_TIMER_PRINT;
83 fputs("\n", stderr);
85 G_TIMER_START;
86 bignum = 0;
87 for (i=0; i<NumThreads; i++) {
88 pthread_create(&tid[i], NULL, simplespin, NULL);
90 for ( i = 0; i < NumThreads; i++)
91 pthread_join(tid[i], NULL);
92 fprintf(stderr, "Spin-lock:\n[%d]%d PROCESS_PRIVATE ", i, bignum);
93 G_TIMER_END;
94 G_TIMER_PRINT;
96 G_TIMER_START;
97 bignum = 0;
98 for (i=0; i<NumThreads; i++) {
99 pthread_create(&tid[i], NULL, simplespins, NULL);
101 for ( i = 0; i < NumThreads; i++)
102 pthread_join(tid[i], NULL);
103 fprintf(stderr, "[%d]%d PROCESS_SHARED ", i, bignum);
104 G_TIMER_END;
105 G_TIMER_PRINT;
106 fputs("\n", stderr);
107 G_TIMER_START;
108 bignum = 0;
109 for (i=0; i<NumThreads; i++) {
110 pthread_create(&tid[i], NULL, simplemux1, NULL);
112 for ( i = 0; i < NumThreads; i++)
113 pthread_join(tid[i], NULL);
114 fprintf(stderr, "Mux-lock:\n[%d]%d NULL ", i, bignum);
115 G_TIMER_END;
116 G_TIMER_PRINT;
118 G_TIMER_START;
119 bignum = 0;
120 for (i=0; i<NumThreads; i++) {
121 pthread_create(&tid[i], NULL, simplemux2, NULL);
123 for ( i = 0; i < NumThreads; i++)
124 pthread_join(tid[i], NULL);
125 fprintf(stderr, "[%d]%d RECURSIVE ", i, bignum);
126 G_TIMER_END;
127 G_TIMER_PRINT;
128 G_TIMER_START;
129 bignum = 0;
130 for (i=0; i<NumThreads; i++) {
131 pthread_create(&tid[i], NULL, simplemux3, NULL);
133 for ( i = 0; i < NumThreads; i++)
134 pthread_join(tid[i], NULL);
135 fprintf(stderr, "[%d]%d ERRORCHECK ", i, bignum);
136 G_TIMER_END;
137 G_TIMER_PRINT;
138 G_TIMER_START;
139 bignum = 0;
140 for (i=0; i<NumThreads; i++) {
141 pthread_create(&tid[i], NULL, simplemux4, NULL);
143 for ( i = 0; i < NumThreads; i++)
144 pthread_join(tid[i], NULL);
145 fprintf(stderr, "[%d]%d ADAPTIVE ", i, bignum);
146 G_TIMER_END;
147 G_TIMER_PRINT;
148 G_TIMER_START;
149 bignum = 0;
150 for (i=0; i<NumThreads; i++) {
151 pthread_create(&tid[i], NULL, simplemux5, NULL);
153 for ( i = 0; i < NumThreads; i++)
154 pthread_join(tid[i], NULL);
155 fprintf(stderr, "[%d]%d FAST ", i, bignum);
156 G_TIMER_END;
157 G_TIMER_PRINT;
158 fputs("\n", stderr);
159 G_TIMER_START;
160 bignum = 0;
161 for (i=0; i<NumThreads; i++) {
162 pthread_create(&tid[i], NULL, simplecas1, NULL);
164 for ( i = 0; i < NumThreads; i++)
165 pthread_join(tid[i], NULL);
166 fprintf(stderr, "Atomic:\n[%d]%d fetch_and_add ", i, bignum);
167 G_TIMER_END;
168 G_TIMER_PRINT;
170 G_TIMER_START;
171 bignum = 0;
172 for (i=0; i<NumThreads; i++) {
173 pthread_create(&tid[i], NULL, simplecas2, NULL);
175 for ( i = 0; i < NumThreads; i++)
176 pthread_join(tid[i], NULL);
177 fprintf(stderr, "[%d]%d add_and_fetch ", i, bignum);
178 G_TIMER_END;
179 G_TIMER_PRINT;
181 G_TIMER_START;
182 bignum = 0;
183 for (i=0; i<NumThreads; i++) {
184 pthread_create(&tid[i], NULL, simplecas3, NULL);
186 for ( i = 0; i < NumThreads; i++)
187 pthread_join(tid[i], NULL);
188 fprintf(stderr, "[%d]%d val cmpxchg ", i, bignum);
189 G_TIMER_END;
190 G_TIMER_PRINT;
192 G_TIMER_START;
193 bignum = 0;
194 for (i=0; i<NumThreads; i++) {
195 pthread_create(&tid[i], NULL, simplecas4, NULL);
197 for ( i = 0; i < NumThreads; i++)
198 pthread_join(tid[i], NULL);
199 fprintf(stderr, "[%d]%d bool cmpxchg ", i, bignum);
200 G_TIMER_END;
201 G_TIMER_PRINT;
202 exit(0);
203 } /* main */
206 void * simplemux1(void * parm)
208 int i;
209 for(i=0;i<SumCount;i++) {
210 pthread_mutex_lock(&mut1);
211 bignum++; /* critical section */
212 pthread_mutex_unlock(&mut1);
214 return NULL;
217 void * simplemux2(void * parm)
219 int i;
220 for(i=0;i<SumCount;i++) {
221 pthread_mutex_lock(&mut2);
222 bignum++; /* critical section */
223 pthread_mutex_unlock(&mut2);
225 return NULL;
228 void * simplemux3(void * parm)
230 int i;
231 for(i=0;i<SumCount;i++) {
232 pthread_mutex_lock(&mut3);
233 bignum++; /* critical section */
234 pthread_mutex_unlock(&mut3);
236 return NULL;
239 void * simplemux4(void * parm)
241 int i;
242 for(i=0;i<SumCount;i++) {
243 pthread_mutex_lock(&mut4);
244 bignum++; /* critical section */
245 pthread_mutex_unlock(&mut4);
247 return NULL;
250 void * simplemux5(void * parm)
252 int i;
253 for(i=0;i<SumCount;i++) {
254 pthread_mutex_lock(&mut5);
255 bignum++; /* critical section */
256 pthread_mutex_unlock(&mut5);
258 return NULL;
261 void * simplespin(void * parm)
263 int i;
264 for(i=0;i<SumCount;i++) {
265 pthread_spin_lock(&spin);
266 bignum++; /* critical section */
267 pthread_spin_unlock(&spin);
269 return NULL;
272 void * simplespins(void * parm)
274 int i;
275 for(i=0;i<SumCount;i++) {
276 pthread_spin_lock(&spins);
277 bignum++; /* critical section */
278 pthread_spin_unlock(&spins);
280 return NULL;
283 void * simplecas1(void * parm)
285 int i;
286 for(i=0;i<SumCount;i++) {
287 __sync_fetch_and_add(&bignum,1); /* critical section */
289 return NULL;
291 void * simplecas2(void * parm)
293 int i;
294 for(i=0;i<SumCount;i++) {
295 __sync_add_and_fetch(&bignum,1); /* critical section */
297 return NULL;
299 void * simplecas3(void * parm)
301 int i;
302 for(i=0;i<SumCount;i++) {
303 int old,ret;
304 do {
305 old=bignum;
306 ret=__sync_val_compare_and_swap(&bignum,old,old+1);
307 //if (ret!=old) printf("O:%d R:%d\n",old,ret);
308 } while (ret!=old);
310 return NULL;
312 void * simplecas4(void * parm)
314 int i;
315 for(i=0;i<SumCount;i++) {
316 int old;
317 do {
318 old=bignum;
319 } while (!__sync_bool_compare_and_swap(&bignum,old,old+1));
321 return NULL;
324 //#pragma GCC optimize 0
325 void * simplena(void * parm)
327 register int i;
328 for(i=0;i<SumCount;++i) {
329 ++bignum; /* critical section */
331 return NULL;
333 //#pragma GCC optimize 3