S2 mini crashes

I have a bug in a Code i can not debug.
The (almost same) code was running on a Wemos D1 mini.
But the S2 crashes in the last lines of the setup:

void setup() {
  ...
  Serial.println("before reconnect");
  reconnect();
  Serial.println("setup end");
}

The setup() launches the reconnect().
reconnect() executes fully until the end (Serial.println("reconnect end"):wink: - I see the "reconnect end" in the Serial.

The last command in the setup() is not executed.
The S2 resets before printing "setup end".

I can not explain this. Any advice on how to debug this?

Full code:

#include <RCSwitch.h>
#include <WiFi.h>
#include <PubSubClient.h>
#include <IRremoteESP8266.h>
#include <IRsend.h>
#include "config.h"
#include "tv_remote_database.h"
#define BUILTIN_LED 15 // Change this to the pin number of your board's

RCSwitch mySwitch = RCSwitch(); // Create an instance of the RCSwitch library
WiFiClient espClient;
PubSubClient client(espClient);
IRsend irsend(IR_PIN);
unsigned long lastPublish = 0;


void flashLed(int repetitions, int on_duration, int off_duration = 0) {
  for (int i = 0; i < repetitions; i++) {
    digitalWrite(BUILTIN_LED, LOW); // Turn on the LED
    delay(on_duration);
    digitalWrite(BUILTIN_LED, HIGH); // Turn off the LED
    delay(off_duration);
  }
}

void flashforever() {
  while (true) {
    flashLed(1, 100, 100);
  }
}

void setup_wifi() {
  delay(10);
  Serial.println();
  Serial.print("Connecting to ");
  Serial.println(ssid);

  WiFi.begin(ssid, password);

  while (WiFi.status() != WL_CONNECTED) {
    Serial.print(".");
    flashLed(1, 100, 500); // Blink once every 500ms while trying to connect to WiFi
  }

  flashLed(3, 100, 100); // Blink 3 times if connected to WiFi
  Serial.println("");
  Serial.println("WiFi connected");
  Serial.println("IP address: ");
  Serial.println(WiFi.localIP());
}


void reconnect() {
  while (!client.connected()) {
    Serial.print("Attempting MQTT connection... ");
    if (client.connect("S2_MQTT_Sender", mqtt_username, mqtt_password)) {
      Serial.println("connected");
      // Flash the built-in LED 3 times after connecting to the MQTT broker
      flashLed(3, 300, 300);
    } else {
      Serial.print("failed, rc=");
      Serial.print(client.state());
      Serial.println(" try again in 5 seconds");
      flashLed(2, 100, 400); // Blink twice if failed to connect to MQTT broker
      if (client.state() == -2) {
        Serial.println("Network unreachable, redoing WiFi setup...");
        WiFi.disconnect(); // Disconnect from the WiFi network
        delay(1000); // Wait for a while
        setup_wifi(); // Redo the WiFi setup
      }
      delay(2000);
    }
  }
  // Subscribe to all device topics
  for (int i = 0; i < numDevices; i++) {
    char topic[10];
    snprintf(topic, 30, "Sender/RC/%s", devices[i][0].c_str());
    client.subscribe(topic);
    Serial.print("Subscribed to ");
    Serial.println(topic);
  }

  // Subscribe to the IR topic
  client.subscribe("Sender/IR");
  Serial.println("Subscribed to Sender/IR");
  Serial.println("reconnect end");
}

void setup() {
  Serial.begin(115200);
  pinMode(BUILTIN_LED, OUTPUT);
  digitalWrite(BUILTIN_LED, HIGH);
  mySwitch.enableTransmit(TRANSMITTER_PIN);
  setup_wifi();

  client.setServer(mqtt_server, mqtt_port);
  client.setCallback(callback);
  Serial.println("before reconnect");
  reconnect();
  Serial.println("setup end");
}

void loop() {
  Serial.println("Loop start");
  if (!client.connected()) {
    reconnect();
  }
  client.loop();
  if (millis() - lastPublish > 5000) {
    client.publish("Sender/state", "online");
    lastPublish = millis();
  }
}

void callback(char* topic, byte* payload, unsigned int length) {
  // Find the device based on the topic for RC commands
  flashLed(2, 50, 100);
  int deviceIndex = -1;
  for (int i = 0; i < numDevices; i++) {
    std::string deviceTopic = std::string("Sender/RC/") + devices[i][0].c_str();
    if (String(topic) == deviceTopic.c_str()) {
      deviceIndex = i;
      break;
    }
  }

  if (deviceIndex != -1) {
    handleRCCommand(devices[deviceIndex], payload, length);
  } else if (String(topic) == "Sender/IR") {
    handleAndSendIRCommand(payload, length);
  } else {
    Serial.println("Received message for unknown device or topic");
  }
}


void handleAndSendIRCommand(byte* payload, unsigned int length) {
  // Parse the message
  String message = "";
  for (int i = 0; i < length; i++) {
    message += (char)payload[i];
  }

  // Check if the message exists in the IR_CODES_MAP
  if (IR_CODES_MAP.find(message.c_str()) != IR_CODES_MAP.end()) {
    unsigned long irCode = IR_CODES_MAP.at(message.c_str());
    
    // Send the IR code
    IRsend irsend(IR_PIN);
    irsend.begin();

    irsend.sendSAMSUNG(irCode, 32, 1);
    Serial.print("Sent IR code: ");
    Serial.println(message); // Print the name of the IR code instead of the hex value

  } else {
    Serial.print("Received unknown IR command: ");
    Serial.println(message);
  }
}


void handleRCCommand(const String device[], byte* payload, unsigned int length) {
  // Parse the message
  String message = "";
  for (int i = 0; i < length; i++) {
    message += (char)payload[i];
  }

  // Send the command
  if (message == "on" || message == "ON") {
    sendRCCode(device, true);
  } else if (message == "off" || message == "OFF") {
    sendRCCode(device, false);
  } else {
    Serial.println("Received unknown message for RC command");
  }
}

void sendRCCode(const String device[], bool on) {
  int protocol = device[4].toInt();
  int pulseLength = device[3].toInt();

  mySwitch.setProtocol(protocol);
  mySwitch.setPulseLength(pulseLength);

  int commandCode = on ? device[1].toInt() : device[2].toInt();
  mySwitch.send(commandCode, 24);

  Serial.print("Sent ");
  Serial.print(on ? "on" : "off");
  Serial.print(" command for ");
  Serial.println(device[0]);
}

I hope you see the error you made here. Fortunately the ESP resets after you corrupted it's memory.

1 Like

You reply made me laugh hard :smiley:
Thanks so much for pointing me to sth.

Actually I do not even understand what I did wrong. This part of the code was generated by ChatGPT, my c++ skills are medicore. But from your wording, it should be something fatal.

const String devices[][5] = {

  {"A", "1361", "1364", "300", "1"},
  {"B", "4433", "4436", "300", "1"},
  {"C", "5201", "5204", "300", "1"},
  {"D", "5393", "5396", "300", "1"},
  {"E", "4195665", "4195668", "300", "1"},
  {"PC", "13637", "13637", "300", "1"}
};

This is how device is defined

topic declared as size 10 but you tell snprintf topic size is 30..

cppreference.com/w/c/io/fprintf

sorry.. ~q

Another reason never to use such services. They pretend to do something for you but have no clue about what they're doing. That's the result. The artificial fool doesn't know that the two lines depend on each other so it's up to you to know that.

It's time to get some experience. But be warned, ChatGPT is not a teacher! There are many good tutorials on the Net.

You have to be careful with debug prints, the print()/println() functions put the text into the transmit buffer, but the actual serial transmission does not complete until some time later. When the code crashes, whatever is left in the buffer never gets sent. Calling Serial.flush() after the print() will force the code to wait until the buffer empties.

'never use such services' is something I would vastly argue against. I am pretty good with python and since I am using chatGPT, the amount of code I develop every day had increased at least 3x.
Also I can do project I otherwise would not have the time to do, as this one.

But I agree. It is stupid to just use the code it outputs without checking and rethinking it.

Then again, I can not understand how the esp d1 mini could run this exact lines, while the s2 crashes.

I will fix it the lines naxt week and update you if this solved the problem. Huge thanks for the hint once again.

Corrupted memory doesn't have the same effect on different boards. It's an error on the ESP8266 too and a minimal code change might show a strange behavior at any time.

This topic was automatically closed 180 days after the last reply. New replies are no longer allowed.