00001 #ifndef COMMONS_PTHREAD_BARRIER_H
00002 #define COMMONS_PTHREAD_BARRIER_H
00003 
00004 #include <commons/check.h>
00005 #include <pthread.h>
00006 
00007 #define pthread_barrier_t       my_barrier_t
00008 
00009 #ifdef PRESERVE_PTHREAD_BARRIER // don't define pthread_barrier_*()
00010 #define pthread_barrier_init    my_barrier_init
00011 #define pthread_barrier_wait    my_barrier_wait
00012 #define pthread_barrier_destroy my_barrier_destroy
00013 #endif
00014 
00015 struct my_barrier_t
00016 {
00017   pthread_mutex_t lock;
00018   pthread_cond_t cond;
00019   int required;
00020   int present;
00021 };
00022 
00023 int
00024 pthread_barrier_init(pthread_barrier_t* b, pthread_barrierattr_t*,
00025                      unsigned count)
00026 {
00027   check0(pthread_mutex_init(&b->lock, NULL));
00028   check0(pthread_cond_init (&b->cond, NULL));
00029   b->required = count;
00030   b->present = 0;
00031   return 0;
00032 }
00033 
00034 int
00035 pthread_barrier_wait(pthread_barrier_t* b)
00036 {
00037   check0(pthread_mutex_lock(&b->lock));
00038   if (++b->present == b->required) {
00039     check0(pthread_cond_broadcast(&b->cond));
00040   } else {
00041     check0(pthread_cond_wait(&b->cond, &b->lock));
00042   }
00043   check0(pthread_mutex_unlock(&b->lock));
00044   return 0;
00045 }
00046 
00047 int
00048 pthread_barrier_destroy(pthread_barrier_t* b)
00049 {
00050   check0(pthread_mutex_destroy(&b->lock));
00051   check0(pthread_cond_destroy(&b->cond));
00052   return 0;
00053 }
00054 
00055 #endif