EventWaitHandle.cs 3.1 KB

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