diff options
Diffstat (limited to 'libgo/go/sync/rwmutex.go')
-rw-r--r-- | libgo/go/sync/rwmutex.go | 29 |
1 files changed, 17 insertions, 12 deletions
diff --git a/libgo/go/sync/rwmutex.go b/libgo/go/sync/rwmutex.go index 16a2f92..dc0faf6 100644 --- a/libgo/go/sync/rwmutex.go +++ b/libgo/go/sync/rwmutex.go @@ -47,7 +47,7 @@ func (rw *RWMutex) RLock() { } if atomic.AddInt32(&rw.readerCount, 1) < 0 { // A writer is pending, wait for it. - runtime_SemacquireMutex(&rw.readerSem, false) + runtime_SemacquireMutex(&rw.readerSem, false, 0) } if race.Enabled { race.Enable() @@ -66,21 +66,26 @@ func (rw *RWMutex) RUnlock() { race.Disable() } if r := atomic.AddInt32(&rw.readerCount, -1); r < 0 { - if r+1 == 0 || r+1 == -rwmutexMaxReaders { - race.Enable() - throw("sync: RUnlock of unlocked RWMutex") - } - // A writer is pending. - if atomic.AddInt32(&rw.readerWait, -1) == 0 { - // The last reader unblocks the writer. - runtime_Semrelease(&rw.writerSem, false) - } + // Outlined slow-path to allow the fast-path to be inlined + rw.rUnlockSlow(r) } if race.Enabled { race.Enable() } } +func (rw *RWMutex) rUnlockSlow(r int32) { + if r+1 == 0 || r+1 == -rwmutexMaxReaders { + race.Enable() + throw("sync: RUnlock of unlocked RWMutex") + } + // A writer is pending. + if atomic.AddInt32(&rw.readerWait, -1) == 0 { + // The last reader unblocks the writer. + runtime_Semrelease(&rw.writerSem, false, 1) + } +} + // Lock locks rw for writing. // If the lock is already locked for reading or writing, // Lock blocks until the lock is available. @@ -95,7 +100,7 @@ func (rw *RWMutex) Lock() { r := atomic.AddInt32(&rw.readerCount, -rwmutexMaxReaders) + rwmutexMaxReaders // Wait for active readers. if r != 0 && atomic.AddInt32(&rw.readerWait, r) != 0 { - runtime_SemacquireMutex(&rw.writerSem, false) + runtime_SemacquireMutex(&rw.writerSem, false, 0) } if race.Enabled { race.Enable() @@ -125,7 +130,7 @@ func (rw *RWMutex) Unlock() { } // Unblock blocked readers, if any. for i := 0; i < int(r); i++ { - runtime_Semrelease(&rw.readerSem, false) + runtime_Semrelease(&rw.readerSem, false, 0) } // Allow other writers to proceed. rw.w.Unlock() |