/// <summary> /// Sends an end frame. /// </summary> /// <returns>The session state after sending the end frame.</returns> protected AmqpObjectState SendEnd() { StateTransition transition = this.TransitState("S:END", StateTransition.SendClose); End end = new End(); Exception exception = this.TerminalException; if (exception != null) { end.Error = Error.FromException(exception); } this.SendCommand(end); return(transition.To); }
void OnReceiveOpen(Open open) { StateTransition stateTransition = this.TransitState("R:OPEN", StateTransition.ReceiveOpen); uint peerIdleTimeout = open.IdleTimeOut(); if (peerIdleTimeout < this.Settings.MinIdleTimeout) { this.CompleteOpen(false, new AmqpException(AmqpErrorCode.NotAllowed, AmqpResources.GetString(AmqpResources.AmqpIdleTimeoutNotSupported, peerIdleTimeout, this.Settings.MinIdleTimeout))); return; } this.Negotiate(open); this.NotifyOpening(open); if (stateTransition.To == AmqpObjectState.OpenReceived) { this.SendOpen(); } if (this.isInitiator) { // check if open returned an error right away Error openError = null; if (open.Properties != null && open.Properties.TryGetValue <Error>(AmqpConstants.OpenErrorName, out openError)) { this.CompleteOpen(stateTransition.From == AmqpObjectState.Start, new AmqpException(openError)); return; } } uint myIdleTimeout = this.Settings.IdleTimeOut(); peerIdleTimeout = open.IdleTimeOut(); if (peerIdleTimeout != uint.MaxValue || myIdleTimeout != uint.MaxValue) { this.heartBeat = HeartBeat.Initialize(this, myIdleTimeout, peerIdleTimeout); } this.CompleteOpen(stateTransition.From == AmqpObjectState.Start, null); }
AmqpObjectState SendDetach() { StateTransition transition = this.TransitState("S:DETACH", StateTransition.SendClose); Detach detach = new Detach(); detach.Handle = this.LocalHandle; detach.Closed = true; Exception exception = this.TerminalException; if (exception != null && transition.To != AmqpObjectState.End) { detach.Error = Error.FromException(exception); } this.Session.SendCommand(detach); AmqpTrace.Provider.AmqpLinkDetach(this, this.Name, this.LocalHandle ?? 0u, "S:DETACH", detach.Error != null ? detach.Error.Condition.Value : string.Empty); return(transition.To); }
public static bool CanTransite(AmqpObjectState from, StateTransition[] states) { for (int i = 0; i < states.Length; i++) { if (states[i].From == from) { return true; } } return false; }
void OnReceiveAttach(Attach attach) { StateTransition stateTransition = this.TransitState("R:ATTACH", StateTransition.ReceiveOpen); Error error = this.Negotiate(attach); if (error != null) { this.OnLinkOpenFailed(new AmqpException(error)); return; } if (stateTransition.From == AmqpObjectState.OpenSent) { if (this.IsReceiver) { Source source = this.settings.Source as Source; if (source != null && source.Dynamic()) { source.Address = ((Source)attach.Source).Address; } this.OnReceiveStateOpenSent(attach); } else { Target target = this.settings.Target as Target; if (target != null && target.Dynamic()) { target.Address = ((Target)attach.Target).Address; } } if (attach.Properties != null) { if (this.Settings.Properties == null) { this.settings.Properties = attach.Properties; } else { this.settings.Properties.Merge(attach.Properties); } } } if (stateTransition.To == AmqpObjectState.Opened) { if ((this.IsReceiver && attach.Source == null) || (!this.IsReceiver && attach.Target == null)) { // not linkendpoint was created on the remote side // a detach should be sent immediately by peer with error return; } if (this.IsReceiver) { this.deliveryCount = attach.InitialDeliveryCount.Value; this.settings.Source = attach.Source; } else { this.settings.Target = attach.Target; } // in some scenario (e.g. EventHub) the service // side can override the settle type based on // entity settings. this.settings.SettleType = attach.SettleType(); this.CompleteOpen(false, null); } else if (stateTransition.To == AmqpObjectState.OpenReceived) { try { this.Session.LinkFactory.BeginOpenLink(this, this.DefaultOpenTimeout, onProviderLinkOpened, this); } catch (Exception exception) when(!Fx.IsFatal(exception)) { this.OnLinkOpenFailed(exception); } } }