Java DatagramSocket 未接收来自某些路由器的 UDP 广播

标签 java sockets networking udp broadcast

我有一个 Android 客户端和普通 Java 服务器都在同一子网上,并且我正在从客户端向服务器发送 UDP 广播数据包。对于某些路由器(Netgear、Cisco),服务器可以愉快地接收数据包,但对于我的华硕路由器,当服务器机器接收数据包时,服务器DatagramSocket却不会。 p>

注意在所有情况下,Wireshark 都会显示数据包正在到达服务器计算机。但是当使用华硕路由器时,DatagramSocket 似乎看不到它们。为了简单起见,服务器只有到路由器的以太网连接。

代码非常标准。

客户:

DatagramSocket socket = null;
try {
    socket = new DatagramSocket();
    socket.setSoTimeout(500); // 500 millis

    while (isRunning()) {
        final InetAddress broadcastAddress = getSubnetBroadcastAddress();
        final DatagramPacket outboundPacket = new DatagramPacket(REQUEST_MESSAGE, REQUEST_MESSAGE.length, broadcastAddress, broadcastPort);
        socket.send(outboundPacket);
    }

} catch (IOException e) {
    Log.i(TAG, "Beacon failed", e);
} finally {
    if (socket != null) {
        socket.close();
    }
}

private InetAddress getSubnetBroadcastAddress() throws IOException {
    final WifiManager wifi = (WifiManager) context.getSystemService(Context.WIFI_SERVICE);
    final DhcpInfo dhcp = wifi.getDhcpInfo();
    if (dhcp == null) {
        // No successful DHCP request. Go with best effort.
        Log.d(TAG, "#getBroadcastAddress - No DHCP info so using generic broadcast address");
        return InetAddress.getByName("255.255.255.255");
    }

    final int broadcast = (dhcp.ipAddress & dhcp.netmask) | ~dhcp.netmask;
    final byte[] quads = new byte[4];
    for (int k = 0; k < 4; k++) {
        quads[k] = (byte) ((broadcast >> k * 8) & 0xFF);
    }
    return InetAddress.getByAddress(quads);
}

服务器:

    DatagramSocket socket = null;
    try {
        socket = new DatagramSocket(broadcastPort);
        socket.setSoTimeout(LISTENING_TIMEOUT);
        socket.setBroadcast(true);
        while (keepRunning) {
            try {
                final byte[] buffer = new byte[1024];
                final DatagramPacket receivedPacket = new DatagramPacket(buffer, buffer.length);
                socket.receive(receivedPacket);
                log.debug("Received packet : " + receivedPacket.toString());
            } catch (SocketTimeoutException e) {
                log.debug("#run BeaconRunnable socket timed out");
            }
        }
    } catch (IOException e) {
        log.warn("Error while receiving message", e);
        if (socket != null) {
            socket.close();
        }
    }

是什么导致 DatagramSocket 看不到华硕路由器的 UDP 广播数据包?

最佳答案

对于那些关注..

上面的代码没有任何问题。 路由器配置没有任何问题。

Windows 防火墙中添加了一条规则,阻止来自公共(public)连接的传入 UDP,并且华硕路由器由于某种原因被视为公共(public)连接。

禁用该规则让一切正常。

关于Java DatagramSocket 未接收来自某些路由器的 UDP 广播,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29369387/

相关文章:

sockets - UDP 中的通信协议(protocol)

c - 关闭套接字后,套接字连接保持已建立状态

c# - 如何获取所有连接到网络的计算机列表?

Java http文件上传和服务器响应

java - 聊天服务器。线程问题

java - “镜像”二维数组 [Java]

java - 并发线程读取套接字

networking - 跟踪某个端口的路由

java 枚举 - 在其他 java 文件中使用时不编译

java - JMX 通知设计