1 /** Broadcast a (POSIX threads) signal to all running threads, where the
2 * number of threads can be specified on the command line. This test program
3 * is intended not only to test the correctness of drd but also to test
4 * whether performance does not degrade too much when the number of threads
17 // Counting semaphore.
21 pthread_mutex_t m_mutex
;
22 pthread_cond_t m_cond
;
26 void csema_ctr(struct csema
* p
)
28 memset(p
, 0, sizeof(*p
));
29 pthread_mutex_init(&p
->m_mutex
, 0);
30 pthread_cond_init(&p
->m_cond
, 0);
33 void csema_dtr(struct csema
* p
)
35 pthread_cond_destroy(&p
->m_cond
);
36 pthread_mutex_destroy(&p
->m_mutex
);
39 void csema_p(struct csema
* p
, const int n
)
41 pthread_mutex_lock(&p
->m_mutex
);
42 while (p
->m_count
< n
)
43 pthread_cond_wait(&p
->m_cond
, &p
->m_mutex
);
45 pthread_cond_signal(&p
->m_cond
);
46 pthread_mutex_unlock(&p
->m_mutex
);
49 void csema_v(struct csema
* p
)
51 pthread_mutex_lock(&p
->m_mutex
);
53 pthread_cond_signal(&p
->m_cond
);
54 pthread_mutex_unlock(&p
->m_mutex
);
65 void cthread_ctr(struct cthread
* p
)
71 void cthread_dtr(struct cthread
* p
)
77 static int s_debug
= 0;
78 static int s_trace
= 0;
79 static int s_signal_count
;
80 static pthread_mutex_t s_mutex
;
81 static pthread_cond_t s_cond
;
84 // Function definitions.
86 static void thread_func(struct cthread
* thread_info
)
90 pthread_mutex_lock(&s_mutex
);
92 for (i
= 0; i
< s_signal_count
; i
++)
96 printf("thread %d [%d] (1)\n", thread_info
->m_threadnum
, i
);
98 csema_v(thread_info
->m_sema
);
100 // Wait until the main thread signals us via pthread_cond_broadcast().
101 pthread_cond_wait(&s_cond
, &s_mutex
);
104 printf("thread %d [%d] (2)\n", thread_info
->m_threadnum
, i
);
108 pthread_mutex_unlock(&s_mutex
);
111 int main(int argc
, char** argv
)
116 while ((optchar
= getopt(argc
, argv
, "d")) != EOF
)
129 /* This test should complete in 15s or less. If the test does not complete */
130 /* within that time, abort the test via the signal SIGALRM. */
133 s_signal_count
= argc
> optind
? atoi(argv
[optind
]) : 10;
134 thread_count
= argc
> optind
+ 1 ? atoi(argv
[optind
+ 1]) : 10;
137 printf("&s_cond = %p\n", &s_cond
);
139 pthread_mutex_init(&s_mutex
, 0);
140 pthread_cond_init(&s_cond
, 0);
145 struct cthread
* thread_vec
;
148 thread_vec
= malloc(sizeof(struct cthread
) * thread_count
);
149 for (p
= thread_vec
; p
!= thread_vec
+ thread_count
; p
++)
152 p
->m_threadnum
= p
- thread_vec
;
154 pthread_create(&p
->m_thread
, 0,
155 (void*(*)(void*))thread_func
, &*p
);
157 for (i
= 0; i
< s_signal_count
; i
++)
160 printf("main [%d] (1)\n", i
);
161 csema_p(&sema
, thread_count
);
163 printf("main [%d] (2)\n", i
);
164 pthread_mutex_lock(&s_mutex
);
165 pthread_cond_broadcast(&s_cond
);
166 pthread_mutex_unlock(&s_mutex
);
168 printf("main [%d] (3)\n", i
);
170 for (i
= 0; i
< thread_count
; i
++)
172 pthread_join(thread_vec
[i
].m_thread
, 0);
173 cthread_dtr(&thread_vec
[i
]);
178 pthread_cond_destroy(&s_cond
);
179 pthread_mutex_destroy(&s_mutex
);
181 fprintf(stderr
, "Done.\n");