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.

237 lines
4.4 KiB

  1. /*++
  2. Copyright (c) 1999-2000 Microsoft Corporation
  3. Module Name:
  4. locks.h
  5. Abstract:
  6. Various C++ class for sync. object
  7. Author:
  8. HueiWang 2/17/2000
  9. --*/
  10. #ifndef __LOCKS_H
  11. #define __LOCKS_H
  12. #include <windows.h>
  13. #include <winbase.h>
  14. #include "assert.h"
  15. #define ARRAY_COUNT(a) sizeof(a) / sizeof(a[0])
  16. typedef enum {RESOURCELOCK_SHARE, RESOURCELOCK_EXCLUSIVE} RESOURCELOCKTYPE;
  17. //
  18. // Class to wrap around RTL resource lock
  19. //
  20. class CResourceLock {
  21. private:
  22. RTL_RESOURCE m_hResource;
  23. public:
  24. CResourceLock() {
  25. RtlInitializeResource(&m_hResource);
  26. }
  27. ~CResourceLock() {
  28. RtlDeleteResource(&m_hResource);
  29. }
  30. BOOL
  31. ExclusiveLock( BOOL Wait = TRUE ) {
  32. return RtlAcquireResourceExclusive( &m_hResource, Wait == TRUE );
  33. }
  34. BOOL
  35. SharedLock( BOOL Wait = TRUE ) {
  36. return RtlAcquireResourceShared( &m_hResource, Wait == TRUE );
  37. }
  38. VOID
  39. ConvertSharedToExclusive() {
  40. RtlConvertSharedToExclusive( &m_hResource );
  41. }
  42. VOID
  43. ConvertExclusiveToShared() {
  44. RtlConvertExclusiveToShared( &m_hResource );
  45. }
  46. VOID
  47. ReleaseLock() {
  48. RtlReleaseResource( &m_hResource );
  49. }
  50. };
  51. class CResourceLocker
  52. {
  53. private:
  54. CResourceLock& m_cs;
  55. BOOL bExclusive;
  56. public:
  57. //
  58. // Object constructor, lock resource based on lock type
  59. //
  60. CResourceLocker(
  61. CResourceLock& m,
  62. RESOURCELOCKTYPE type = RESOURCELOCK_SHARE
  63. ) : m_cs(m)
  64. {
  65. BOOL bSuccess = TRUE;
  66. if( RESOURCELOCK_EXCLUSIVE == type ) {
  67. bSuccess = m.ExclusiveLock( TRUE );
  68. }
  69. else {
  70. bSuccess = m.SharedLock( TRUE );
  71. }
  72. bExclusive = (RESOURCELOCK_EXCLUSIVE == type);
  73. ASSERT( TRUE == bSuccess );
  74. }
  75. //
  76. // Object destructor, release resource lock.
  77. //
  78. ~CResourceLocker()
  79. {
  80. m_cs.ReleaseLock();
  81. }
  82. void
  83. ConvertToShareLock() {
  84. if( bExclusive ) {
  85. m_cs.ConvertExclusiveToShared();
  86. bExclusive = FALSE;
  87. }
  88. else {
  89. ASSERT(FALSE);
  90. }
  91. }
  92. void
  93. ConvertToExclusiveLock() {
  94. if( FALSE == bExclusive ) {
  95. m_cs.ConvertSharedToExclusive();
  96. bExclusive = TRUE;
  97. }
  98. else {
  99. ASSERT(FALSE);
  100. }
  101. }
  102. };
  103. //
  104. // Critical section C++ class.
  105. //
  106. class CCriticalSection
  107. {
  108. CRITICAL_SECTION m_CS;
  109. BOOL m_bGood;
  110. public:
  111. CCriticalSection(
  112. DWORD dwSpinCount = 4000 // see InitializeCriticalSection...
  113. ) : m_bGood(TRUE)
  114. {
  115. DWORD dwExceptionCode;
  116. __try {
  117. // MSDN : InitializeCriticalSectionAndSpinCount() might return
  118. // FALSE or throw exception.
  119. m_bGood = InitializeCriticalSectionAndSpinCount(&m_CS, dwSpinCount);
  120. }
  121. __except(EXCEPTION_EXECUTE_HANDLER)
  122. {
  123. SetLastError(GetExceptionCode());
  124. m_bGood = FALSE;
  125. }
  126. // throw exception so that object creation will failed and
  127. // COM/RPC interface will return exception.
  128. if( !m_bGood )
  129. {
  130. dwExceptionCode = GetLastError();
  131. throw dwExceptionCode;
  132. }
  133. }
  134. ~CCriticalSection()
  135. {
  136. if(IsGood() == TRUE)
  137. {
  138. DeleteCriticalSection(&m_CS);
  139. m_bGood = FALSE;
  140. }
  141. }
  142. BOOL
  143. IsGood()
  144. {
  145. return m_bGood;
  146. }
  147. void Lock()
  148. {
  149. EnterCriticalSection(&m_CS);
  150. }
  151. void UnLock()
  152. {
  153. LeaveCriticalSection(&m_CS);
  154. }
  155. BOOL TryLock()
  156. {
  157. return TryEnterCriticalSection(&m_CS);
  158. }
  159. };
  160. //
  161. // Critical section locker, this class lock the critical section
  162. // at object constructor and release object at destructor, purpose is to
  163. // prevent forgoting to release a critical section.
  164. //
  165. // usage is
  166. //
  167. // void
  168. // Foo( void )
  169. // {
  170. // CCriticalSectionLocker l( <some CCriticalSection instance> )
  171. //
  172. // }
  173. //
  174. //
  175. class CCriticalSectionLocker
  176. {
  177. private:
  178. CCriticalSection& m_cs;
  179. public:
  180. CCriticalSectionLocker( CCriticalSection& m ) : m_cs(m)
  181. {
  182. m.Lock();
  183. }
  184. ~CCriticalSectionLocker()
  185. {
  186. m_cs.UnLock();
  187. }
  188. };
  189. #endif