public static Schedule ( WaitCallback callback, object state ) : void | ||
callback | WaitCallback | |
state | object | |
return | void |
void OnReceiveMessage(AmqpMessage message) { if (this.messageListener != null) { this.messageListener(message); } else { ReceiveAsyncResult waiter = null; int creditToIssue = 0; bool releaseMessage = false; lock (this.SyncRoot) { if (this.waiterList != null && this.waiterList.Count > 0) { waiter = this.waiterList.First.Value; this.waiterList.RemoveFirst(); waiter.OnRemoved(); creditToIssue = this.Settings.AutoSendFlow ? 0 : this.GetOnDemandReceiveCredit(); } else if (!this.Settings.AutoSendFlow && this.Settings.SettleType != SettleMode.SettleOnSend) { releaseMessage = true; } else if (this.messageQueue != null) { this.messageQueue.Enqueue(message); AmqpTrace.Provider.AmqpCacheMessage( this, message.DeliveryId.Value, this.messageQueue.Count, this.messageQueue.IsPrefetchingBySize, this.TotalCacheSizeInBytes ?? 0, this.Settings == null ? 0 : this.Settings.TotalLinkCredit, this.LinkCredit); } } if (releaseMessage) { this.ReleaseMessage(message); message.Dispose(); } if (creditToIssue > 0) { this.IssueCredit((uint)creditToIssue, false, AmqpConstants.NullBinary); } if (waiter != null) { // Schedule the completion on another thread so we don't block the I/O thread ActionItem.Schedule( o => { var state = (Tuple <ReceiveAsyncResult, IEnumerable <AmqpMessage> >)o; state.Item1.Signal(state.Item2, false); }, new Tuple <ReceiveAsyncResult, IEnumerable <AmqpMessage> >(waiter, new AmqpMessage[] { message })); } } }
void HandleCancellation(bool scheduleComplete) { if (Interlocked.CompareExchange(ref this.complete, 1, 0) == 0) { this.timer.Change(Timeout.Infinite, Timeout.Infinite); if (scheduleComplete) { ActionItem.Schedule(s => ((SleepAsyncResult)s).Complete(false), this); } else { this.Complete(true); } } }
public void Abort() { this.closed = true; ActionItem.Schedule(o => { var thisPtr = (WorkCollection <TKey, TWork, TOutcome>)o; List <TKey> keys = new List <TKey>(thisPtr.pendingWork.Keys); foreach (TKey key in keys) { TWork work; if (thisPtr.pendingWork.TryRemove(key, out work)) { work.Cancel(false, new OperationCanceledException()); } } }, this); }
public void CompleteWork(TKey key, bool syncComplete, TOutcome outcome) { TWork work; if (this.pendingWork.TryRemove(key, out work)) { if (syncComplete) { work.Done(true, outcome); } else { // Schedule the completion so we do not block the I/O thread ActionItem.Schedule( o => { var state = (Tuple <TWork, TOutcome>)o; state.Item1.Done(false, state.Item2); }, new Tuple <TWork, TOutcome>(work, outcome)); } } }
void CancelPendingOperations(bool aborted, out Queue <AmqpMessage> messagesToRelease) { messagesToRelease = null; LinkedList <ReceiveAsyncResult> waiters = null; lock (this.SyncRoot) { messagesToRelease = this.messageQueue; waiters = this.waiterList; this.messageQueue = null; this.waiterList = null; } if (waiters != null) { ActionItem.Schedule(o => { var state = (Tuple <LinkedList <ReceiveAsyncResult>, bool>)o; LinkedList <ReceiveAsyncResult> waitersToCancel = state.Item1; foreach (ReceiveAsyncResult waiter in waitersToCancel) { if (state.Item2) { waiter.Cancel(); } else { waiter.Signal(false, null); } } }, new Tuple <LinkedList <ReceiveAsyncResult>, bool>(waiters, aborted)); } if (this.pendingDispositions != null) { this.pendingDispositions.Abort(); } }
bool IWorkDelegate <AmqpMessage> .Invoke(AmqpMessage message) { DeliveryState deliveryState = message.State; if (deliveryState != null && deliveryState.DescriptorCode == Released.Code) { // message has been cancelled (e.g. timed out) return(true); } bool success = this.TrySendDelivery(message); if (!success && this.Session.State == AmqpObjectState.Opened && DateTime.UtcNow - this.lastFlowRequestTime >= MinRequestCreditWindow) { // Tell the other side that we have some messages to send this.lastFlowRequestTime = DateTime.UtcNow; ActionItem.Schedule(s => OnRequestCredit(s), this); } return(success); }
void OnReceiveMessage(AmqpMessage message) { if (this.messageListener != null) { this.messageListener(message); } else { ReceiveAsyncResult waiter = null; int creditToIssue = 0; bool releaseMessage = false; lock (this.SyncRoot) { if (this.waiterList != null && this.waiterList.Count > 0) { var firstWaiter = this.waiterList.First.Value; if (this.messageQueue.IsPrefetchingBySize) { if (this.messageQueue.UpdateCreditToIssue(message)) { this.SetTotalLinkCredit(this.messageQueue.BoundedTotalLinkCredit, true); } } firstWaiter.Add(message); if (firstWaiter.RequestedMessageCount == 1 || firstWaiter.MessageCount >= firstWaiter.RequestedMessageCount) { this.waiterList.RemoveFirst(); firstWaiter.OnRemoved(); creditToIssue = this.Settings.AutoSendFlow ? 0 : this.GetOnDemandReceiveCredit(); waiter = firstWaiter; } } else if (!this.Settings.AutoSendFlow && this.Settings.SettleType != SettleMode.SettleOnSend) { releaseMessage = true; } else if (this.messageQueue != null) { this.messageQueue.Enqueue(message); AmqpTrace.Provider.AmqpCacheMessage( this, message.DeliveryId.Value, this.messageQueue.Count, this.messageQueue.IsPrefetchingBySize, this.TotalCacheSizeInBytes ?? 0, this.Settings == null ? 0 : this.Settings.TotalLinkCredit, this.LinkCredit); } } if (releaseMessage) { this.ReleaseMessage(message); message.Dispose(); } if (creditToIssue > 0) { this.IssueCredit((uint)creditToIssue, false, AmqpConstants.NullBinary); } if (waiter != null) { // Schedule the completion on another thread so we don't block the I/O thread ActionItem.Schedule(o => { var w = (ReceiveAsyncResult)o; w.Signal(false); }, waiter); } } }