summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKurt Miller <kurt@cvs.openbsd.org>2007-05-25 22:38:40 +0000
committerKurt Miller <kurt@cvs.openbsd.org>2007-05-25 22:38:40 +0000
commit3e63d12de85bb03339039fd726ca30e5f9a849c2 (patch)
tree7b026359e462d95a854f89302808c4b26cb220f4
parentcf6b0419225c37055a1411362f764ffe042bfe5e (diff)
protect against races while initializing static mutexes. okay marc@ tedu@
-rw-r--r--lib/librthread/rthread_sync.c19
1 files changed, 13 insertions, 6 deletions
diff --git a/lib/librthread/rthread_sync.c b/lib/librthread/rthread_sync.c
index 47d8ccda1fa..28706b6181d 100644
--- a/lib/librthread/rthread_sync.c
+++ b/lib/librthread/rthread_sync.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: rthread_sync.c,v 1.16 2006/01/05 04:06:48 marc Exp $ */
+/* $OpenBSD: rthread_sync.c,v 1.17 2007/05/25 22:38:39 kurt Exp $ */
/*
* Copyright (c) 2004,2005 Ted Unangst <tedu@openbsd.org>
* All Rights Reserved.
@@ -37,6 +37,7 @@
#include "rthread.h"
+static _spinlock_lock_t static_init_lock = _SPINLOCK_UNLOCKED;
/*
* Internal implementation of semaphores
@@ -252,13 +253,19 @@ pthread_mutex_destroy(pthread_mutex_t *mutexp)
static int
_rthread_mutex_lock(pthread_mutex_t *mutexp, int trywait)
{
- pthread_mutex_t mutex = *mutexp;
+ pthread_mutex_t mutex;
pthread_t thread = pthread_self();
-
- if (!mutex) {
- pthread_mutex_init(mutexp, NULL);
- mutex = *mutexp;
+ int ret = 0;
+
+ if (*mutexp == NULL) {
+ _spinlock(&static_init_lock);
+ if (*mutexp == NULL)
+ ret = pthread_mutex_init(mutexp, NULL);
+ _spinunlock(&static_init_lock);
+ if (ret != 0)
+ return (EINVAL);
}
+ mutex = *mutexp;
if (mutex->owner == thread) {
if (mutex->type == PTHREAD_MUTEX_RECURSIVE) {
mutex->count++;