// // Created by nano on 8/23/26. // #ifndef MCU_CODE_WIRELESS_COMMS_H #define MCU_CODE_WIRELESS_COMMS_H #include "esp_now.h" #include "nvs_flash.h" #include "uart_serial.h" #include "freertos/FreeRTOS.h" #include "freertos/task.h" #define PAYLOAD_SIZE 1 #define ESPNOW_PMK "pmk1234567890123" // ESPNOW primary master for the example to use. The length of ESPNOW primary master must be 16 bytes. #define ESPNOW_LMK "lmk1234567890123" // ESPNOW local master for the example to use. The length of ESPNOW local master must be 16 bytes. #define ESPNOW_SEND_COUNT 1 // range 1-65535; Total count of unicast ESPNOW data to be sent. #define ESPNOW_SEND_DELAY 0 // range 0-65535; default 1000; Delay between sending two ESPNOW data, unit: ms. #define ESPNOW_SEND_LEN (2 + PAYLOAD_SIZE) // range 10-1470; Length of ESPNOW data to be sent, unit: byte. #define ESPNOW_CHANNEL 11 #define ESPNOW_QUEUE_SIZE 512 #define CONFIG_ESPNOW_ENABLE_LONG_RANGE #define CONFIG_ESPNOW_WIFI_MODE_STATION // #define CONFIG_ESPNOW_ENABLE_POWER_SAVE #ifdef CONFIG_ESPNOW_WIFI_MODE_STATION #define ESPNOW_WIFI_MODE WIFI_MODE_STA #define ESPNOW_WIFI_IF WIFI_IF_STA #else #define ESPNOW_WIFI_MODE WIFI_MODE_AP #define ESPNOW_WIFI_IF WIFI_IF_AP #endif #define IS_BROADCAST_ADDR(addr) (memcmp(addr, s_broadcast_mac, ESP_NOW_ETH_ALEN) == 0) enum { ESPNOW_DATA_BROADCAST, ESPNOW_DATA_UNICAST, ESPNOW_DATA_MAX, }; typedef enum { ESPNOW_SEND_CB, ESPNOW_RECV_CB, } espnow_event_id_t; typedef struct { uint8_t mac_addr[ESP_NOW_ETH_ALEN]; esp_now_send_status_t status; } espnow_event_send_cb_t; typedef struct { uint8_t mac_addr[ESP_NOW_ETH_ALEN]; uint8_t *data; int data_len; } espnow_event_recv_cb_t; typedef union { espnow_event_send_cb_t send_cb; espnow_event_recv_cb_t recv_cb; } espnow_event_info_t; /* When ESPNOW sending or receiving callback function is called, post event to ESPNOW task. */ typedef struct { espnow_event_id_t id; espnow_event_info_t info; } espnow_event_t; /* User defined field of ESPNOW data in this example. */ typedef struct { uint16_t crc; //CRC16 value of ESPNOW data. uint8_t payload[PAYLOAD_SIZE]; //Real payload of ESPNOW data. } __attribute__((packed)) espnow_data_t; /* Parameters of sending ESPNOW data. */ typedef struct { int len; //Length of ESPNOW data to be sent, unit: byte. uint8_t *buffer; //Buffer pointing to ESPNOW data. uint8_t dest_mac[ESP_NOW_ETH_ALEN]; //MAC address of destination device. } espnow_send_param_t; typedef struct espnow_task_params_t { espnow_send_param_t *send_param; uart_serial uart; } espnow_task_params_t; class wireless_comms { public: wireless_comms(int wifi_channel = ESPNOW_CHANNEL) { // Initialize NVS esp_err_t ret = nvs_flash_init(); if (ret == ESP_ERR_NVS_NO_FREE_PAGES || ret == ESP_ERR_NVS_NEW_VERSION_FOUND) { ESP_ERROR_CHECK( nvs_flash_erase() ); ret = nvs_flash_init(); } ESP_ERROR_CHECK( ret ); wifi_init(wifi_channel); espnow_init(wifi_channel); } void set_dest_mac(const uint8_t dest_mac[ESP_NOW_ETH_ALEN]); void create_rtos_task(const uart_serial &uart) const { auto *task_params = new espnow_task_params_t{.send_param = send_param, .uart = uart}; // heap, outlives this call xTaskCreate(espnow_task, "espnow_task", 2048, task_params, 4, NULL); // note: task_params is intentionally leaked for the task's lifetime; // free it inside espnow_task if the task can ever exit } static esp_err_t add_peer(const uint8_t dest_mac[ESP_NOW_ETH_ALEN]); static void delete_peer(const uint8_t dest_mac[ESP_NOW_ETH_ALEN]); static esp_err_t send_byte(uint8_t data) ; private: espnow_send_param_t * send_param = nullptr; static void wifi_init(int channel); static void espnow_send_callback(const esp_now_send_info_t *tx_info, esp_now_send_status_t status); static void espnow_recv_callback(const esp_now_recv_info_t *recv_info, const uint8_t *data, int len); static int espnow_data_parse(uint8_t *data, uint16_t data_len); static void espnow_send_data_prepare(espnow_send_param_t *send_param); esp_err_t espnow_init(int wifi_channel); static void espnow_deinit(espnow_send_param_t *send_param); static void espnow_task(void *pvParameter); }; #endif //MCU_CODE_WIRELESS_COMMS_H