Beispiel #1
0
        private Task ConnectAsyncCore(IPAddress[] addresses, int port)
        {
            // Validate the args, similar to how Socket.Connect(IPAddress[], int) would.
            if (addresses == null)
            {
                throw new ArgumentNullException(nameof(addresses));
            }
            if (addresses.Length == 0)
            {
                throw new ArgumentException(SR.net_invalidAddressList, nameof(addresses));
            }
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            // If the client socket has already materialized, this API can't be used.
            // Similarly if another operation to set the socket is already in progress.
            if (_clientSocket != null)
            {
                throw new PlatformNotSupportedException(SR.net_sockets_connect_multiaddress_notsupported);
            }

            // Do the real work.
            EnterClientLock();
            return(ConnectAsyncCorePrivate(addresses, port));
        }
Beispiel #2
0
        // This creates a TcpListener that listens on both IPv4 and IPv6 on the given port.
        public static TcpListener Create(int port)
        {
            if (NetEventSource.IsEnabled)
            {
                NetEventSource.Enter(null, port);
            }

            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            TcpListener listener;

            if (Socket.OSSupportsIPv6)
            {
                // If OS supports IPv6 use dual mode so both address families work.
                listener = new TcpListener(IPAddress.IPv6Any, port);
                listener.Server.DualMode = true;
            }
            else
            {
                // If not, fall-back to old IPv4.
                listener = new TcpListener(IPAddress.Any, port);
            }

            if (NetEventSource.IsEnabled)
            {
                NetEventSource.Exit(null, port);
            }

            return(listener);
        }
Beispiel #3
0
        // Connects the Client to the specified port on the specified host.
        public void Connect(IPAddress address, int port)
        {
            if (Logging.On)
            {
                Logging.Enter(Logging.Sockets, this, "Connect", address);
            }

            if (_cleanedUp)
            {
                throw new ObjectDisposedException(this.GetType().FullName);
            }
            if (address == null)
            {
                throw new ArgumentNullException("address");
            }
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException("port");
            }

            IPEndPoint remoteEP = new IPEndPoint(address, port);

            Connect(remoteEP);
            if (Logging.On)
            {
                Logging.Exit(Logging.Sockets, this, "Connect", null);
            }
        }
Beispiel #4
0
        // Connects the Client to the specified port on the specified host.
        public void Connect(IPAddress address, int port)
        {
            if (NetEventSource.Log.IsEnabled())
            {
                NetEventSource.Enter(this, address);
            }

            ThrowIfDisposed();

            if (address == null)
            {
                throw new ArgumentNullException(nameof(address));
            }
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            IPEndPoint remoteEP = new IPEndPoint(address, port);

            Connect(remoteEP);

            if (NetEventSource.Log.IsEnabled())
            {
                NetEventSource.Exit(this);
            }
        }
Beispiel #5
0
        // Connects the Client to the specified port on the specified host.
        public void Connect(IPAddress address, int port)
        {
            if (NetEventSource.IsEnabled)
            {
                NetEventSource.Enter(this, address);
            }

            if (_cleanedUp)
            {
                throw new ObjectDisposedException(GetType().FullName);
            }
            if (address == null)
            {
                throw new ArgumentNullException(nameof(address));
            }
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            IPEndPoint remoteEP = new IPEndPoint(address, port);

            Connect(remoteEP);

            if (NetEventSource.IsEnabled)
            {
                NetEventSource.Exit(this);
            }
        }
Beispiel #6
0
        // Initializes a new instance of the System.Net.Sockets.TcpClient class and connects to the specified port on
        // the specified host.
        public TcpClient(string hostname, int port)
        {
            if (NetEventSource.IsEnabled)
            {
                NetEventSource.Enter(this, hostname);
            }

            if (hostname == null)
            {
                throw new ArgumentNullException(nameof(hostname));
            }
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            try
            {
                Connect(hostname, port);
            }
            catch
            {
                _clientSocket?.Close();
                throw;
            }

            if (NetEventSource.IsEnabled)
            {
                NetEventSource.Exit(this);
            }
        }
Beispiel #7
0
        // Initializes a new instance of the System.Net.Sockets.TcpClient class and connects to the specified port on
        // the specified host.
        public TcpClient(string hostname, int port)
        {
            if (NetEventSource.Log.IsEnabled())
            {
                NetEventSource.Info(this, hostname);
            }

            if (hostname == null)
            {
                throw new ArgumentNullException(nameof(hostname));
            }
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            _family = AddressFamily.Unknown;

            try
            {
                Connect(hostname, port);
            }
            catch
            {
                _clientSocket?.Close();
                throw;
            }
        }
Beispiel #8
0
        // Creates a new instance of the UdpClient class that communicates on the
        // specified port number.
        public UdpClient(int port, AddressFamily family)
        {
            // Validate input parameters.
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            // Validate the address family.
            if (family != AddressFamily.InterNetwork && family != AddressFamily.InterNetworkV6)
            {
                throw new ArgumentException(SR.Format(SR.net_protocol_invalid_family, "UDP"), nameof(family));
            }

            IPEndPoint localEP;

            _family = family;

            if (_family == AddressFamily.InterNetwork)
            {
                localEP = new IPEndPoint(IPAddress.Any, port);
            }
            else
            {
                localEP = new IPEndPoint(IPAddress.IPv6Any, port);
            }

            CreateClientSocket();

            _clientSocket.Bind(localEP);
        }
Beispiel #9
0
        public TcpListener(int port)
        {
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            _serverSocketEP = new IPEndPoint(IPAddress.Any, port);
            _serverSocket   = new Socket(_serverSocketEP.AddressFamily, SocketType.Stream, ProtocolType.Tcp);
        }
Beispiel #10
0
        // Connects the Client to the specified port on the specified host.
        public void Connect(IPAddress address, int port)
        {
            ThrowIfDisposed();

            ArgumentNullException.ThrowIfNull(address);
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            IPEndPoint remoteEP = new IPEndPoint(address, port);

            Connect(remoteEP);
        }
Beispiel #11
0
        // Connects the Client to the specified port on the specified host.
        public void Connect(string hostname, int port)
        {
            ThrowIfDisposed();

            ArgumentNullException.ThrowIfNull(hostname);
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            Client.Connect(hostname, port);
            _family = Client.AddressFamily;
            _active = true;
        }
Beispiel #12
0
        public UdpClient(string hostname, int port)
        {
            ArgumentNullException.ThrowIfNull(hostname);
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            // NOTE: Need to create different kinds of sockets based on the addresses
            //       returned from DNS. As a result, we defer the creation of the
            //       socket until the Connect method.

            Connect(hostname, port);
        }
Beispiel #13
0
        // Initializes a new instance of the TcpListener class that listens to the specified IP address
        // and port.
        public TcpListener(IPAddress localaddr, int port)
        {
            if (NetEventSource.Log.IsEnabled())
            {
                NetEventSource.Info(this, localaddr);
            }

            ArgumentNullException.ThrowIfNull(localaddr);
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            _serverSocketEP = new IPEndPoint(localaddr, port);
            _serverSocket   = new Socket(_serverSocketEP.AddressFamily, SocketType.Stream, ProtocolType.Tcp);
        }
Beispiel #14
0
        public void Connect(IPAddress addr, int port)
        {
            ThrowIfDisposed();

            if (addr == null)
            {
                throw new ArgumentNullException(nameof(addr));
            }
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            IPEndPoint endPoint = new IPEndPoint(addr, port);

            Connect(endPoint);
        }
Beispiel #15
0
        public void Connect(IPAddress addr, int port)
        {
            if (_cleanedUp)
            {
                throw new ObjectDisposedException(this.GetType().FullName);
            }
            if (addr == null)
            {
                throw new ArgumentNullException(nameof(addr));
            }
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            IPEndPoint endPoint = new IPEndPoint(addr, port);

            Connect(endPoint);
        }
Beispiel #16
0
        // Initializes a new instance of the System.Net.Sockets.TcpClient class and connects to the
        // specified port on the specified host.
        public TcpClient(string hostname, int port)
        {
            if (Logging.On)
            {
                Logging.Enter(Logging.Sockets, this, "TcpClient", hostname);
            }

            if (hostname == null)
            {
                throw new ArgumentNullException("hostname");
            }
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException("port");
            }

            // IPv6: Delay creating the client socket until we have
            //       performed DNS resolution and know which address
            //       families we can use.
            try
            {
                Connect(hostname, port);
            }
            catch (Exception e)
            {
                if (e is OutOfMemoryException)
                {
                    throw;
                }

                if (_clientSocket != null)
                {
                    _clientSocket.Dispose();
                }
                throw e;
            }

            if (Logging.On)
            {
                Logging.Exit(Logging.Sockets, this, "TcpClient", null);
            }
        }
Beispiel #17
0
        private void StartConnectCore(string host, int port)
        {
            // Validate the args, similar to how Socket.Connect(string, int) would.
            if (host == null)
            {
                throw new ArgumentNullException(nameof(host));
            }
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            // If the client socket has already materialized, this API can't be used.
            if (_clientSocket != null)
            {
                throw new PlatformNotSupportedException(SR.net_sockets_connect_multiaddress_notsupported);
            }

            EnterClientLock();
        }
Beispiel #18
0
        // Initializes a new instance of the System.Net.Sockets.TcpClient class and connects to the specified port on
        // the specified host.
        public TcpClient(string hostname, int port)
        {
            if (NetEventSource.Log.IsEnabled())
            {
                NetEventSource.Enter(NetEventSource.ComponentType.Socket, this, nameof(TcpClient), hostname);
            }

            if (hostname == null)
            {
                throw new ArgumentNullException(nameof(hostname));
            }

            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            // IPv6: Delay creating the client socket until we have
            //       performed DNS resolution and know which address
            //       families we can use.

            try
            {
                Connect(hostname, port);
            }

            catch
            {
                if (_clientSocket != null)
                {
                    _clientSocket.Close();
                }
                throw;
            }

            if (NetEventSource.Log.IsEnabled())
            {
                NetEventSource.Exit(NetEventSource.ComponentType.Socket, this, nameof(TcpClient), null);
            }
        }
Beispiel #19
0
        // This creates a TcpListener that listens on both IPv4 and IPv6 on the given port.
        public static TcpListener Create(int port)
        {
            if (Logging.On)
            {
                Logging.Enter(Logging.Sockets, "TcpListener.Create", "Port: " + port);
            }

            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException("port");
            }

            TcpListener listener = new TcpListener(IPAddress.IPv6Any, port);

            listener.Server.DualMode = true;
            if (Logging.On)
            {
                Logging.Exit(Logging.Sockets, "TcpListener.Create", "Port: " + port);
            }

            return(listener);
        }
Beispiel #20
0
        // Establishes a connection with the host at the specified address on the
        // specified port.
        public void Connect(IPAddress addr, int port)
        {
            // Validate input parameters.
            if (_cleanedUp)
            {
                throw new ObjectDisposedException(this.GetType().FullName);
            }
            if (addr == null)
            {
                throw new ArgumentNullException("addr");
            }
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException("port");
            }

            // IPv6 Changes: Removed redundant call to CheckForBroadcast() since
            //               it is made in the real Connect() method.
            IPEndPoint endPoint = new IPEndPoint(addr, port);

            Connect(endPoint);
        }
Beispiel #21
0
        // Initializes a new instance of the TcpListener class that listens to the specified IP address
        // and port.
        public TcpListener(IPAddress localaddr, int port)
        {
            if (NetEventSource.Log.IsEnabled())
            {
                NetEventSource.Enter(NetEventSource.ComponentType.Socket, this, "TcpListener", localaddr);
            }

            if (localaddr == null)
            {
                throw new ArgumentNullException(nameof(localaddr));
            }
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            _serverSocketEP = new IPEndPoint(localaddr, port);
            _serverSocket   = new Socket(_serverSocketEP.AddressFamily, SocketType.Stream, ProtocolType.Tcp);
            if (NetEventSource.Log.IsEnabled())
            {
                NetEventSource.Exit(NetEventSource.ComponentType.Socket, this, "TcpListener", null);
            }
        }
Beispiel #22
0
        // Initializes a new instance of the TcpListener class that listens to the specified IP address
        // and port.
        public TcpListener(IPAddress localaddr, int port)
        {
            if (Logging.On)
            {
                Logging.Enter(Logging.Sockets, this, "TcpListener", localaddr);
            }

            if (localaddr == null)
            {
                throw new ArgumentNullException("localaddr");
            }
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException("port");
            }

            _serverSocketEP = new IPEndPoint(localaddr, port);
            _serverSocket   = new Socket(_serverSocketEP.AddressFamily, SocketType.Stream, ProtocolType.Tcp);
            if (Logging.On)
            {
                Logging.Exit(Logging.Sockets, this, "TcpListener", null);
            }
        }
Beispiel #23
0
        // This creates a TcpListener that listens on both IPv4 and IPv6 on the given port.
        public static TcpListener Create(int port)
        {
            if (NetEventSource.IsEnabled)
            {
                NetEventSource.Enter(null, port);
            }

            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            TcpListener listener = new TcpListener(IPAddress.IPv6Any, port);

            listener.Server.DualMode = true;

            if (NetEventSource.IsEnabled)
            {
                NetEventSource.Exit(null, port);
            }

            return(listener);
        }
Beispiel #24
0
        // This creates a TcpListener that listens on both IPv4 and IPv6 on the given port.
        public static TcpListener Create(int port)
        {
            if (NetEventSource.Log.IsEnabled())
            {
                NetEventSource.Enter(NetEventSource.ComponentType.Socket, "TcpListener.Create", "Port: " + port, null);
            }

            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            TcpListener listener = new TcpListener(IPAddress.IPv6Any, port);

            listener.Server.DualMode = true;

            if (NetEventSource.Log.IsEnabled())
            {
                NetEventSource.Exit(NetEventSource.ComponentType.Socket, "TcpListener.Create", "Port: " + port, null);
            }

            return(listener);
        }
Beispiel #25
0
        // Connects the Client to the specified port on the specified host.
        public void Connect(string hostname, int port)
        {
            if (NetEventSource.Log.IsEnabled())
            {
                NetEventSource.Enter(NetEventSource.ComponentType.Socket, this, nameof(Connect), hostname);
            }
            if (_cleanedUp)
            {
                throw new ObjectDisposedException(this.GetType().FullName);
            }
            if (hostname == null)
            {
                throw new ArgumentNullException(nameof(hostname));
            }
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            // Check for already connected and throw here. This check
            // is not required in the other connect methods as they
            // will throw from WinSock. Here, the situation is more
            // complex since we have to resolve a hostname so it's
            // easier to simply block the request up front.
            if (_active)
            {
                throw new SocketException((int)SocketError.IsConnected);
            }

            ConnectCore(hostname, port);

            if (NetEventSource.Log.IsEnabled())
            {
                NetEventSource.Exit(NetEventSource.ComponentType.Socket, this, nameof(Connect), null);
            }
        }
Beispiel #26
0
        public void Connect(string hostname, int port)
        {
            ThrowIfDisposed();

            if (hostname == null)
            {
                throw new ArgumentNullException(nameof(hostname));
            }
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            // We must now look for addresses that use a compatible address family to the client socket. However, in the
            // case of the <hostname,port> constructor we will have deferred creating the socket and will do that here
            // instead.

            IPAddress[] addresses = Dns.GetHostAddresses(hostname);

            Exception lastex     = null;
            Socket    ipv6Socket = null;
            Socket    ipv4Socket = null;

            try
            {
                if (_clientSocket == null)
                {
                    if (Socket.OSSupportsIPv4)
                    {
                        ipv4Socket = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
                    }
                    if (Socket.OSSupportsIPv6)
                    {
                        ipv6Socket = new Socket(AddressFamily.InterNetworkV6, SocketType.Dgram, ProtocolType.Udp);
                    }
                }


                foreach (IPAddress address in addresses)
                {
                    try
                    {
                        if (_clientSocket == null)
                        {
                            // We came via the <hostname,port> constructor. Set the
                            // address family appropriately, create the socket and
                            // try to connect.
                            if (address.AddressFamily == AddressFamily.InterNetwork && ipv4Socket != null)
                            {
                                ipv4Socket.Connect(address, port);
                                _clientSocket = ipv4Socket;
                                if (ipv6Socket != null)
                                {
                                    ipv6Socket.Close();
                                }
                            }
                            else if (ipv6Socket != null)
                            {
                                ipv6Socket.Connect(address, port);
                                _clientSocket = ipv6Socket;
                                if (ipv4Socket != null)
                                {
                                    ipv4Socket.Close();
                                }
                            }


                            _family = address.AddressFamily;
                            _active = true;
                            break;
                        }
                        else if (IsAddressFamilyCompatible(address.AddressFamily))
                        {
                            // Only use addresses with a matching family
                            Connect(new IPEndPoint(address, port));
                            _active = true;
                            break;
                        }
                    }
                    catch (Exception ex)
                    {
                        if (ExceptionCheck.IsFatal(ex))
                        {
                            throw;
                        }
                        lastex = ex;
                    }
                }
            }

            catch (Exception ex)
            {
                if (ExceptionCheck.IsFatal(ex))
                {
                    throw;
                }
                lastex = ex;
            }
            finally
            {
                //cleanup temp sockets if failed
                //main socket gets closed when tcpclient gets closed

                //did we connect?
                if (!_active)
                {
                    if (ipv6Socket != null)
                    {
                        ipv6Socket.Close();
                    }

                    if (ipv4Socket != null)
                    {
                        ipv4Socket.Close();
                    }

                    // The connect failed - rethrow the last error we had
                    if (lastex != null)
                    {
                        throw lastex;
                    }
                    else
                    {
                        throw new SocketException((int)SocketError.NotConnected);
                    }
                }
            }
        }
Beispiel #27
0
        // Connects the Client to the specified port on the specified host.
        public void Connect(string hostname, int port)
        {
            if (Logging.On)
            {
                Logging.Enter(Logging.Sockets, this, "Connect", hostname);
            }

            if (_cleanedUp)
            {
                throw new ObjectDisposedException(this.GetType().FullName);
            }
            if (hostname == null)
            {
                throw new ArgumentNullException("hostname");
            }
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException("port");
            }

            // Check for already connected and throw here. This check
            // is not required in the other connect methods as they
            // will throw from WinSock. Here, the situation is more
            // complex since we have to resolve a hostname so it's
            // easier to simply block the request up front.
            if (_active)
            {
                throw new SocketException((int)SocketError.IsConnected);
            }

            // IPv6: We need to process each of the addresses return from
            //       DNS when trying to connect. Use of AddressList[0] is
            //       bad form.
            IPAddress[] addresses  = Dns.GetHostAddressesAsync(hostname).GetAwaiter().GetResult();
            Exception   lastex     = null;
            Socket      ipv6Socket = null;
            Socket      ipv4Socket = null;

            try
            {
                if (_clientSocket == null)
                {
                    if (Socket.OSSupportsIPv4)
                    {
                        ipv4Socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
                    }
                    if (Socket.OSSupportsIPv6)
                    {
                        ipv6Socket = new Socket(AddressFamily.InterNetworkV6, SocketType.Stream, ProtocolType.Tcp);
                    }
                }

                foreach (IPAddress address in addresses)
                {
                    try
                    {
                        if (_clientSocket == null)
                        {
                            // We came via the <hostname,port> constructor. Set the
                            // address family appropriately, create the socket and
                            // try to connect.
                            if (address.AddressFamily == AddressFamily.InterNetwork && ipv4Socket != null)
                            {
                                ipv4Socket.Connect(address, port);
                                _clientSocket = ipv4Socket;
                                if (ipv6Socket != null)
                                {
                                    ipv6Socket.Dispose();
                                }
                            }
                            else if (ipv6Socket != null)
                            {
                                ipv6Socket.Connect(address, port);
                                _clientSocket = ipv6Socket;
                                if (ipv4Socket != null)
                                {
                                    ipv4Socket.Dispose();
                                }
                            }

                            _family = address.AddressFamily;
                            _active = true;
                            break;
                        }
                        else if (address.AddressFamily == _family)
                        {
                            // Only use addresses with a matching family.
                            Connect(new IPEndPoint(address, port));
                            _active = true;
                            break;
                        }
                    }
                    catch (Exception ex)
                    {
                        if (ex is OutOfMemoryException)
                        {
                            throw;
                        }
                        lastex = ex;
                    }
                }
            }
            catch (Exception ex)
            {
                if (ex is OutOfMemoryException)
                {
                    throw;
                }
                lastex = ex;
            }
            finally
            {
                // Cleanup temp sockets if failed. Main socket gets closed when TCPClient gets closed.

                // Did we connect?
                if (!_active)
                {
                    if (ipv6Socket != null)
                    {
                        ipv6Socket.Dispose();
                    }

                    if (ipv4Socket != null)
                    {
                        ipv4Socket.Dispose();
                    }

                    // The connect failed - rethrow the last error we had.
                    if (lastex != null)
                    {
                        throw lastex;
                    }
                    else
                    {
                        throw new SocketException((int)SocketError.NotConnected);
                    }
                }
            }

            if (Logging.On)
            {
                Logging.Exit(Logging.Sockets, this, "Connect", null);
            }
        }
Beispiel #28
0
        // Connects the Client to the specified port on the specified host.
        public void Connect(string hostname, int port)
        {
            if (NetEventSource.IsEnabled)
            {
                NetEventSource.Enter(this, hostname);
            }

            if (_cleanedUp)
            {
                throw new ObjectDisposedException(GetType().FullName);
            }
            if (hostname == null)
            {
                throw new ArgumentNullException(nameof(hostname));
            }
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            // Check for already connected and throw here. This check
            // is not required in the other connect methods as they
            // will throw from WinSock. Here, the situation is more
            // complex since we have to resolve a hostname so it's
            // easier to simply block the request up front.
            if (_active)
            {
                throw new SocketException((int)SocketError.IsConnected);
            }

            // IPv6: We need to process each of the addresses returned from
            //       DNS when trying to connect. Use of AddressList[0] is
            //       bad form.
            IPAddress[]           addresses = Dns.GetHostAddresses(hostname);
            ExceptionDispatchInfo lastex    = null;

            try
            {
                foreach (IPAddress address in addresses)
                {
                    Socket tmpSocket = null;
                    try
                    {
                        if (_clientSocket == null)
                        {
                            // We came via the <hostname,port> constructor. Set the address family appropriately,
                            // create the socket and try to connect.
                            Debug.Assert(address.AddressFamily == AddressFamily.InterNetwork || address.AddressFamily == AddressFamily.InterNetworkV6);
                            if ((address.AddressFamily == AddressFamily.InterNetwork && Socket.OSSupportsIPv4) || Socket.OSSupportsIPv6)
                            {
                                tmpSocket = new Socket(address.AddressFamily, SocketType.Stream, ProtocolType.Tcp);
                                tmpSocket.Connect(address, port);
                                _clientSocket = tmpSocket;
                                tmpSocket     = null;
                            }

                            _family = address.AddressFamily;
                            _active = true;
                            break;
                        }
                        else if (address.AddressFamily == _family || _family == AddressFamily.Unknown)
                        {
                            // Only use addresses with a matching family
                            Connect(new IPEndPoint(address, port));
                            _active = true;
                            break;
                        }
                    }
                    catch (Exception ex) when(!(ex is OutOfMemoryException))
                    {
                        if (tmpSocket != null)
                        {
                            tmpSocket.Dispose();
                            tmpSocket = null;
                        }
                        lastex = ExceptionDispatchInfo.Capture(ex);
                    }
                }
            }
            finally
            {
                if (!_active)
                {
                    // The connect failed - rethrow the last error we had
                    lastex?.Throw();
                    throw new SocketException((int)SocketError.NotConnected);
                }
            }

            if (NetEventSource.IsEnabled)
            {
                NetEventSource.Exit(this);
            }
        }
Beispiel #29
0
        // Establishes a connection to the specified port on the specified host.
        public void Connect(string hostname, int port)
        {
            // Validate input parameters.
            if (_cleanedUp)
            {
                throw new ObjectDisposedException(this.GetType().FullName);
            }
            if (hostname == null)
            {
                throw new ArgumentNullException("hostname");
            }
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException("port");
            }

            // IPv6 Changes: instead of just using the first address in the list,
            //               we must now look for addresses that use a compatible
            //               address family to the client socket.
            //               However, in the case of the <hostname,port> constructor
            //               we will have deferred creating the socket and will
            //               do that here instead.
            //               In addition, the redundant CheckForBroadcast call was
            //               removed here since it is called from Connect().
            IPAddress[] addresses = Dns.GetHostAddressesAsync(hostname).GetAwaiter().GetResult();

            Exception lastex     = null;
            Socket    ipv6Socket = null;
            Socket    ipv4Socket = null;

            try
            {
                if (_clientSocket == null)
                {
                    if (Socket.OSSupportsIPv4)
                    {
                        ipv4Socket = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
                    }
                    if (Socket.OSSupportsIPv6)
                    {
                        ipv6Socket = new Socket(AddressFamily.InterNetworkV6, SocketType.Dgram, ProtocolType.Udp);
                    }
                }

                foreach (IPAddress address in addresses)
                {
                    try
                    {
                        if (_clientSocket == null)
                        {
                            // We came via the <hostname,port> constructor. Set the
                            // address family appropriately, create the socket and
                            // try to connect.
                            if (address.AddressFamily == AddressFamily.InterNetwork && ipv4Socket != null)
                            {
                                ipv4Socket.Connect(address, port);
                                _clientSocket = ipv4Socket;
                                if (ipv6Socket != null)
                                {
                                    ipv6Socket.Dispose();
                                }
                            }
                            else if (ipv6Socket != null)
                            {
                                ipv6Socket.Connect(address, port);
                                _clientSocket = ipv6Socket;
                                if (ipv4Socket != null)
                                {
                                    ipv4Socket.Dispose();
                                }
                            }

                            _family = address.AddressFamily;
                            _active = true;
                            break;
                        }
                        else if (address.AddressFamily == _family)
                        {
                            // Only use addresses with a matching family.
                            Connect(new IPEndPoint(address, port));
                            _active = true;
                            break;
                        }
                    }
                    catch (Exception ex)
                    {
                        if (ExceptionCheck.IsFatal(ex))
                        {
                            throw;
                        }
                        lastex = ex;
                    }
                }
            }
            catch (Exception ex)
            {
                if (ExceptionCheck.IsFatal(ex))
                {
                    throw;
                }
                lastex = ex;
            }
            finally
            {
                // Cleanup temp sockets on failure. The main socket gets closed when the UDPClient
                // gets closed.

                // Did we connect?
                if (!_active)
                {
                    if (ipv6Socket != null)
                    {
                        ipv6Socket.Dispose();
                    }

                    if (ipv4Socket != null)
                    {
                        ipv4Socket.Dispose();
                    }

                    // The connect failed - rethrow the last error we had.
                    if (lastex != null)
                    {
                        throw lastex;
                    }
                    else
                    {
                        throw new SocketException((int)SocketError.NotConnected);
                    }
                }
            }
        }
Beispiel #30
0
        // Connects the Client to the specified port on the specified host.
        public void Connect(string hostname, int port)
        {
            ThrowIfDisposed();

            ArgumentNullException.ThrowIfNull(hostname);
            if (!TcpValidationHelpers.ValidatePortNumber(port))
            {
                throw new ArgumentOutOfRangeException(nameof(port));
            }

            // Check for already connected and throw here. This check
            // is not required in the other connect methods as they
            // will throw from WinSock. Here, the situation is more
            // complex since we have to resolve a hostname so it's
            // easier to simply block the request up front.
            if (_active)
            {
                throw new SocketException((int)SocketError.IsConnected);
            }

            // IPv6: We need to process each of the addresses returned from
            //       DNS when trying to connect. Use of AddressList[0] is
            //       bad form.
            IPAddress[]           addresses = Dns.GetHostAddresses(hostname);
            ExceptionDispatchInfo?lastex    = null;

            try
            {
                foreach (IPAddress address in addresses)
                {
                    try
                    {
                        if (_clientSocket == null)
                        {
                            // We came via the <hostname,port> constructor. Set the address family appropriately,
                            // create the socket and try to connect.
                            Debug.Assert(address.AddressFamily == AddressFamily.InterNetwork || address.AddressFamily == AddressFamily.InterNetworkV6);
                            if ((address.AddressFamily == AddressFamily.InterNetwork && Socket.OSSupportsIPv4) || Socket.OSSupportsIPv6)
                            {
                                var socket = new Socket(address.AddressFamily, SocketType.Stream, ProtocolType.Tcp);
                                if (address.IsIPv4MappedToIPv6)
                                {
                                    socket.DualMode = true;
                                }

                                // Use of Interlocked.Exchanged ensures _clientSocket is written before Disposed is read.
                                Interlocked.Exchange(ref _clientSocket !, socket);
                                if (Disposed)
                                {
                                    // Dispose the socket so it throws ObjectDisposedException when we Connect.
                                    socket.Dispose();
                                }

                                try
                                {
                                    socket.Connect(address, port);
                                }
                                catch
                                {
                                    _clientSocket = null !;
                                    throw;
                                }
                            }

                            _family = address.AddressFamily;
                            _active = true;
                            break;
                        }
                        else if (address.AddressFamily == _family || _family == AddressFamily.Unknown)
                        {
                            // Only use addresses with a matching family
                            Connect(new IPEndPoint(address, port));
                            _active = true;
                            break;
                        }
                    }
                    catch (Exception ex) when(!(ex is OutOfMemoryException))
                    {
                        lastex = ExceptionDispatchInfo.Capture(ex);
                    }
                }
            }
            finally
            {
                if (!_active)
                {
                    // The connect failed - rethrow the last error we had
                    lastex?.Throw();
                    throw new SocketException((int)SocketError.NotConnected);
                }
            }
        }