[Resolved] Unable to receive UDP multicasts

mh-dev
Posts: 25
Joined: Mon Nov 30, 2015 5:14 am

[Resolved] Unable to receive UDP multicasts

Postby mh-dev » Thu Feb 09, 2017 5:47 am

I tried to receive a UDP multicast message, but was unable to do so. I tried multiple variations, but none of them actually was able to receive something. I verified that the packages are actually transmitted over the Wifi connection since my tests involved 2 PCs and 2 ESP32 instances. Neither a send from another ESP32 nor from a PC could be received

Test scenario 1:
- start up Java receiver on computer A
- start up C receiver on ESP32 A
- execute a send on computer B
Result scenario 1:
- Java receiver gets the message on computer A
- ESP32 A does not get the message

Test scenario 2:
- start up Java receiver on computer A
- start up C receiver on ESP32 A
- execute a send on ESP 32 B
Result scenario 2:
- Java receiver gets the message on ESP32 B
- C receiver on ESP32 A does not get message

Used C receiver code for ESP32 A. I tried multiple variations of UDP multicast programs all with the same result. I assume I miss something obviously?

Code: Select all

    int sock;
    int flag_on = 1;
    struct sockaddr_in multicast_addr;
    char message_received[MAX_LEN+1];
    int msgrecv_len;
    struct ip_mreq mc_req;
    char* multicast_ip;
    unsigned short multicast_port;
    struct sockaddr_in from_addr;
    unsigned int from_len;

    multicast_ip = "239.255.255.250";
    multicast_port = atoi("1900");

    if ((sock = socket(PF_INET, SOCK_DGRAM, IPPROTO_UDP)) < 0)
    {
        ESP_LOGE(TAG, "socket() failed");
        exit(1);
    }

    if ((setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, &flag_on, sizeof(flag_on))) < 0)
    {
        ESP_LOGE(TAG, "setsockopt() failed %s", strerror(errno));
        exit(1);
    }

    memset(&multicast_addr, 0, sizeof(multicast_addr));
    multicast_addr.sin_family      = AF_INET;
    multicast_addr.sin_addr.s_addr = htonl(INADDR_ANY);
    multicast_addr.sin_port        = htons(multicast_port);


    if ((bind(sock, (struct sockaddr *) &multicast_addr, sizeof(multicast_addr))) < 0)
    {
        ESP_LOGE(TAG, "bind() failed");
        exit(1);
    }

    mc_req.imr_multiaddr.s_addr = inet_addr(multicast_ip);
    mc_req.imr_interface.s_addr = htonl(INADDR_ANY);

    if ((setsockopt(sock, IPPROTO_IP, IP_ADD_MEMBERSHIP, (void*) &mc_req, sizeof(mc_req))) < 0)
    {
        ESP_LOGE(TAG, "setsockopt() failed");
        exit(1);
    }

    while(1)
    {
        memset(message_received, 0, sizeof(message_received));
        from_len = sizeof(from_addr);
        memset(&from_addr, 0, from_len);
        ESP_LOGI(TAG, "Wait for message");

        if ((msgrecv_len = recvfrom(sock, message_received, MAX_LEN, 0, (struct sockaddr*)&from_addr, &from_len)) < 0)
        {
            ESP_LOGE(TAG, "recvfrom() failed");
            break;
        }

        ESP_LOGI(TAG, "Message received");
        ESP_LOGI(TAG, "Received %d bytes from %s: ", msgrecv_len, inet_ntoa(from_addr.sin_addr));
        ESP_LOGI(TAG, "%s", message_received);
    }

Last edited by mh-dev on Mon Feb 13, 2017 3:28 pm, edited 1 time in total.

User avatar
rudi ;-)
Posts: 1446
Joined: Fri Nov 13, 2015 3:25 pm

Re: Unable to receive UDP multicasts

Postby rudi ;-) » Thu Feb 09, 2017 10:38 am

mh-dev wrote:
I assume I miss something obviously?

Code: Select all

..
char message_received[MAX_LEN+1];
..
multicast_ip = "239.255.255.250";
multicast_port = atoi("1900");
..

#includes ?
#defines? ( MAX_LEN )...
#headers?
..
does your network realy use 239.255.255.0/255
..
router firewall port public net / private net
..

best wishes
rudi ;-)
-------------------------------------
love it, change it or leave it.
-------------------------------------
問候飛出去的朋友遍全球魯迪

mh-dev
Posts: 25
Joined: Mon Nov 30, 2015 5:14 am

Re: Unable to receive UDP multicasts

Postby mh-dev » Thu Feb 09, 2017 2:28 pm

You can find the whole program below (initialize_sta_wifi calls the passed function after event 'SYSTEM_EVENT_STA_GOT_IP' occurs)

Connected to the access point from the provider. I don't expect network related issues since the multicast works in general. I picked the SSP IP/Port for this tests put tried other multicast/ports too.

Code: Select all

#include "esp_err.h"
#include "nvs_flash.h"
#include "lwip/sockets.h"
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "esp_log.h"
#include "string.h"
#include "wifi-initializer.h"
#include "sdkconfig.h"

const static char *TAG = "Multicast";

#define MAX_LEN  1024

void receive_multicast()
{
    int sock;
    int flag_on = 1;
    struct sockaddr_in multicast_addr;
    char message_received[MAX_LEN+1];
    int msgrecv_len;
    struct ip_mreq mc_req;
    char* multicast_ip;
    unsigned short multicast_port;
    struct sockaddr_in from_addr;
    unsigned int from_len;

    multicast_ip = "239.255.255.250";
    multicast_port = atoi("1900");

    if ((sock = socket(PF_INET, SOCK_DGRAM, IPPROTO_UDP)) < 0)
    {
        ESP_LOGE(TAG, "socket() failed");
        exit(1);
    }

    if ((setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, &flag_on, sizeof(flag_on))) < 0)
    {
        ESP_LOGE(TAG, "setsockopt() failed");
        exit(1);
    }

    memset(&multicast_addr, 0, sizeof(multicast_addr));
    multicast_addr.sin_family      = AF_INET;
    multicast_addr.sin_addr.s_addr = htonl(INADDR_ANY);
    multicast_addr.sin_port        = htons(multicast_port);


    if ((bind(sock, (struct sockaddr *) &multicast_addr, sizeof(multicast_addr))) < 0)
    {
        ESP_LOGE(TAG, "bind() failed");
        exit(1);
    }

    mc_req.imr_multiaddr.s_addr = inet_addr(multicast_ip);
    mc_req.imr_interface.s_addr = htonl(INADDR_ANY);

    if ((setsockopt(sock, IPPROTO_IP, IP_ADD_MEMBERSHIP, (void*) &mc_req, sizeof(mc_req))) < 0)
    {
        ESP_LOGE(TAG, "setsockopt() failed");
        exit(1);
    }

    while(1)
    {
        memset(message_received, 0, sizeof(message_received));
        from_len = sizeof(from_addr);
        memset(&from_addr, 0, from_len);
        ESP_LOGI(TAG, "Wait for message");

        if ((msgrecv_len = recvfrom(sock, message_received, MAX_LEN, 0, (struct sockaddr*)&from_addr, &from_len)) < 0)
        {
            ESP_LOGE(TAG, "recvfrom() failed");
            break;
        }

        ESP_LOGI(TAG, "Message received");
        ESP_LOGI(TAG, "Received %d bytes from %s: ", msgrecv_len, inet_ntoa(from_addr.sin_addr));
        ESP_LOGI(TAG, "%s", message_received);
    }

    /* send a DROP MEMBERSHIP message via setsockopt */
    if ((setsockopt(sock, IPPROTO_IP, IP_DROP_MEMBERSHIP, (void*) &mc_req, sizeof(mc_req))) < 0)
    {
        ESP_LOGE(TAG, "setsockopt() failed");
        exit(1);
    }
    close(sock);
}

void send_multicast()
{
    int sock;
    char *message_to_send = "Hello";
    unsigned int send_len;
    char* multicast_ip;
    unsigned short multicast_port;
    unsigned char multicast_ttl=10;
    struct sockaddr_in multicast_addr;


    multicast_ip ="239.255.255.250";
    multicast_port = atoi("1900");

    if ((sock = socket(PF_INET, SOCK_DGRAM, IPPROTO_UDP)) < 0)
    {
        ESP_LOGE(TAG,"socket() failed");
        exit(1);
    }

    if ((setsockopt(sock, IPPROTO_IP, IP_MULTICAST_TTL, (void*) &multicast_ttl, sizeof(multicast_ttl))) < 0)
    {
        ESP_LOGE(TAG,"setsockopt() failed");
        exit(1);
    }

    memset(&multicast_addr, 0, sizeof(multicast_addr));
    multicast_addr.sin_family      = AF_INET;
    multicast_addr.sin_addr.s_addr = inet_addr(multicast_ip);
    multicast_addr.sin_port        = htons(multicast_port);

    send_len = strlen(message_to_send);
    if ((sendto(sock, message_to_send, send_len, 0, (struct sockaddr *) &multicast_addr,
                sizeof(multicast_addr))) != send_len)
    {
        ESP_LOGE(TAG,"Error in number of bytes");
        exit(1);
    }
    ESP_LOGI(TAG,"Send done");
    close(sock);
}

void app_main(void)
{
    nvs_flash_init();
    initialize_sta_wifi(receive_multicast);
//    initialize_sta_wifi(send_multicast);
}

mh-dev
Posts: 25
Joined: Mon Nov 30, 2015 5:14 am

Re: Unable to receive UDP multicasts

Postby mh-dev » Fri Feb 10, 2017 5:19 am

I did some further testing today and it works if I use my mobile phone as AP.

Not sure whats going on. I am able to receive the multicast on another device if I use the AP from my provider.
This might be a bug. I do some further research if my AP configuration might be the problem. Otherwise this seems for me like an issue with the ESP32 / its firmware.

WiFive
Posts: 2822
Joined: Tue Dec 01, 2015 7:35 am

Re: Unable to receive UDP multicasts

Postby WiFive » Fri Feb 10, 2017 5:33 am

Have you tested the mdns example to see if you have the same problem?

mh-dev
Posts: 25
Joined: Mon Nov 30, 2015 5:14 am

Re: Unable to receive UDP multicasts

Postby mh-dev » Fri Feb 10, 2017 5:56 am

No I did not test the mdns example.
I've tested a simple tcp/ip server and an UDP sender both work.

Now I am seeing the following. The ESP was afterwards able to receive UDP multicasts also on my provider AP.
I picked a second ESP32 board with the identical program. It connected to the provider AP and it was not able to receive a UPD multicast. (Most of my tests had a running receiver on my secondary notebook running that was able to receive the multicast)
My next test was to disable the mixed mode and disabled the 5GHz net. Suddenly the other ESP32 board was now able to receive Multicasts. Next test was to enable the 5GHz mixed mode again. The ESP32 was afterwards still able to receive UPD multicasts.
This whole situation does not make any sense to me.
I did a full erase of one of the boards and flashed it again and it is still able to receive multicasts. I have one ESP32 board still originally sealed, so I theoretically I have one untouched device left.
I would like to avoid using it for another random test, since I don't see the value in it right now.

Edit: Did another erase followed by flash monitor don't receive messages again.
Edit2: Disabled 5GHz net -> working again -> enable 5GHz net -> still working -> erase & flash monitor -> still working -> erase & flash monitor again -> not working anymore

WiFive
Posts: 2822
Joined: Tue Dec 01, 2015 7:35 am

Re: Unable to receive UDP multicasts

Postby WiFive » Fri Feb 10, 2017 7:18 am

Are you saying that even if the sender and receiver are both on the 2.4ghz network the esp32 receiver won't get the message if the 5ghz network is enabled for any length of time?

mh-dev
Posts: 25
Joined: Mon Nov 30, 2015 5:14 am

Re: Unable to receive UDP multicasts

Postby mh-dev » Fri Feb 10, 2017 2:10 pm

Yes, all tests are done with all devices on the 2,4GHz wifi network.

Should I create a dedicated bug report for this?

mh-dev
Posts: 25
Joined: Mon Nov 30, 2015 5:14 am

Re: Unable to receive UDP multicasts

Postby mh-dev » Sat Feb 11, 2017 1:49 am

Additional information.

Power loss seems to play a role. Both device were not working anymore when I came home today.
So I started the enable procedure. Disabled 5G wifi both are working. Enabled 5G again both were still working after I pressed the reset button. One stopped working after 'make flash' not 100% sure I might unplugged the USB cable temporary and it stopped working.
So I was in state were one was working and one not. (5G still running)
Tried a few resets on the other device and it was still working. Removed the USB cable for a few seconds and plugged it in again. Followed by make monitor and it was not able to receive messages anymore.
I will create an issue in the github repository to increase the visibility of the problem and see if someone else can reproduce the issue.
Let me know if you need any additional information or test.


This is in my opinion a serious issue and a show stopper for multiple applications.

WiFive
Posts: 2822
Joined: Tue Dec 01, 2015 7:35 am

Re: Unable to receive UDP multicasts

Postby WiFive » Sat Feb 11, 2017 2:26 am

So even the laptop is on 2.4ghz band the whole time? Never stops working when using your phone as AP? Sounds like your dual band AP could be the problem how many devices are using the 5ghz band?

Who is online

Users browsing this forum: somesh and 22 guests