public static int WaitAny(object[] waitHandles, TimeSpan timeout) { if (waitHandles == null) { throw new ArgumentNullException("waitHandles"); } if (waitHandles.Length == 0) { throw new ArgumentException("Empty waitHandles should not be passed in."); } int num = -1; List <WaitHandle> list = new List <WaitHandle>(waitHandles.Length); ManualOneShotEvent.ManualOneShotInfo[] array = new ManualOneShotEvent.ManualOneShotInfo[waitHandles.Length]; try { for (int i = 0; i < waitHandles.Length; i++) { object obj = waitHandles[i]; if (obj == null) { throw new ArgumentNullException("An array element of waitHandles should not be null."); } array[i] = new ManualOneShotEvent.ManualOneShotInfo(); if (obj is ManualOneShotEvent) { ManualOneShotEvent.ManualOneShotInfo manualOneShotInfo = array[i]; ManualOneShotEvent manualOneShotEvent = obj as ManualOneShotEvent; manualOneShotInfo.IsManualOneShotEvent = true; manualOneShotInfo.ManualOneShotEvent = manualOneShotEvent; ManualOneShotEvent.IncrementResult incrementResult = manualOneShotEvent.IncrementRefCountIfNecessary(); if (incrementResult == ManualOneShotEvent.IncrementResult.NotIncrementedShuttingDown) { manualOneShotInfo.IsClosed = true; } else if (incrementResult == ManualOneShotEvent.IncrementResult.NotIncrementedAlreadySignaled) { manualOneShotInfo.IsPreSignaled = true; } else { manualOneShotInfo.IsWaitRegistered = true; list.Add(manualOneShotEvent.m_firstEventCompleted); } } else { if (!(obj is WaitHandle)) { throw new ArgumentException("An object of type {0} was passed in to the array. It must be either of type ManualOneShotEvent or WaitHandle.", obj.GetType().ToString()); } list.Add(obj as WaitHandle); } } if (array.All((ManualOneShotEvent.ManualOneShotInfo info) => info.IsManualOneShotEvent && info.IsClosed)) { ManualOneShotEvent.Tracer.TraceError(0L, "ManualOneShotEvent.WaitAny(): Every event is a ManualOneShotEvent and is already closed! Returning WaitTimeout."); return(258); } if (array.Any((ManualOneShotEvent.ManualOneShotInfo info) => info.IsManualOneShotEvent && info.IsPreSignaled)) { int num2 = -1; for (int j = 0; j < array.Length; j++) { ManualOneShotEvent.ManualOneShotInfo manualOneShotInfo2 = array[j]; if (manualOneShotInfo2.IsManualOneShotEvent && manualOneShotInfo2.IsPreSignaled && num2 == -1) { num2 = j; } if (manualOneShotInfo2.IsManualOneShotEvent && manualOneShotInfo2.IsWaitRegistered) { manualOneShotInfo2.ManualOneShotEvent.DecrementRefCountAndCloseIfNecessary(); manualOneShotInfo2.IsWaitUnregistered = true; } } return(num2); } num = WaitHandle.WaitAny(list.ToArray(), timeout); } finally { foreach (ManualOneShotEvent.ManualOneShotInfo manualOneShotInfo3 in array) { if (manualOneShotInfo3 != null && manualOneShotInfo3.IsManualOneShotEvent && manualOneShotInfo3.IsWaitRegistered && !manualOneShotInfo3.IsWaitUnregistered) { manualOneShotInfo3.ManualOneShotEvent.DecrementRefCountAndCloseIfNecessary(); manualOneShotInfo3.IsWaitUnregistered = true; } } } if (num == 258) { ManualOneShotEvent.Tracer.TraceError <TimeSpan>(0L, "ManualOneShotEvent.WaitAny(): Wait timed out after {0}!", timeout); return(num); } ManualOneShotEvent.Tracer.TraceDebug <int>(0L, "ManualOneShotEvent.WaitAny(): Event with *internal* index {0} was signaled.", num); int num3 = -1; int num4 = 0; for (int l = 0; l < array.Length; l++) { ManualOneShotEvent.ManualOneShotInfo manualOneShotInfo4 = array[l]; if (!manualOneShotInfo4.IsManualOneShotEvent || !manualOneShotInfo4.IsClosed) { num4++; } if (num == num4 - 1) { num3 = l; break; } } ManualOneShotEvent.Tracer.TraceDebug <int>(0L, "ManualOneShotEvent.WaitAny(): Event with index {0} was signaled. Returning {0}.", num3); return(num3); }
private void InternalInvoke(Action invokableAction, Action foregroundAction, TimeSpan invokeTimeout, bool sendWatsonReportNoThrow, object cancelEvent) { ExTraceGlobals.ClusterTracer.TraceDebug((long)this.GetHashCode(), "InternalInvoke calling BeginInvoke"); IAsyncResult result = invokableAction.BeginInvoke(new AsyncCallback(this.CompletionCallback), invokableAction); DateTime utcNow = DateTime.UtcNow; WaitHandle asyncWaitHandle = result.AsyncWaitHandle; bool flag = true; bool flag2 = false; try { if (foregroundAction != null) { foregroundAction(); } flag2 = true; TimeSpan timeSpan = DateTime.UtcNow.Subtract(utcNow); TimeSpan timeout; if (invokeTimeout == InvokeWithTimeout.InfiniteTimeSpan) { timeout = invokeTimeout; } else if (timeSpan < invokeTimeout) { timeout = invokeTimeout.Subtract(timeSpan); } else { timeout = TimeSpan.Zero; } int num = 1; if (cancelEvent != null) { num = 2; } object[] array = new object[num]; array[0] = asyncWaitHandle; if (cancelEvent != null) { array[1] = cancelEvent; } int num2 = ManualOneShotEvent.WaitAny(array, timeout); bool flag3 = false; bool flag4 = false; if (num2 == 258) { flag3 = true; } else if (num2 == 1) { flag4 = true; } if (flag3 || flag4) { if (flag3 && sendWatsonReportNoThrow) { if (this.m_asyncRefCount == 1) { flag3 = false; } } else if (Interlocked.Decrement(ref this.m_asyncRefCount) == 0) { flag3 = false; flag4 = false; } } if (flag3) { TimeoutException ex = new TimeoutException(Strings.OperationTimedOut(invokeTimeout.ToString())); if (!sendWatsonReportNoThrow) { flag = false; throw ex; } this.SendWatsonReport <TimeoutException>(ex); invokableAction.EndInvoke(result); } else { if (flag4) { OperationAbortedException ex2 = new OperationAbortedException(); flag = false; throw ex2; } invokableAction.EndInvoke(result); } } finally { if (!flag2) { if (Interlocked.Decrement(ref this.m_asyncRefCount) > 0) { flag = false; } else { Exception ex3 = this.RunOperation(delegate { invokableAction.EndInvoke(result); }); if (ex3 != null) { ExTraceGlobals.ClusterTracer.TraceError <Exception>((long)this.GetHashCode(), "EndInvoke() has thrown an exception after the foreground thread threw an exception. Exception: {0}", ex3); } } } if (flag && asyncWaitHandle != null) { asyncWaitHandle.Close(); } } }