This is the mail archive of the
libc-alpha@sources.redhat.com
mailing list for the glibc project.
rwlocks writer preference patch (take 2)
- To: Kaz Kylheku <kaz at ashi dot footprints dot net>
- Subject: rwlocks writer preference patch (take 2)
- From: Momchil Velikov <velco at fadata dot bg>
- Date: 10 Nov 2000 15:24:35 +0000
- Cc: GLIBC list <libc-alpha at sources dot redhat dot com>, debian-glibc at lists dot debian dot org, velco at fadata dot bg
Hi,
Here's the second version of the patch, as suggested by Kaz.
Regards,
-velco
--- rwlock.c.orig Thu Nov 9 15:19:19 2000
+++ rwlock.c Fri Nov 10 14:55:55 2000
@@ -234,11 +234,11 @@
have_lock_already = rwlock_have_already(&self, rwlock,
&existing, &out_of_mem);
- for (;;)
- {
if (self == NULL)
self = thread_self ();
+ for (;;)
+ {
__pthread_lock (&rwlock->__rw_lock, self);
if (rwlock_can_rdlock(rwlock, have_lock_already))
@@ -310,9 +310,9 @@
{
pthread_descr self = thread_self ();
+ __pthread_lock (&rwlock->__rw_lock, self);
while(1)
{
- __pthread_lock (&rwlock->__rw_lock, self);
if (rwlock->__rw_readers == 0 && rwlock->__rw_writer == NULL)
{
rwlock->__rw_writer = self;
@@ -324,6 +324,14 @@
enqueue (&rwlock->__rw_write_waiting, self);
__pthread_unlock (&rwlock->__rw_lock);
suspend (self); /* This is not a cancellation point */
+ __pthread_lock (&rwlock->__rw_lock, self);
+
+ /* Check if someone handed us ownership of the lock */
+ if (rwlock->__rw_writer == self)
+ {
+ __pthread_unlock (&rwlock->__rw_lock);
+ return 0;
+ }
}
}
@@ -362,7 +370,8 @@
}
rwlock->__rw_writer = NULL;
- if (rwlock->__rw_kind == PTHREAD_RWLOCK_PREFER_READER_NP
+ if ((rwlock->__rw_kind == PTHREAD_RWLOCK_PREFER_READER_NP
+ && !queue_is_empty(&rwlock->__rw_read_waiting))
|| (th = dequeue (&rwlock->__rw_write_waiting)) == NULL)
{
/* Restart all waiting readers. */
@@ -375,6 +384,7 @@
else
{
/* Restart one waiting writer. */
+ rwlock->__rw_writer = th;
__pthread_unlock (&rwlock->__rw_lock);
restart (th);
}
@@ -390,8 +400,11 @@
--rwlock->__rw_readers;
if (rwlock->__rw_readers == 0)
+ {
/* Restart one waiting writer, if any. */
th = dequeue (&rwlock->__rw_write_waiting);
+ rwlock->__rw_writer = th;
+ }
else
th = NULL;
@@ -430,8 +443,8 @@
int
pthread_rwlockattr_init (pthread_rwlockattr_t *attr)
{
- attr->__lockkind = 0;
- attr->__pshared = 0;
+ attr->__lockkind = PTHREAD_RWLOCK_DEFAULT_NP;
+ attr->__pshared = PTHREAD_PROCESS_PRIVATE;
return 0;
}
@@ -477,6 +490,7 @@
{
if (pref != PTHREAD_RWLOCK_PREFER_READER_NP
&& pref != PTHREAD_RWLOCK_PREFER_WRITER_NP
+ && pref != PTHREAD_RWLOCK_PREFER_WRITER_NONRECURSIVE_NP
&& pref != PTHREAD_RWLOCK_DEFAULT_NP)
return EINVAL;