/// <summary> /// Gets or creates a channel /// </summary> /// <returns>The channel with the given name.</returns> /// <param name="attribute">The attribute describing the channel.</param> /// <typeparam name="T">The type of data in the channel.</typeparam> public IChannel <T> GetOrCreate <T>(ChannelNameAttribute attribute) { if (attribute == null) { throw new ArgumentNullException(nameof(attribute)); } lock (__lock) { var res = RecursiveLookup(attribute.Name); if (res != null) { return((IChannel <T>)res); } else { var chan = DoCreateChannel <T>(attribute); if (!string.IsNullOrWhiteSpace(attribute.Name)) { m_lookup.Add(attribute.Name, chan); } return(chan); } } }
/// <summary> /// Creates the channel by calling the ChannelManager. /// </summary> /// <returns>The channel with the given name.</returns> /// <param name="attribute">The attribute describing the channel to create.</param> /// <typeparam name="T">The type of data in the channel.</typeparam> protected virtual IChannel <T> DoCreateChannel <T>(ChannelNameAttribute attribute) { // Recusively visit the scope create helpers var cur = this; while (cur != null) { if (!string.IsNullOrWhiteSpace(attribute.Name) && cur.m_namedCreateHelpers.TryGetValue(attribute.Name, out var creator)) { var res = creator(this, attribute); if (res != null) { return((IChannel <T>)res); } } foreach (var p in cur.m_createOverrides) { var res = p(this, attribute); if (res != null) { return((IChannel <T>)res); } } cur = cur.ParentScope; } return(ChannelManager.CreateChannelForScope <T>(attribute)); }
/// <summary> /// Handler method to create a profiling channel /// </summary> /// <returns>The profiling channel.</returns> /// <param name="scope">The scope calling the method.</param> /// <param name="attr">The channel attribute.</param> /// <param name="type">The type to create the channel for</param> private static IUntypedChannel Creator(ChannelScope scope, ChannelNameAttribute attr, Type type) { return ((IUntypedChannel)typeof(ProfilerChannelScope) .GetMethod(nameof(CreateProfilingChannel), System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.DeclaredOnly | System.Reflection.BindingFlags.NonPublic) .MakeGenericMethod(type) .Invoke(scope, new object[] { attr })); }
/// <summary> /// Helper method to invoke the default channel instance creator /// </summary> /// <returns>The created channel.</returns> /// <param name="attribute">The attribute describing the channel to create.</param> protected IChannel <T> BaseCreateChannel <T>(ChannelNameAttribute attribute) { if (ParentScope != Root) { return(ParentScope.GetOrCreate <T>(attribute)); } return(ChannelManager.CreateChannelForScope <T>(attribute)); }
/// <summary> /// Initializes a new instance of the <see cref="CoCoL.ChannelNameMarker"/> class. /// </summary> /// <param name="attribute">The attribute describing the channel.</param> public ChannelNameMarker(ChannelNameAttribute attribute) { if (attribute == null) { throw new ArgumentNullException("attribute"); } this.Attribute = attribute; }
/// <summary> /// Creates a channel for use in a scope /// </summary> /// <returns>The channel.</returns> /// <param name="attribute">The attribute describing the channel.</param> /// <typeparam name="T">The channel type.</typeparam> internal static IChannel <T> CreateChannelForScope <T>(ChannelNameAttribute attribute) { if (attribute is BroadcastChannelNameAttribute) { return(new BroadcastingChannel <T>(attribute)); } else { return(new Channel <T>(attribute)); } }
/// <summary> /// Initializes a new instance of the <see cref="CoCoL.ChannelMarkerWrapper<T>"/> class. /// </summary> /// <param name="attribute">The attribute describing the channel.</param> public ChannelMarkerWrapper(ChannelNameAttribute attribute) { if (attribute == null) { throw new ArgumentNullException("attribute"); } Attribute = attribute; ForWrite = ChannelMarker.ForWrite <T>(attribute); ForRead = ChannelMarker.ForRead <T>(attribute); }
/// <summary> /// Creates the channel by calling the ChannelManager. /// </summary> /// <returns>The channel with the given name.</returns> /// <param name="attribute">The attribute describing the channel to create.</param> /// <typeparam name="T">The type of data in the channel.</typeparam> protected virtual IChannel <T> DoCreateChannel <T>(ChannelNameAttribute attribute) { var cur = this; while (cur != null && cur != Root) { var res = cur.TryCreateChannel <T>(attribute); if (res != null) { return(res); } cur = cur.ParentScope; } return(ChannelManager.CreateChannelForScope <T>(attribute)); }
/// <summary> /// Initializes a new instance of the <see cref="T:CoCoL.BroadcastingChannel<1>"/> class. /// </summary> /// <param name="attr">The channel name attributes.</param> internal BroadcastingChannel(ChannelNameAttribute attr) : base(attr) { if (attr is BroadcastChannelNameAttribute) { m_initialBarrierSize = ((BroadcastChannelNameAttribute)attr).InitialBarrierSize; m_minimumReaders = ((BroadcastChannelNameAttribute)attr).MinimumReaders; } if (m_minimumReaders > 0 && m_maxPendingReaders > 0 && m_maxPendingReaders < m_minimumReaders) { throw new ArgumentOutOfRangeException(string.Format("The setup requires {0} readers waiting, but the channel only allows {1} waiting readers", m_minimumReaders, m_maxPendingReaders)); } if (m_initialBarrierSize > 0 && m_maxPendingReaders > 0 && m_maxPendingReaders < m_initialBarrierSize) { throw new ArgumentOutOfRangeException(string.Format("The setup requires {0} readers waiting, but the channel only allows {1} waiting readers", m_initialBarrierSize, m_maxPendingReaders)); } }
/// <summary> /// Initializes a new instance of the <see cref="CoCoL.Channel<T>"/> class. /// </summary> /// <param name="attribute">The attribute describing the channel</param> internal Channel(ChannelNameAttribute attribute) { if (attribute == null) { throw new ArgumentNullException("attribute"); } if (attribute.BufferSize < 0) { throw new ArgumentOutOfRangeException("BufferSize", "The size parameter must be greater than or equal to zero"); } this.Name = attribute.Name; m_bufferSize = attribute.BufferSize; m_maxPendingReaders = attribute.MaxPendingReaders; m_maxPendingWriters = attribute.MaxPendingWriters; m_pendingReadersOverflowStrategy = attribute.PendingReadersOverflowStrategy; m_pendingWritersOverflowStrategy = attribute.PendingWritersOverflowStrategy; }
/// <summary> /// Initializes a new instance of the <see cref="CoCoL.WriteMarker<T>"/> class. /// </summary> /// <param name="attribute">The attribute describing the channel.</param> public WriteMarker(ChannelNameAttribute attribute) : base(attribute) { }
/// <summary> /// Initializes a new instance of the <see cref="CoCoL.ReadMarker<T>"/> class. /// </summary> /// <param name="attribute">The attribute describing the channel.</param> public ReadMarker(ChannelNameAttribute attribute) : base(attribute) { }
/// <summary> /// Initializes a new instance of the <see cref="CoCoL.ChannelNameMarker"/> class. /// </summary> /// <param name="attribute">The attribute describing the channel.</param> protected ChannelNameMarker(ChannelNameAttribute attribute) { this.Attribute = attribute ?? throw new ArgumentNullException(nameof(attribute)); }
/// <summary> /// Creates the channel by calling the ChannelManager. /// </summary> /// <returns>The channel with the given name.</returns> /// <param name="attribute">The attribute describing the channel to create.</param> /// <typeparam name="T">The type of data in the channel.</typeparam> protected virtual IChannel <T> DoCreateChannel <T>(ChannelNameAttribute attribute) { return(ChannelManager.CreateChannelForScope <T>(attribute)); }
/// <summary> /// Creates a marker property for a read channel /// </summary> /// <returns>The marker instance.</returns> /// <param name="attribute">The attribute describing the channel.</param> /// <typeparam name="T">The type of data passed on the channel.</typeparam> public static IReadChannel <T> ForRead <T>(ChannelNameAttribute attribute) { return(new ReadMarker <T>(attribute)); }
/// <summary> /// Returns the default channel type /// </summary> /// <returns>The created channel.</returns> /// <param name="attribute">The channel attribute.</param> /// <typeparam name="T">The channel type parameter.</typeparam> protected override IChannel <T> TryCreateChannel <T>(ChannelNameAttribute attribute) { return(ChannelManager.CreateChannelForScope <T>(attribute)); }
/// <summary> /// Gets or creates a channel /// </summary> /// <returns>The or create.</returns> /// <param name="attribute">The attribute describing the channel to create.</param> /// <param name="datatype">The type of data communicated through the channel.</param> public IRetireAbleChannel GetOrCreate(ChannelNameAttribute attribute, Type datatype) { return((IRetireAbleChannel)typeof(ChannelScope).GetMethod("GetOrCreate", new [] { typeof(ChannelNameAttribute) }) .MakeGenericMethod(datatype) .Invoke(this, new object[] { attribute })); }
/// <summary> /// Creates a channel, possibly unnamed. /// If a channel name is provided, the channel is created in the supplied scope. /// If a channel with the given name is already found in the supplied scope, the named channel is returned. /// </summary> /// <returns>The named channel.</returns> /// <param name="attr">The attribute describing the channel.</param> /// <param name="scope">The scope to create a named channel in, defaults to null which means the current scope</param> /// <typeparam name="T">The channel type.</typeparam> public static IChannel <T> CreateChannel <T>(ChannelNameAttribute attr, ChannelScope scope = null) { return(GetChannel <T>(attr, scope)); }
/// <summary> /// Hook method that allows custom channel creation /// </summary> /// <returns>The created channel or null, if there is no special handler.</returns> /// <param name="attribute">The attribute describing the channel to create.</param> /// <typeparam name="T">The type of data in the channel.</typeparam> protected override IChannel <T> TryCreateChannel <T>(ChannelNameAttribute attribute) { return(m_selector(attribute.Name) ? (IChannel <T>)m_creator(this, attribute, typeof(T)) : null); }
/// <summary> /// Initializes a new instance of the <see cref="T:CoCoL.ChannelMarkerWrapper<T>"/> class. /// </summary> /// <param name="attribute">The attribute describing the channel.</param> public ChannelMarkerWrapper(ChannelNameAttribute attribute) { Attribute = attribute ?? throw new ArgumentNullException(nameof(attribute)); ForWrite = ChannelMarker.ForWrite <T>(attribute); ForRead = ChannelMarker.ForRead <T>(attribute); }
/// <summary> /// Hook method that allows custom channel creation /// </summary> /// <returns>The created channel or null, if there is no special handler.</returns> /// <param name="attribute">The attribute describing the channel to create.</param> /// <typeparam name="T">The type of data in the channel.</typeparam> protected virtual IChannel <T> TryCreateChannel <T>(ChannelNameAttribute attribute) { return(null); }
/// <summary> /// Gets or creates a named channel. /// </summary> /// <returns>The named channel.</returns> /// <param name="attr">The attribute describing the channel.</param> /// <param name="scope">The scope to create a named channel in, defaults to null which means the current scope</param> /// <typeparam name="T">The channel type.</typeparam> public static IChannel <T> GetChannel <T>(ChannelNameAttribute attr, ChannelScope scope = null) { return((scope ?? ChannelScope.Current).GetOrCreate <T>(attr)); }
/// <summary> /// Creates a marker property for a write channel /// </summary> /// <returns>The marker instance.</returns> /// <param name="attribute">The attribute describing the channel.</param> /// <typeparam name="T">The type of data passed on the channel.</typeparam> public static IWriteChannel <T> ForWrite <T>(ChannelNameAttribute attribute) { return(new WriteMarker <T>(attribute)); }
/// <summary> /// Creates a channel that is wrapped in a profiling channel instance /// </summary> /// <returns>The profiling-wrapped channel.</returns> /// <param name="attribute">The channel attribute.</param> /// <typeparam name="T">The channel type parameter.</typeparam> private IChannel <T> CreateProfilingChannel <T>(ChannelNameAttribute attribute) { return(new ProfilingChannel <T>(this.BaseCreateChannel <T>(attribute))); }
/// <summary> /// Gets or creates a named channel. /// </summary> /// <returns>The named channel.</returns> /// <param name="attr">The attribute describing the channel.</param> /// <param name="scope">The scope to create a named channel in, defaults to null which means the current scope</param> /// <typeparam name="T">The channel type.</typeparam> public static IChannel <T> Get <T>(ChannelNameAttribute attr, ChannelScope scope = null) { return(ChannelManager.GetChannel <T>(attr, scope)); }