ESP8266 Mesh packet sending process introduction

foreword

Recently, I was debugging the mesh function of ESP8266. After staring at the code and debugging information for a few days, I finally found that mesh is very simple to use (unfortunately, I don’t know anything about its working principle). Personally, I feel that other package sending programs are basically They all follow this process, so I decided to record the process of this mesh's json package function for future reference.

Program source code

void ICACHE_FLASH_ATTR mesh_json_bcast_test()
{
    char buf[32];
    uint8_t src[6];
    uint8_t dst[6];
    struct mesh_header_format *header = NULL;
    /** 获取mac地址 */
    if (!wifi_get_macaddr(STATION_IF, src)) 
    {
        MESH_PARSER_PRINT("bcast get sta mac fail\n");
        return;
    }

    os_memset(buf, 0, sizeof(buf));
    os_sprintf(buf, "%s", "{\"bcast\":\"");
    os_sprintf(buf + os_strlen(buf), MACSTR, MAC2STR(src));
    os_sprintf(buf + os_strlen(buf), "%s", "\"}\r\n");

    os_memset(dst, 0, sizeof(dst));  // use bcast to get all the devices working in mesh from root.
    /** 创建一个数据包 */
    header = (struct mesh_header_format *)espconn_mesh_create_packet(
    dst,     // destiny address (bcast)
    src,     // source address
    false,   // not p2p packet
    true,    // piggyback congest request
    M_PROTO_JSON,   // packe with JSON format
    os_strlen(buf), // data length
    false,   // no option
    0,       // option total len
    false,   // no frag
    0,       // frag type, this packet doesn't use frag
    false,   // more frag
    0,       // frag index
    0);      // frag length
    /** 进行数据包地址正确性检查 */
    if (!header) 
    {
        MESH_PARSER_PRINT("bcast create packet fail\n");
        return;
    }
    /** 设置用户数据 */
    if (!espconn_mesh_set_usr_data(header, buf, os_strlen(buf))) 
    {
        MESH_DEMO_PRINT("bcast set user data fail\n");
        MESH_DEMO_FREE(header);
        return;
    }
    /** 发送数据 */
    if (espconn_mesh_sent(&g_ser_conn, (uint8_t *)header, header->len)) 
    {
        MESH_DEMO_PRINT("bcast mesh is busy\n");
        espconn_mesh_connect(&g_ser_conn);
        MESH_DEMO_FREE(header);
        return;
    }

    MESH_DEMO_FREE(header);
}

Process introduction

  1. First get the mac address of the module through wifi_get_macaddr .
  2. Configure the contents of the user data packet (buf).
  3. Initialize the target mac address (if the MAC address is zero, it is regarded as sending data packets to all devices in the network).
  4. Create a packet (pointed to by the pointer header) by calling the espconn_mesh_create_packet function.
  5. Add the contents of the user data packet to the data packet to be sent by calling the espconn_mesh_set_usr_data function.
  6. Send data by calling the espconn_mesh_sent function (the user needs to manually release the memory of this data packet after the data is sent).

It can be seen from the above flow chart that the json package first needs to create and configure the data package, then set the user data of the data package, and finally send the data through the package sending program.

Related API introduction

一、wifi_get_macaddr

Function Query MAC address -
function prototype bool wifi_get_macaddr (uint8 if_index, uint8 * macaddr) -
parameter if_index The current configuration of the obtained soft-ap
parameter enumeration STATION_IF 0x00
- SOFTAP_IF 0x01
parameter * macaddr The obtained mac address
return value true Obtain the mac address successfully
- false Failed to get mac address

二、espconn_mesh_create_packet

Function Create mesh packets -
function prototype void * espconn_mesh_create_packet ( uint8_t* dst_addr, uint8_t* src_addr, bool p2p, bool piggyback_cr, enum mesh_usr_proto_type proto, uint16_t data_len, bool option, uint16_t ot_len, bool frag, enum mesh_option_type frag_type, bool mf, uint16_t frag_idx, uint16_t frag_id ) -
parameter *dst_addr Receiver's mac address (if it is zero, it means that the receiver is all devices in the network)
parameter *src_addr sender's mac address
parameter p2p Whether it is a node-to-node packet (bool type)
parameter piggyback_cr piggyback stream request (bool type)
parameter proto The current configuration of the obtained soft-ap
parameter enumeration M_PROTO_NONE User Data for Network Management Pack
- M_PROTO_HTTP User data style is HTTP style
- M_PROTO_JSON User data style is JSON style
- M_PROTO_MQTT User data style is MQTT style
- M_PROTO_BIN User data style is binary style
parameter data_len length of user data
parameter option Operation option enable (bool type)
parameter от_лен Operation option data length
parameter frag fragmentation enable flag (bool type)
parameter frag_type fragmentation type
parameter enumeration M_O_CONGEST_REQ blocking request
- M_O_CONGEST_RESP Respond to blocking requests
- M_O_ROUTER_SPREAD Router information extension options
- M_O_ROUTE_ADD Node join options
- M_O_ROUTE_DEL Node rollout options
- M_O_TOPO_REQ Topology Request Options
- M_O_TOPO_RESP Topology Response Options
- M_O_MCAST_GRP Multicast of group lists
- M_O_MESH_FRAG mesh management fragment options
- M_O_USR_FRAG user data fragment
- M_O_USR_OPTION User options
parameter mf 更多的fragmentation
参数 frag_idx fragmentation首
参数 frag_id fragmentation id
返回值 void * 返回一个由系统创建的数据包的地址(该地址空间需要用户手动释放)

三、 espconn_mesh_set_usr_data

功能 设置mesh发送包的用户数据 -
函数原型 bool espconn_mesh_set_usr_data ( struct mesh_header_format* head, uint8_t* usr_data, uint16_t data_len ) -
参数 *head 发送包的地址
参数 *usr_data 用户数据缓存区
参数 data_len 数据长度
返回值 true 设置成功
- false 设置失败

四、 espconn_mesh_sent

功能 mesh发送数据包 -
函数原型 int8_t espconn_mesh_sent ( struct espconn* usr_esp, uint8* pdata, uint16 len ) -
参数 *usr_esp 网络连接结构体
参数 *pdata 数据包的地址
参数 len 数据包的长度
返回值 ESPCONN_OK(0) 发送成功
- ESPCONN_MEM(-1) 内存不足
- ESPCONN_MAXNUM(-7) 发送数据缓存区已满
- ESPCONN_ARG(-12) 非法参数
- ESPCONN_IF(-14) 发送UDP数据失败

参考资料

[1]. ESP8266 Mesh 用户手册
[2]. ESP8266 ESP-MESH API 参考
[3]. ESP8266Non-OS SDK API参考

Guess you like

Origin http://43.154.161.224:23101/article/api/json?id=325582340&siteId=291194637