diff options
Diffstat (limited to 'lib/libthr/thread/thr_cond.c')
-rw-r--r-- | lib/libthr/thread/thr_cond.c | 53 |
1 files changed, 53 insertions, 0 deletions
diff --git a/lib/libthr/thread/thr_cond.c b/lib/libthr/thread/thr_cond.c index 85eecaa..ac8035a 100644 --- a/lib/libthr/thread/thr_cond.c +++ b/lib/libthr/thread/thr_cond.c @@ -290,3 +290,56 @@ _pthread_cond_broadcast(pthread_cond_t * cond) return (cond_signal_common(cond, 1)); } + +int +_pthread_cond_wait_unlocked(pthread_cond_t *cond, pthread_mutex_t *mutex, + const struct timespec *abstime) +{ + struct pthread *curthread = _get_curthread(); + struct timespec ts, ts2, *tsp; + pthread_cond_t cv; + int ret; + + cv = *cond; + THR_UMUTEX_LOCK(curthread, &cv->c_lock); + _pthread_mutex_unlock(mutex); + + if (abstime != NULL) { + clock_gettime(cv->c_clockid, &ts); + TIMESPEC_SUB(&ts2, abstime, &ts); + tsp = &ts2; + } else + tsp = NULL; + + ret = _thr_ucond_wait(&cv->c_kerncv, &cv->c_lock, tsp, 0); + if (ret == EINTR) + ret = 0; + return (ret); +} + +int +_pthread_cond_broadcast_unlock(pthread_cond_t *cond, pthread_mutex_t *mutex, int broadcast) +{ + struct pthread *curthread = _get_curthread(); + pthread_cond_t cv; + int ret = 0; + + /* + * If the condition variable is statically initialized, perform dynamic + * initialization. + */ + if (__predict_false(*cond == NULL && + (ret = init_static(curthread, cond)) != 0)) + return (ret); + + cv = *cond; + THR_UMUTEX_LOCK(curthread, &cv->c_lock); + _pthread_mutex_unlock(mutex); + if (!broadcast) + ret = _thr_ucond_signal(&cv->c_kerncv); + else + ret = _thr_ucond_broadcast(&cv->c_kerncv); + THR_UMUTEX_UNLOCK(curthread, &cv->c_lock); + return (ret); +} + |