0

I am making a project, in which I need to store the WiFi credentials to the EEPROM. For now, I am able to store a bool array in the EEPROM, but I am not able to store the char variables as the ESP32 crashes. I can't share the complete code since it is REALLY long, but here are the problematic functions:

To save to the EEPROM:

//////////////////////////////////WORKING////////////////////////////////
void saveToEEPROM() {
 // Save the contents of the array in EEPROM memory
 for (int i = 0; i < NUM_PARAM_ITEMS; i++) {
 EEPROM.write(i, menu_items_param_bool[i]);
 }
//////////////////////////////////////////////////////////////////////////////////////
//////////////////////////////////NOT WORKING////////////////////////////////
 // Save WiFi credentials in EEPROM if not empty
 int offset = NUM_PARAM_ITEMS;
 if (strlen(ssid1) > 0) {
 for (int i = 0; i < strlen(ssid1); i++) {
 EEPROM.write(offset + i, ssid1[i]);
 }
 offset += strlen(ssid1);
 EEPROM.write(offset, '0円'); // Null-terminate the SSID1 string
 }
 offset++;
 if (strlen(password1) > 0) {
 for (int i = 0; i < strlen(password1); i++) {
 EEPROM.write(offset + i, password1[i]);
 }
 offset += strlen(password1);
 EEPROM.write(offset, '0円'); // Null-terminate the Password1 string
 }
 offset++;
 if (strlen(ssid2) > 0) {
 for (int i = 0; i < strlen(ssid2); i++) {
 EEPROM.write(offset + i, ssid2[i]);
 }
 offset += strlen(ssid2);
 EEPROM.write(offset, '0円'); // Null-terminate the SSID2 string
 }
 offset++;
 if (strlen(password2) > 0) {
 for (int i = 0; i < strlen(password2); i++) {
 EEPROM.write(offset + i, password2[i]);
 }
 offset += strlen(password2);
 EEPROM.write(offset, '0円'); // Null-terminate the Password2 string
 }
 EEPROM.commit(); // Don't forget to call the commit() function to save the data to EEPROM
}

To read from the EEPROM:

void readFromEEPROM() {
//////////////////////////////////WORKING////////////////////////////////
 // Read the contents of the EEPROM memory and restore it to the array
 for (int i = 0; i < NUM_PARAM_ITEMS; i++) {
 menu_items_param_bool[i] = EEPROM.read(i);
 }
//////////////////////////////////NOT WORKING//////////////////////////////////
 // Read WiFi credentials from EEPROM if not empty
 int offset = NUM_PARAM_ITEMS;
 // Read SSID1
 int ssid1Length = EEPROM.read(offset);
 if (ssid1Length > 0) {
 for (int i = 0; i < ssid1Length; i++) {
 ssid1[i] = (char)EEPROM.read(offset + i + 1);
 }
 ssid1[ssid1Length] = '0円'; // Null-terminate the SSID1 string
 Serial.print("SSID1: ");
 Serial.println(ssid1);
 }
 offset += ssid1Length + 1;
 // Read Password1
 int password1Length = EEPROM.read(offset);
 if (password1Length > 0) {
 for (int i = 0; i < password1Length; i++) {
 password1[i] = (char)EEPROM.read(offset + i + 1);
 }
 password1[password1Length] = '0円'; // Null-terminate the Password1 string
 Serial.print("PASSWORD1: ");
 Serial.println(password1);
 }
 offset += password1Length + 1;
 // Read SSID2
 int ssid2Length = EEPROM.read(offset);
 if (ssid2Length > 0) {
 for (int i = 0; i < ssid2Length; i++) {
 ssid2[i] = (char)EEPROM.read(offset + i + 1);
 }
 ssid2[ssid2Length] = '0円'; // Null-terminate the SSID2 string
 Serial.print("SSID2: ");
 Serial.println(ssid2);
 }
 offset += ssid2Length + 1;
 // Read Password2
 int password2Length = EEPROM.read(offset);
 if (password2Length > 0) {
 for (int i = 0; i < password2Length; i++) {
 password2[i] = (char)EEPROM.read(offset + i + 1);
 }
 password2[password2Length] = '0円'; // Null-terminate the Password2 string
 Serial.print("PASSWORD2: ");
 Serial.println(password2);
 }
}

And the variables to save and read are:

char ssid1[32] = "ssid1"; // SSID of the first WiFi network
char password1[64] = "password1"; // Password of the first WiFi network
char ssid2[32] = "ssid2"; // SSID of the second WiFi network
char password2[64] = "password2"; // Password of the second WiFi network

Can anybody help me?

ocrdu
1,7953 gold badges12 silver badges24 bronze badges
asked Jan 27, 2024 at 20:10
2
  • 1
    what is the specific problem? ... but not the Char variables does not desctibe what actually happens ... please update your question above ... do not add a comment below Commented Jan 27, 2024 at 20:18
  • 2
    In your read routine you are trying to read the length of the string from EEPROM, but you never saved the length there, just the null terminated strings themselves. For that to work you would need to write strlen() to EEPROM directly before the string Commented Jan 27, 2024 at 20:27

1 Answer 1

1

There are multiple issues with your code.

  1. If strlen(anystring) is zero, you write nothing, but increment offset.
  2. You try to read the lengths of the strings from EEPROM, but you never write them there.

Some things are complicated and can be simplified.

  1. You don't need to explicitly write '0円' (end-of-string marker), since each of your strings already includes it.
  2. Increment offset directly in the course.

This is a possible corrected solution. It uses the length and the end-of-string marker for each stored string.

 // Write anystring
 int anystringLength = strlen(anystring);
 EEPROM.write(offset, anystringLength);
 offset++;
 for (int i = 0; i <= anystringLength; i++) {
 EEPROM.write(offset, anystring[i]);
 offset++;
 }
 // Read anystring
 int anystringLength = EEPROM.read(offset);
 offset++;
 for (int i = 0; i <= anystringLength; i++) {
 anystring[i] = (char)EEPROM.read(offset);
 offset++;
 }
 // start of debug output
 Serial.print("any String: ");
 Serial.println(anystring);
 // end of debug output

Note: To make things explicit, using the offset and incrementing it are separated. You can combine them, though. But terse code tend to be misinterpreted.

This is another possible solution. Instead of expecting the length written before a string, read it until you find the end-of-string marker.

The writing loop writes all characters including the final end-of-string marker. This works for empty strings, too.

 int i;
 // Write anystring
 i = 0;
 do {
 char c = anystring[i];
 EEPROM.write(offset, c);
 offset++;
 i++;
 } while (c != '0円');

The reading loop does the same in the opposite direction. Using the do-while loop ensures that the end-of-string marker is read in any case.

 int i;
 // Read anystring
 i = 0;
 do {
 char c = EEPROM.read(offset);
 anystring[i] = c;
 offset++;
 i++;
 } while (c != '0円');
 // start of debug output
 Serial.print("any String: ");
 Serial.println(anystring);
 // end of debug output

Like the original the solutions lack error checks, for example of too long strings, which are left as an exercise to the reader.

Another bonus point will be received, if you extract these loops into functions. It simplifies the code and removes duplicates. [Edit] I found that the EEPROM class already provides writeString() and readString(). You should read its documentation and consider the usage.

answered Jan 28, 2024 at 8:27

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.