summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorRich Felker <dalias@aerifal.cx>2011-09-28 19:45:37 -0400
committerRich Felker <dalias@aerifal.cx>2011-09-28 19:45:37 -0400
commitde543b05c87d79a9313991810e9ee8ecdaad8f19 (patch)
treeabde9355e67731c9e8b48ccdd107405cb35b6e03 /src
parentede5ae7b0bb5a7ed9edeb2eeb8e24d30af64d185 (diff)
downloadmusl-de543b05c87d79a9313991810e9ee8ecdaad8f19.tar.gz
musl-de543b05c87d79a9313991810e9ee8ecdaad8f19.tar.bz2
musl-de543b05c87d79a9313991810e9ee8ecdaad8f19.tar.xz
musl-de543b05c87d79a9313991810e9ee8ecdaad8f19.zip
fix excessive/insufficient wakes in __vm_unlock
there is no need to send a wake when the lock count does not hit zero, but when it does, all waiters must be woken (since all with the same sign are eligible to obtain the lock).
Diffstat (limited to 'src')
-rw-r--r--src/thread/pthread_barrier_wait.c6
1 files changed, 3 insertions, 3 deletions
diff --git a/src/thread/pthread_barrier_wait.c b/src/thread/pthread_barrier_wait.c
index 71f7b5fe..6052925a 100644
--- a/src/thread/pthread_barrier_wait.c
+++ b/src/thread/pthread_barrier_wait.c
@@ -13,9 +13,9 @@ void __vm_lock(int inc)
void __vm_unlock(void)
{
- if (vmlock[0]>0) a_dec(vmlock);
- else a_inc(vmlock);
- if (vmlock[1]) __wake(vmlock, 1, 1);
+ int inc = vmlock[0]>0 ? -1 : 1;
+ if (a_fetch_add(vmlock, inc)==-inc && vmlock[1])
+ __wake(vmlock, -1, 1);
}
static int pshared_barrier_wait(pthread_barrier_t *b)