arduino-esp32
arduino-esp32 copied to clipboard
unicast ESP-NOW works in SoftAP but stops working when actually connected to an AP
Board
Wemos ESP32-C3
Device Description
no other hardware attached
Hardware Configuration
no other hardware attached
Version
v2.0.14
IDE Name
Arduino IDE 1.8.19
Operating System
Ubuntu
Flash frequency
80
PSRAM enabled
yes
Upload speed
921600
Description
When the ESP32 is connected to an AP, it stops receiving unicast ESP-NOW messages. It still receives broadcast messages.
I have manually checked/set the channel of my AP with my setup.
My original code was written toward all ESP8266's and works, but I decided to port the RX side to an ESP32-C3.
Right now I'm transmitting from ESP8266's to an ESP32-C3 and unicast in connected STA mode seems broken.
Sketch
I've placed my stripped down testcase in a repo:
https://github.com/goatzillax/espnow_crosstest
Debug Message
none
Other Steps to Reproduce
My TX side is an ESP8266, and the RX side is an ESP32-C3. The RX side seems broken.
I have checked existing issues, online documentation and the Troubleshooting Guide
- [X] I confirm I have checked existing issues, online documentation and Troubleshooting guide.
ESP-NOW works only on the channel that the radio is currently on. When you have set WiFi to enable STA and you are connected to a network, the radio's channel is equal to that of the AP that you have connected to. So ESP-NOW is working, but because the Radio have changed it's channel, you are probably listening on the wrong one.
What wording do I need to use to communicate that I have attempted every check possible to make sure they are on the correct channel even in STA mode?
My full app works on an 8266. The RX side connects as STA, and the TX side scans all wifi channels until it finds the correct one. When the RX is moved over to the ESP32-C3, it never manages to find a working channel.
I only stripped the test case down to make it easier to review.
Let me try saying the same thing in a different way.
The TX is set to channel 5 with the unicast address of the receiver. Here is the output of the RX with bogus STA credentials so it falls back to SoftAP mode and I press the reset button on the transmitter.
[ 6864][D][WiFiGeneric.cpp:1039] _eventCallback(): Arduino Event: 5 - STA_DISCONNECTED
[ 6864][W][WiFiGeneric.cpp:1061] _eventCallback(): Reason: 201 - NO_AP_FOUND
[ 6867][D][WiFiGeneric.cpp:1085] _eventCallback(): WiFi AutoReconnect Running
[ 9705][D][WiFiGeneric.cpp:1039] _eventCallback(): Arduino Event: 5 - STA_DISCONNECTED
[ 9705][W][WiFiGeneric.cpp:1061] _eventCallback(): Reason: 201 - NO_AP_FOUND
[ 9708][D][WiFiGeneric.cpp:1085] _eventCallback(): WiFi AutoReconnect Running
[ 11921][D][WiFiGeneric.cpp:1039] _eventCallback(): Arduino Event: 11 - AP_STOP
[ 11922][D][WiFiGeneric.cpp:1039] _eventCallback(): Arduino Event: 10 - AP_START
192.168.4.1
Wi-Fi Channel: 5
msg received
So that works. 192.168.4.1 is the SoftAP address.
I reflash the RX with correct wifi creds and it connects to my network, and I press the reset button on the transmitter.
MAC Address: xx:xx:xx:xx:xx:xx
192.168.2.155
Wi-Fi Channel: 5
And that's it. I don't get a message received.
Here is the nmcli dump from the Linux machine.
IN-USE BSSID SSID MODE CHAN RATE SIGNAL BARS SECURITY
xx:xx:xx:xx:xx:xx ESP_xxxxxx Infra 5 135 Mbit/s 100 ▂▄▆█ --
* xx:xx:xx:xx:xx:xx xxxxxx Infra 5 130 Mbit/s 94 ▂▄▆█ WPA1 WPA2
The second AP is of course the one I'm connecting to.
To recap:
- The TX is unicast and hardcoded to wifi channel 5
- The RX self reports as being on wifi channel 5 in STA mode
- Outside command line utilities confirm everything is on channel 5
- The same idea works on ESP8266
- The same code works in SoftAP on ESP32
So does it sound like I don't have the right channel?
Can you try to also have AP enabled, while STA is connected?
Yes. I just modified my code to have it run WiFi.disconnect() upon button press.
When it first boots up, it has both AP and STA configured and connected. No messages are ever received from the TX.
MAC Address: xx:xx:xx:xx:xx:xx
192.168.2.155
192.168.4.1
Wi-Fi Channel: 5
I can ping them from another host after connecting to each one.
$ ping 192.168.2.155
PING 192.168.2.155 (192.168.2.155) 56(84) bytes of data.
64 bytes from 192.168.2.155: icmp_seq=1 ttl=255 time=159 ms
^C
--- 192.168.2.155 ping statistics ---
1 packets transmitted, 1 received, 0% packet loss, time 0ms
rtt min/avg/max/mdev = 158.801/158.801/158.801/0.000 ms
$ ping 192.168.4.1
PING 192.168.4.1 (192.168.4.1) 56(84) bytes of data.
64 bytes from 192.168.4.1: icmp_seq=1 ttl=255 time=2.69 ms
64 bytes from 192.168.4.1: icmp_seq=2 ttl=255 time=1.16 ms
^C
--- 192.168.4.1 ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 1002ms
rtt min/avg/max/mdev = 1.162/1.927/2.693/0.765 ms
Once I press the button, the STA disconnects, the AP stays running, and now it receives messages.
disconnecting WiFi
[ 15831][V][WiFiGeneric.cpp:362] _arduino_event_cb(): STA Disconnected: SSID: xxxxxxxxxx, BSSID: xx:xx:xx:xx:xx:xx, Reason: 8
[ 15831][D][WiFiGeneric.cpp:1039] _eventCallback(): Arduino Event: 5 - STA_DISCONNECTED
[ 15838][W][WiFiGeneric.cpp:1061] _eventCallback(): Reason: 8 - ASSOC_LEAVE
msg received
msg received
[ 58978][V][WiFiGeneric.cpp:407] _arduino_event_cb(): AP Station Connected: MAC: xx:xx:xx:xx:xx:xx, AID: 1
[ 58979][D][WiFiGeneric.cpp:1039] _eventCallback(): Arduino Event: 12 - AP_STACONNECTED
[ 59026][V][WiFiGeneric.cpp:421] _arduino_event_cb(): AP Station IP Assigned:192.168.4.2
[ 59027][D][WiFiGeneric.cpp:1039] _eventCallback(): Arduino Event: 14 - AP_STAIPASSIGNED
Looking over the tests/examples:
- The tests/examples only strictly test a. Channel 1, which is the default anyways so that doesn't make a lot of sense b. Slave operating as SoftAP
- The tests/examples don't even keep up with some of your own API breakages, which kind of hints at them not even being run
And again, this functionality works on the ESP8266 so this appears to be a regression.
The tests should sweep the channels. I believe this can be automated with no additional hardware and minor code tweaks, and it will likely more closely resemble a real use case.
One option would be to post an issue in ESP-IDF's repository and see if they have any idea. Arduino 2.0.14 runs on ESP-IDF 4.4.6. If you install from github, then master is on ESP-IDF v5.1.2.
Yes, I found multiple issues on the ESP-IDF repository like this one:
https://github.com/espressif/esp-idf/issues/10341
Which has been open for nearly a year. There was another one but I can't seem to find it again.
Given what I've seen of the testcases, it's likely that the functionality is still quite broken because there's no testing, and the testcase won't even compile due to API breakage.
@me-no-dev I am not sure the idf version in Arduino IDE 1.8.19, this issue should be fixed in IDF 5.0. @goatzillax if you want to use the IDF 4.3 / 4.4 ,you can inir the espnow first and then connect to an AP.
If fixed in 5.0, then user can try the latest Alpha/RC of ESP32 Arduino v3.0.0
Hello all, here there is a working code, it have both transmitter and receiver, running on the ESP32, to set the module as WIFI_STATION and connect to an AP, must be configured as:
WiFi.mode(WIFI_AP_STA );
As the ESP-Now IDF said: it must be set as the channel that station or softap is on.
The transmitter have a search channel routine to find the receiver channel,
Tested on a ESP32-C3 (revision v0.4). Arduino IDE 2.3.2, v2.0.14 (ESP-IDF v4.4.6).
Note:
Change:
ESP_IF_WIFI_STA
by this:
WIFI_IF_STA
in both code, Transmitter and Receiver.
Enjoy coding !
Jose Luis