2015-03-31 110 views
0

我有一个Android客户端和纯Java服务器都在同一个子网上,并且我正在从客户端向服务器发送UDP广播数据包。对于一些路由器(Netgear,Cisco),服务器愉快地接收数据包,但是对于我的华硕路由器,服务器机器接收到数据包,服务器DatagramSocket没有。Java DatagramSocket没有接收到来自某些路由器的UDP广播

NB在任何情况下,Wireshark都会显示数据包正在到达服务器计算机。但是当使用Asus路由器时,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广播包?

回答

1

对于后面的那些......

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

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

禁用该规则会让所有的工作都成功。