1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
|
#if (_WINDOWS_CE)
using System;
using System.Runtime.InteropServices;
using System.Threading;
namespace Amib.Threading.Internal
{
/// <summary>
/// EventWaitHandle class
/// In WindowsCE this class doesn't exist and I needed the WaitAll and WaitAny implementation.
/// So I wrote this class to implement these two methods with some of their overloads.
/// It uses the WaitForMultipleObjects API to do the WaitAll and WaitAny.
/// Note that this class doesn't even inherit from WaitHandle!
/// </summary>
public class STPEventWaitHandle
{
#region Public Constants
public const int WaitTimeout = Timeout.Infinite;
#endregion
#region Private External Constants
private const Int32 WAIT_FAILED = -1;
private const Int32 WAIT_TIMEOUT = 0x102;
private const UInt32 INFINITE = 0xFFFFFFFF;
#endregion
#region WaitAll and WaitAny
internal static bool WaitOne(WaitHandle waitHandle, int millisecondsTimeout, bool exitContext)
{
return waitHandle.WaitOne(millisecondsTimeout, exitContext);
}
private static IntPtr[] PrepareNativeHandles(WaitHandle[] waitHandles)
{
IntPtr[] nativeHandles = new IntPtr[waitHandles.Length];
for (int i = 0; i < waitHandles.Length; i++)
{
nativeHandles[i] = waitHandles[i].Handle;
}
return nativeHandles;
}
public static bool WaitAll(WaitHandle[] waitHandles, int millisecondsTimeout, bool exitContext)
{
uint timeout = millisecondsTimeout < 0 ? INFINITE : (uint)millisecondsTimeout;
IntPtr[] nativeHandles = PrepareNativeHandles(waitHandles);
int result = WaitForMultipleObjects((uint)waitHandles.Length, nativeHandles, true, timeout);
if (result == WAIT_TIMEOUT || result == WAIT_FAILED)
{
return false;
}
return true;
}
public static int WaitAny(WaitHandle[] waitHandles, int millisecondsTimeout, bool exitContext)
{
uint timeout = millisecondsTimeout < 0 ? INFINITE : (uint)millisecondsTimeout;
IntPtr[] nativeHandles = PrepareNativeHandles(waitHandles);
int result = WaitForMultipleObjects((uint)waitHandles.Length, nativeHandles, false, timeout);
if (result >= 0 && result < waitHandles.Length)
{
return result;
}
return -1;
}
public static int WaitAny(WaitHandle[] waitHandles)
{
return WaitAny(waitHandles, Timeout.Infinite, false);
}
public static int WaitAny(WaitHandle[] waitHandles, TimeSpan timeout, bool exitContext)
{
int millisecondsTimeout = (int)timeout.TotalMilliseconds;
return WaitAny(waitHandles, millisecondsTimeout, false);
}
#endregion
#region External methods
[DllImport("coredll.dll", SetLastError = true)]
public static extern int WaitForMultipleObjects(uint nCount, IntPtr[] lpHandles, bool fWaitAll, uint dwMilliseconds);
#endregion
}
}
#endif
|