#ifndef GLTB_RWLOCK_H_ #define GLTB_RWLOCK_H_ #ifdef WIN32 #include #else #include #endif #include "referencedobject.h" #include "refptr.h" namespace gltb { /** * A simple read/write lock class. It behaves as you expect: you can have * multiple read locks at the same time, but only one exclusive write lock. * However, there are important restrictions that you have to be aware of: * * - requesting the write lock in a thread that currently holds a read * lock causes a deadlock * - _Win32_: the read lock is non-reentrant on the same thread * - _POSIX_: the read lock is reentrant, but the number of unlocks must be * the same as the number of locks on the same thread */ class RWLock : public ReferencedObject { public: RWLock(); ~RWLock(); void readLock(); void readUnlock(); void writeLock(); void writeUnlock(); static RefPtr createRWLock(); private: #ifdef WIN32 SRWLOCK rwLock; #else pthread_rwlock_t rwLock; #endif }; class RWLockGuard { public: enum LockType { Read, Write }; RWLockGuard(gltb::RefPtr lock, LockType lockType) : lock(lock), lockType(lockType) { switch(lockType) { case Read: lock->readLock(); break; case Write: lock->writeLock(); break; } } ~RWLockGuard() { switch(lockType) { case Read: lock->readUnlock(); break; case Write: lock->writeUnlock(); break; } } private: gltb::RefPtr lock; LockType lockType; }; } #endif