Java Android 2.0.1(目前在DROID上)的多播是否中断,或者我是否遗漏了什么?

Java Android 2.0.1(目前在DROID上)的多播是否中断,或者我是否遗漏了什么?,java,android,multicast,datagram,Java,Android,Multicast,Datagram,这段代码在Ubuntu、Windows和MacOSX上都能完美运行。在运行Android 2.1.1的NexusOne上也能正常运行 我开始发送和收听多播数据报,所有的计算机和NexusOne都能完美地看到对方。然后我在Droid上运行相同的代码(固件2.0.1),并且每个人都将收到Droid发送的数据包,但Droid将只侦听自己的数据包 这是一个线程的run()方法,该线程不断地在多播组上侦听发送到该组的传入数据包 我正在本地网络上运行测试,路由器中启用了多播支持。 我的目标是通过向多播组广播

这段代码在Ubuntu、Windows和MacOSX上都能完美运行。在运行Android 2.1.1的NexusOne上也能正常运行

我开始发送和收听多播数据报,所有的计算机和NexusOne都能完美地看到对方。然后我在Droid上运行相同的代码(固件2.0.1),并且每个人都将收到Droid发送的数据包,但Droid将只侦听自己的数据包

这是一个线程的
run()
方法,该线程不断地在多播组上侦听发送到该组的传入数据包

我正在本地网络上运行测试,路由器中启用了多播支持。 我的目标是通过向多播组广播软件包,让设备在联机时彼此相遇

public void run() {
    byte[] buffer = new byte[65535];
    DatagramPacket dp = new DatagramPacket(buffer, buffer.length);

    try {
        MulticastSocket ms = new MulticastSocket(_port);
        ms.setNetworkInterface(_ni); //non loopback network interface passed
        ms.joinGroup(_ia); //the multicast address, currently 224.0.1.16
        Log.v(TAG,"Joined Group " + _ia);

        while (true) {
            ms.receive(dp);
            String s = new String(dp.getData(),0,dp.getLength());
            Log.v(TAG,"Received Package on "+ _ni.getName() +": " + s);
            Message m = new Message();
            Bundle b = new Bundle();
            b.putString("event", "Listener ("+_ni.getName()+"): \"" + s + "\"");
            m.setData(b);
            dispatchMessage(m); //send to ui thread
        }
    } catch (SocketException se) {
        System.err.println(se);
    } catch (IOException ie) {
        System.err.println(ie);
    }
}
这是从每个可用的有效网络接口(不是环回接口)发送多播数据报的代码

然后当你完成的时候

if (_wifiMulticastLock != null && _wifiMulticastLock.isHeld())
    _wifiMulticastLock.release();
在我这样做之后,Droid开始在多播组上发送和接收UDP数据报

public void run() {
    byte[] buffer = new byte[65535];
    DatagramPacket dp = new DatagramPacket(buffer, buffer.length);

    try {
        MulticastSocket ms = new MulticastSocket(_port);
        ms.setNetworkInterface(_ni); //non loopback network interface passed
        ms.joinGroup(_ia); //the multicast address, currently 224.0.1.16
        Log.v(TAG,"Joined Group " + _ia);

        while (true) {
            ms.receive(dp);
            String s = new String(dp.getData(),0,dp.getLength());
            Log.v(TAG,"Received Package on "+ _ni.getName() +": " + s);
            Message m = new Message();
            Bundle b = new Bundle();
            b.putString("event", "Listener ("+_ni.getName()+"): \"" + s + "\"");
            m.setData(b);
            dispatchMessage(m); //send to ui thread
        }
    } catch (SocketException se) {
        System.err.println(se);
    } catch (IOException ie) {
        System.err.println(ie);
    }
}
2010年7月6日更新

对于每个请求,这是我当前的代码,下一个方法存在于一个抽象类中,可以用于广播和多播接收器

public void run() {
    onInit();
    try {
        byte[] data = new byte[65535];
        while (isProcessing()) {
            try {
                DatagramPacket receivedDatagram = new DatagramPacket(data, data.length);
                _socket.receive(receivedDatagram);
                onDatagramReceived(receivedDatagram);
                data = new byte[65535]; // This pattern is for saving memory allocation.
            } catch (InterruptedIOException e) {
                if (!isProcessing())
                    break;
            }
        } // while

    } catch (Exception e) {
        Log.e(TAG, e.getMessage(), e);
    } finally {
        onStop();
        _socket.close();
        _socket.disconnect();
    }
}
扩展类应该实现
onInit()
onDatagramReceived()

对于多播接收器,
onInit()
看起来像这样:

_socket = new MulticastSocket(PORT_MULTICAST);
InetAddress groupAddress = InetAddress.getByAddress(MULTICAST_GROUP_ADDRESS); 
InetAddress groupInetAddress = FrostWireUtils.fastResolveAddress(groupAddress); //reflection hack to not resolve ips
try {
    _socket.setSoTimeout(500);
    _socket.setTimeToLive(MULTICAST_TTL_GLOBAL);
    _socket.setReuseAddress(true);
    _socket.setNetworkInterface(
        WifiUtils.getWifiNetworkInterface());
    _socket.joinGroup(groupInetAddress);
    WifiUtils.lockMulticast();
} catch (Exception e) {
    Log.e(TAG, e.getMessage(), e);
}

我实现了另一个测试,这次使用UDP广播。 它起作用了


结论:据我所知,固件2.0.1上的摩托罗拉Droid手机不支持多播,但您可以始终在广播地址上使用常规数据包。

请参阅此线程上的更新(2010年4月2日)。我已经设法让Droid使用固件2.0.1通过多播锁通过多播进行通信。“WifiManager.MulticastLock允许应用程序接收Wifi多播数据包。通常,Wifi堆栈会过滤掉未明确寻址到此设备的数据包。访问多播锁将导致堆栈接收寻址到多播地址的数据包。处理这些额外数据包可能会导致明显的电池耗电,因此应不需要时禁用。“我正在尝试在Nexus One(固件2.1.1)上接收多播数据包。我使用了上面的代码,但到目前为止运气不好。你能附上你的完整资料吗?这样我可以把它和我的比较一下?谢谢,EyalEya,我添加了一个更新,希望对你有所帮助。
_socket = new MulticastSocket(PORT_MULTICAST);
InetAddress groupAddress = InetAddress.getByAddress(MULTICAST_GROUP_ADDRESS); 
InetAddress groupInetAddress = FrostWireUtils.fastResolveAddress(groupAddress); //reflection hack to not resolve ips
try {
    _socket.setSoTimeout(500);
    _socket.setTimeToLive(MULTICAST_TTL_GLOBAL);
    _socket.setReuseAddress(true);
    _socket.setNetworkInterface(
        WifiUtils.getWifiNetworkInterface());
    _socket.joinGroup(groupInetAddress);
    WifiUtils.lockMulticast();
} catch (Exception e) {
    Log.e(TAG, e.getMessage(), e);
}