TransportManager.cs source code in C# .NET

Source code for the .NET framework in C#

                        

Code:

/ WCF / WCF / 3.5.30729.1 / untmp / Orcas / SP / ndp / cdf / src / WCF / ServiceModel / System / ServiceModel / Channels / TransportManager.cs / 1 / TransportManager.cs

                            //---------------------------------------------------------------------------- 
// Copyright (c) Microsoft Corporation.  All rights reserved.
//---------------------------------------------------------------------------
namespace System.ServiceModel.Channels
{ 
    using System.Collections.Generic;
    using System.ServiceModel; 
    using System.Diagnostics; 
    using System.IO;
    using System.Net; 
    using System.ServiceModel.Diagnostics;
    using System.Text;
    using System.Threading;
    using System.Web; 
    using System.Web.Hosting;
 
    abstract class TransportManager 
    {
        ServiceModelActivity activity; 
        int openCount;
        object thisLock = new object();

        protected ServiceModelActivity Activity 
        {
            get { return this.activity; } 
        } 

        internal abstract string Scheme { get;} 

        internal object ThisLock
        {
            get { return this.thisLock; } 
        }
 
        internal void Close(TransportChannelListener channelListener) 
        {
            using (ServiceModelActivity.BoundOperation(this.Activity)) 
            {
                this.Unregister(channelListener);
            }
            lock (ThisLock) 
            {
                if (openCount <= 0) 
                { 
                    DiagnosticUtility.DebugAssert("Invalid Open/Close state machine.");
                    throw DiagnosticUtility.ExceptionUtility.ThrowHelperInternal(false); 
                }

                openCount--;
 
                if (openCount == 0)
                { 
                    // Wrap the final close here with transfers. 
                    using (ServiceModelActivity.BoundOperation(this.Activity, true))
                    { 
                        OnClose();
                    }
                    if (this.Activity != null)
                    { 
                        this.Activity.Dispose();
                    } 
                } 
            }
        } 

        internal static void EnsureRegistered(UriPrefixTable addressTable,
            TChannelListener channelListener, HostNameComparisonMode registeredComparisonMode)
            where TChannelListener : TransportChannelListener 
        {
            TChannelListener existingFactory; 
            if (!addressTable.TryLookupUri(channelListener.Uri, registeredComparisonMode, out existingFactory) || 
                (existingFactory != channelListener))
            { 
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new InvalidOperationException(SR.GetString(
                    SR.ListenerFactoryNotRegistered, channelListener.Uri)));
            }
        } 

        // Must be called under lock(ThisLock). 
        protected void Fault(UriPrefixTable addressTable, Exception exception) 
            where TChannelListener : ChannelListenerBase
        { 
            foreach (KeyValuePair pair in addressTable.GetAll())
            {
                TChannelListener listener = pair.Value;
                listener.Fault(exception); 
                listener.Abort();
            } 
        } 

        internal abstract void OnClose(); 
        internal abstract void OnOpen();

        internal void Open(TransportChannelListener channelListener)
        { 
            if (DiagnosticUtility.ShouldUseActivity)
            { 
                if (this.activity == null) 
                {
                    this.activity = ServiceModelActivity.CreateActivity(true); 
                    if (DiagnosticUtility.ShouldUseActivity)
                    {
                        DiagnosticUtility.DiagnosticTrace.TraceTransfer(this.Activity.Id);
                        ServiceModelActivity.Start(this.Activity, SR.GetString(SR.ActivityListenAt, channelListener.Uri.ToString()), ActivityType.ListenAt); 
                    }
                } 
                channelListener.Activity = this.Activity; 
            }
            using (ServiceModelActivity.BoundOperation(this.Activity)) 
            {
                if (DiagnosticUtility.ShouldTraceInformation)
                {
                    DiagnosticUtility.DiagnosticTrace.TraceEvent(TraceEventType.Information, TraceCode.TransportListen, 
                        SR.GetString(SR.TraceCodeTransportListen, channelListener.Uri.ToString()), null, null, this);
                } 
                this.Register(channelListener); 
                try
                { 
                    lock (ThisLock)
                    {
                        if (openCount == 0)
                        { 
                            OnOpen();
                        } 
 
                        openCount++;
                    } 
                }
                catch
                {
                    this.Unregister(channelListener); 
                    throw;
                } 
            } 
        }
 
        internal abstract void Register(TransportChannelListener channelListener);

        // should only call this under ThisLock (unless accessing purely for inspection)
        protected void ThrowIfOpen() 
        {
            if (openCount > 0) 
            { 
                throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(
                    new InvalidOperationException(SR.GetString(SR.TransportManagerOpen))); 
            }
        }

        internal abstract void Unregister(TransportChannelListener channelListener); 
    }
 
 
    delegate IList SelectTransportManagersCallback();
    class TransportManagerContainer 
    {
        IList transportManagers;
        TransportChannelListener listener;
        bool closed; 
        object tableLock;
 
        public TransportManagerContainer(TransportChannelListener listener) 
        {
            this.listener = listener; 
            this.tableLock = listener.TransportManagerTable;
            this.transportManagers = new List();
        }
 
        TransportManagerContainer(TransportManagerContainer source)
        { 
            this.listener = source.listener; 
            this.tableLock = source.tableLock;
            this.transportManagers = new List(); 
            for (int i = 0; i < source.transportManagers.Count; i++)
            {
                this.transportManagers.Add(source.transportManagers[i]);
            } 
        }
 
        // copy contents into a new container (used for listener/channel lifetime decoupling) 
        public static TransportManagerContainer TransferTransportManagers(TransportManagerContainer source)
        { 
            TransportManagerContainer result = null;

            lock (source.tableLock)
            { 
                if (source.transportManagers.Count > 0)
                { 
                    result = new TransportManagerContainer(source); 
                    source.transportManagers.Clear();
                } 
            }

            return result;
        } 

        public IAsyncResult BeginOpen(SelectTransportManagersCallback selectTransportManagerCallback, 
            AsyncCallback callback, object state) 
        {
            return new OpenAsyncResult(selectTransportManagerCallback, this, callback, state); 
        }

        public void EndOpen(IAsyncResult result)
        { 
            OpenAsyncResult.End(result);
        } 
 
        public void Open(SelectTransportManagersCallback selectTransportManagerCallback)
        { 
            lock (this.tableLock)
            {
                if (closed) // if we've been aborted then don't get transport managers
                { 
                    return;
                } 
 
                IList foundTransportManagers = selectTransportManagerCallback();
                if (foundTransportManagers == null) // nothing to do 
                {
                    return;
                }
 
                for (int i = 0; i < foundTransportManagers.Count; i++)
                { 
                    TransportManager transportManager = foundTransportManagers[i]; 
                    transportManager.Open(this.listener);
                    this.transportManagers.Add(transportManager); 
                }
            }
        }
 
        public IAsyncResult BeginClose(TimeSpan timeout, AsyncCallback callback, object state)
        { 
            return new CloseAsyncResult(this, callback, state); 
        }
 
        public void EndClose(IAsyncResult result)
        {
            CloseAsyncResult.End(result);
        } 

        public void Close() 
        { 
            if (this.closed)
            { 
                return;
            }

            lock (this.tableLock) 
            {
                if (this.closed) 
                { 
                    return;
                } 

                this.closed = true;

                foreach (TransportManager transportManager in this.transportManagers) 
                {
                    transportManager.Close(listener); 
                } 
                this.transportManagers.Clear();
            } 
        }

        abstract class OpenOrCloseAsyncResult : TraceAsyncResult
        { 
            TransportManagerContainer parent;
            static WaitCallback scheduledCallback = new WaitCallback(OnScheduled); 
 
            protected OpenOrCloseAsyncResult(TransportManagerContainer parent, AsyncCallback callback,
                object state) 
                : base(callback, state)
            {
                this.parent = parent;
            } 

            protected void Begin() 
            { 
                IOThreadScheduler.ScheduleCallback(scheduledCallback, this);
            } 

            static void OnScheduled(object state)
            {
                ((OpenOrCloseAsyncResult)state).OnScheduled(); 
            }
 
            void OnScheduled() 
            {
                using (ServiceModelActivity.BoundOperation(this.CallbackActivity)) 
                {
                    Exception completionException = null;
                    try
                    { 
                        this.OnScheduled(this.parent);
                    } 
#pragma warning suppress 56500 // [....], transferring exception to another thread 
                    catch (Exception e)
                    { 
                        if (DiagnosticUtility.IsFatal(e))
                        {
                            throw;
                        } 
                        completionException = e;
                    } 
 
                    this.Complete(false, completionException);
                } 
            }

            protected abstract void OnScheduled(TransportManagerContainer parent);
        } 

        sealed class CloseAsyncResult : OpenOrCloseAsyncResult 
        { 
            public CloseAsyncResult(TransportManagerContainer parent, AsyncCallback callback,
                object state) 
                : base(parent, callback, state)
            {
                this.Begin();
            } 

            public static void End(IAsyncResult result) 
            { 
                AsyncResult.End(result);
            } 

            protected override void OnScheduled(TransportManagerContainer parent)
            {
                parent.Close(); 
            }
        } 
 
        sealed class OpenAsyncResult : OpenOrCloseAsyncResult
        { 
            SelectTransportManagersCallback selectTransportManagerCallback;

            public OpenAsyncResult(SelectTransportManagersCallback selectTransportManagerCallback, TransportManagerContainer parent,
                AsyncCallback callback, object state) 
                : base(parent, callback, state)
            { 
                this.selectTransportManagerCallback = selectTransportManagerCallback; 
                this.Begin();
            } 

            public static void End(IAsyncResult result)
            {
                AsyncResult.End(result); 
            }
 
            protected override void OnScheduled(TransportManagerContainer parent) 
            {
                parent.Open(this.selectTransportManagerCallback); 
            }
        }
    }
} 

// File provided for Reference Use Only by Microsoft Corporation (c) 2007.
// Copyright (c) Microsoft Corporation. All rights reserved.
                        

Link Menu

Network programming in C#, Network Programming in VB.NET, Network Programming in .NET
This book is available now!
Buy at Amazon US or
Buy at Amazon UK