Exemple #1
0
            public override Task ConnectAsync(EndPoint remoteAddress, EndPoint localAddress)
            {
                var promise = new TaskCompletionSource();

                if (Volatile.Read(ref _channel.v_state) == State.Connected)
                {
                    var cause = new AlreadyConnectedException();
                    Util.SafeSetFailure(promise, cause, Logger);
                    _ = _channel.Pipeline.FireExceptionCaught(cause);
                    return(promise.Task);
                }

                if (Volatile.Read(ref _channel.v_connectPromise) is object)
                {
                    ThrowHelper.ThrowConnectionPendingException();
                }

                _ = Interlocked.Exchange(ref _channel.v_connectPromise, promise);

                if (Volatile.Read(ref _channel.v_state) != State.Bound)
                {
                    // Not bound yet and no localAddress specified - get one.
                    if (localAddress is null)
                    {
                        localAddress = new LocalAddress(_channel);
                    }
                }

                if (localAddress is object)
                {
                    try
                    {
                        _channel.DoBind(localAddress);
                    }
                    catch (Exception ex)
                    {
                        Util.SafeSetFailure(promise, ex, Logger);
                        _ = _channel.CloseAsync();
                        return(promise.Task);
                    }
                }

                IChannel boundChannel = LocalChannelRegistry.Get(remoteAddress);

                if (!(boundChannel is LocalServerChannel serverChannel))
                {
                    Exception cause = new ConnectException($"connection refused: {remoteAddress}", null);
                    Util.SafeSetFailure(promise, cause, Logger);
                    _ = _channel.CloseAsync();
                    return(promise.Task);
                }

                _ = Interlocked.Exchange(ref _channel.v_peer, serverChannel.Serve(_channel));
                return(promise.Task);
            }
            public override Task ConnectAsync(EndPoint remoteAddress, EndPoint localAddress)
            {
                var promise = new TaskCompletionSource();

                if (this.localChannel.state == State.Connected)
                {
                    var cause = new AlreadyConnectedException();
                    Util.SafeSetFailure(promise, cause, Logger);
                    this.localChannel.Pipeline.FireExceptionCaught(cause);
                    return(promise.Task);
                }

                if (this.localChannel.connectPromise != null)
                {
                    throw new ConnectionPendingException();
                }

                this.localChannel.connectPromise = promise;

                if (this.localChannel.state != State.Bound)
                {
                    // Not bound yet and no localAddress specified - get one.
                    if (localAddress == null)
                    {
                        localAddress = new LocalAddress(this.localChannel);
                    }
                }

                if (localAddress != null)
                {
                    try
                    {
                        this.localChannel.DoBind(localAddress);
                    }
                    catch (Exception ex)
                    {
                        Util.SafeSetFailure(promise, ex, Logger);
                        this.channel.CloseAsync();
                        return(promise.Task);
                    }
                }

                IChannel boundChannel = LocalChannelRegistry.Get(remoteAddress);

                if (!(boundChannel is LocalServerChannel))
                {
                    Exception cause = new ConnectException($"connection refused: {remoteAddress}", null);
                    Util.SafeSetFailure(promise, cause, Logger);
                    this.localChannel.CloseAsync();
                    return(promise.Task);
                }

                this.localChannel.peer = ((LocalServerChannel)boundChannel).Serve(this.localChannel);
                return(promise.Task);
            }