PERFORCE change 68455 for review
David Xu
davidxu at FreeBSD.org
Thu Jan 6 21:14:33 PST 2005
http://perforce.freebsd.org/chv.cgi?CH=68455
Change 68455 by davidxu at davidxu_celeron on 2005/01/07 05:13:46
use atomic operation, remove static initializing lock.
Affected files ...
.. //depot/projects/davidxu_thread/src/lib/libthread/thread/thr_rwlock.c#3 edit
Differences ...
==== //depot/projects/davidxu_thread/src/lib/libthread/thread/thr_rwlock.c#3 (text+ko) ====
@@ -51,52 +51,9 @@
/*
* Prototypes
*/
-static int init_static(pthread_rwlock_t *rwlock);
-
static int
-init_static(pthread_rwlock_t *rwlock)
-{
- struct pthread *thread = _get_curthread();
- int ret;
-
- THR_LOCK_ACQUIRE(thread, &_rwlock_static_lock);
-
- if (*rwlock == NULL)
- ret = _pthread_rwlock_init(rwlock, NULL);
- else
- ret = 0;
-
- THR_LOCK_RELEASE(thread, &_rwlock_static_lock);
- return (ret);
-}
-
-int
-_pthread_rwlock_destroy (pthread_rwlock_t *rwlock)
-{
- int ret;
-
- if (rwlock == NULL)
- ret = EINVAL;
- else {
- pthread_rwlock_t prwlock;
-
- prwlock = *rwlock;
-
- _pthread_mutex_destroy(&prwlock->lock);
- _pthread_cond_destroy(&prwlock->read_signal);
- _pthread_cond_destroy(&prwlock->write_signal);
- free(prwlock);
-
- *rwlock = NULL;
-
- ret = 0;
- }
- return (ret);
-}
-
-int
-_pthread_rwlock_init (pthread_rwlock_t *rwlock, const pthread_rwlockattr_t *attr)
+rwlock_init(pthread_rwlock_t *rwlock, const pthread_rwlockattr_t *attr)
{
pthread_rwlock_t prwlock;
int ret;
@@ -129,8 +86,12 @@
/* success */
prwlock->state = 0;
prwlock->blocked_writers = 0;
-
- *rwlock = prwlock;
+ if (!atomic_cmpset_acq_ptr(rwlock, NULL, prwlock)) {
+ /* we lost a race, it was already initialized */
+ _pthread_cond_destroy(&prwlock->read_signal);
+ _pthread_mutex_destroy(&prwlock->lock);
+ free(prwlock);
+ }
}
}
}
@@ -138,6 +99,37 @@
return (ret);
}
+int
+_pthread_rwlock_destroy (pthread_rwlock_t *rwlock)
+{
+ int ret;
+
+ if (rwlock == NULL)
+ ret = EINVAL;
+ else {
+ pthread_rwlock_t prwlock;
+
+ prwlock = *rwlock;
+
+ _pthread_mutex_destroy(&prwlock->lock);
+ _pthread_cond_destroy(&prwlock->read_signal);
+ _pthread_cond_destroy(&prwlock->write_signal);
+ free(prwlock);
+
+ *rwlock = NULL;
+
+ ret = 0;
+ }
+ return (ret);
+}
+
+int
+_pthread_rwlock_init (pthread_rwlock_t *rwlock, const pthread_rwlockattr_t *attr)
+{
+ *rwlock = NULL;
+ return (rwlock_init(rwlock, attr));
+}
+
static int
rwlock_rdlock_common (pthread_rwlock_t *rwlock, const struct timespec *abstime)
{
@@ -152,7 +144,7 @@
/* check for static initialization */
if (prwlock == NULL) {
- if ((ret = init_static(rwlock)) != 0)
+ if ((ret = rwlock_init(rwlock, NULL)) != 0)
return (ret);
prwlock = *rwlock;
@@ -244,7 +236,7 @@
/* check for static initialization */
if (prwlock == NULL) {
- if ((ret = init_static(rwlock)) != 0)
+ if ((ret = rwlock_init(rwlock, NULL)) != 0)
return (ret);
prwlock = *rwlock;
@@ -289,7 +281,7 @@
/* check for static initialization */
if (prwlock == NULL) {
- if ((ret = init_static(rwlock)) != 0)
+ if ((ret = rwlock_init(rwlock, NULL)) != 0)
return (ret);
prwlock = *rwlock;
@@ -367,7 +359,7 @@
/* check for static initialization */
if (prwlock == NULL) {
- if ((ret = init_static(rwlock)) != 0)
+ if ((ret = rwlock_init(rwlock, NULL)) != 0)
return (ret);
prwlock = *rwlock;
More information about the p4-projects
mailing list