1

I am using 3 Esp32 modules. One being master and other two being nodes. Nodes are connecting to the master's AP. Master is connected with GSM module to execute the web api. Master esp is having a Async Webserver which takes the http requests from the nodes and executes the appropriate web api. This web api returns the result and finally this result is sent back to the node as the response to the http request.

While running this code, Randomly on any request i face wdt reset.

Hence my question is, how should i handle the wdt resets and keep my program running softly.

E (32706) task_wdt: Task watchdog got triggered. The following tasks did not reset the watchdog in time:
E (32706) task_wdt: - async_tcp (CPU 0/1)
E (32706) task_wdt: Tasks currently running:
E (32706) task_wdt: CPU 0: IDLE0
E (32706) task_wdt: CPU 1: async_tcp
E (32706) task_wdt: Aborting.
abort() was called at PC 0x400e1cc3 on core 0
Backtrace: 0x4008c434:0x3ffbe170 0x4008c665:0x3ffbe190 0x400e1cc3:0x3ffbe1b0 0x40084771:0x3ffbe1d0 0x4016aaf3:0x3ffbc0d0 0x400e307a:0x3ffbc0f0 0x4008a361:0x3ffbc110 0x40088b7d:0x3ffbc130

My Code Snippet is given below,

Master

HttpClient http(gsmClient, "www.mydummyserver.com", 80);
AsyncWebServer server(80);

const char* ssid = "ESP32-Access-Point";
const char* password = "123456789";
IPAddress ip(192,168,5,2);
IPAddress gateway(192,168,5,1);
IPAddress subnet(255,255,255,0);
const char* PARAM_MESSAGE = "message";

void notFound(AsyncWebServerRequest *request) {
    request->send(404, "text/plain", "Not found");
}

void setup() {

  Serial.begin(115200);
  WiFi.mode(WIFI_AP);
  delay(100);
  WiFi.softAPConfig(ip, gateway, subnet); 
  WiFi.softAP(ssid, password);

server.on("/", HTTP_GET, [](AsyncWebServerRequest *request){
        request->send(200, "text/plain", "Hello, world");
    });

 server.on("/myApi", HTTP_POST, [] (AsyncWebServerRequest *request) {

        String message;
        if (request->hasParam(PARAM_MESSAGE)) {
            message = request->getParam(PARAM_MESSAGE)->value();
        } else {
            message = "No message sent";
        }

        http.setTimeout(20000);
        String postData = "Param1=abcd&Param2=pqrs";
        http.beginRequest();
        http.post("http://www.mydummyserver.com/testapi.php");
        http.sendHeader("Content-Type", "application/x-www-form-urlencoded");
        http.sendHeader("Content-Length", postData.length());
        http.beginBody();
        http.print(postData);
        http.endRequest();
        int statusCode = http.responseStatusCode();
        String response = http.responseBody();

        Serial.print("Status code: ");
        Serial.println(statusCode);
        Serial.print("Response: ");
        Serial.println(response);
        request->send(200, "text/plain", "Response: " + message);

    });

 server.onNotFound(notFound);

    server.begin();

}

void loop() {

}

Node

HTTPClient httpClient;

void setup() {

  Serial.begin(115200);

  WiFi.begin("ESP32-Access-Point", "123456789");

  Serial.print("WiFi ");

  while (WiFi.status() != WL_CONNECTED) {
    Serial.print(".");
    delay(10);

  }

  Serial.println("connected:" + WiFi.SSID());

}

void executeApi() {

  Serial.println("Executing Api...");

  httpClient.setTimeout(20000);
  httpClient.begin("http://192.168.5.2/myApi");
  httpClient.addHeader("Content-Type", "application/x-www-form-urlencoded; charset=UTF-8");
  String contentStr = "Param1=abcd&Param2=pqrs";

  int httpResponseCode = httpClient.POST(contentStr);

  Serial.print("HTTP Response code: ");
  Serial.println(httpResponseCode);

  httpClient.end();

}

String cmd = "";
void loop() {

  if (Serial.available() > 0) {

    cmd = (Serial.readStringUntil('\n'));

    if (cmd.length() > 0) {

      if (cmd == "api") {
        executeApi();

      }

    }

  }

}

For sulutions i have tried following things,

a. I tried to write this into the loop() function.

 while(true){ 
   delay(1); 
 }

b. Tried disabling the wdt

disableCore0WDT()
disableCore1WDT()

but none of these giving good results.

  • How do you wire the GSM module with the master, I don't see any code in your master related to configure or setup for communicating with the GSM. Is there any reason your node url endpoint is testapi, while it does not exist on your master's route (your master has a route handler for endpoint myApi. is your node connecting to web server directly instead of the master (which is a relay/proxy server). – hcheung Apr 6 at 14:17
  • @hcheung Hi, Due to privacy issues i could not share the real data. GSM module and ESP are connected using HardwareSerial. I have corrected the code mistake for url endpoints. My node is connecting to master first and then it is executing remote server apis. – java bee Apr 6 at 14:37
0

The following recommandations, as you are providing not enough relevant info

  • Install ESP-exeption decoder and analyse your backtrace - post it here so we see what indetail caused the wdt
  • Async webserver tends to cause this behavior if a response tends to take to long a well placed yield() sometimes helps to prevent that behavior - to anaylse you need ESP-exeption decoder
  • as loop() is running on core1 some/no process (idle) on core0 caused the behavior. You cann look up task assignment to cores be done manually to distribute the tasks (or send a yield() timed to core0 to reset the wdt
  • placing timeouts in combination with sleep/deep sleep (although you dont seem to use them) are also causes for wdt resets
  • a hackey trick is to set CONFIG_ASYNC_TCP_USE_WDT 0 but is ok for testing

If you look into async_tcp the possible culprit you see one line xTaskCreateUniversal(_async_service_task, "async_tcp", 8192 * 2, NULL, 3, &_async_service_task_handle, CONFIG_ASYNC_TCP_RUNNING_CORE);
Here an example how I use it to prevent wdt resets
Place in setup()

disableCore0WDT();
disableCore1WDT();
disableLoopWDT(); // You forgot this one !

and because of this routine in the async_tcp lib

static void _async_service_task(void *pvParameters){
    lwip_event_packet_t * packet = NULL;
   for (;;) {
    if(_get_async_event(&packet)){
#if CONFIG_ASYNC_TCP_USE_WDT
        if(esp_task_wdt_add(NULL) != ESP_OK){
            log_e("Failed to add async task to WDT");
        }           
 #endif
        _handle_async_event(packet);
 #if CONFIG_ASYNC_TCP_USE_WDT
        if(esp_task_wdt_delete(NULL) != ESP_OK){
            log_e("Failed to remove loop task from WDT");
        }
#endif
    }
 }
  vTaskDelete(NULL);
   _async_service_task_handle = NULL;
}

I set the CONFIG_ASYNC_TCP_USE_WDT 0 and it works so far.

| improve this answer | |
  • Hi .. thanks for the detailed suggestion. i tried this too but still the same error happening, Can u guide me more ? – java bee Apr 15 at 11:17
  • also when i paste the following error i have mentioned in questions does in exception decoder it prints nothing.. I guess the exception clearly states the issue without any traces. – java bee Apr 15 at 11:20
  • You have to paste the part starting after Backtrace: ==>0x4 to the end into thedecoderits not possible to hve nothing, So the sequence is compile and upload, serial moiitor wait till error copy & paste backtrace ESP decoder -> copy result THAN post to your question (edit!) Thanks – Codebreaker007 Apr 15 at 14:19
  • Hi . I have pasted in question what my serial monitor is showing. Other than this no other error data serial monitor is showing. – java bee Apr 15 at 14:23
  • IF YOU WANT HELP I need what I posted above you have to do it in your environment as I can not decode the backtrace without your elf file and all your settings/libs/path/version etc - please help me to help you – Codebreaker007 Apr 15 at 16:28

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.