10

I'm asking for help since it seems I cannot find a way to send an UDP broadcast inside a local network using Dart.

So far I managed to communicate using UDP with RawDatagramSocket. I'm able to send a message to a specific address.

What I'm not able to do is to send a broadcast to any device inside a local network (network mask is 255.255.255.0), and to wait for possible (multiple) answer(s). Here is the code I'm using:

RawDatagramSocket.bind('127.0.0.1', 8889)
    .then((RawDatagramSocket udpSocket) {
        udpSocket.listen((e) {
            Datagram dg = udpSocket.receive();
            if (dg != null) {
                //stuff
            }
        });
        udpSocket.send(utf8.encode('TEST'), DESTINATION_ADDRESS, 8889);
});

I tried to replace DESTINATION_ADDRESS with InternetAddress.anyIPv4, but I had no luck. I also found the property broadcastEnabled inside RawDatagramSocket, but I cannot find further informations about how to make use of it.

Thanks in advance for you help.

Alessandro
  • 1,046
  • 1
  • 11
  • 19
  • Broadcast UDP is often blocked by network devices due to the load it causes. Consider using multicast to get a message out to multiple receivers. – Andy Brown Nov 28 '21 at 13:11

2 Answers2

12

There are two problems:

  1. Use InternetAddress.anyIPv4 for binding on all network interfaces;

  2. Enable permission for broadcasting with property broadcastEnabled

Obviously use a broadcast address: for a /24 network use x.y.z.255 address.

This snippet works:

import 'dart:io';
import 'dart:convert';

main() {

  var DESTINATION_ADDRESS=InternetAddress("x.y.z.255");

  RawDatagramSocket.bind(InternetAddress.anyIPv4, 8889).then((RawDatagramSocket udpSocket) {
    udpSocket.broadcastEnabled = true;
    udpSocket.listen((e) {
      Datagram dg = udpSocket.receive();
      if (dg != null) {
        print("received ${dg.data}");
      }
    });
    List<int> data =utf8.encode('TEST');
    udpSocket.send(data, DESTINATION_ADDRESS, 8889);
  });
}
attdona
  • 17,196
  • 7
  • 49
  • 60
  • Unfortunately, this has been my first approach (and I just tested it again using your snippet), but it doesn't work. Let's say I have a sever listening for UDP packets at 'x.y.z.5': if `DESTINATION_ADDRESS` is set to 'x.y.z.255' the server doesn't receive anything, but if it's set to 'x.y.z.5' the server correctly receives the packet. – Alessandro Jan 23 '19 at 16:01
  • For me it works using the same host. It should be a receiver side problem. Are you binding to the broadcast address `x.y.x.255`? – attdona Jan 23 '19 at 16:14
  • Thanks, I managed to make it work, though it didn't actually solve my problem. Thing is, I'm using Flutter, and I thought that mentioning Dart or Flutter would have been equivalent. It turned out it isn't. In a simple `.dart` script the broadcast works, and I'm able to receive the message even from another host. Using Flutter, the same script isn't working. Are you able to help me, or should I seek help asking a new question? – Alessandro Jan 23 '19 at 16:44
  • It sound like you are you using an emulator. Try a real device, It should work. – attdona Jan 23 '19 at 17:54
  • I'm having the same issue with Flutter. Have you solved this one @Alessandro ? – Gabriel Ziegler Oct 12 '19 at 22:35
  • @GabrielZiegler Yes, as suggested by attdona I used a real device and it worked. Probably with some tweaks you can make it work on an emulator, but I haven't tried it. – Alessandro Oct 14 '19 at 08:37
  • I was already using a real device, but it wouldn't work. I have managed to use Adhara Socket for this tho. – Gabriel Ziegler Oct 14 '19 at 11:55
  • 2
    how should I enable permission for broadcastEnabled – Yogesh Chawla Feb 11 '20 at 03:53
  • Thanks so much @attdona, this solved my issue. I was able to send my udp packet and now with the socket bound to InternetAddress.anyIPv4 it was able to get the response from the server I was looking for. The permissions thing was also a very helpful fix. – Eradicatore Dec 13 '20 at 13:43
  • If you are testing your flutter app on an emulator you should be aware that you will not be on the same LAN as your development computer. Sometimes it is just easier to debug with a physical device. – Rick Jun 09 '23 at 19:58
0
socket.send(
  'HELLO!'.codeUnits,
  InternetAddress('255.255.255.255'),
  8080,
);

Try LAN instead of WLAN.

qiuqimin
  • 85
  • 1
  • 6