bblanchon / ArduinoJson

📟 JSON library for Arduino and embedded C++. Simple and efficient.
https://arduinojson.org
MIT License
6.72k stars 1.12k forks source link

EepromStream and serialize/deserialize JSON do not appear to work on ESP32 #1291

Closed KnightOfNih closed 4 years ago

KnightOfNih commented 4 years ago

Hi Team,

I'm attempting to follow the tutorial "How to store a JSON document in EEPROM" but can't seem to get it to save and then load correctly.

I'm performing a simple read, increment counter, save, reboot pattern. Does ESP.reset() also remove the EEPROM?

The libraries were added via PlatformIO.

Platform:

[env:esp32prod]
platform = espressif32
board = esp32dev
framework = arduino
monitor_speed = 115200

Code:

#include <Arduino.h>
#include <ArduinoJson.h>
#include <StreamUtils.h>

StaticJsonDocument<256> doc; // Document we will hold the num in
int num = 0;                 // Simple counter

void setup() {
  Serial.begin(115200);

  EepromStream eepromStream(0, 256);
  deserializeJson(doc, eepromStream);

  if(doc["num"]){
    Serial.println("Loaded doc's num value.");
    num = doc["num"];
  } else {
    Serial.println("No 'num' variable in eeprom.");
  }
}

void loop() {

  num++;
  Serial.println(num);

  if((num % 3 == 0)){
    Serial.println("Saving ...");
    EepromStream eepromStream(0, 256);
    serializeJson(doc, eepromStream);
    eepromStream.flush();  // (for ESP)
    Serial.println("Rebooting ...");
    ESP.restart();
  }

  delay(1000);
}

Output:

configsip: 0, SPIWP:0xee
clk_drv:0x00,q_drv:0x00,d_drv:0x00,cs0_drv:0x00,hd_drv:0x00,wp_drv:0x00
mode:DIO, clock div:2
load:0x3fff0018,len:4
load:0x3fff0
01c,len:1044
load:0x40078000,len:8896
load:0x40080400,len:5828
entry 0x400806ac
No 'num' variable in eeprom.
1
2
3
Saving ...
Rebooting ...
ets Jun  8 2016 00:22:57

rst:0xc (SW_CPU_RESET),boot:0x13 (SPI_FAST_FLASH_BOOT)
configsip: 0, SPIWP:0xee
clk_drv:0x00,q_drv:0x00,d_drv:0x00,cs0_drv:0x00,hd_drv:0x00,wp_drv:0x00
mode:DIO, clock div:2
load:0x3fff0018,len:4
load:0x3fff001c,len:1044
load:0x40078000,len:8896
load:0x40080400,len:5828
entry 0x400806ac
No 'num' variable in eeprom.
1
2
3
Saving ...
Rebooting ...

Build:


> Executing task: platformio run <

Processing esp32prod (platform: espressif32; board: esp32dev; framework: arduino)
-----------------------------------------------------------------------------------------------------------------------------------------------------------------
Verbose mode can be enabled via `-v, --verbose` option
CONFIGURATION: https://docs.platformio.org/page/boards/espressif32/esp32dev.html
PLATFORM: Espressif 32 1.12.1 > Espressif ESP32 Dev Module
HARDWARE: ESP32 240MHz, 320KB RAM, 4MB Flash
DEBUG: Current (esp-prog) External (esp-prog, iot-bus-jtag, jlink, minimodule, olimex-arm-usb-ocd, olimex-arm-usb-ocd-h, olimex-arm-usb-tiny-h, olimex-jtag-tiny, tumpa)
PACKAGES: 
 - framework-arduinoespressif32 3.10004.200129 (1.0.4) 
 - tool-esptoolpy 1.20600.0 (2.6.0) 
 - toolchain-xtensa32 2.50200.80 (5.2.0)
LDF: Library Dependency Finder -> http://bit.ly/configure-pio-ldf
LDF Modes: Finder ~ chain, Compatibility ~ soft
Found 29 compatible libraries
Scanning dependencies...
Dependency Graph
|-- <ArduinoJson> 6.15.2
|-- <StreamUtils> 1.4.0
|   |-- <EEPROM> 1.0.3
Building in release mode
Compiling .pio/build/esp32prod/src/main.cpp.o
Generating partitions .pio/build/esp32prod/partitions.bin
Archiving .pio/build/esp32prod/liba51/libArduinoJson_ID64.a
Indexing .pio/build/esp32prod/liba51/libArduinoJson_ID64.a
Compiling .pio/build/esp32prod/lib456/EEPROM/EEPROM.cpp.o
Archiving .pio/build/esp32prod/lib67a/libStreamUtils_ID6347.a
Archiving .pio/build/esp32prod/libFrameworkArduinoVariant.a
Indexing .pio/build/esp32prod/lib67a/libStreamUtils_ID6347.a
Indexing .pio/build/esp32prod/libFrameworkArduinoVariant.a
Compiling .pio/build/esp32prod/FrameworkArduino/Esp.cpp.o
Compiling .pio/build/esp32prod/FrameworkArduino/FunctionalInterrupt.cpp.o
Compiling .pio/build/esp32prod/FrameworkArduino/HardwareSerial.cpp.o
Compiling .pio/build/esp32prod/FrameworkArduino/IPAddress.cpp.o
Compiling .pio/build/esp32prod/FrameworkArduino/IPv6Address.cpp.o
Compiling .pio/build/esp32prod/FrameworkArduino/MD5Builder.cpp.o
Compiling .pio/build/esp32prod/FrameworkArduino/Print.cpp.o
Compiling .pio/build/esp32prod/FrameworkArduino/Stream.cpp.o
Archiving .pio/build/esp32prod/lib456/libEEPROM.a
Indexing .pio/build/esp32prod/lib456/libEEPROM.a
Compiling .pio/build/esp32prod/FrameworkArduino/StreamString.cpp.o
Compiling .pio/build/esp32prod/FrameworkArduino/WMath.cpp.o
Compiling .pio/build/esp32prod/FrameworkArduino/WString.cpp.o
Compiling .pio/build/esp32prod/FrameworkArduino/base64.cpp.o
Compiling .pio/build/esp32prod/FrameworkArduino/cbuf.cpp.o
Compiling .pio/build/esp32prod/FrameworkArduino/esp32-hal-adc.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/esp32-hal-bt.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/esp32-hal-cpu.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/esp32-hal-dac.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/esp32-hal-gpio.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/esp32-hal-i2c.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/esp32-hal-ledc.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/esp32-hal-matrix.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/esp32-hal-misc.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/esp32-hal-psram.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/esp32-hal-rmt.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/esp32-hal-sigmadelta.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/esp32-hal-spi.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/esp32-hal-time.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/esp32-hal-timer.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/esp32-hal-touch.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/esp32-hal-uart.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/libb64/cdecode.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/libb64/cencode.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/main.cpp.o
Compiling .pio/build/esp32prod/FrameworkArduino/stdlib_noniso.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/wiring_pulse.c.o
Compiling .pio/build/esp32prod/FrameworkArduino/wiring_shift.c.o
Archiving .pio/build/esp32prod/libFrameworkArduino.a
Indexing .pio/build/esp32prod/libFrameworkArduino.a
Linking .pio/build/esp32prod/firmware.elf
Retrieving maximum program size .pio/build/esp32prod/firmware.elf
Building .pio/build/esp32prod/firmware.bin
Checking size .pio/build/esp32prod/firmware.elf
Advanced Memory Usage is available via "PlatformIO Home > Project Inspect"
RAM:   [          ]   4.8% (used 15852 bytes from 327680 bytes)
Flash: [==        ]  17.4% (used 228357 bytes from 1310720 bytes)
esptool.py v2.6
================================================================== [SUCCESS] Took 6.62 seconds ==================================================================

Terminal will be reused by tasks, press any key to close it.
bblanchon commented 4 years ago

Hi @KnightOfNih,

It seems that you forgot to call EEPROM.begin(). I updated the documentation accordingly.

Best regards, Benoit

KnightOfNih commented 4 years ago

Thanks Benoit! This really helps me out. I'll try it today.

KnightOfNih commented 4 years ago

Added EEPROM.begin(512) to the setup function but same result. 1 2 3 reboot, 1 2 3 reboot

void setup() {
  Serial.begin(115200);
  EEPROM.begin(512);

  EepromStream eepromStream(0, 256);
  ...

Tried a few variations to no effect.

KnightOfNih commented 4 years ago

On a related note, I have been able to get basic EEPROM read/write to work by following this tutorial so it doesn't feel like a board issue.

https://randomnerdtutorials.com/esp32-flash-memory/

bblanchon commented 4 years ago

I've read your program several times, but I don't see where it sets the value of doc["num"]; it seems that it only reads it. Can you double-check this?

If it's still not working:

KnightOfNih commented 4 years ago

Sigh ... actually setting the value would be critical, wouldn't it? I must have removed it when I was refactoring. At any rate, it works! I verified the EEPROM.begin(512); portion was also required. Final code below.

#include <Arduino.h>
#include <ArduinoJson.h>
#include <StreamUtils.h>

StaticJsonDocument<256> doc; // Document we will hold the num in
int num = 0;                 // Simple counter

void setup() {
  Serial.begin(115200);
  EEPROM.begin(512);

  EepromStream eepromStream(0, 256);
  deserializeJson(doc, eepromStream);

  if(doc["num"]){
    Serial.println("Loaded doc's num value.");
    num = doc["num"];
  } else {
    Serial.println("No 'num' variable in eeprom.");
  }
}

void loop() {

  num++;
  Serial.println(num);

  if((num % 3 == 0)){
    Serial.println("Saving ...");

    EepromStream eepromStream(0, 256);
    doc["num"] = num;
    serializeJson(doc, eepromStream);
    eepromStream.flush();  // (for ESP)

    Serial.println("Rebooting ...");
    ESP.restart();
  }

  delay(1000);
}
KnightOfNih commented 4 years ago

Thank you very much for all your help btw. Is there a way to contribute to your github repo or buy you a beer? Thank you again!

bblanchon commented 4 years ago

@KnightOfNih, thank you for posting the working code; I'm pretty sure it will help other users.

If you want to support the project, please consider purchasing my book Mastering ArduinoJson.