网络切换后UDP广播失效问题排查求助
UDP广播切换网络接口后失效问题排查求助
前置条件
- PC1(Windows系统):
- LAN地址:10.0.1.11
- WiFi地址:10.0.1.10
- PC2(Windows系统):
- WiFi地址:10.0.1.4
操作步骤及现象
- 禁用PC1的WiFi,启用LAN,确认IP地址为10.0.1.11;
- 启用PC2的WiFi,确认IP地址为10.0.1.4;
- 在PC1上启动UDP广播程序(可接收同LAN内其他PC的UDP应答包),在PC2上启动UDP接收器(接收广播消息后会回复发送方);
- 在PC1上启动Wireshark捕获网络包;
- 确认PC1收到来自PC2的应答消息;
- 在UDP广播程序运行期间,禁用PC1的LAN并启用WiFi,确认IP地址切换为WiFi接口的10.0.1.10;
- 一段时间后发现PC1无法收到PC2的UDP应答,通过Wireshark也未捕获到PC1发送的任何广播包(无论使用过滤规则
ip.proto==UDP && ip.src==10.0.1.10还是ip.proto==UDP && ip.src==10.0.1.11); - 查看PC1的UDP接收器日志,发现异常现象:PC1从LAN切换到WiFi后,日志中出现已禁用的LAN接口IP(10.0.1.11)响应广播的记录。
广播消息发送代码
Socket sendSocket = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp); // Use GetHostAddresses() to enumerate the local IPAddress string hostName = Dns.GetHostName(); var addressList = Dns.GetHostAddresses(hostName); foreach (var ip in addressList) { if (ip.AddressFamily != AddressFamily.InterNetwork) { continue; } IPEndPoint ep = null; IPAddress ipSend = null; ipSend = IPAddress.Parse(ip.ToString()); ipSend.Address |= 0xFF000000; ep = new IPEndPoint(ipSend, 1020); sendSocket.SendTo(broadcastMessage, ep); } //Use GetAllNetworkInterfaces() to enumerate the local IPAddress NetworkInterface[] nics = NetworkInterface.GetAllNetworkInterfaces(); foreach (NetworkInterface adapter in nics) { if (adapter.NetworkInterfaceType == NetworkInterfaceType.Ethernet || adapter.NetworkInterfaceType == NetworkInterfaceType.Wireless80211) { IPInterfaceProperties ip = adapter.GetIPProperties(); UnicastIPAddressInformationCollection ipCollection = ip.UnicastAddresses; foreach (UnicastIPAddressInformation ipadd in ipCollection) { if (ipadd.Address.AddressFamily == AddressFamily.InterNetwork) { IPEndPoint ep = null; IPAddress ipSend = null; ipSend = IPAddress.Parse(ipadd.Address.ToString()); ipSend.Address |= 0xFF000000; ep = new IPEndPoint(ipSend, 1020); sendSocket.SendTo(broadcastMessage, ep); } } } } //Use GetHostEntry() to enumerate the local IPAddress IPHostEntry host = Dns.GetHostEntry(hostName, AddressFamily.InterNetwork); foreach (var ip in host.AddressList) { IPEndPoint ep = null; IPAddress ipSend = null; ipSend = IPAddress.Parse(ip.ToString()); ipSend.Address |= 0xFF000000; ep = new IPEndPoint(ipSend, 1020); sendSocket.SendTo(broadcastMessage, ep); }
我尝试了上述3种枚举本地IP地址并生成广播地址的方法,但均未生效。
看起来,网络从LAN切换到WiFi后,调用SendTo() API发送的广播消息并未通过PC1的TCP/IP协议栈(否则Wireshark应能捕获到相关数据包)。
求问针对该问题有什么排查思路或解决方案?
UDP接收器代码
socket = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp); socket.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, 1); socket.Bind(new IPEndPoint(IPAddress.Any, 1020)); socket.ReceiveTimeout = 100; _udpReceiver = new UdpClient{Client = socket}; _udpReceiver.Client.ReceiveBufferSize = 1024 * 1024; endPoint = new IPEndPoint(IPAddress.Any, 0); while (!_stopReceiveEvent.WaitOne(1)) { byte[] rawBytes = _udpReceiver.Receive(ref endPoint); if (rawBytes.Length <= 0){ continue; } string receivedDeviceIPAddr = endPoint.Address.ToString(); Console.WriteLine($"Recieve UDP response from {receivedDeviceIPAddr} : {endPoint.Port}"); }
内容的提问来源于stack exchange,提问作者chaingun
相关产品推荐
相关产品推荐

