Connection to "Name" failed Retrying in "500" milliseconds

Using the Uno R4 Wifi board in Arduino cloud my code has restarts if the cloud or WiFi ever drop out. This usually works but sometimes the R4 fails to connect back up to WiFi. The error message is this:
12:55:21.709 -> .Connection to "Name" failed
12:55:22.801 -> Retrying in "500" milliseconds
(Gave this message repeatedly for several days)
(pushed reset button here)
12:55:22.801 -> .Start...
12:55:27.654 -> WiFi.status(): 0
12:55:27.654 -> Current WiFi Firmware: 0.4.1
12:55:28.882 -> Connected to "Name"
All is once more OK.

Is there a library where I can insert another restart if I ever get that message as I have seen it fail to recover many times.

In other words if I ever see the message "Connection to "Name" failed" I just want to reboot. Is it possible?

Please post a full sketch that illustrates the problem

Here is some not very pretty code. The issue is though failing to connect to Wifi on boot up occasionally...

#include "arduino_secrets.h"
/* 
  Sketch generated by the Arduino IoT Cloud Thing "Untitled"
 

  Arduino IoT Cloud Variables description

  The following variables are automatically generated and updated when changes are made to the Thing

  String command;
  float soilMoisture1;
  int analog1;
  int slider1;
  bool bool1;

  Variables which are marked as READ/WRITE in the Cloud Thing will also have functions
  which are called when their values are changed from the Dashboard.
  These functions are generated with the Thing and added at the end of this sketch.
*/

// Rev A1  20 July 2024  Basic cloud functions

#include "thingProperties.h"
#include "Arduino_LED_Matrix.h"
ArduinoLEDMatrix matrix;
#include "frames.h" 

//---------------------------------------------------------------
void setup() 
{  
  // 1. Serial
  Serial.begin(9600);  
  delay(1500); // Wait for a Serial Monitor 
  Serial.println("Start...");

  // 2. Cloud
  initProperties(); // Defined in thingProperties.h
  
  // The watchdog can be disabled by including the "false" argument as follows
  // ArduinoCloud.begin(ArduinoIoTPreferredConnection, false);
  // watchdog is disabled and will not carry out the function for which it was intended, 
  // namely a reset of the processor when there are long-term loss of comms to the cloud 
  
  ArduinoCloud.begin(ArduinoIoTPreferredConnection); // Connect to Arduino IoT Cloud  
  ArduinoCloud.update();
  delay(1000);
  
  while(ArduinoCloud.connected() == 0) 
     {
       ArduinoCloud.update();     
       Serial.print(".");
       delay(1000);
     }
    
  command = PropertyActions::CLEAR; // clear the command window to avoid a boot loop and so command only executes once  // doesn't work sgc
  Serial.println("\n***Cloud Connected 1***");
    
  //   More information related to the state of network and IoT Cloud connection and errors
  //   The higher number the more granular information you get.
  //   The default is 0 (only errors), Maximum is 4
  setDebugMessageLevel(4); // 0..4, 0 is only errors
  ArduinoCloud.printDebugInfo();

  ArduinoCloud.addCallback(ArduinoIoTCloudEvent::DISCONNECT, doThisOnDisconnect); // reset if Cloud is disconnected
  ArduinoCloud.addCallback(ArduinoIoTCloudEvent::CONNECT, doThisOnConnect);

  // 3. Report RSSI  
  char msg[20] = "";
  sprintf(msg, "RSSI=%idB", (int)WiFi.RSSI());
  Serial.println(msg);
  if( (int)WiFi.RSSI() < -65) // sgc  Also check code to identify the correct AP
   {
     Serial.println("\n***RSSI too low 1! Restart!!!***\n\n");   
     // delay a little here to let network come back up? Try for the correct AP
     matrix.loadFrame(danger);
     NVIC_SystemReset();    
   }

  // 4. Analog input for sensors
  //analogReadResolution(14); // 10, 12, 14, default is 10 bit (0-1023) change to 14-bit resolution for analog voltage, int reading = analogRead(A3); // returns a value between 0-16383
  
  // 5. LED Matrix on R4 board
  //   https://docs.arduino.cc/tutorials/uno-r4-wifi/led-matrix  
  matrix.begin(); // LED Matrix
  //matrix.renderBitmap(arrow_up, 8, 12);
  //matrix.loadFrame(stop);

  // 6. Report to dashboard and debug serial
  
  // doesn't work sgc
  command = PropertyActions::CLEAR; // clear the command window to avoid a boot loop and so command only executes once  
  //command = "\x1b";
  ArduinoCloud.update(); 
  //ArduinoCloud.update();
  //ArduinoCloud.update();
    
  Serial.println("setup done!");
}

//---------------------------------------------------------------
void loop() 
{
  blinkLedNoDelay();  

  // delay(big number); // force a watchdog reset
  
  if(WiFi.status() != WL_CONNECTED) 
  {    
    Serial.println("\n***WiFi not connected!!! Restart!!!***\n\n");
    matrix.loadFrame(danger);
    NVIC_SystemReset();   
  }

  if( (int)WiFi.RSSI() < -65) // sgc  Also check code to identify the correct AP
   {
     Serial.println("\n***RSSI too low 2! Restart!!!***\n\n");     
     matrix.loadFrame(danger);
     NVIC_SystemReset();     
   }

  ArduinoCloud.update();
  
  if (ArduinoCloud.connected() == 0) 
  {
    // Not connected
    Serial.println("\n***Cloud not connected!!! Restart!!!***\n\n");
    matrix.loadFrame(danger);    
    NVIC_SystemReset();      
  } 
  else 
  {
    // Continue...
  }  
}

//---------------------------------------------------------------
// ArduinoCloud.addCallback(ArduinoIoTCloudEvent::DISCONNECT, doThisOnDisconnect);
// https://forum.arduino.cc/t/reset-by-software-arduino-r4/1154313/11        
void doThisOnDisconnect()
{
  Serial.println("***Cloud disconnect!!! Restart!!!***");
  matrix.loadFrame(danger);
  NVIC_SystemReset();    
}

//---------------------------------------------------------------
void doThisOnConnect()
{
  Serial.println("\n***Cloud Connected*** 2");
  command = PropertyActions::CLEAR;
  ArduinoCloud.update();
  matrix.loadFrame(happy);  
}

//---------------------------------------------------------------
void readMoisture(int sensor) // sensor 0 or 1 = A0 or A1
{
  if(sensor == 0)
  {
    soilMoisture1 = ((float)analogRead(A3)/1023.0) * 5.0; // 0 to 1023, 5V ref
    //Serial.println(moisture1);
    //Serial.println(analogRead(A3));
    
  }
    
  // else    
  
}



//---------------------------------------------------------------
// reference: https://www.baldengineer.com/arduino-how-do-you-reset-millis.html
void blinkLedNoDelay(void)  // Blink the LED without using Delay in the main loop
{
  static long now;
  static const int period = 2000; // millisecs
  static long lastChangeTime = 0; 

  // blink LED without delay in loop
  now = millis();                       
  //if(now > (lastChangeTime + period)) // Bug! Doesn't roll over correctly!
  if((now - lastChangeTime) >= period)  // ---FIXED---
  {
    if(digitalRead(LED_BUILTIN) == HIGH)
    {
      digitalWrite(LED_BUILTIN, LOW);       
    }  
    else
    {
      digitalWrite(LED_BUILTIN, HIGH);      
    }
    
    lastChangeTime = now;    
    
    
    readMoisture(0);
    
  }
}

//---------------------------------------------------------------
/*
  Analog1 is READ_WRITE variable, onAnalog1Change() is
  executed every time a new value is received from IoT Cloud.
*/
void onAnalog1Change()  
{
  // Add your code here to act upon Analog1 change
  Serial.println("analog1 changed");
}

//---------------------------------------------------------------
/*
  Bool1 is READ_WRITE variable, onBool1Change() is
  executed every time a new value is received from IoT Cloud.
*/
void onBool1Change()  
{
  // Add your code here to act upon Bool1 change
  Serial.println("bool1 changed");
  Serial.print("bool1 = ");
  Serial.println(bool1);

  if(bool1)
  {
    matrix.loadFrame(arrow_right);
    command = "LED ON\n";
  }  
  else
  {
    matrix.loadFrame(stop); // draw some current to check for voltage sags
    command = "LED OFF\n";
  }  
}

//---------------------------------------------------------------
/*
  Since Command is READ_WRITE variable, onCommandChange() is
  executed every time a new value is received from IoT Cloud.
*/
void onCommandChange()  
{
  // Add your code here to act upon Command change
  //char cmd[250] = ""; // has to be big enough to contain everything in the command window (might be big!)
  
  //strcpy(cmd, command.c_str()); // https://www.arduino.cc/reference/en/language/variables/data-types/string/functions/c_str/
  
  Serial.print("Command received = ");
  //Serial.println(cmd); 
  Serial.println(command.c_str()); 

  //command = PropertyActions::CLEAR; // clear the command window to avoid a boot loop and so command only executes once   
  
  //if(!strcmp(cmd, "rst"))
  //if(!strcmp(command.c_str(), "rst"))
  if(command == "rst")
      {        
        command = PropertyActions::CLEAR; // clear the command window to avoid a boot loop        
        ArduinoCloud.update(); 
        
        Serial.println("Resetting");        
        delay(100);
        
        NVIC_SystemReset();       
      } 
  
  if(!strcmp(command.c_str(), "clr"))
  {
    command = PropertyActions::CLEAR;  // Clear the Message widget
    
  }

  if(!strcmp(command.c_str(), "read"))
  {
    //command = PropertyActions::CLEAR;  
    //ArduinoCloud.update(); // this seems to make the clear work
    //delay(100);
    
    int reading = analogRead(A3); // default 10 bits (0-1023), can be 10,12 or 14, default ref = 5V
    char msg[20];
    sprintf(msg, "A3 = %i", reading);
    command = msg;       
  }
  

  if(!strcmp(command.c_str(), "?"))
      {
        command = PropertyActions::CLEAR;  // takes a while but one of these eventually clears the Message widget
        ArduinoCloud.update();

        command = ("Commands: \nclr  =  clear message widget\n read = read A3 voltage\n rst = reset (clear message to avoid boot loop!),\n ? = this help (clear message to avoid boot crashes!");
        // ArduinoCloud.update();
        // command = ("---");
        //response = ("Commands: \nclr  =  clear message widget\n read = read A3 voltage\n rst = reset (clear message to avoid boot loop!),\n ? = this help (clear message to avoid boot crashes!");
        //command = ("clr = clear message widget");  this doesn't work sgc
        //command = ("rst = reset. Note! Manually clear window before reset!");
        //command = ("help or ? = This help");       
      }
}

//---------------------------------------------------------------
/*
  Since Slider1 is READ_WRITE variable, onSlider1Change() is
  executed every time a new value is received from IoT Cloud.
*/
void onSlider1Change()  
{
  // Add your code here to act upon Slider1 change
  analog1 = slider1; // echo slider value to the analog guage
  Serial.print("slider1 = ");
  Serial.println(slider1);
}







I added a reboot at the bottom of loop so that it runs loop once then restarts. Like this:

NVIC_SystemReset();   

It rebooted and connected 246 times before it failed to connect. Here is the error:
First good connections:
15:08:33.655 -> Cloud Connected 1
...
16:10:26.010 -> Start...
16:10:26.154 -> WiFi.status(): 0
16:10:26.154 -> Current WiFi Firmware: 0.4.1
16:10:27.402 -> Connected to "Coyote"
16:10:27.402 -> ...
16:10:36.558 -> Cloud Connected 1
16:10:36.558 -> ***** Arduino IoT Cloud - configuration info *****
16:10:36.558 -> Device ID: c292e412-71a7-4263-9e39-e5f0eee9317b
16:10:36.605 -> MQTT Broker: iot.arduino.cc:8883
16:10:36.605 -> RSSI=-51dB
16:10:36.659 -> setup done!

Then:
16:10:38.879 -> Start...
16:10:39.012 -> WiFi.status(): 0
16:10:39.064 -> Current WiFi Firmware: 0.4.1
16:10:40.277 -> Connected to "Coyote"
16:10:40.277 -> .ArduinoIoTCloudTCP::handle_SyncTime could not get valid time. Retrying now.
16:10:42.403 -> ..ArduinoIoTCloudTCP::handle_SyncTime could not get valid time. Retrying now.
16:10:45.511 -> ..ArduinoIoTCloudTCP::handle_SyncTime could not get valid time. Retrying now.
16:10:48.618 -> ..ArduinoIoTCloudTCP::handle_SyncTime could not get valid time. Retrying now.
16:10:51.735 -> ...ArduinoIoTCloudTCP::handle_ConnectMqttBroker could not connect to iot.arduino.cc:8883 Error: -1
16:11:03.071 -> ...ArduinoIoTCloudTCP::handle_SyncTime could not get valid time. Retrying now.
16:11:07.177 -> ...ArduinoIoTCloudTCP::handle_ConnectMqttBroker could not connect to iot.arduino.cc:8883 Error: -1
16:11:18.080 -> .....ArduinoIoTCloudTCP::handle_SyncTime could not get valid time. Retrying now.
16:11:24.209 -> ...ArduinoIoTCloudTCP::handle_ConnectMqttBroker could not connect to iot.arduino.cc:8883 Error: -1
16:11:33.147 -> .........ArduinoIoTCloudTCP::handle_SyncTime could not get valid time. Retrying now.
16:11:43.265 -> ...ArduinoIoTCloudTCP::handle_ConnectMqttBroker could not connect to iot.arduino.cc:8883 Error: -1
16:11:54.139 -> .................ArduinoIoTCloudTCP::handle_SyncTime could not get valid time. Retrying now.
16:12:12.251 -> ...ArduinoIoTCloudTCP::handle_ConnectMqttBroker could not connect to iot.arduino.cc:8883 Error: -2
16:12:25.779 -> .Connection to "Coyote" lost.
16:12:26.866 -> Attempting reconnection
16:12:26.866 -> ..WiFi.status(): 0
16:12:28.934 -> Current WiFi Firmware: 99.99.99
16:12:28.934 -> .Connection to "Coyote" failed
16:12:30.017 -> Retrying in "500" milliseconds
16:12:30.017 -> .Connection to "Coyote" failed
16:12:31.133 -> Retrying in "500" milliseconds
16:12:31.133 -> .Connection to "Coyote" failed

Stuck here forever or until reset button or power cycle.

Notice that when it fails WiFi firmware version reports as:
Current WiFi Firmware: 99.99.99
Indicating that something is very corrupt in the boot process.

Again, can I get down into the code for:

ArduinoCloud.begin(ArduinoIoTPreferredConnection); 

where I could detect the hang and reboot again?

Hi @St3v3C, can you try using this PR WiFiS3 At improvements by andreagilardoni · Pull Request #349 · arduino/ArduinoCore-renesas · GitHub? We noticed some issues on the AT command parser that probably are happening to you.

Thanks @agilardoni. Have these improvements been pushed back to the version I will find on the normal cloud website? That is, do I just re-compile to try this or do I need to do something else to get the branch with these fixes into my project?