espressif / arduino-esp32

Arduino core for the ESP32
GNU Lesser General Public License v2.1
13.44k stars 7.38k forks source link

Wifi disconnects after some time, reconnection fails #3362

Closed fpiernas closed 4 years ago

fpiernas commented 4 years ago

Hardware:

Board: Wemos D1 R32 Core Installation version: Don't know IDE name: Arduino IDE Flash Frequency: 80Mhz PSRAM enabled: no Upload Speed: 921600 Computer OS: Windows 10

Description:

I have a Wemos D1 R32 to open the garage door. It has been working perfectly 24/7 for over a year and it's still working fine.

I bought another Wemos D1 R32 for a project with some relays to turn lights on and off, and this one is giving me problems.

It's connected to the same router as the other board, using a static IP. On boot, it connects and works fine, I can tell this by doing a 1000 packets Ping, no packets lost. But after some hours, packets start to get lost, more and more, until the code detects the wifi connection is lost and tries to reconnect, but fails.

The interesting thing is that the connection and reconnection code is the same I'm using in the first board that works perfect, but somehow it's failing on the second board.

I also noticed that my router says that the board is connected but not associated nor authorized. The wifi key is a 20 character alfanumeric WPA2 password. The board that works is shown as asociated and authorized.

imgur.com/a/02H8xl6

Sketch:

(This is not the full sketch since it's very long, with UDP, rotary encoder and OLED codes, I will post what I think is giving the problems)

#include "WiFi.h"

unsigned int reconnect_count=0;
void setup() {
    IPAddress local_IP(192, 168, 1, 9);
    IPAddress gateway(192, 168, 1, 1);
    IPAddress subnet(255, 255, 255, 0);
    IPAddress primaryDNS(8, 8, 8, 8);   //optional
    IPAddress secondaryDNS(1, 1, 1, 1); //optional
    if (!WiFi.config(local_IP, gateway, subnet, primaryDNS, secondaryDNS)) {
      Serial.println("STA Failed to configure");
    }
    WiFi.begin(ssid, password);
    while(1) {
        delay(5000);
        WiFi.begin(ssid, password);
        if(WiFi.waitForConnectResult() == WL_CONNECTED) break;
        else Serial.println("WiFi Failed");
    }
    //Do other stuff
}

void loop() {

    delay(500);
    if(millis()-reconnect_count >= 120000)
    {
           if(WiFi.waitForConnectResult() != WL_CONNECTED)
           {
                 while(1) 
                 {
                      delay(5000);
                      WiFi.begin(ssid, password);
                      if(WiFi.waitForConnectResult() == WL_CONNECTED) break;
                      else Serial.println("WiFi Failed");
                  }
            }
           reconnect_count=millis();
    }
    //Do other stuff
}
lnrobby commented 4 years ago

I am having a similar problem. I am testing by changing the SSID on my router and it fails to reconnect after leaving for a good while (over 10 hours maybe.) The app is sending data from a queue to an MQTT server. It is running on a Lolin D32 and is repeatable on more than one device. The app is built in Arduino IDE.

I am not doing any sort of wifi reconnect as I am expecting it to reconnect automatically. Maybe this is where I am going wrong. if (client.connect(DeviceMac, iniSpiff.MQTTUSER, iniSpiff.MQTTPASSWORD)) {

I have had the problem on version V1.0.4 and before this version V1.0.2 (I upgraded to see if it went away). This is what I get as output (set as Core Debug Level Verbose)

11:52:20.244 -> Attempting to reconnect in reconnect code..- Items in Queue 11:52:20.244 -> 20 11:52:20.244 -> A4:CF:12:12:65:B4 11:52:20.244 -> [V][ssl_client.cpp:56] start_ssl_client(): Free internal heap before TLS 253560 11:52:20.244 -> [V][ssl_client.cpp:58] start_ssl_client(): Starting socket 11:52:24.253 -> [E][WiFiGeneric.cpp:654] hostByName(): DNS Failed for m24.cloudmqtt.com 11:52:24.253 -> [E][WiFiClientSecure.cpp:132] connect(): start_ssl_client: -1 11:52:24.253 -> [V][ssl_client.cpp:248] stop_ssl_socket(): Cleaning SSL connection. 11:52:25.244 -> Attempting to reconnect in reconnect code..- Items in Queue 20

Pressing the reset button works and the device starts correctly.

I have now written a really simple sketch that just connects to wifi and then tries to connect to a url. This sketch fails just the same as above, again with no automatic reconnect.

09:58:50.970 -> [V][ssl_client.cpp:56] start_ssl_client(): Free internal heap before TLS 264656 09:58:50.970 -> [V][ssl_client.cpp:58] start_ssl_client(): Starting socket 09:58:54.970 -> [E][WiFiGeneric.cpp:654] hostByName(): DNS Failed for webhook.site 09:58:54.970 -> [E][WiFiClientSecure.cpp:132] connect(): start_ssl_client: -1 09:58:55.005 -> [V][ssl_client.cpp:248] stop_ssl_socket(): Cleaning SSL connection. 09:58:59.977 -> [V][ssl_client.cpp:248] stop_ssl_socket(): Cleaning SSL connection. 09:58:59.977 -> Connecting to webhook.site

21/10/19 17:36 Tried a really simple app that just connects t othe wifi. I then changed the SSID on the router and got 6:39:40.828 -> [W][WiFiGeneric.cpp:353] _eventCallback(): Reason: 2 - AUTH_EXPIRE 16:39:40.828 -> [WiFi-event] event: 5 16:39:40.828 -> Disconnected from WiFi access point 16:39:40.828 -> WiFi lost connection. Reason: 2 16:39:42.858 -> [D][WiFiGeneric.cpp:337] _eventCallback(): Event: 5 - STA_DISCONNECTED 16:39:42.858 -> [W][WiFiGeneric.cpp:353] _eventCallback(): Reason: 201 - NO_AP_FOUND 16:39:42.858 -> [WiFi-event] event: 5 16:39:42.858 -> Disconnected from WiFi access point 16:39:42.858 -> WiFi lost connection. Reason: 201

I then brought the SSID back and it connected ok.

16:39:54.814 -> [D][WiFiGeneric.cpp:337] _eventCallback(): Event: 4 - STA_CONNECTED 16:39:54.849 -> [WiFi-event] event: 4 16:39:54.849 -> Connected to access point 16:39:54.849 -> [D][WiFiGeneric.cpp:337] _eventCallback(): Event: 7 - STA_GOT_IP 16:39:54.849 -> [D][WiFiGeneric.cpp:381] _eventCallback(): STA IP: 192.168.171.126, MASK: 255.255.255.0, GW: 192.168.171.1 16:39:54.849 -> .168.171.126 16:39:54.849 -> WiFi connected 16:39:54.849 -> IP address: 16:39:54.849 -> 192.168.171.126

I then dropped the SSID and got this

16:40:34.166 -> [D][WiFiGeneric.cpp:337] _eventCallback(): Event: 5 - STA_DISCONNECTED 16:40:34.166 -> [W][WiFiGeneric.cpp:353] _eventCallback(): Reason: 7 - NOT_ASSOCED 16:42:34.154 -> [D][WiFiGeneric.cpp:337] _eventCallback(): Event: 8 - STA_LOST_IP 16:42:34.154 -> [WiFi-event] event: 8 16:42:34.154 -> Lost IP address and IP address is reset to 0

Nothing at all since then, so it appears to be hung.

maxdd commented 4 years ago

Well known issue on Arduino. The only solution as of today is to move to esp-idf

fpiernas commented 4 years ago

Well known issue on Arduino. The only solution as of today is to move to esp-idf

I forgot about this thread. The issue kind of self solved somehow and the Wemos D1 R32 with its ESP32 now works fine and reconnections work after a reset or blackout.

Edit: the problem is back xD This is what happens when a problem self solves and you don't know what caused it.

Again my router shows the ESP32 MAC address but it's marked as not associated and not authorized.

I still don't know what the problem was. The distance to the router is the same, I also erased the flash before updating sketches as usual, but it self solved.

fpiernas commented 4 years ago

So I changed the sketch and now I call this function to connect on boot and reconnect on connection lost:

void recon() { WiFi.disconnect(true); WiFi.mode(WIFI_STA); IPAddress local_IP(192, 168, 1, 10); IPAddress gateway(192, 168, 1, 1); IPAddress subnet(255, 255, 255, 0); IPAddress primaryDNS(8, 8, 8, 8); //optional IPAddress secondaryDNS(1, 1, 1, 1); //optional if (!WiFi.config(local_IP, gateway, subnet, primaryDNS, secondaryDNS)){ Serial.println("Error WIFI."); delay(1000); } while(true) { WiFi.begin(ssid, password); delay(10000); if(WiFi.status() == WL_CONNECTED) break;
else Serial.println("WiFi Failed"); } return; }

Fun thing about it, the ESP32 is now completely unable to connect. It attempts reconnections when status returns not connected, but it won't connect. There are moments where that function finishes because it has managed to reconnect, only that it hasn't. On my router page I can see that it's not connected.

Some of you may say the problem is the router, but as I said in the first post, there is another ESP32 connected to that router and it has been working great for more than a year.

These last weeks I have been reading a lot about this issue. I don't know what is failing on this ESP32 that it's not on the other. Is it the rotary enconder library? The pin14 I'm using? (I read somewhere that pin14 cannot be used for ADC if wifi's on, but I'm using it as digital output.

I also doubt that's the issue because this ESP32 could stay working for several days and after each power cycle it got worse.

lnrobby commented 4 years ago

Well known issue on Arduino.

Hi maxdd, can you explain a bit more, I have searched and can't find much about it being a well known issue. Thanks

maxdd commented 4 years ago

Hello Inrobby, you just can have a look at the open issue by tiping "reconnection"

https://github.com/espressif/arduino-esp32/issues/2127 https://github.com/espressif/arduino-esp32/issues/1464 https://github.com/espressif/arduino-esp32/issues/653 https://github.com/espressif/arduino-esp32/issues/307

The underline problem here is that somehow the WiFi library is not there yet for esp32. The only working solution i've found to make it works (and believe i've tried a lot) is to make use of the following code

static void configureWiFi()
{
    WiFi.persistent(false);
    WiFi.disconnect(true);
    WiFi.mode(WIFI_OFF);
    WiFi.mode(WIFI_STA);
    WiFi.config(INADDR_NONE, INADDR_NONE, INADDR_NONE);

    WiFi.onEvent([](WiFiEvent_t event, WiFiEventInfo_t info) {
        Serial.print("WiFi connected. IP: ");
        Serial.println(IPAddress(info.got_ip.ip_info.ip.addr));
        WiFiConnected = true;
    },
        WiFiEvent_t::SYSTEM_EVENT_STA_GOT_IP);

    WiFi.onEvent([](WiFiEvent_t event, WiFiEventInfo_t info) {
        Serial.print("WiFi lost connection. Reason: ");
        Serial.println(info.disconnected.reason);
        WiFi.persistent(false);
        WiFi.disconnect(true);
        //WiFiConnected = false;
        ESP.restart();
    },
        WiFiEvent_t::SYSTEM_EVENT_STA_DISCONNECTED);
}

In my case, ever since i used this, i never dropped once (but never say never). First "failed" try is always there though

lnrobby commented 4 years ago

Maxdd

Thanks for this. I will try this. Shame no-one is picking up the actual problem to fix it.

fpiernas commented 4 years ago

Hi again, I have activated the debug level verbose and I see nothing but lots of AUTH_EXPIRE and STA_DISCONNECTED callbacks, I don't know if this helps to identify the problem.

bsayiner commented 4 years ago

Does this issue be related to the ADC2 channel? Because Wifi drivers use ADC2 pins

fpiernas commented 4 years ago

Does this issue be related to the ADC2 channel? Because Wifi drivers use ADC2 pins

But does that mean you can't use those even as digital outputs?

bsayiner commented 4 years ago

Does this issue be related to the ADC2 channel? Because Wifi drivers use ADC2 pins

But does that mean you can't use those even as digital outputs?

I saw that at this thread #1829

stale[bot] commented 4 years ago

[STALE_SET] This issue has been automatically marked as stale because it has not had recent activity. It will be closed in 14 days if no further activity occurs. Thank you for your contributions.

stale[bot] commented 4 years ago

[STALE_DEL] This stale issue has been automatically closed. Thank you for your contributions.

deepakjos2000 commented 3 years ago

I faced similar problem, Saw all the posts, my problem is that my wifi.staus() gets 0 after 2 hrs and i tried all the disconnecting loops etc, like get the wifi.status() = 0 then wifi.disconnect(). Though I am not a core programmer, I was afraid to peep into the wifi libraries. However, I enabled the debug mode and saw that there are events only returning 4 and 7 even after disconnect, that means the device was not truly disconnecting the wifi. So I decided to look into the library src codes and found something strange written in WifiSta.cpp - line 245: bool WiFiSTAClass::disconnect(bool wifioff, bool eraseap) { wifi_config_t conf;

if(WiFi.getMode() & WIFI_MODE_STA){
    if(eraseap){
        memset(&conf, 0, sizeof(wifi_config_t));
        if(esp_wifi_set_config(WIFI_IF_STA, &conf)){
            log_e("clear config failed!");
        }
    }
    if(esp_wifi_disconnect()){
        log_e("disconnect failed!");
        return false;
    }
    if(wifioff) {
         return WiFi.enableSTA(false);
    }
    return true;
}

return false;

}

That means it needs wifi.disconnect (bool , bool). So I wrote wifi.disconnect(1,1) in the event check loop like this: if(wifi_status_watch != WiFi.status()){Serial.print("WiFi.status(): ");Serial.println(WiFi.status());wifi_status_watch = WiFi.status();} if (((WiFi.status() == 0)||(WiFi.status() == 5)) && (millis() > check_wifi && check_wifi_disconnect == 0)) { Serial.println("disconnecting wifi..."); WiFi.disconnect(1,1); //disconnect(bool wifioff, bool eraseap) check_wifi_disconnect = 1; wifi_disconnect_time = 0; check_wifi = millis() + 30000; Serial.print("WiFi.status(): ");Serial.println(WiFi.status());wifi_status_watch = WiFi.status(); } if (((WiFi.status() == 0)||(WiFi.status() == 6))&& (wifi_disconnect_time >= 10) && (check_wifi_disconnect == 1)) { Serial.println("Reconnecting to WiFi...");

      check_wifi_disconnect = 0;

      WiFi.begin(Wifi_setting.ssid, Wifi_setting.password); 

    }

so when the wifi.status() == 0 (or wifi.status() == 5, just to check right now if truly the device disconnects or not) when i shut down router, the status goes to == 5 ) Then first the wifi.status return 255 (means no wifi shield, I guess here it clears all the difficult bits) The it goes to status == 1, then scans, like this i get almost all the required status.

I am still not sure if it will work like this even after 2 hours or not, but I am hoping that with all this clear status modes there has to be no reason for device to connect properly. Will post the results.

NOUSHADO commented 3 years ago

hi sir how are you i am facing the issue like wifi disconnects after 1 or 2 hours

can you help me for this i am not much familier with c+c+ language can you suggest me how to solve this issue

skarpushin commented 10 months ago

Happening to me too. Board ESP32-D0WD-V3 (revision v3.0). After ~5h of working disconnects and cannot connect anymore.

voidzero commented 3 months ago

Same problem here as long as I've got my 433 MHz receiver connected on GPIO 26 (I have a Wemos D1 R32). As soon as I disconnect the pin: WiFi works. Even if I haven't configured the pin!

edit: never mind, it was a fluke. Issues just come and go.. more often than not I can't get a connection.