我试图为一个无线网状网络创建一个程序(除了名字之外,所有的adhoc)。大多数网络将处理TCP消息,但为了确定所有邻居的IP(因为它们在启动时将是未知的),我选择使用UDP广播进行初始发现消息。这段代码,在大多数情况下是无关紧要的,因为最初的测试看来是有效的,目前我没有调用它。
下面是接收和注册邻居IP的部分。
protected override void ReceiveMessageUDP()
{
while (live)
{
try
{
UdpListener = new UdpClient(_PORTRECEIVE);
UdpListener.EnableBroadcast = true;
Socket socket = UdpListener.Client;
IPEndPoint endPoint1 = new IPEndPoint(IPAddress.Loopback, _PORTRECEIVE);
IPEndPoint endPoint2 = new IPEndPoint(IPAddress.Any, _PORTRECEIVE);
socket.Bind(endPoint2);
socket.Listen(25);
Socket connected = socket.Accept();
byte[] buffer = new byte[1024];
int length = connected.Receive(buffer);
IPAddress remoteIP = ((IPEndPoint)connected.RemoteEndPoint).Address;
if (!ipAddresses.Contains(remoteIP))
ipAddresses.Add(remoteIP);
Message.Add(Encoding.ASCII.GetString(buffer, 0, length));
}
catch (SocketException e) { Console.WriteLine(e.ErrorCode); }
catch (Exception) { }
}
}
我用两个IPEndPoints都进行了测试,无论我如何设置,Bind都失败了,SocketException.ErrorCode 10022。Windows Socket错误代码. 这是一个无效的参数, 但我很困惑这意味着什么, 因为所需的参数是一个 EndPoint。
这在第一次运行时就失败了,所以我并不是在尝试重新绑定端口。
你已经将端口绑定到了 UdpCLient
的时候,您就不能将同一个端口绑定到单独的端口。 您不能再将同一端口绑定到单独的 IPEndPoint
.
UdpListener = new UdpClient(_PORTRECEIVE); // binds port to UDP client
...
IPEndPoint endPoint2 = new IPEndPoint(IPAddress.Any, _PORTRECEIVE);
socket.Bind(endPoint2); // attempts to bind same port to end point
如果你想用这种方式,请建立并绑定好 IPEndPoint
进而构建 UdpClient
而不是端口。
IPEndPoint endPoint2 = new IPEndPoint(IPAddress.Any, _PORTRECEIVE);
socket.Bind(endPoint2); // bind port to end point
UdpListener = new UdpClient(endPoint2); // binds port to UDP client via endpoint
我不明白为什么您还要设置另一个终端。endPoint1
在同一个端口上。 这很可能会导致问题,如果和当你尝试使用这个。
我同意 steve 的观点。然而,你说
"UDP不允许绑定或其他东西。"
但它允许。你可以将任何套接字(不管是不是udp)绑定到任何网络接口。Steve给了一个提示来实现它。我是这样做的。
LocalEP = new IPEndPoint(<local IP>, _PORTRECEIVE) ;
listener = New UdpClient(LocalEP) ;
正如Steve所指出的,一旦一个UdpClient被实例化,它就不允许重新绑定到其他接口上。诀窍是事先告诉构造函数绑定到你想要的接口。用你想使用的本地接口的IP地址来代替。
当然,这只有在你有(或可能有)几个网络接口,并且想使用一个特定的接口时才有用。否则,我看到有有效网关的接口通常是客户机默认绑定的接口。而这通常是正确的。
罗伯托