Index: Include/Classes/System/Threading/WaitHandle.ab
===================================================================
--- Include/Classes/System/Threading/WaitHandle.ab	(revision 46)
+++ Include/Classes/System/Threading/WaitHandle.ab	(revision 46)
@@ -0,0 +1,103 @@
+' Classes/System/Threading/WaitHandle.ab
+
+#ifndef __SYSTEM_THREADING_WAITHANDLE_AB__
+#define __SYSTEM_THREADING_WAITHANDLE_AB__
+
+Class WaitHandle
+Public
+	Virtual Sub ~WaitHandle()
+		Close()
+	End Sub
+
+	' Const Function SafeWaitHandle() As SafeWaitHandle
+	' Sub SafeWaitHandle(h As SafeWaitHandle)
+
+	Const Virtual Function Handle() As HANDLE
+		Return h
+	End Function
+
+	Virtual Sub Handle(newHandle As HANDLE)
+		h = newHandle
+	End Sub
+
+	Virtual Sub Close()
+		CloseHandle(h)
+	End Sub
+
+	Sub WaitOne()
+		WaitOne(INFINITE, FALSE)
+	End Sub
+
+	Sub WaitOne(millisecondsTimeout As Long, exitContext As BOOL)
+		WaitHandle.ExitThreadIfWaitIsFailed(WaitForSingleObject(h, millisecondsTimeout As DWord))
+	End Sub
+
+'	Sub WaitOne(timeout As TimeSpan, exitContext As BOOL)
+/*
+	Static Sub WaitAll(count As DWord, handles As *HANDLE)
+		WaitAll(count, handles, INFINITE, FALSE)
+	End Sub
+
+	Static Sub WaitAll(count As DWord, handles As *HANDLE, millisecondsTimeout As Long, exitContext As BOOL)
+		WaitHandle.ExitThreadIfWaitIsFailed(WaitForMultipleObjects(count, handles, TRUE, millisecondsTimeout))
+	End Sub
+
+'	Static Sub WaitAll(timeout As TimeSpan, handles As *HANDLE, millisecondsTimeout As Long, exitContext As BOOL)
+
+	Static Sub WaitAny(count As DWord, handles As *HANDLE)
+		WaitAny(count, handles, INFINITE, FALSE)
+	End Sub
+
+	Static Sub WaitAny(count As DWord, handles As *HANDLE, millisecondsTimeout As Long, exitContext As BOOL)
+		WaitHandle.ExitThreadIfWaitIsFailed(WaitForMultipleObjects(count, handles, FALSE, millisecondsTimeout))
+	End Sub
+
+'	Static Sub WaitAny(timeout As TimeSpan, handles As *HANDLE, millisecondsTimeout As Long, exitContext As BOOL)
+*/
+	Static Sub SignalAndWait(ByRef toSignal As WaitHandle, ByRef toWaitOn As WaitHandle)
+		SignalAndWait(toSignal, toWaitOn, INFINITE, FALSE)
+	End Sub
+
+	Static Sub SignalAndWait(ByRef toSignal As WaitHandle, ByRef toWaitOn As WaitHandle, millisecondsTimeout As Long, exitContext As BOOL)
+		Dim pSignalObjectAndWait = GetProcAddress(GetModuleHandle("Kernel32.dll"), "SignalObjectAndWait") _
+			As *Function(hObjectToSignal As HANDLE, hObjectToWaitOn As HANDLE, dwMilliseconds As DWord, bAlertable As DWord) As DWord
+		If pSignalObjectAndWait = 0 Then
+			' PlatformNotSupportedException
+			Debug
+			ExitThread(0)
+		End If
+		ExitThreadIfWaitIsFailed(pSignalAndWait(toSignal.Handle, toWaitOn.Handle, millisecondsTimeout As DWord))
+	End Sub
+
+'	Static Sub SignalAndWait(ByRef toSignal As WaitHandle, ByRef toWaitOn As WaitHandle, timeout As TimeSpan, exitContext As BOOL)
+
+' Protected
+	Sub WaitHandle()
+	End Sub
+
+Protected
+	Static Const InvalidHandle = INVALID_HANDLE_VALUE As HANDLE
+
+Private
+	h As HANDLE
+
+	Static Sub ExitThreadIfWaitIsFailed(ret As DWord)
+		Select Case ret
+			Case WAIT_OBJECT_0
+				Exit Sub
+			Case WAIT_TIMEOUT
+				Exit Sub
+			Case WAIT_ABANDONED
+				' Throw AbandonedMutexException
+				Debug
+				ExitThread(0)
+			'Case WAIT_FAILED
+			Case Else
+				' ObjectDisposedException?
+				Debug
+				ExitThread(0)
+		End Select
+	End Sub
+End Class
+
+#endif '__SYSTEM_THREADING_WAITHANDLE_AB__
