Leaked source code of windows server 2003
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
|
|
#ifndef _CEXRWLCK_H
#define _CEXRWLCK_H
#include <limits.h>
#ifndef WIN16
//
// This class contains the meat - does actual locking etc...
//
class CExShareLock { private : long cReadLock ; // Number of Readers who have passed through the lock OR
// the number of readers waiting for the lock (will be negative).
// A value of 0 means nobody in the lock
long cOutRdrs ; // The number of readers remainin in the lock if
// there is a writer waiting. This can become temporarily negative
CRITICAL_SECTION critWriters ; // Critical section to allow only one writer into the lock at a time
HANDLE hWaitingWriters ; // Semaphore for waiting writers to block on (Only 1 ever, others will
// be queued on critWriters)
HANDLE hWaitingReaders ; // Semaphore for waiting readers to block on
public : CExShareLock( ) ; ~CExShareLock( ) ;
void ShareLock( ) ; void ShareUnlock( ) ; void ExclusiveLock( ) ; void ExclusiveUnlock( ) ;
BOOL SharedToExclusive( ) ; // returns TRUE if successful
} ;
//
// This class implements a wrapper class around CExShareLock class so that
// it alows the nested hold on Exclusive lock if a thread
// has an exclusive lock and calls for holding exclusive lock or Share lock
// again
//
class CExShareLockWithNestAllowed { private : CExShareLock m_lock; // class around which the wrapper is formed
DWORD m_dwThreadID; // The thread id of the thred currently holding
// the exclusive lock
DWORD m_dwNestCount; // The count of number of nested calls to lock by the thread holding the
// exclusive lock less 1
public : CExShareLockWithNestAllowed( ) : m_dwThreadID(0xffffffff), m_dwNestCount(0) { // nothing
}; ~CExShareLockWithNestAllowed( ) { Assert( (m_dwThreadID == 0xffffffff ) && ( m_dwNestCount == 0 ) ); }
void ShareLock( ) { if(! nest() ) { m_lock.ShareLock(); } }
void ShareUnlock( ) { if (! unnest() ) { m_lock.ShareUnlock(); } }
void ExclusiveLock( ) { if(! nest() ) { m_lock.ExclusiveLock(); Assert( m_dwNestCount == 0 ); Assert( m_dwThreadID == 0xffffffff ); m_dwThreadID = GetCurrentThreadId(); } }
void ExclusiveUnlock( ) { if (! unnest() ) { m_dwThreadID = 0xffffffff; m_lock.ExclusiveUnlock(); } }
protected : BOOL nest() { if( m_dwThreadID != GetCurrentThreadId() ) return ( FALSE ); m_dwNestCount++; return( TRUE ); } BOOL unnest() { if ( ! m_dwNestCount ) return ( FALSE ); Assert( m_dwThreadID == GetCurrentThreadId() ); m_dwNestCount--; return( TRUE); } };
#else
class CExShareLock { public: CExShareLock() { InitializeCriticalSection(&m_cs); }; ~CExShareLock() { DeleteCriticalSection(&m_cs); }; void ShareLock(){ EnterCriticalSection(&m_cs); }; void ShareUnlock() { LeaveCriticalSection(&m_cs); }; void ExclusiveLock(){ EnterCriticalSection(&m_cs); }; void ExclusiveUnlock() { LeaveCriticalSection(&m_cs); }; BOOL SharedToExclusive() { return (TRUE); }; private: CRITICAL_SECTION m_cs;
};
class CExShareLockWithNestAllowed { public: CExShareLockWithNestAllowed() { InitializeCriticalSection(&m_cs); }; ~CExShareLockWithNestAllowed() { DeleteCriticalSection(&m_cs); }; void ShareLock(){ EnterCriticalSection(&m_cs); }; void ShareUnlock() { LeaveCriticalSection(&m_cs); }; void ExclusiveLock(){ EnterCriticalSection(&m_cs); }; void ExclusiveUnlock() { LeaveCriticalSection(&m_cs); }; private: CRITICAL_SECTION m_cs;
};
#endif
#endif
|