diff options
author | Marc Laukien <marc@zeroc.com> | 2002-09-22 15:57:38 +0000 |
---|---|---|
committer | Marc Laukien <marc@zeroc.com> | 2002-09-22 15:57:38 +0000 |
commit | dff71be00b07d293b318fede3167b3c48f2270b8 (patch) | |
tree | 35e0236914020cd396dca7675119fb3c435693ac /cpp/src/IceUtil/RWRecMutex.cpp | |
parent | thread fixes (diff) | |
download | ice-dff71be00b07d293b318fede3167b3c48f2270b8.tar.bz2 ice-dff71be00b07d293b318fede3167b3c48f2270b8.tar.xz ice-dff71be00b07d293b318fede3167b3c48f2270b8.zip |
dos2unix
Diffstat (limited to 'cpp/src/IceUtil/RWRecMutex.cpp')
-rw-r--r-- | cpp/src/IceUtil/RWRecMutex.cpp | 710 |
1 files changed, 355 insertions, 355 deletions
diff --git a/cpp/src/IceUtil/RWRecMutex.cpp b/cpp/src/IceUtil/RWRecMutex.cpp index ef632a347ec..7cde5079a98 100644 --- a/cpp/src/IceUtil/RWRecMutex.cpp +++ b/cpp/src/IceUtil/RWRecMutex.cpp @@ -1,355 +1,355 @@ -// **********************************************************************
-//
-// Copyright (c) 2001
-// Mutable Realms, Inc.
-// Huntsville, AL, USA
-//
-// All Rights Reserved
-//
-// **********************************************************************
-
-#include <IceUtil/RWRecMutex.h>
-#include <IceUtil/Exception.h>
-#include <IceUtil/Time.h>
-
-#include <assert.h>
-
-IceUtil::RWRecMutex::RWRecMutex() :
- _count(0),
- _waitingWriters(0)
-{
-}
-
-IceUtil::RWRecMutex::~RWRecMutex()
-{
-}
-
-void
-IceUtil::RWRecMutex::readlock() const
-{
- Mutex::Lock lock(_mutex);
-
- //
- // Wait while a writer holds the lock or while writers are waiting
- // to get the lock.
- //
- while(_count < 0 || _waitingWriters != 0)
- {
- _readers.wait(lock);
- }
- _count++;
-}
-
-void
-IceUtil::RWRecMutex::tryReadlock() const
-{
- Mutex::Lock lock(_mutex);
-
- //
- // Would block if a writer holds the lock or if writers are
- // waiting to get the lock.
- //
- if(_count < 0 || _waitingWriters != 0)
- {
- throw ThreadLockedException(__FILE__, __LINE__);
- }
- _count++;
-}
-
-void
-IceUtil::RWRecMutex::timedTryReadlock(const Time& timeout) const
-{
- Mutex::Lock lock(_mutex);
-
- //
- // Wait while a writer holds the lock or while writers are waiting
- // to get the lock.
- //
- Time end = Time::now() + timeout;
- while(_count < 0 || _waitingWriters != 0)
- {
- Time remainder = end - Time::now();
- if(remainder > Time())
- {
- _readers.timedWait(lock, remainder);
- }
- else
- {
- throw ThreadLockedException(__FILE__, __LINE__);
- }
- }
-
- _count++;
-}
-
-void
-IceUtil::RWRecMutex::writelock() const
-{
- Mutex::Lock lock(_mutex);
-
- //
- // If the mutex is already write locked by this writer then
- // decrement _count, and return.
- //
- if(_count < 0 && _writerControl == ThreadControl())
- {
- --_count;
- return;
- }
-
- //
- // Wait for the lock to become available and increment the number
- // of waiting writers.
- //
- while(_count != 0)
- {
- _waitingWriters++;
- try
- {
- _writers.wait(lock);
- }
- catch(...)
- {
- --_waitingWriters;
- throw;
- }
- _waitingWriters--;
- }
-
- //
- // Got the lock, indicate it's held by a writer.
- //
- _count = -1;
-}
-
-void
-IceUtil::RWRecMutex::tryWritelock() const
-{
- Mutex::Lock lock(_mutex);
-
- //
- // If the mutex is already write locked by this writer then
- // decrement _count, and return.
- //
- if(_count < 0 && _writerControl == ThreadControl())
- {
- --_count;
- return;
- }
-
- //
- // If there are readers or other writers then the call would block.
- //
- if(_count != 0)
- {
- throw ThreadLockedException(__FILE__, __LINE__);
- }
-
- //
- // Got the lock, indicate it's held by a writer.
- //
- _count = -1;
-}
-
-void
-IceUtil::RWRecMutex::timedTryWritelock(const Time& timeout) const
-{
- Mutex::Lock lock(_mutex);
-
- //
- // If the mutex is already write locked by this writer then
- // decrement _count, and return.
- //
- if(_count < 0 && _writerControl == ThreadControl())
- {
- --_count;
- return;
- }
-
- //
- // Wait for the lock to become available and increment the number
- // of waiting writers.
- //
- Time end = Time::now() + timeout;
- while(_count != 0)
- {
- Time remainder = end - Time::now();
- if(remainder > Time())
- {
- _waitingWriters++;
- try
- {
- _writers.timedWait(lock, remainder);
- }
- catch(...)
- {
- --_waitingWriters;
- throw;
- }
- _waitingWriters--;
- }
- else
- {
- throw ThreadLockedException(__FILE__, __LINE__);
- }
- }
-
- //
- // Got the lock, indicate it's held by a writer.
- //
- _count = -1;
-}
-
-void
-IceUtil::RWRecMutex::unlock() const
-{
- bool ww;
- bool wr;
- {
- Mutex::Lock lock(_mutex);
-
- assert(_count != 0);
-
- //
- // If _count < 0, the calling thread is a writer that holds the
- // lock, so release the lock. Otherwise, _count is guaranteed to
- // be > 0, so the calling thread is a reader releasing the lock.
- //
- if(_count < 0)
- {
- //
- // Writer called unlock
- //
- ++_count;
-
- //
- // If the write lock wasn't totally released we're done.
- //
- if(_count != 0)
- {
- return;
- }
- }
- else
- {
- //
- // Reader called unlock
- //
- --_count;
- }
-
- //
- // Writers are waiting (ww) if _waitingWriters > 0. In that
- // case, it's OK to let another writer into the region once there
- // are no more readers (_count == 0). Otherwise, no writers are
- // waiting but readers may be waiting (wr).
- //
- ww = (_waitingWriters != 0 && _count == 0);
- wr = (_waitingWriters == 0);
- }
-
- //
- // Wake up a waiting writer if there is one. If not, wake up all
- // readers (just in case -- there may be none).
- //
- if(ww)
- {
- //
- // Wake writer
- //
- _writers.signal();
- }
- else if(wr)
- {
- //
- // Wake readers
- //
- _readers.broadcast();
- }
-}
-
-void
-IceUtil::RWRecMutex::upgrade() const
-{
- Mutex::Lock lock(_mutex);
-
- //
- // Reader called unlock
- //
- assert(_count > 0);
- --_count;
-
- //
- // Wait to acquire the write lock.
- //
- while(_count != 0)
- {
- _waitingWriters++;
- try
- {
- _writers.wait(lock);
- }
- catch(...)
- {
- --_waitingWriters;
- throw;
- }
- _waitingWriters--;
-
-
- }
-
- //
- // Got the lock, indicate it's held by a writer.
- //
- _count = -1;
-}
-
-void
-IceUtil::RWRecMutex::timedUpgrade(const Time& timeout) const
-{
- Mutex::Lock lock(_mutex);
-
- //
- // Reader called unlock
- //
- assert(_count > 0);
- --_count;
-
- //
- // Wait to acquire the write lock.
- //
- Time end = Time::now() + timeout;
- while(_count != 0)
- {
- Time remainder = end - Time::now();
- if(remainder > Time())
- {
- _waitingWriters++;
- try
- {
- _writers.timedWait(lock, remainder);
- }
- catch(...)
- {
- --_waitingWriters;
- throw;
- }
- _waitingWriters--;
- }
- else
- {
- //
- // If a timeout occurred then the lock wasn't acquired. Ensure
- // that the _count is increased again before returning.
- //
- ++_count;
- throw ThreadLockedException(__FILE__, __LINE__);
- }
- }
-
- //
- // Got the lock, indicate it's held by a writer.
- //
- _count = -1;
-}
+// ********************************************************************** +// +// Copyright (c) 2001 +// Mutable Realms, Inc. +// Huntsville, AL, USA +// +// All Rights Reserved +// +// ********************************************************************** + +#include <IceUtil/RWRecMutex.h> +#include <IceUtil/Exception.h> +#include <IceUtil/Time.h> + +#include <assert.h> + +IceUtil::RWRecMutex::RWRecMutex() : + _count(0), + _waitingWriters(0) +{ +} + +IceUtil::RWRecMutex::~RWRecMutex() +{ +} + +void +IceUtil::RWRecMutex::readlock() const +{ + Mutex::Lock lock(_mutex); + + // + // Wait while a writer holds the lock or while writers are waiting + // to get the lock. + // + while(_count < 0 || _waitingWriters != 0) + { + _readers.wait(lock); + } + _count++; +} + +void +IceUtil::RWRecMutex::tryReadlock() const +{ + Mutex::Lock lock(_mutex); + + // + // Would block if a writer holds the lock or if writers are + // waiting to get the lock. + // + if(_count < 0 || _waitingWriters != 0) + { + throw ThreadLockedException(__FILE__, __LINE__); + } + _count++; +} + +void +IceUtil::RWRecMutex::timedTryReadlock(const Time& timeout) const +{ + Mutex::Lock lock(_mutex); + + // + // Wait while a writer holds the lock or while writers are waiting + // to get the lock. + // + Time end = Time::now() + timeout; + while(_count < 0 || _waitingWriters != 0) + { + Time remainder = end - Time::now(); + if(remainder > Time()) + { + _readers.timedWait(lock, remainder); + } + else + { + throw ThreadLockedException(__FILE__, __LINE__); + } + } + + _count++; +} + +void +IceUtil::RWRecMutex::writelock() const +{ + Mutex::Lock lock(_mutex); + + // + // If the mutex is already write locked by this writer then + // decrement _count, and return. + // + if(_count < 0 && _writerControl == ThreadControl()) + { + --_count; + return; + } + + // + // Wait for the lock to become available and increment the number + // of waiting writers. + // + while(_count != 0) + { + _waitingWriters++; + try + { + _writers.wait(lock); + } + catch(...) + { + --_waitingWriters; + throw; + } + _waitingWriters--; + } + + // + // Got the lock, indicate it's held by a writer. + // + _count = -1; +} + +void +IceUtil::RWRecMutex::tryWritelock() const +{ + Mutex::Lock lock(_mutex); + + // + // If the mutex is already write locked by this writer then + // decrement _count, and return. + // + if(_count < 0 && _writerControl == ThreadControl()) + { + --_count; + return; + } + + // + // If there are readers or other writers then the call would block. + // + if(_count != 0) + { + throw ThreadLockedException(__FILE__, __LINE__); + } + + // + // Got the lock, indicate it's held by a writer. + // + _count = -1; +} + +void +IceUtil::RWRecMutex::timedTryWritelock(const Time& timeout) const +{ + Mutex::Lock lock(_mutex); + + // + // If the mutex is already write locked by this writer then + // decrement _count, and return. + // + if(_count < 0 && _writerControl == ThreadControl()) + { + --_count; + return; + } + + // + // Wait for the lock to become available and increment the number + // of waiting writers. + // + Time end = Time::now() + timeout; + while(_count != 0) + { + Time remainder = end - Time::now(); + if(remainder > Time()) + { + _waitingWriters++; + try + { + _writers.timedWait(lock, remainder); + } + catch(...) + { + --_waitingWriters; + throw; + } + _waitingWriters--; + } + else + { + throw ThreadLockedException(__FILE__, __LINE__); + } + } + + // + // Got the lock, indicate it's held by a writer. + // + _count = -1; +} + +void +IceUtil::RWRecMutex::unlock() const +{ + bool ww; + bool wr; + { + Mutex::Lock lock(_mutex); + + assert(_count != 0); + + // + // If _count < 0, the calling thread is a writer that holds the + // lock, so release the lock. Otherwise, _count is guaranteed to + // be > 0, so the calling thread is a reader releasing the lock. + // + if(_count < 0) + { + // + // Writer called unlock + // + ++_count; + + // + // If the write lock wasn't totally released we're done. + // + if(_count != 0) + { + return; + } + } + else + { + // + // Reader called unlock + // + --_count; + } + + // + // Writers are waiting (ww) if _waitingWriters > 0. In that + // case, it's OK to let another writer into the region once there + // are no more readers (_count == 0). Otherwise, no writers are + // waiting but readers may be waiting (wr). + // + ww = (_waitingWriters != 0 && _count == 0); + wr = (_waitingWriters == 0); + } + + // + // Wake up a waiting writer if there is one. If not, wake up all + // readers (just in case -- there may be none). + // + if(ww) + { + // + // Wake writer + // + _writers.signal(); + } + else if(wr) + { + // + // Wake readers + // + _readers.broadcast(); + } +} + +void +IceUtil::RWRecMutex::upgrade() const +{ + Mutex::Lock lock(_mutex); + + // + // Reader called unlock + // + assert(_count > 0); + --_count; + + // + // Wait to acquire the write lock. + // + while(_count != 0) + { + _waitingWriters++; + try + { + _writers.wait(lock); + } + catch(...) + { + --_waitingWriters; + throw; + } + _waitingWriters--; + + + } + + // + // Got the lock, indicate it's held by a writer. + // + _count = -1; +} + +void +IceUtil::RWRecMutex::timedUpgrade(const Time& timeout) const +{ + Mutex::Lock lock(_mutex); + + // + // Reader called unlock + // + assert(_count > 0); + --_count; + + // + // Wait to acquire the write lock. + // + Time end = Time::now() + timeout; + while(_count != 0) + { + Time remainder = end - Time::now(); + if(remainder > Time()) + { + _waitingWriters++; + try + { + _writers.timedWait(lock, remainder); + } + catch(...) + { + --_waitingWriters; + throw; + } + _waitingWriters--; + } + else + { + // + // If a timeout occurred then the lock wasn't acquired. Ensure + // that the _count is increased again before returning. + // + ++_count; + throw ThreadLockedException(__FILE__, __LINE__); + } + } + + // + // Got the lock, indicate it's held by a writer. + // + _count = -1; +} |