- 
                Notifications
    You must be signed in to change notification settings 
- Fork 1.1k
Description
The high-level problem is that on my AP, under some power modes, when running a http server, the RPI eventually disconnects and becomes unreachable. It never recovers when this happens. I have reproduced this a lot using micropython, and more recently using this example from the pico-examples repository.
Port, board and/or hardware
RP2040 on Raspberry Pi Pico W
Reproduction
- Clone https://github.com/edmcman/rpi-temp-server/tree/debug
- Edit SSID/password in main.py
- Run pipkin --port /dev/ttyACM0 install -r requirements.txt
- Edit the IP address in test.bash to batch the Pico W's IP
- Run test.bash a bunch of times.
Expected behaviour
The test.bash script tests whether the web server remains accessible after progressively longer periods of times with no requests. It is expected that the web server will remain available and the script will print "Test succeeded".
Observed behaviour
When run 20 times with a limit of 2048 second periods, 8 out of the 20 runs failed, meaning that the web server became inaccessible. Here is a breakdown of the power modes during failures:
fgrep -l -R Fail *.log | xargs fgrep Random | awk '{print $4}' | sort | uniq -c
      6 network.WLAN.PM_POWERSAVE
      2 None
And the overall distribution of tested pm values:
      2 0xa11140
      8 network.WLAN.PM_NONE
      1 network.WLAN.PM_PERFORMANCE
      7 network.WLAN.PM_POWERSAVE
      3 None
I am not sure why they are so uneven.
Here is a zip file of my collected logs:
logs-2048.zip
Other Information
When the Pico W becomes inaccessible, the logs contain the following messages repeated very often:
[ 2509685] ASYNC(0000,49,0,0,0)
I believe the 49 message indicates crypto verification failure. Under normal operation, it appears to be correlated with PSK_SUP messages. But as soon as it starts repeating by itself the Pico W is offline.
Also, an asynchronous task that calls WLAN.isconnected() and WLAN.status() shows that the Pico W is connected, even though it does not seem to be:
[snip]
[ 3505634] ASYNC(0000,49,0,0,0)
[ 3507681] ASYNC(0000,49,0,0,0)
[ 3508397] ASYNC(0000,49,0,0,0)
Still checking Wi-Fi connection...
Debug: connected: True status: 3
Actual PM: 0xa11142
High level problem
I think that under some power management modes, the Pico is missing rekeying and disassociate messages. The only way to detect that this situation has happened is to detect crypto failures and rejoin the network. I believe the 49 messages are crypto failures.
One way forward is to respond to crypto failures by rejoining the network, like most other wifi implementations. I did file an issue with the cyw43-driver, since it seems to me like the driver ought to be handling this.
Another way forward might be to change the default power mode in pico-sdk. Here, most of my testing is micropython-centric. I've found the infinite disconnection to happen during both the micro-python default power mode, and the power mode setting of 0xa11140 suggested in the Connecting to the Internet document.
Outside of micropython, the default power mode for the pico_w httpd example disconnects.  I think this uses PM_PERFORMANCE from perusing the source code, but I am not sure.
Happy to help in any way that I can. I have enough information that I can simply work around the problem, but I'd prefer to see it fixed so that the next person doesn't have to deal with this.