167 lines
5.7 KiB
C#
167 lines
5.7 KiB
C#
//------------------------------------------------------------
|
|
// Copyright (c) Microsoft Corporation. All rights reserved.
|
|
//------------------------------------------------------------
|
|
|
|
namespace System.ServiceModel.Channels
|
|
{
|
|
using System.Runtime;
|
|
|
|
class TransportReplyChannelAcceptor : ReplyChannelAcceptor
|
|
{
|
|
TransportManagerContainer transportManagerContainer;
|
|
TransportChannelListener listener;
|
|
|
|
public TransportReplyChannelAcceptor(TransportChannelListener listener)
|
|
: base(listener)
|
|
{
|
|
this.listener = listener;
|
|
}
|
|
|
|
protected override ReplyChannel OnCreateChannel()
|
|
{
|
|
return new TransportReplyChannel(this.ChannelManager, null);
|
|
}
|
|
|
|
protected override void OnOpening()
|
|
{
|
|
base.OnOpening();
|
|
this.transportManagerContainer = this.listener.GetTransportManagers();
|
|
this.listener = null;
|
|
}
|
|
|
|
protected override void OnAbort()
|
|
{
|
|
base.OnAbort();
|
|
if (this.transportManagerContainer != null && !TransferTransportManagers())
|
|
{
|
|
this.transportManagerContainer.Abort();
|
|
}
|
|
}
|
|
|
|
IAsyncResult DummyBeginClose(TimeSpan timeout, AsyncCallback callback, object state)
|
|
{
|
|
return new CompletedAsyncResult(callback, state);
|
|
}
|
|
|
|
void DummyEndClose(IAsyncResult result)
|
|
{
|
|
CompletedAsyncResult.End(result);
|
|
}
|
|
|
|
protected override IAsyncResult OnBeginClose(TimeSpan timeout, AsyncCallback callback, object state)
|
|
{
|
|
ChainedBeginHandler begin1 = DummyBeginClose;
|
|
ChainedEndHandler end1 = DummyEndClose;
|
|
if (this.transportManagerContainer != null && !TransferTransportManagers())
|
|
{
|
|
begin1 = this.transportManagerContainer.BeginClose;
|
|
end1 = this.transportManagerContainer.EndClose;
|
|
}
|
|
|
|
return new ChainedAsyncResult(timeout, callback, state, base.OnBeginClose, base.OnEndClose, begin1, end1);
|
|
}
|
|
|
|
protected override void OnEndClose(IAsyncResult result)
|
|
{
|
|
ChainedAsyncResult.End(result);
|
|
}
|
|
|
|
protected override void OnClose(TimeSpan timeout)
|
|
{
|
|
TimeoutHelper timeoutHelper = new TimeoutHelper(timeout);
|
|
base.OnClose(timeoutHelper.RemainingTime());
|
|
if (this.transportManagerContainer != null && !TransferTransportManagers())
|
|
{
|
|
this.transportManagerContainer.Close(timeoutHelper.RemainingTime());
|
|
}
|
|
}
|
|
|
|
// used to decouple our channel and listener lifetimes
|
|
bool TransferTransportManagers()
|
|
{
|
|
TransportReplyChannel singletonChannel = (TransportReplyChannel)base.GetCurrentChannel();
|
|
if (singletonChannel == null)
|
|
{
|
|
return false;
|
|
}
|
|
else
|
|
{
|
|
return singletonChannel.TransferTransportManagers(this.transportManagerContainer);
|
|
}
|
|
}
|
|
|
|
// tracks TransportManager so that the channel can outlive the Listener
|
|
protected class TransportReplyChannel : ReplyChannel
|
|
{
|
|
TransportManagerContainer transportManagerContainer;
|
|
|
|
public TransportReplyChannel(ChannelManagerBase channelManager, EndpointAddress localAddress)
|
|
: base(channelManager, localAddress)
|
|
{
|
|
}
|
|
|
|
public bool TransferTransportManagers(TransportManagerContainer transportManagerContainer)
|
|
{
|
|
lock (ThisLock)
|
|
{
|
|
if (this.State != CommunicationState.Opened)
|
|
{
|
|
return false;
|
|
}
|
|
|
|
this.transportManagerContainer = transportManagerContainer;
|
|
return true;
|
|
}
|
|
}
|
|
|
|
protected override void OnAbort()
|
|
{
|
|
if (this.transportManagerContainer != null)
|
|
{
|
|
this.transportManagerContainer.Abort();
|
|
}
|
|
base.OnAbort();
|
|
}
|
|
|
|
protected override void OnClose(TimeSpan timeout)
|
|
{
|
|
TimeoutHelper timeoutHelper = new TimeoutHelper(timeout);
|
|
if (this.transportManagerContainer != null)
|
|
{
|
|
this.transportManagerContainer.Close(timeoutHelper.RemainingTime());
|
|
}
|
|
base.OnClose(timeoutHelper.RemainingTime());
|
|
}
|
|
|
|
IAsyncResult DummyBeginClose(TimeSpan timeout, AsyncCallback callback, object state)
|
|
{
|
|
return new CompletedAsyncResult(callback, state);
|
|
}
|
|
|
|
void DummyEndClose(IAsyncResult result)
|
|
{
|
|
CompletedAsyncResult.End(result);
|
|
}
|
|
|
|
protected override IAsyncResult OnBeginClose(TimeSpan timeout, AsyncCallback callback, object state)
|
|
{
|
|
ChainedBeginHandler begin1 = DummyBeginClose;
|
|
ChainedEndHandler end1 = DummyEndClose;
|
|
if (this.transportManagerContainer != null)
|
|
{
|
|
begin1 = this.transportManagerContainer.BeginClose;
|
|
end1 = this.transportManagerContainer.EndClose;
|
|
}
|
|
|
|
return new ChainedAsyncResult(timeout, callback, state, begin1, end1,
|
|
base.OnBeginClose, base.OnEndClose);
|
|
}
|
|
|
|
protected override void OnEndClose(IAsyncResult result)
|
|
{
|
|
ChainedAsyncResult.End(result);
|
|
}
|
|
}
|
|
}
|
|
}
|