Использование espnow и wifi ESP8266

Пытался переделать для ESP8266 код для ESP32 , перебор каналов роутера .
Код для ESP32:

bool channelFound = false;
uint8_t channel = 1;

void onDataSent(const uint8_t* mac_addr, esp_now_send_status_t status) {
  if (!channelFound && status != ESP_NOW_SEND_SUCCESS) { 
    tryNextChannel();
  }
  else {
    channelFound = true;
  }
}

void tryNextChannel() {
  channel = channel % 13 + 1;
  esp_wifi_set_promiscuous(true);
  esp_wifi_set_channel(channel, WIFI_SECOND_CHAN_NONE);
  esp_wifi_set_promiscuous(false);
  Serial.println(channel);
}

Делаю так для ESP8266:

bool channelFound = false;
uint8_t channel = 1;	
	void tryNextChannel() 
{
    channel = channel % 13 + 1;
    wifi_promiscuous_enable(1);
    wifi_set_channel(channel);
    wifi_promiscuous_enable(0);
}
void OnDataSent(uint8_t* mac_addr, uint8_t sendStatus) 
{
    if (!channelFound && sendStatus != 1) // вместо 1
    {
        tryNextChannel();
    }
    else 
    {
        channelFound = true;
    }
}

В ESP8266 не нашел аналогичное WIFI_SECOND_CHAN_NONE.

В SDK есть:"ESP-NOW отправляет обратный вызов:
void esp_now_send_cb_t(u8 *mac_addr, u8 status)
Параметр:
u8 *mac_addr: MAC-адрес целевого устройства
u8 status: статус отправки пакета ESP-NOW.
mt_tx_status {

MT_TX_STATUS_OK = 0,

MT_TX_STATUS_FAILED,

}
Статус будет обновлен до MT_TX_STATUS_OK, если ESP-NOW отправит пакет.
успешно."
Но не могу его правильно вставить.
Если ставлю единицу перебирает постоянно, а после успешной передачи должен остановиться, если ставлю MT_TX_STATUS_OK - ошибка компиляции.

Непонятно причём тут роутер.
Для 8266, вроде, нет смысла каналы esp-now пепебирать, он на одном вещает.

Когда работает espnow и WiFi (сервер) канал передатчика должен быть равен каналу, который выбирает роутер, иначе не будет передачи.

Ну, вобщем, в 8266 с каналами для esp-now маета какая-то. Я год назад ковырялся, в конце концов плюнул и на ESP32 перелез.

Может на досуге вернусь, посмотрю RTL-SDR-ом, если он захватит, действительно ли в 8266 каналы меняются при работе в ESP-NOW.

И нахрена тут перебор? Прочитай доку, найди как определить канал роутера, и используй его.

Передатчик , который находится за пределами действия роутера не может сканировать его. Когда находится в зоне wifi, проблем то нет.
Тут только перебор.
Если роутер настроить конкретно на канал, тогда да, прописал и всё.

Чего ты там собрался перебирать если ты находишься вне зоны сигнала? Бред какой.

Это не бред! Пока канал передатчика не будет такой же как и роутера, есп приемник не получит пакет данных.Это не я придумал! Espnow так работает.
Когда я запускаю код просто переборкой, у меня в данный момент, только когда канал равен 2 пакет проходит, просто программа так и всё 13 каналов перебирает, хотелось бы после удачной передачи остановить перебор.
Лучше с этим помогите.

Да, нужно менять, если использовать сеть wifi , для вывода принятых данных куда нибудь.
Если без него использовать , то это не нужно делать, это касается и esp32 и esp8266.

Добрый день!
Сам с этой проблемой бился пару недель!
Видимо, реализация на Arduino сильно отличается от того, что написано в pdf для ESP. То, что каналы для ESP-NOW и WiFi должны быть одинаковы - это да, но, на практике столкнулся неприятным глюком, о котором пишете Вы.
Моя ситуация: головной контроллер подключен к WiFi и работает на 10 канале. Выносной датчик при сопряжении с головным устройством не знает ни канала, ни MAC-адреса головного устройства. Головное устройство перевожу в режим PAIRING. Начинаю перебор каналов на сопрягаемом устройстве. По теории, когда каналы совпадут, то мы получим успешно отправленную передачу. Но, хрен там!

  1. При переборе каналов в 99% процентов случаев головное устройство уже получает посылку от сопрягаемого на 9 канале, в 1% случаев на 8 канале. Если тут же остановить перебор, то получим разные каналы и в дальнейшем получим потерю пакетов больше 95%. Как это работает при сопряжении - я не понимаю.
  2. Головное отправляет ответ, но, сопрягаемое в 20% игнорирует эту посылку.
    Я специально менял каналы роутера, проверял сканером весь диапазон WiFi на занятость каналов. Но, я живу в частном секторе и соседских сетей очень мало и наши каналы разнесены достаточно далеко. Так что помеху от соседей можно исключить.
    В итоге, решил проблему так:
  3. Оба устройства переводятся в режим PAIR_REQUESTED (просто переменная состояния в скетче). В этом режиме головное принимает пакеты от всех, кто к нему постучится, но, пакет должен быть той же структуры, что и головного (чтобы кто-то левый не прицепился, можно добавить и шифрование канала ESP для 100% уверенности, но, пока сделал так), а сопрягаемое устройство на каждом канале шлет пакет с кодом сопряжения (paramName = PAIRING, paramValue = DEVICE_ROLE):
#define DEVICE_ROLE 101 // Тип устройства: 100 = только датчик температуры, 101 = датчик с экраном, 102 = уличный датчик
enum PairingStatus {
  PAIR_REQUEST,        // Требуется режим сопряжения
  PAIR_REQUESTED,      // Режим спаривания запущен
  PAIR_CHANGECHANNEL,  // Требуется смена радиоканала
  PAIR_PAIRED,         // Спаривание установлено
  PAIR_NOTPAIRED,      // Спаривание не получилось
};
// Структура данных для обмена шлюза с выносными датчиками/панелями и
// должна совпадать с оной на принимающей стороне
// Направление потока paramReadDirection для передачи данных в шлюз:
// false - запрос на чтение параметра paramName из шлюза
// true - записать значение paramValue параметра paramName в шлюз 
typedef struct {
  uint8_t paramName;  // Наименование параметра из нумератора
  uint16_t paramValue;           // Значение параметра
  uint8_t workChannel;           // Текущий канал шлюза
  bool paramReadDirection;       // false - чтение из шлюза в пульт, true - запись из пульта в шлюз
} struct_message;

struct_message ESP_sendData, ESP_recvData;  // Создаем структуру сообщения

Если головное устройство получило пакет, то сохраняет у себя МАС-адрес отправителя, его тип по DEVICE_ROLE и отправляет обратно пакет с кодом сопряжения и своим каналом. И не прекращает сопряжение, пока выносное устройство не подтвердит сопряжение вместо DEVICE_ROLE числом 255. Тогда сопряжение считается выполненным и оба устройства переводятся в режим PAIR_PAIRED и работают в обычном режиме. Но, при этом головное устройство в каждой посылке подтверждает свой канал. Если выносное устройство видит, что канал сменился или от головного долго не приходят данные, то начинает перебор каналов и смотрит, на каком канале ответил головной контроллер (лог выносного устройства при потере связи с головным):

Подождали. Меняем канал
Превышен таймаут ожидания ответа. Отключаю ESP-NOW
Ищу новый канал связи: 09
Устанавливаем канал. Включаем WiFi
Начало инициализации ESP-NOW на 09 канале
Регистрируем шлюз на новом канале
Регистрация шлюза прошла успешно. 50-02-91-E0-E6-67
Отправка paramName: 127; paramValue: 0, Direction: ReadFromGW

Што-то мне такое помнится, что espnow в 8266 вообще на одном канале работал, какой ему не задай.

Число перебираемых каналов можно вообще сократить до трех штук. У меня Ubiquiti всегда из трех выбирает (вроде как 1, 6, 11). А они не дураки…

Да, похоже на правду! Скорее всего фильтры каналов по другому работают. Хотя, кто этих китайцев поймёт :slight_smile: