espressif / esp-mesh-lite

A lite version Wi-Fi Mesh, each node can access the network over the IP layer.
133 stars 22 forks source link

WiFi在WIFI_PROTOCOL_11B模式下,esp_mesh_lite_try_sending_msg 发送300字节不能发出,一直超时 (AEGHB-794) #121

Open guo652917087 opened 2 months ago

guo652917087 commented 2 months ago
  1. 请问 WiFi在WIFI_PROTOCOL_11B模式下,esp_mesh_lite_try_sending_msg 最大可以发送多少个字节?发包间隔多少?
  2. WiFi在WIFI_PROTOCOL_LR模式下,esp_mesh_lite_try_sending_msg 最大可以发送多少个字节?发包间隔多少?

固定在11B模式下,只能ping路由器成功,发包一直发不出。 固定在11G模式下,就能发包成功。

guo652917087 commented 2 months ago

经过反复测试,在11B和LR模式下,mesh内部发送接口esp_mesh_lite_try_sending_msg 和 esp_mesh_lite_try_sending_raw_msg都不能发出数据。可以通过socket发送数据到外网。应该是个大的BUG!!

tswen commented 2 months ago

11B 模式和 LR 模式下通信是没有问题的,你是怎么测试使用的,方便发一下你的测试代码吗?

guo652917087 commented 1 month ago

@tswen

两个设备,一个设备固定根节点,一个子设备。

条件1

根节点设置: esp_mesh_lite_set_allowed_level ( 1 ); esp_wifi_set_protocol ( WIFI_IF_AP, WIFI_PROTOCOL_11B | WIFI_PROTOCOL_11G | WIFI_PROTOCOL_11N | WIFI_PROTOCOL_LR );

子节点设置 esp_mesh_lite_set_allowed_level ( 0 ); esp_mesh_lite_set_disallowed_level ( 1 ); esp_wifi_set_protocol ( WIFI_IF_AP, WIFI_PROTOCOL_11B | WIFI_PROTOCOL_11G | WIFI_PROTOCOL_11N | WIFI_PROTOCOL_LR ); esp_wifi_set_protocol ( WIFI_IF_STA, WIFI_PROTOCOL_11B | WIFI_PROTOCOL_LR ); 或者 esp_wifi_set_protocol ( WIFI_IF_STA, WIFI_PROTOCOL_LR ); 此种条件, 1)esp_mesh_lite_try_sending_msg 和 esp_mesh_lite_try_sending_raw_msg 不能发送数据,会发不出, 2)用ping命令,指定ping包长度-s 1200一直能ping到路由器上的IP。 3)移植iperf,测试到路由器上的IP速度在0.5Mbs,说明tcp socket ok.


条件2

根节点设置: esp_mesh_lite_set_allowed_level ( 1 ); esp_wifi_set_protocol ( WIFI_IF_AP, WIFI_PROTOCOL_11B| WIFI_PROTOCOL_LR );

子节点设置 esp_mesh_lite_set_allowed_level ( 0 ); esp_mesh_lite_set_disallowed_level ( 1 ); esp_wifi_set_protocol ( WIFI_IF_AP, WIFI_PROTOCOL_11B | WIFI_PROTOCOL_11G | WIFI_PROTOCOL_11N | WIFI_PROTOCOL_LR ); esp_wifi_set_protocol ( WIFI_IF_STA, WIFI_PROTOCOL_11B | WIFI_PROTOCOL_11G | WIFI_PROTOCOL_11N | WIFI_PROTOCOL_LR); 此种条件, esp_mesh_lite_try_sending_msg 和 esp_mesh_lite_try_sending_raw_msg 能发送300度个字节数据,大概率会发不出,用ping命令,指定ping包长度-s 1200一直能ping到路由器上的IP。 超过512字节就歇菜发不出了。

条件3,限定esp_wifi_set_protocol ( WIFI_IF_AP, WIFI_PROTOCOL_LR ); esp_mesh_lite_try_sending_msg 和 esp_mesh_lite_try_sending_raw_msg就什么都不能发。几个字节都不行。

guo652917087 commented 1 month ago

@tswen 还发现:

用了ESP32S3做了SPI ETH网口,作为根节点的WAN口功能,发现在同一个路由器下,modbus tcp一直超时,经测试对比,发现两个根设备在同时接入在同一局域网,同网段后,ping包超时,mqtt也经常掉线,modbus tcp slave也经常超时,只要断开其中一个根设备的WAN口,另一台esp32s3根设备WAN口的网络通信就正常。

我猜测,应该是espressif__iot_bridge 软件上 的TCP/IP没处理好,互相反复转发,或者esp32s3内部路由表回环。

tswen commented 1 month ago

https://github.com/espressif/esp-mesh-lite/blob/master/examples/rainmaker/led_light/components/app_bridge/app_mesh_lite_comm.c 可以参考下这个文件里面的使用方法。 是否有通过 esp_mesh_lite_msg_action_list_register 注册,定义的 type 是什么呢?可以将通信这部分代码发出来帮您看一下吗?

wifi mode 是不会影响这个通信的,我怀疑还是大概率是接口使用问题。

tswen commented 1 month ago

@tswen 还发现:

用了ESP32S3做了SPI ETH网口,作为根节点的WAN口功能,发现在同一个路由器下,modbus tcp一直超时,经测试对比,发现两个根设备在同时接入在同一局域网,同网段后,ping包超时,mqtt也经常掉线,modbus tcp slave也经常超时,只要断开其中一个根设备的WAN口,另一台esp32s3根设备WAN口的网络通信就正常。

我猜测,应该是espressif__iot_bridge 软件上 的TCP/IP没处理好,互相反复转发,或者esp32s3内部路由表回环。

你的意思是 根节点A(Station 连接路由器)和 根节点B(ETH 连接路由器)同时连接路由器时,两个设备的应用层通信会超时?断开 根节点A,根节点 B 就好了?

根节点 A 和根节点 B 从路由器那边拿到的 ip 分别是多少,路由器可以抓包吗?

guo652917087 commented 1 month ago

@tswen 提供一份简单的测试代码给你验证,针对11B和LR模式,不能发出数据问题。


#include <inttypes.h>
#include "esp_log.h"
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "freertos/timers.h"

#include "esp_wifi.h"
#include "nvs_flash.h"
#include <sys/socket.h>

#include "esp_mac.h"
#include "esp_bridge.h"
#include "esp_mesh_lite.h"

#define IS_ROOT 1

#define TEST_MESSGAE_LENGTH                             1024 // 200 500

#define WIFI_MESH_ACTION_JSON_DOWN                      "down"
#define WIFI_MESH_ACTION_JSON_DOWN_ACK                  "down_ack"
#define WIFI_MESH_ACTION_JSON_UP                        "up"
#define WIFI_MESH_ACTION_JSON_UP_ACK                    "up_ack"

#define WIFI_PASSWORD                                   "88888888"

static int g_msgid = 0;
static char g_node_eui[13];
static char g_root_eui[13];

static SemaphoreHandle_t list_mutex;

static int g_lost_connect = 0;

#define MSG_LIST_MAX 100

struct msg_list_t
{
    char eui[13];
    uint32_t msgid;
    uint32_t time;
};

struct msg_list_s
{
    uint16_t num;
    struct msg_list_t messages[MSG_LIST_MAX];
};

static struct msg_list_s msg_list;

static int msg_list_compare ( const void *a, const void *b, void *arg )
{
    struct msg_list_t *p = ( struct msg_list_t * ) a;
    struct msg_list_t *q = ( struct msg_list_t * ) b;
    int *counter = ( int * ) arg;
    int p_count, q_count;

    p_count = p->time;
    q_count = q->time;

    if ( p_count > q_count )
        *counter = *counter + 1;

    return p_count - q_count;
}

static void msg_list_sort ( struct msg_list_s *list )
{
    int counter = 0;

    if ( 0 == list->num )
    {
        return;
    }

    qsort_r ( list->messages, list->num, sizeof ( list->messages[0] ), msg_list_compare, &counter );
}

void add_msgid_to_list ( struct msg_list_s *list, char *eui, uint32_t msgid )
{
    uint32_t time_us = 0;
    int i;

    time_us = esp_timer_get_time();

    for ( i = 0; i < ( int ) list->num; i++ )
    {
        if ( time_us  > list->messages[i].time + ( 5 * 1000000 ) )
        {
            printf ( "#######ERR: msg id:%ld timeout##########\n" , list->messages[i].msgid );
            list->messages[i].msgid = 0;
            list->messages[i].time = time_us;
            memset ( list->messages[i].eui, 0, sizeof ( list->messages[i].eui ) );
            msg_list_sort ( list );
            list->num--;
            g_lost_connect++;
        }

    }

    if ( list->num > MSG_LIST_MAX - 1 )
    {
        printf ( "INFO: msg list full\n"  );
        return ;
    }

    list->messages[list->num].msgid = msgid;
    strncpy ( list->messages[list->num].eui, eui, sizeof ( list->messages[list->num].eui ) );
    list->messages[list->num].time = time_us;
    list->num++;
    msg_list_sort ( list );

}

static void del_msg_from_list ( struct msg_list_s *list, char *eui, uint32_t msgid )
{
    uint32_t time_us = 0;
    int diff_time_us = 0;
    int i;

    for ( i = 0; i < ( int ) list->num; i++ )
    {
        if (  msgid == list->messages[i].msgid && strcmp ( eui, list->messages[i].eui ) == 0 )
        {
            time_us = esp_timer_get_time();
            diff_time_us = time_us - list->messages[i].time;
            list->messages[i].msgid = 0;
            memset ( list->messages[i].eui, 0, sizeof ( list->messages[i].eui ) );
            list->messages[i].time = time_us;
            msg_list_sort ( list );
            list->num--;
            g_lost_connect = 0;
        }

    }

}

static void msg_list_init ( struct msg_list_s *list )
{
    int i;
    memset ( list, 0, sizeof ( *list ) );

    for ( i = 0; i < MSG_LIST_MAX; i++ )
    {
        list->messages[i].time = 0;
        list->messages[i].msgid = 0;
        memset ( list->messages[i].eui, 0, sizeof ( list->messages[i].eui ) );
    }
}

int node_send_to_root ( void  )
{

    cJSON *root = NULL;
    cJSON *payload = NULL;

    root = cJSON_CreateObject();

    if ( root == NULL )
    {
        return -1;
    }

    payload = cJSON_CreateObject();

    if ( payload == NULL )
    {
        cJSON_Delete ( root );
        return -1;
    }

    cJSON_AddNumberToObject ( root, "id", g_msgid );
    cJSON_AddStringToObject ( root, "eui", g_node_eui );
    cJSON_AddNumberToObject ( root, "uptime", esp_timer_get_time() / 1000 );

    char buff[1500];
    memset ( buff, '1', sizeof ( buff ) );
    buff[TEST_MESSGAE_LENGTH] = 0;

    cJSON_AddStringToObject ( root, "data", buff );

    wifi_ap_record_t ap_info;

    esp_wifi_sta_get_ap_info ( &ap_info );

    memset ( g_root_eui, 0, sizeof ( g_root_eui ) );
    sprintf ( g_root_eui, "%02x%02x%02x%02x%02x%02x", ap_info.bssid[0], ap_info.bssid[1], ap_info.bssid[2], ap_info.bssid[3], ap_info.bssid[4], ap_info.bssid[5] );

    xSemaphoreTake ( list_mutex, portMAX_DELAY );
    add_msgid_to_list ( &msg_list, g_root_eui, g_msgid );
    xSemaphoreGive ( list_mutex );

    esp_mesh_lite_try_sending_msg ( WIFI_MESH_ACTION_JSON_UP, WIFI_MESH_ACTION_JSON_UP_ACK, 5, root, &esp_mesh_lite_send_msg_to_root );

    g_msgid++;

    cJSON_Delete ( root );

    return ESP_OK;
}

int root_send_to_node ( char *eui , uint32_t msgid )
{

    cJSON *root = NULL;
    cJSON *payload = NULL;

    root = cJSON_CreateObject();

    if ( root == NULL )
    {
        return -1;
    }

    payload = cJSON_CreateObject();

    if ( payload == NULL )
    {
        cJSON_Delete ( root );
        return -1;
    }

    cJSON_AddNumberToObject ( root, "id", msgid );
    cJSON_AddStringToObject ( root, "eui", eui );
    cJSON_AddNumberToObject ( root, "uptime", esp_timer_get_time() / 1000 );

    char buff[1500];
    memset ( buff, '1', sizeof ( buff ) );
    buff[TEST_MESSGAE_LENGTH] = 0;
    cJSON_AddStringToObject ( root, "data", buff );

    xSemaphoreTake ( list_mutex, portMAX_DELAY );
    add_msgid_to_list ( &msg_list, eui, g_msgid );
    xSemaphoreGive ( list_mutex );

    esp_mesh_lite_try_sending_msg ( WIFI_MESH_ACTION_JSON_DOWN, WIFI_MESH_ACTION_JSON_DOWN_ACK, 5, root, &esp_mesh_lite_send_broadcast_msg_to_child );

    cJSON_Delete ( root );

    return ESP_OK;
}

static cJSON* json_down_process ( cJSON * payload, uint32_t seq )
{

    cJSON *obj = NULL;
    cJSON *response = NULL;
    char device_eui[18];
    uint32_t msgid = 0;
    uint32_t uptime = 0;
    bool is_ours = false;
    bool is_broadcast = false;
    bool forward = false;

    memset ( device_eui, 0, sizeof ( device_eui ) );

    obj = cJSON_GetObjectItem ( payload, "eui" );

    if ( obj != NULL && cJSON_IsString ( obj ) )
    {
        strcpy ( device_eui, obj->valuestring );

        if ( strcmp ( g_node_eui, device_eui ) == 0 )
        {
            is_ours = true;
        }
        else  if ( strncmp ( "ffffffffffff", obj->valuestring , 12 ) == 0 )
        {
            is_broadcast = true;
        }
    }

    obj = cJSON_GetObjectItem ( payload, "id" );

    if ( obj != NULL && cJSON_IsNumber ( obj ) )
    {
        msgid = ( uint32_t ) obj->valuedouble;

    }

    obj = cJSON_GetObjectItem ( payload, "uptime" );

    if ( obj != NULL && cJSON_IsNumber ( obj ) )
    {
        uptime = ( uint32_t ) obj->valuedouble;
    }

    obj = cJSON_GetObjectItem ( payload, "data" );

    if ( obj != NULL && cJSON_IsString ( obj ) )
    {
        printf ( "down data len:%d\r\n", strlen ( obj->valuestring ) );
    }

    if ( is_broadcast )
    {
        forward = true;

    }
    else if ( is_ours )
    {
        forward = false;
        response = cJSON_CreateObject();
        cJSON_AddNumberToObject ( response, "uptime", uptime );
        cJSON_AddNumberToObject ( response, "id", msgid );
        cJSON_AddStringToObject ( response, "eui", g_node_eui );
    }
    else
    {
        forward = true;
    }

    if ( forward )
    {
        esp_mesh_lite_try_sending_msg ( WIFI_MESH_ACTION_JSON_DOWN, WIFI_MESH_ACTION_JSON_DOWN_ACK, 3, payload, &esp_mesh_lite_send_broadcast_msg_to_child );

    }

    return response;
}

static cJSON* json_down_ack_process ( cJSON * payload, uint32_t seq )
{
    cJSON *obj = NULL;
    uint32_t msgid = 0;
    uint32_t uptime;
    char device_eui[18];
    int diff = 0;

    obj = cJSON_GetObjectItem ( payload, "id" );

    if ( obj != NULL && cJSON_IsNumber ( obj ) )
    {
        msgid = ( uint32_t ) obj->valuedouble;
    }

    memset ( device_eui, 0, sizeof ( device_eui ) );

    obj = cJSON_GetObjectItem ( payload, "eui" );

    if ( obj != NULL && cJSON_IsString ( obj ) )
    {
        strcpy ( device_eui, obj->valuestring );
    }

    obj = cJSON_GetObjectItem ( payload, "uptime" );

    if ( obj != NULL && cJSON_IsNumber ( obj ) )
    {
        uptime = ( uint32_t ) obj->valuedouble;
        diff =  esp_timer_get_time() / 1000 - uptime;
        printf ( "root recv ack,msgid:%ld,delay:%d ms\r\n", msgid, diff );

        xSemaphoreTake ( list_mutex, portMAX_DELAY );
        del_msg_from_list ( &msg_list, device_eui, msgid );
        xSemaphoreGive ( list_mutex );
    }

    return NULL;

}
static cJSON* json_up_process ( cJSON * payload, uint32_t seq )
{
    cJSON *obj = NULL;
    cJSON *response = NULL;
    char device_eui[18];
    uint32_t msgid = 0;
    uint32_t uptime = 0;

    memset ( device_eui, 0, sizeof ( device_eui ) );

    obj = cJSON_GetObjectItem ( payload, "eui" );

    if ( obj != NULL && cJSON_IsString ( obj ) )
    {
        strcpy ( device_eui, obj->valuestring );
    }

    obj = cJSON_GetObjectItem ( payload, "id" );

    if ( obj != NULL && cJSON_IsNumber ( obj ) )
    {
        msgid = ( uint32_t ) obj->valuedouble;
    }

    obj = cJSON_GetObjectItem ( payload, "uptime" );

    if ( obj != NULL && cJSON_IsNumber ( obj ) )
    {
        uptime = ( uint32_t ) obj->valuedouble;
    }

    obj = cJSON_GetObjectItem ( payload, "data" );

    if ( obj != NULL && cJSON_IsString ( obj ) )
    {
        printf ( "recv from:%s data len:%d\r\n", device_eui, strlen ( obj->valuestring ) );
    }

    response = cJSON_CreateObject();

    cJSON_AddNumberToObject ( response, "uptime", uptime );
    cJSON_AddNumberToObject ( response, "id", msgid );

    return response;

}

static cJSON* json_up_ack_process ( cJSON * payload, uint32_t seq )
{
    cJSON *obj = NULL;
    uint32_t uptime = 0;
    uint32_t msgid = 0;
    int diff = 0;

    obj = cJSON_GetObjectItem ( payload, "id" );

    if ( obj != NULL && cJSON_IsNumber ( obj ) )
    {
        msgid = ( uint32_t ) obj->valuedouble;
    }

    obj = cJSON_GetObjectItem ( payload, "uptime" );

    if ( obj != NULL && cJSON_IsNumber ( obj ) )
    {
        uptime = ( uint32_t ) obj->valuedouble;
        diff =  esp_timer_get_time() / 1000 - uptime;
        printf ( "node recv ack ,msgid:%ld,delay:%d ms\r\n", msgid, diff );
        xSemaphoreTake ( list_mutex, portMAX_DELAY );
        del_msg_from_list ( &msg_list, g_root_eui, msgid );
        xSemaphoreGive ( list_mutex );
    }

    return NULL;
}

static const esp_mesh_lite_msg_action_t wifi_mesh_action[] =
{
    {WIFI_MESH_ACTION_JSON_DOWN, WIFI_MESH_ACTION_JSON_DOWN_ACK, json_down_process},
    {WIFI_MESH_ACTION_JSON_DOWN_ACK, NULL, json_down_ack_process},
    {WIFI_MESH_ACTION_JSON_UP, WIFI_MESH_ACTION_JSON_UP_ACK, json_up_process},
    {WIFI_MESH_ACTION_JSON_UP_ACK, NULL, json_up_ack_process},
    {NULL, NULL, NULL}
};

void app_wifi_set_softap_info ( void )
{
    char softap_ssid[32];
    uint8_t softap_mac[6];
    esp_wifi_get_mac ( WIFI_IF_AP, softap_mac );
    memset ( softap_ssid, 0x0, sizeof ( softap_ssid ) );
    snprintf ( softap_ssid, sizeof ( softap_ssid ), "%.25s_%02x%02x%02x", "test", softap_mac[3], softap_mac[4], softap_mac[5] );
    esp_mesh_lite_set_softap_ssid_to_nvs ( softap_ssid );
    esp_mesh_lite_set_softap_psw_to_nvs ( WIFI_PASSWORD );
    esp_mesh_lite_set_softap_info ( softap_ssid, WIFI_PASSWORD );
}

void app_main()
{

    esp_err_t ret = nvs_flash_init();

    if ( ret == ESP_ERR_NVS_NO_FREE_PAGES || ret == ESP_ERR_NVS_NEW_VERSION_FOUND )
    {
        // NVS partition was truncated and needs to be erased
        // Retry nvs_flash_init
        ESP_ERROR_CHECK ( nvs_flash_erase() );
        ret = nvs_flash_init();
    }

    ESP_ERROR_CHECK ( esp_netif_init() );
    ESP_ERROR_CHECK ( esp_event_loop_create_default() );

    esp_bridge_create_all_netif();

    uint8_t mac[6];
    memset ( mac, 0x0, sizeof ( mac ) );

    wifi_config_t wifi_config;
    memset ( &wifi_config, 0x0, sizeof ( wifi_config_t ) );

    esp_bridge_wifi_set_config ( WIFI_IF_STA, &wifi_config );

    // Softap

    uint8_t gw_mac[6];

    memset ( gw_mac, 0x0, sizeof ( gw_mac ) );

    //snprintf ( g_device->wifi_ap_pass, sizeof ( g_device->wifi_ap_pass ), "%s", CONFIG_BRIDGE_SOFTAP_PASSWORD );

    snprintf ( ( char * ) wifi_config.ap.ssid, sizeof ( wifi_config.ap.ssid ), "%s", "test_ap" );
    strlcpy ( ( char * ) wifi_config.ap.password, WIFI_PASSWORD, sizeof ( wifi_config.ap.password ) );

    wifi_config.ap.channel = 1;

    esp_bridge_wifi_set_config ( WIFI_IF_AP, &wifi_config );

    esp_wifi_set_ps ( WIFI_PS_NONE );

    esp_mesh_lite_config_t mesh_lite_config = ESP_MESH_LITE_DEFAULT_INIT();
    mesh_lite_config.join_mesh_ignore_router_status = true;

#if IS_ROOT
    esp_wifi_get_mac ( WIFI_IF_AP, mac );
    sprintf ( g_root_eui, "%02x%02x%02x%02x%02x%02x", mac[0], mac[1], mac[2], mac[3], mac[4], mac[5] );
    mesh_lite_config.join_mesh_without_configured_wifi = false;
#else
    esp_wifi_get_mac ( WIFI_IF_STA, mac );
    sprintf ( g_node_eui, "%02x%02x%02x%02x%02x%02x", mac[0], mac[1], mac[2], mac[3], mac[4], mac[5] );
    mesh_lite_config.join_mesh_without_configured_wifi = true;
#endif
    esp_mesh_lite_init ( &mesh_lite_config );

    list_mutex = xSemaphoreCreateMutex();

    app_wifi_set_softap_info();

#if IS_ROOT
    printf ( "Root node\r\n" );
    esp_mesh_lite_set_allowed_level ( 1 );
    esp_wifi_set_protocol ( WIFI_IF_AP,  WIFI_PROTOCOL_11B | WIFI_PROTOCOL_11G | WIFI_PROTOCOL_11N | WIFI_PROTOCOL_LR );

#else
    printf ( "Child node\r\n" );
    esp_mesh_lite_set_disallowed_level ( 1 );

    esp_wifi_set_protocol ( WIFI_IF_AP,  WIFI_PROTOCOL_11B | WIFI_PROTOCOL_11G | WIFI_PROTOCOL_11N | WIFI_PROTOCOL_LR );
    esp_wifi_set_protocol ( WIFI_IF_STA,  WIFI_PROTOCOL_11B | WIFI_PROTOCOL_11G | WIFI_PROTOCOL_11N | WIFI_PROTOCOL_LR );
    //esp_wifi_set_protocol ( WIFI_IF_STA, WIFI_PROTOCOL_11B| WIFI_PROTOCOL_LR );

#endif

    msg_list_init ( &msg_list );

    esp_mesh_lite_erase_rtc_store();

    esp_mesh_lite_start();

    esp_mesh_lite_msg_action_list_register ( wifi_mesh_action );

    while ( 1 )
    {

#if IS_ROOT
        char eui[13];
        wifi_sta_list_t wifi_sta_list;
        esp_wifi_ap_get_sta_list ( &wifi_sta_list );

        if ( wifi_sta_list.num > 0 )
        {
            printf ( "child node number: %d\r\n", wifi_sta_list.num );

            for ( int i = 0; i < wifi_sta_list.num; i++ )
            {
                //printf ( "Child [%d] mac: " MACSTR, i, MAC2STR ( wifi_sta_list.sta[i].mac ) );
                //printf ( "\r\nChild [%d] rssi: %d\r\n",  i, wifi_sta_list.sta[i].rssi );
                memset ( eui, 0, sizeof ( eui ) );
                sprintf ( eui, "%02x%02x%02x%02x%02x%02x", wifi_sta_list.sta[i].mac[0], wifi_sta_list.sta[i].mac[1], wifi_sta_list.sta[i].mac[2], wifi_sta_list.sta[i].mac[3], wifi_sta_list.sta[i].mac[4], wifi_sta_list.sta[i].mac[5] );
                root_send_to_node ( eui , g_msgid );
                vTaskDelay ( 100 / portTICK_PERIOD_MS );// one by one
            }

            g_msgid++;
        }

#else

        if ( esp_mesh_lite_get_level() > ROOT )
        {
            node_send_to_root();
        }

        if ( g_lost_connect > 30 )
        {
            esp_mesh_lite_connect();
            printf ( "child try to reconnect\r\n" );
            g_lost_connect = 0;
        }

#endif
        vTaskDelay ( 1000 / portTICK_PERIOD_MS );

    }

}

/* --- EOF ------------------------------------------------------------------ */

我测试使用了esp32s3 模块,根节点 修改宏定义 #define IS_ROOT 1 子节点 修改宏定义 #define IS_ROOT 0

当前代码可以执行,子节点串口打印


W (2878) wifi:Password length matches WPA2 standards, authmode threshold changes from OPEN to WPA2
I (2887) [vendor_ie]: wifi_cfg test_ap_cd5229 router_config  
I (2894) [vendor_ie]: esp_mesh_lite_wifi_connect return ESP_OK 
I (3165) wifi:new:<1,1>, old:<1,1>, ap:<1,1>, sta:<1,1>, prof:1, snd_ch_cfg:0x0
I (3165) wifi:state: init -> auth (0xb0)
I (3181) wifi:state: auth -> assoc (0x0)
I (3207) wifi:Association refused temporarily time 1500, comeback time 1600 (TUs)
I (4845) wifi:state: assoc -> assoc (0x0)
I (4853) wifi:state: assoc -> run (0x10)
I (4878) wifi:connected with test_ap_cd5229, aid = 1, channel 1, 40U, bssid = f4:12:fa:cd:52:29
I (4878) wifi:security: WPA2-PSK, phy: lrbgn, rssi: -61
I (4881) wifi:pm start, type: 0

I (4883) wifi:dp: 1, bi: 102400, li: 3, scale listen interval from 307200 us to 307200 us
I (4892) wifi:set rx beacon pti, rx_bcn_pti: 14, bcn_timeout: 25000, mt_pti: 14, mt_time: 10000
I (4966) wifi:dp: 2, bi: 102400, li: 4, scale listen interval from 307200 us to 409600 us
I (4967) wifi:AP's beacon interval = 102400 us, DTIM period = 2
down data len:1024
I (5901) esp_netif_handlers: sta ip: 192.168.5.2, mask: 255.255.255.0, gw: 192.168.5.1
I (5901) bridge_wifi: Connected with IP Address:192.168.5.2
I (5905) bridge_common: [WIFI_AP_DEF ]
I (5909) bridge_common: IP Address:192.168.4.1
I (5914) bridge_common: GW Address:192.168.4.1
I (5919) bridge_common: NM Address:255.255.255.0
I (5925) bridge_common: ip reallocate new:192.168.4.1
I (5931) bridge_wifi: SoftAP IP network segment has changed, deauth all station
I (5939) [vendor_ie]: RTC store: temp_mesh_id:255; ssid:test_ap_cd5229; bssid:f4:12:fa:cd:52:29; crc:1963211612 
down data len:1024
node recv ack ,msgid:3,delay:15 ms
down data len:1024
node recv ack ,msgid:4,delay:28 ms
down data len:1024
#######ERR: msg id:0 timeout##########
node recv ack ,msgid:5,delay:12 ms
down data len:1024
#######ERR: msg id:1 timeout##########
node recv ack ,msgid:6,delay:24 ms
down data len:1024
#######ERR: msg id:2 timeout##########
node recv ack ,msgid:7,delay:17 ms
down data len:1024
node recv ack ,msgid:8,delay:31 ms
down data len:1024
node recv ack ,msgid:9,delay:40 ms
node recv ack ,msgid:10,delay:13 ms
down data len:1024
node recv ack ,msgid:11,delay:28 ms
down data len:1024
node recv ack ,msgid:12,delay:9 ms
down data len:1024
node recv ack ,msgid:13,delay:60 ms
down data len:1024
node recv ack ,msgid:14,delay:29 ms
down data len:1024
node recv ack ,msgid:15,delay:53 ms
down data len:1024
node recv ack ,msgid:16,delay:25 ms

这是正常能通信的,注释掉 543行代码 //esp_wifi_set_protocol ( WIFI_IF_STA, WIFI_PROTOCOL_11B | WIFI_PROTOCOL_11G | WIFI_PROTOCOL_11N | WIFI_PROTOCOL_LR ); 打开 544行代码 esp_wifi_set_protocol ( WIFI_IF_STA, WIFI_PROTOCOL_11B| WIFI_PROTOCOL_LR );

子节点通信异常,串口打印

 (2868) [vendor_ie]: wifi_cfg test_ap_cd5229 router_config  
I (2875) [vendor_ie]: esp_mesh_lite_wifi_connect return ESP_OK 
I (3144) wifi:new:<1,1>, old:<1,1>, ap:<1,1>, sta:<1,0>, prof:1, snd_ch_cfg:0x0
I (3144) wifi:state: init -> auth (0xb0)
I (3153) wifi:state: auth -> assoc (0x0)
I (3159) wifi:Association refused temporarily time 1500, comeback time 1600 (TUs)
I (4797) wifi:state: assoc -> assoc (0x0)
I (4802) wifi:state: assoc -> run (0x10)
I (4824) wifi:connected with test_ap_cd5229, aid = 1, channel 1, BW20, bssid = f4:12:fa:cd:52:29
I (4824) wifi:security: WPA2-PSK, phy: lrb, rssi: -60
I (4826) wifi:pm start, type: 0

I (4829) wifi:dp: 1, bi: 102400, li: 3, scale listen interval from 307200 us to 307200 us
I (4837) wifi:set rx beacon pti, rx_bcn_pti: 14, bcn_timeout: 25000, mt_pti: 14, mt_time: 10000
I (4973) wifi:dp: 2, bi: 102400, li: 4, scale listen interval from 307200 us to 409600 us
I (4973) wifi:AP's beacon interval = 102400 us, DTIM period = 2
I (5846) esp_netif_handlers: sta ip: 192.168.5.2, mask: 255.255.255.0, gw: 192.168.5.1
I (5846) bridge_wifi: Connected with IP Address:192.168.5.2
I (5850) bridge_common: [WIFI_AP_DEF ]
I (5854) bridge_common: IP Address:192.168.4.1
I (5859) bridge_common: GW Address:192.168.4.1
I (5864) bridge_common: NM Address:255.255.255.0
I (5870) bridge_common: ip reallocate new:192.168.4.1
I (5876) bridge_wifi: SoftAP IP network segment has changed, deauth all station
I (5884) [vendor_ie]: RTC store: temp_mesh_id:255; ssid:test_ap_cd5229; bssid:f4:12:fa:cd:52:29; crc:1963211612 
#######ERR: msg id:0 timeout##########
#######ERR: msg id:1 timeout##########
#######ERR: msg id:2 timeout##########
#######ERR: msg id:3 timeout##########
#######ERR: msg id:4 timeout##########
#######ERR: msg id:5 timeout##########
#######ERR: msg id:6 timeout##########
#######ERR: msg id:7 timeout##########
#######ERR: msg id:8 timeout##########
#######ERR: msg id:9 timeout##########
#######ERR: msg id:10 timeout##########
#######ERR: msg id:11 timeout##########
#######ERR: msg id:12 timeout##########
#######ERR: msg id:13 timeout##########
#######ERR: msg id:14 timeout##########
#######ERR: msg id:15 timeout##########
#######ERR: msg id:16 timeout##########
#######ERR: msg id:17 timeout##########
#######ERR: msg id:18 timeout##########
#######ERR: msg id:19 timeout##########
#######ERR: msg id:20 timeout##########
#######ERR: msg id:21 timeout##########
#######ERR: msg id:22 timeout##########
#######ERR: msg id:23 timeout##########
#######ERR: msg id:24 timeout##########
#######ERR: msg id:25 timeout##########
#######ERR: msg id:26 timeout##########
#######ERR: msg id:27 timeout##########
#######ERR: msg id:28 timeout##########
#######ERR: msg id:29 timeout##########
#######ERR: msg id:30 timeout##########
I (39721) [vendor_ie]: esp_mesh_lite_wifi_scan_start return ESP_OK 
child try to reconnect
I (40323) [vendor_ie]: Mesh-Lite Scan done 
#######ERR: msg id:31 timeout##########
#######ERR: msg id:32 timeout##########
#######ERR: msg id:33 timeout##########
#######ERR: msg id:34 timeout##########
#######ERR: msg id:35 timeout##########
#######ERR: msg id:36 timeout##########
#######ERR: msg id:37 timeout##########
#######ERR: msg id:38 timeout##########
#######ERR: msg id:39 timeout##########
#######ERR: msg id:40 timeout##########
#######ERR: msg id:41 timeout##########
#######ERR: msg id:42 timeout##########
#######ERR: msg id:43 timeout##########
#######ERR: msg id:44 timeout##########
#######ERR: msg id:45 timeout##########
#######ERR: msg id:46 timeout##########
#######ERR: msg id:47 timeout##########
#######ERR: msg id:48 timeout##########
#######ERR: msg id:49 timeout##########
#######ERR: msg id:50 timeout##########
#######ERR: msg id:51 timeout##########
#######ERR: msg id:52 timeout##########
#######ERR: msg id:53 timeout##########
#######ERR: msg id:54 timeout##########
#######ERR: msg id:55 timeout##########
#######ERR: msg id:56 timeout##########
#######ERR: msg id:57 timeout##########
#######ERR: msg id:58 timeout##########
#######ERR: msg id:59 timeout##########
#######ERR: msg id:60 timeout##########
#######ERR: msg id:61 timeout##########
I (70752) [vendor_ie]: esp_mesh_lite_wifi_scan_start return ESP_OK 
child try to reconnect
I (71354) [vendor_ie]: Mesh-Lite Scan done
guo652917087 commented 1 month ago

@tswen 还发现: 用了ESP32S3做了SPI ETH网口,作为根节点的WAN口功能,发现在同一个路由器下,modbus tcp一直超时,经测试对比,发现两个根设备在同时接入在同一局域网,同网段后,ping包超时,mqtt也经常掉线,modbus tcp slave也经常超时,只要断开其中一个根设备的WAN口,另一台esp32s3根设备WAN口的网络通信就正常。 我猜测,应该是espressif__iot_bridge 软件上 的TCP/IP没处理好,互相反复转发,或者esp32s3内部路由表回环。

你的意思是 根节点A(Station 连接路由器)和 根节点B(ETH 连接路由器)同时连接路由器时,两个设备的应用层通信会超时?断开 根节点A,根节点 B 就好了?

根节点 A 和根节点 B 从路由器那边拿到的 ip 分别是多少,路由器可以抓包吗?

电脑IP192.168.31.169,两台有WAN口的根设备esp32s3 IP 分别为192.168.31.100和192.168.31.101 ,提供wireshark抓包modbus tcp文件,解压后,用wireshark打开。

抓包文件.zip

两个modbus poll,只要两台esp32s3在同一个局域网,就一直不断有超时出现,然后拔掉一台网线,另一台就不会超时了。

image

tswen commented 3 weeks ago
        if ( time_us  > list->messages[i].time + ( 5 * 1000000 ) )
        {
            printf ( "#######ERR: msg id:%ld timeout##########\n" , list->messages[i].msgid );

看代码跟 mesh-lite 逻辑以及发送接口没有关系,只是你这里的判断导致走到了 ERR,你可以再检查下你的应用层代码。

guo652917087 commented 3 weeks ago
        if ( time_us  > list->messages[i].time + ( 5 * 1000000 ) )
        {
            printf ( "#######ERR: msg id:%ld timeout##########\n" , list->messages[i].msgid );

看代码跟 mesh-lite 逻辑以及发送接口没有关系,只是你这里的判断导致走到了 ERR,你可以再检查下你的应用层代码。

@tswen

请问阁下,有没有认真去执行一下测试代码呢?拿两个模块跑一跑呢?你这样的回答,我是真没想到。

我这里打印是 没有收到ack才执行。收到ack就删除msgid。

说实话,测试代码也提供,估计你也没能看清楚代码的逻辑。

开发项目用到esp平台,测试好几个问题。同时反馈给了esp-modbus、ble mesh、esp-idf,就这个项目反馈巨慢,你还要去测试代码,我也临时写了一份,真是不珍惜别人的劳动。

tswen commented 3 weeks ago
    esp_bridge_wifi_set_config ( WIFI_IF_AP, &wifi_config );

#if IS_ROOT
    esp_wifi_set_protocol ( WIFI_IF_AP,  WIFI_PROTOCOL_11B | WIFI_PROTOCOL_11G | WIFI_PROTOCOL_11N | WIFI_PROTOCOL_LR );
#else
    // esp_wifi_set_protocol ( WIFI_IF_AP,  WIFI_PROTOCOL_11B | WIFI_PROTOCOL_11G | WIFI_PROTOCOL_11N | WIFI_PROTOCOL_LR );
    // esp_wifi_set_protocol ( WIFI_IF_STA,  WIFI_PROTOCOL_11B | WIFI_PROTOCOL_11G | WIFI_PROTOCOL_11N | WIFI_PROTOCOL_LR );
    esp_wifi_set_protocol ( WIFI_IF_STA, WIFI_PROTOCOL_11B| WIFI_PROTOCOL_LR );
#endif

    esp_wifi_set_ps ( WIFI_PS_NONE );

    esp_mesh_lite_config_t mesh_lite_config = ESP_MESH_LITE_DEFAULT_INIT();
    mesh_lite_config.join_mesh_ignore_router_status = true;

#if IS_ROOT
    esp_wifi_get_mac ( WIFI_IF_AP, mac );
    sprintf ( g_root_eui, "%02x%02x%02x%02x%02x%02x", mac[0], mac[1], mac[2], mac[3], mac[4], mac[5] );
    mesh_lite_config.join_mesh_without_configured_wifi = false;
#else
    esp_wifi_get_mac ( WIFI_IF_STA, mac );
    sprintf ( g_node_eui, "%02x%02x%02x%02x%02x%02x", mac[0], mac[1], mac[2], mac[3], mac[4], mac[5] );
    mesh_lite_config.join_mesh_without_configured_wifi = true;
#endif
    esp_mesh_lite_init ( &mesh_lite_config );

    list_mutex = xSemaphoreCreateMutex();

    app_wifi_set_softap_info();

#if IS_ROOT
    printf ( "Root node\r\n" );
    esp_mesh_lite_set_allowed_level ( 1 );
#else
    printf ( "Child node\r\n" );
    esp_mesh_lite_set_disallowed_level ( 1 );
#endif

    msg_list_init ( &msg_list );