summaryrefslogtreecommitdiff
path: root/src/vm/synch.h
diff options
context:
space:
mode:
authordotnet-bot <dotnet-bot@microsoft.com>2015-01-30 14:14:42 -0800
committerdotnet-bot <dotnet-bot@microsoft.com>2015-01-30 14:14:42 -0800
commitef1e2ab328087c61a6878c1e84f4fc5d710aebce (patch)
treedee1bbb89e9d722e16b0d1485e3cdd1b6c8e2cfa /src/vm/synch.h
downloadcoreclr-ef1e2ab328087c61a6878c1e84f4fc5d710aebce.tar.gz
coreclr-ef1e2ab328087c61a6878c1e84f4fc5d710aebce.tar.bz2
coreclr-ef1e2ab328087c61a6878c1e84f4fc5d710aebce.zip
Initial commit to populate CoreCLR repo
[tfs-changeset: 1407945]
Diffstat (limited to 'src/vm/synch.h')
-rw-r--r--src/vm/synch.h209
1 files changed, 209 insertions, 0 deletions
diff --git a/src/vm/synch.h b/src/vm/synch.h
new file mode 100644
index 0000000000..d6061f6566
--- /dev/null
+++ b/src/vm/synch.h
@@ -0,0 +1,209 @@
+//
+// Copyright (c) Microsoft. All rights reserved.
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
+//
+//
+
+//
+
+
+#ifndef __Synch_h__
+#define __Synch_h__
+
+enum WaitMode
+{
+ WaitMode_None =0x0,
+ WaitMode_Alertable = 0x1, // Can be waken by APC. May pumping message.
+ WaitMode_IgnoreSyncCtx = 0x2, // Dispatch to synchronization context if existed.
+ WaitMode_ADUnload = 0x4, // The block is to wait for AD unload start. If it is interrupted by AD Unload, we can start aborting.
+ WaitMode_InDeadlock = 0x8, // The wait can be terminated by host's deadlock detection
+};
+
+
+struct PendingSync;
+class CRWLock;
+
+class CLREventBase
+{
+public:
+ CLREventBase()
+ {
+ LIMITED_METHOD_CONTRACT;
+ m_handle = INVALID_HANDLE_VALUE;
+ m_dwFlags = 0;
+ }
+
+ // Create an Event that is host aware
+ void CreateAutoEvent(BOOL bInitialState);
+ void CreateManualEvent(BOOL bInitialState);
+
+ void CreateMonitorEvent(SIZE_T Cookie); // robust against initialization races - for exclusive use by AwareLock
+
+#ifdef FEATURE_RWLOCK
+ void CreateRWLockReaderEvent(BOOL bInitialState, CRWLock* pRWLock);
+ void CreateRWLockWriterEvent(BOOL bInitialState, CRWLock* pRWLock);
+#endif
+
+ // Create an Event that is not host aware
+ void CreateOSAutoEvent (BOOL bInitialState);
+ void CreateOSManualEvent (BOOL bInitialState);
+
+ void CloseEvent();
+
+ BOOL IsValid() const
+ {
+ LIMITED_METHOD_CONTRACT;
+ return m_handle != INVALID_HANDLE_VALUE;
+ }
+
+ BOOL IsMonitorEventAllocated()
+ {
+ LIMITED_METHOD_CONTRACT;
+ return m_dwFlags & CLREVENT_FLAGS_MONITOREVENT_ALLOCATED;
+ }
+
+#ifndef DACCESS_COMPILE
+ HANDLE GetHandleUNHOSTED() {
+ LIMITED_METHOD_CONTRACT;
+ _ASSERTE (IsOSEvent() || !CLRSyncHosted());
+ return m_handle;
+ }
+#endif // DACCESS_COMPILE
+
+ BOOL Set();
+ void SetMonitorEvent(); // robust against races - for exclusive use by AwareLock
+ BOOL Reset();
+ DWORD Wait(DWORD dwMilliseconds, BOOL bAlertable, PendingSync *syncState=NULL);
+ DWORD WaitEx(DWORD dwMilliseconds, WaitMode mode, PendingSync *syncState=NULL);
+
+protected:
+ HANDLE m_handle;
+
+private:
+ enum
+ {
+ CLREVENT_FLAGS_AUTO_EVENT = 0x0001,
+ CLREVENT_FLAGS_OS_EVENT = 0x0002,
+ CLREVENT_FLAGS_IN_DEADLOCK_DETECTION = 0x0004,
+
+ CLREVENT_FLAGS_MONITOREVENT_ALLOCATED = 0x0008,
+ CLREVENT_FLAGS_MONITOREVENT_SIGNALLED = 0x0010,
+
+ CLREVENT_FLAGS_STATIC = 0x0020,
+
+ // Several bits unused;
+ };
+
+ Volatile<DWORD> m_dwFlags;
+
+ BOOL IsAutoEvent() { LIMITED_METHOD_CONTRACT; return m_dwFlags & CLREVENT_FLAGS_AUTO_EVENT; }
+ void SetAutoEvent ()
+ {
+ LIMITED_METHOD_CONTRACT;
+ // cannot use `|=' operator on `Volatile<DWORD>'
+ m_dwFlags = m_dwFlags | CLREVENT_FLAGS_AUTO_EVENT;
+ }
+ BOOL IsOSEvent() { LIMITED_METHOD_CONTRACT; return m_dwFlags & CLREVENT_FLAGS_OS_EVENT; }
+ void SetOSEvent ()
+ {
+ LIMITED_METHOD_CONTRACT;
+ // cannot use `|=' operator on `Volatile<DWORD>'
+ m_dwFlags = m_dwFlags | CLREVENT_FLAGS_OS_EVENT;
+ }
+ BOOL IsInDeadlockDetection() { LIMITED_METHOD_CONTRACT; return m_dwFlags & CLREVENT_FLAGS_IN_DEADLOCK_DETECTION; }
+ void SetInDeadlockDetection ()
+ {
+ LIMITED_METHOD_CONTRACT;
+ // cannot use `|=' operator on `Volatile<DWORD>'
+ m_dwFlags = m_dwFlags | CLREVENT_FLAGS_IN_DEADLOCK_DETECTION;
+ }
+};
+
+
+class CLREvent : public CLREventBase
+{
+public:
+
+#ifndef DACCESS_COMPILE
+ ~CLREvent()
+ {
+ WRAPPER_NO_CONTRACT;
+
+ CloseEvent();
+ }
+#endif
+};
+
+
+// CLREventStatic
+// Same as CLREvent, but intended to be used for global variables.
+// Instances may leak their handle, because of the order in which
+// global destructors are run. Note that you can still explicitly
+// call CloseHandle, which will indeed not leak the handle.
+class CLREventStatic : public CLREventBase
+{
+};
+
+
+class CLRSemaphore {
+public:
+ CLRSemaphore()
+ : m_handle(INVALID_HANDLE_VALUE)
+ {
+ LIMITED_METHOD_CONTRACT;
+ }
+
+ ~CLRSemaphore()
+ {
+ WRAPPER_NO_CONTRACT;
+ Close ();
+ }
+
+ void Create(DWORD dwInitial, DWORD dwMax);
+ void Close();
+
+ BOOL IsValid() const
+ {
+ LIMITED_METHOD_CONTRACT;
+ return m_handle != INVALID_HANDLE_VALUE;
+ }
+
+ DWORD Wait(DWORD dwMilliseconds, BOOL bAlertable);
+ BOOL Release(LONG lReleaseCount, LONG* lpPreviouseCount);
+
+private:
+ HANDLE m_handle;
+};
+
+class CLRMutex {
+public:
+ CLRMutex()
+ : m_handle(INVALID_HANDLE_VALUE)
+ {
+ LIMITED_METHOD_CONTRACT;
+ }
+
+ ~CLRMutex()
+ {
+ WRAPPER_NO_CONTRACT;
+ Close ();
+ }
+
+ void Create(LPSECURITY_ATTRIBUTES lpMutexAttributes, BOOL bInitialOwner, LPCTSTR lpName);
+ void Close();
+
+ BOOL IsValid() const
+ {
+ LIMITED_METHOD_CONTRACT;
+ return m_handle != INVALID_HANDLE_VALUE;
+ }
+
+ DWORD Wait(DWORD dwMilliseconds, BOOL bAlertable);
+ BOOL Release();
+
+private:
+ HANDLE m_handle;
+};
+
+BOOL CLREventWaitWithTry(CLREventBase *pEvent, DWORD timeout, BOOL fAlertable, DWORD *pStatus);
+#endif