giovedì 13 novembre 2025

test ESPNow con IDF

Ho provato Espnow, un protocollo per inviare brevi messaggi tra Esp32 e simili senza l'appoggio di un accesspoint 

 ho usato Idf 5.3.1 ed il programma di esempio

idf.py create-project-from-example "espressif/esp-now:get-started"

idf.py menuconfig

Example configuration 

CONFIG_ESPNOW_CHANNEL → e.g. 1

 CONFIG_ESPNOW_SEND_LEN → e.g. 200

 CONFIG_ESPNOW_SEND_COUNT → e.g. 100

 CONFIG_ESPNOW_SEND_DELAY → e.g. 1000 (ms)

se non si vuole un progetto di esempio si aggiunge il componente
idf.py add-dependency "espressif/esp-now" 

 l'esempio si puo' usare in assenza di wifi e si carica lo stesso firmware di esempio su entrambi i dispositivi. A seconda di send_param->magic=esp_random() viene scelto quale tra i due dispositivi e' il sender e quale e' il receiver 

se si vuole forzare il ruolo si 

#define FORCE_SENDER 1 // 1 = always sender, 0 = always receiver 

sender.c (a seconda delle impostazione di peer mac la comunicazione puo' essere broadcast, specificando come Mac Address FF:FF:FF:FF:FF:FF od indirizzata specificatamente ad un dispositivo)

==================================== 

#include "esp_wifi.h"
#include "esp_now.h"
#include "esp_log.h"
#include "nvs_flash.h"

#include "string.h"

static const char *TAG = "ESPNOW_SENDER";

// 👉 Replace this with your receiver’s MAC address (check via `esp_read_mac`)
uint8_t peer_mac[] = {0x24, 0x6F, 0x28, 0xAA, 0xBB, 0xCC};

static void send_cb(const uint8_t *mac_addr, esp_now_send_status_t status) {
    ESP_LOGI(TAG, "Send to %02X:%02X:%02X:%02X:%02X:%02X  status: %s",
             mac_addr[0], mac_addr[1], mac_addr[2],
             mac_addr[3], mac_addr[4], mac_addr[5],
             status == ESP_NOW_SEND_SUCCESS ? "OK" : "FAIL");
}

void app_main(void) {
    ESP_ERROR_CHECK(nvs_flash_init());
    ESP_ERROR_CHECK(esp_netif_init());
    ESP_ERROR_CHECK(esp_event_loop_create_default());
    ESP_ERROR_CHECK(esp_wifi_init(&(wifi_init_config_t)WIFI_INIT_CONFIG_DEFAULT()));
    ESP_ERROR_CHECK(esp_wifi_set_mode(WIFI_MODE_STA));
    ESP_ERROR_CHECK(esp_wifi_start());
    ESP_ERROR_CHECK(esp_wifi_set_channel(1, WIFI_SECOND_CHAN_NONE));

    ESP_ERROR_CHECK(esp_now_init());
    ESP_ERROR_CHECK(esp_now_register_send_cb(send_cb));

    esp_now_peer_info_t peer = {0};
    memcpy(peer.peer_addr, peer_mac, 6);
    peer.channel = 1;
    peer.encrypt = false;
    ESP_ERROR_CHECK(esp_now_add_peer(&peer));

    const char *msg = "Hello ESPNOW";
    while (1) {
        esp_err_t res = esp_now_send(peer_mac, (uint8_t *)msg, strlen(msg));
        if (res == ESP_OK) ESP_LOGI(TAG, "Message sent: %s", msg);
        else ESP_LOGE(TAG, "Send error: %s", esp_err_to_name(res));
        vTaskDelay(pdMS_TO_TICKS(1000));
    }
}

================================ 

receiver.c

============================= 

#include "esp_wifi.h"
#include "esp_now.h"
#include "esp_log.h"
#include "nvs_flash.h"

static const char *TAG = "ESPNOW_RECEIVER";

static void recv_cb(const esp_now_recv_info_t *info, const uint8_t *data, int len) {
    ESP_LOGI(TAG, "From %02X:%02X:%02X:%02X:%02X:%02X | Len: %d | Data: %.*s",
             info->src_addr[0], info->src_addr[1], info->src_addr[2],
             info->src_addr[3], info->src_addr[4], info->src_addr[5],
             len, len, data);
}

void app_main(void) {
    ESP_ERROR_CHECK(nvs_flash_init());
    ESP_ERROR_CHECK(esp_netif_init());
    ESP_ERROR_CHECK(esp_event_loop_create_default());
    ESP_ERROR_CHECK(esp_wifi_init(&(wifi_init_config_t)WIFI_INIT_CONFIG_DEFAULT()));
    ESP_ERROR_CHECK(esp_wifi_set_mode(WIFI_MODE_STA));
    ESP_ERROR_CHECK(esp_wifi_start());
    ESP_ERROR_CHECK(esp_wifi_set_channel(1, WIFI_SECOND_CHAN_NONE));

    ESP_ERROR_CHECK(esp_now_init());
    ESP_ERROR_CHECK(esp_now_register_recv_cb(recv_cb));

    ESP_LOGI(TAG, "Receiver ready");
}

================================= 

se si vuole mandare variabili di tipo differente nel pacchetto queste devono essere incluse in una struttura. La lunghezza dei pacchetti e' 250 bytes

================================= 

#include "esp_wifi.h"
#include "esp_now.h"
#include "esp_log.h"
#include "nvs_flash.h"
#include <string.h>

static const char *TAG = "ESPNOW_SENDER";

uint8_t peer_mac[] = {0x24, 0x6F, 0x28, 0xAA, 0xBB, 0xCC};

// Define your custom data structure
typedef struct {
    uint32_t id;
    float temperature;
    float humidity;
    int status;
    char label[16];
} sensor_packet_t;

static void send_cb(const uint8_t *mac_addr, esp_now_send_status_t status) {
    ESP_LOGI(TAG, "Send to %02X:%02X:%02X:%02X:%02X:%02X  status: %s",
             mac_addr[0], mac_addr[1], mac_addr[2],
             mac_addr[3], mac_addr[4], mac_addr[5],
             status == ESP_NOW_SEND_SUCCESS ? "OK" : "FAIL");
}

void app_main(void) {
    ESP_ERROR_CHECK(nvs_flash_init());
    ESP_ERROR_CHECK(esp_netif_init());
    ESP_ERROR_CHECK(esp_event_loop_create_default());
    ESP_ERROR_CHECK(esp_wifi_init(&(wifi_init_config_t)WIFI_INIT_CONFIG_DEFAULT()));
    ESP_ERROR_CHECK(esp_wifi_set_mode(WIFI_MODE_STA));
    ESP_ERROR_CHECK(esp_wifi_start());
    ESP_ERROR_CHECK(esp_wifi_set_channel(1, WIFI_SECOND_CHAN_NONE));

    ESP_ERROR_CHECK(esp_now_init());
    ESP_ERROR_CHECK(esp_now_register_send_cb(send_cb));

    esp_now_peer_info_t peer = {0};
    memcpy(peer.peer_addr, peer_mac, 6);
    peer.channel = 1;
    peer.encrypt = false;
    ESP_ERROR_CHECK(esp_now_add_peer(&peer));

    sensor_packet_t pkt = {0};
    pkt.id = 1;

    while (1) {
        pkt.temperature = 22.5 + (esp_random() % 100) / 10.0;
        pkt.humidity = 60.0 + (esp_random() % 100) / 10.0;
        pkt.status = esp_random() % 2;
        strcpy(pkt.label, "Node_A");

        esp_err_t res = esp_now_send(peer_mac, (uint8_t *)&pkt, sizeof(pkt));
        if (res == ESP_OK)
            ESP_LOGI(TAG, "Sent packet: id=%lu T=%.1f H=%.1f status=%d",
                     pkt.id, pkt.temperature, pkt.humidity, pkt.status);
        else
            ESP_LOGE(TAG, "Send error: %s", esp_err_to_name(res));

        pkt.id++;
        vTaskDelay(pdMS_TO_TICKS(1000));
    }
}

==================== 

#include "esp_wifi.h"
#include "esp_now.h"
#include "esp_log.h"
#include "nvs_flash.h"
#include <string.h>

static const char *TAG = "ESPNOW_RECEIVER";

typedef struct {
    uint32_t id;
    float temperature;
    float humidity;
    int status;
    char label[16];
} sensor_packet_t;

static void recv_cb(const esp_now_recv_info_t *info, const uint8_t *data, int len) {
    if (len != sizeof(sensor_packet_t)) {
        ESP_LOGW(TAG, "Invalid packet size: %d", len);
        return;
    }

    sensor_packet_t pkt;
    memcpy(&pkt, data, sizeof(pkt));

    ESP_LOGI(TAG, "From %02X:%02X:%02X:%02X:%02X:%02X | id=%lu | T=%.1f | H=%.1f | status=%d | label=%s",
             info->src_addr[0], info->src_addr[1], info->src_addr[2],
             info->src_addr[3], info->src_addr[4], info->src_addr[5],
             pkt.id, pkt.temperature, pkt.humidity, pkt.status, pkt.label);
}

void app_main(void) {
    ESP_ERROR_CHECK(nvs_flash_init());
    ESP_ERROR_CHECK(esp_netif_init());
    ESP_ERROR_CHECK(esp_event_loop_create_default());
    ESP_ERROR_CHECK(esp_wifi_init(&(wifi_init_config_t)WIFI_INIT_CONFIG_DEFAULT()));
    ESP_ERROR_CHECK(esp_wifi_set_mode(WIFI_MODE_STA));
    ESP_ERROR_CHECK(esp_wifi_start());
    ESP_ERROR_CHECK(esp_wifi_set_channel(1, WIFI_SECOND_CHAN_NONE));

    ESP_ERROR_CHECK(esp_now_init());
    ESP_ERROR_CHECK(esp_now_register_recv_cb(recv_cb));

    ESP_LOGI(TAG, "Receiver ready");
}
 

 

 

Nessun commento:

Posta un commento

Kernel Panic QrCode

 In tanti anni ho visto qualche kernel panic, ma in questo formato non mi era mai successo    la cosa curiosa che al riavvio successivo ness...