コード例 #1
0
        private SocketError OnBind(IntPtr socket, IntPtr address, int addressSize)
        {
            var socketAddress = GetSocketAddress(address);

            DebugMessage(
                nameof(OnBind),
                "Binding to `{0}:{1}` ...",
                socketAddress?.Address?.IPAddress,
                socketAddress?.Port
                );

            var networkInterface = GetNetworkInterface();
            var interfaceAddress = GetInterfaceAddress(networkInterface, socketAddress?.AddressFamily, true);

            if (socketAddress?.Address == null || networkInterface == null || interfaceAddress == null)
            {
                DebugMessage(
                    nameof(OnBind),
                    "Binding to `{0}:{1}` rejected due to lack of a valid interface address.",
                    socketAddress?.Address?.IPAddress,
                    socketAddress?.Port
                    );

                return(SocketError.SocketError);
            }

            SocketError bindResult;

            if (interfaceAddress.AddressFamily == AddressFamily.InterNetwork &&
                !interfaceAddress.Equals(socketAddress.Address.IPAddress))
            {
                var bindIn = new SocketAddressIn
                {
                    Address = new AddressIn {
                        IPAddress = interfaceAddress
                    },
                    AddressFamily = interfaceAddress.AddressFamily,
                    Port          = socketAddress.Port
                };

                DebugMessage(
                    nameof(OnBind),
                    "Binding to `{0}:{1}` replaced by a binding request to `{2}:{3}`.",
                    socketAddress.Address.IPAddress,
                    socketAddress.Port,
                    bindIn.Address.IPAddress,
                    bindIn.Port
                    );

                socketAddress = bindIn;

                bindResult = Socket.Bind(socket, ref bindIn, Marshal.SizeOf(bindIn));
            }
            else if (interfaceAddress.AddressFamily == AddressFamily.InterNetworkV6 &&
                     !interfaceAddress.Equals(socketAddress.Address.IPAddress))
            {
                var scopeId  = (uint?)networkInterface.GetIPProperties()?.GetIPv6Properties()?.Index ?? 0;
                var flowInfo = (socketAddress as SocketAddressIn6?)?.FlowInfo ?? 0;

                var bindIn6 = new SocketAddressIn6
                {
                    Address = new AddressIn6 {
                        IPAddress = interfaceAddress
                    },
                    AddressFamily = interfaceAddress.AddressFamily,
                    Port          = socketAddress.Port, // Assign a random port
                    ScopeId       = scopeId,
                    FlowInfo      = flowInfo
                };

                DebugMessage(
                    nameof(OnBind),
                    "Binding to `{0}:{1}` replaced by a binding request to `{2}:{3}`.",
                    socketAddress.Address.IPAddress,
                    socketAddress.Port,
                    bindIn6.Address.IPAddress,
                    bindIn6.Port
                    );

                socketAddress = bindIn6;

                bindResult = Socket.Bind(socket, ref bindIn6, Marshal.SizeOf(bindIn6));
            }
            else
            {
                bindResult = Socket.Bind(socket, address, addressSize);
            }

            DebugMessage(
                nameof(OnBind),
                "Binding to `{0}:{1}` resulted in a `{2}` response. [WSALastError = `{3}`]",
                socketAddress.Address.IPAddress,
                socketAddress.Port,
                bindResult,
                Socket.WSAGetLastError()
                );

            return(bindResult);
        }
コード例 #2
0
        private SocketError BindSocketByAddress(IntPtr socket, ISocketAddress socketAddress)
        {
            switch (socketAddress?.AddressFamily)
            {
            case AddressFamily.InterNetwork:

                if (socketAddress.Address?.IPAddress?.Equals(IPAddress.Any) == true)
                {
                    DebugMessage(
                        nameof(BindSocketByAddress),
                        "Binding to interface skipped due to the nature of passed IP Address. [0.0.0.0]"
                        );

                    return(SocketError.Success);
                }

                if (IsIpInRange(socketAddress.Address?.IPAddress, IPAddress.Parse("127.0.0.0"),
                                IPAddress.Parse("127.255.255.255")))
                {
                    DebugMessage(
                        nameof(BindSocketByAddress),
                        "Binding to interface skipped due to the nature of passed IP Address. [Loop Back]"
                        );

                    return(SocketError.Success);    // LoopBack
                }

                if (IsIpInRange(socketAddress.Address?.IPAddress, IPAddress.Parse("10.0.0.0"),
                                IPAddress.Parse("10.255.255.255")))
                {
                    DebugMessage(
                        nameof(BindSocketByAddress),
                        "Binding to interface skipped due to the nature of passed IP Address. [Private Range]"
                        );

                    return(SocketError.Success);    // Private Network
                }

                if (IsIpInRange(socketAddress.Address?.IPAddress, IPAddress.Parse("172.16.0.0"),
                                IPAddress.Parse("172.31.255.255")))
                {
                    DebugMessage(
                        nameof(BindSocketByAddress),
                        "Binding to interface skipped due to the nature of passed IP Address. [Private Range]"
                        );

                    return(SocketError.Success);    // Private Network
                }

                if (IsIpInRange(socketAddress.Address?.IPAddress, IPAddress.Parse("192.168.0.0"),
                                IPAddress.Parse("192.168.255.255")))
                {
                    DebugMessage(
                        nameof(BindSocketByAddress),
                        "Binding to interface skipped due to the nature of passed IP Address. [Private Range]"
                        );

                    return(SocketError.Success);    // Private Network
                }

                if (IsIpInRange(socketAddress.Address?.IPAddress, IPAddress.Parse("169.254.1.0"),
                                IPAddress.Parse("169.254.254.255")))
                {
                    DebugMessage(
                        nameof(BindSocketByAddress),
                        "Binding to interface skipped due to the nature of passed IP Address. [Link Local Network]"
                        );

                    return(SocketError.Success);    // Link Local Network
                }

                if (IsIpInRange(socketAddress.Address?.IPAddress, IPAddress.Parse("224.0.0.0"),
                                IPAddress.Parse("239.255.255.255")))
                {
                    DebugMessage(
                        nameof(BindSocketByAddress),
                        "Binding to interface skipped due to the nature of passed IP Address. [MultiCast Address]"
                        );

                    return(SocketError.Success);    // MultiCast
                }

                break;

            case AddressFamily.InterNetworkV6:

                if (socketAddress.Address?.IPAddress?.Equals(IPAddress.IPv6Any) == true)
                {
                    DebugMessage(
                        nameof(BindSocketByAddress),
                        "Binding to interface skipped due to the nature of passed IP Address. [0000:]"
                        );

                    return(SocketError.Success);
                }

                if (socketAddress.Address?.IPAddress?.Equals(IPAddress.IPv6Loopback) == true)
                {
                    DebugMessage(
                        nameof(BindSocketByAddress),
                        "Binding to interface skipped due to the nature of passed IP Address. [Loop Back]"
                        );

                    return(SocketError.Success);    // LoopBack
                }

                if (IsIpInRange(socketAddress.Address?.IPAddress,
                                IPAddress.Parse("fc00:0000:0000:0000:0000:0000:0000:0000"),
                                IPAddress.Parse("ffff:ffff:ffff:ffff:ffff:ffff:ffff:ffff")))
                {
                    DebugMessage(
                        nameof(BindSocketByAddress),
                        "Binding to interface skipped due to the nature of passed IP Address. [fc00:]"
                        );

                    return(SocketError.Success);    // Unique Local Addresses, Private networks, MultiCast
                }

                break;

            default:
                DebugMessage(
                    nameof(BindSocketByAddress),
                    "Binding to interface skipped due an unsupported address family of `{0}`.",
                    socketAddress?.AddressFamily
                    );

                return(SocketError.Success);
            }

            var networkInterface = GetNetworkInterface();
            var interfaceAddress = GetInterfaceAddress(networkInterface, socketAddress.AddressFamily, false);

            if (networkInterface == null || interfaceAddress == null)
            {
                DebugMessage(
                    nameof(OnBind),
                    "Binding for the `{0}:{1}` rejected due to lack of a valid interface address.",
                    socketAddress.Address?.IPAddress,
                    socketAddress.Port
                    );

                return(SocketError.SocketError);
            }

            if (interfaceAddress.AddressFamily == AddressFamily.InterNetwork)
            {
                var bindIn = new SocketAddressIn
                {
                    Address = new AddressIn {
                        IPAddress = interfaceAddress
                    },
                    AddressFamily = interfaceAddress.AddressFamily,
                    Port          = 0 // Assign a random port
                };

                DebugMessage(
                    nameof(BindSocketByAddress),
                    "Binding to `{0}:{1}` ...",
                    bindIn.Address?.IPAddress,
                    bindIn.Port
                    );

                return(Socket.Bind(socket, ref bindIn, Marshal.SizeOf(bindIn)));
            }

            if (interfaceAddress.AddressFamily == AddressFamily.InterNetworkV6)
            {
                var scopeId  = (uint?)networkInterface.GetIPProperties()?.GetIPv6Properties()?.Index ?? 0;
                var flowInfo = (socketAddress as SocketAddressIn6?)?.FlowInfo ?? 0;

                var bindIn6 = new SocketAddressIn6
                {
                    Address = new AddressIn6 {
                        IPAddress = interfaceAddress
                    },
                    AddressFamily = interfaceAddress.AddressFamily,
                    Port          = 0, // Assign a random port
                    ScopeId       = scopeId,
                    FlowInfo      = flowInfo
                };

                DebugMessage(
                    nameof(BindSocketByAddress),
                    "Binding to `{0}:{1}` ...",
                    bindIn6.Address?.IPAddress,
                    bindIn6.Port
                    );

                return(Socket.Bind(socket, ref bindIn6, Marshal.SizeOf(bindIn6)));
            }

            DebugMessage(
                nameof(BindSocketByAddress),
                "Binding to interface skipped due an unsupported interface address family of `{0}`.",
                interfaceAddress.AddressFamily
                );

            return(SocketError.Success);
        }