-
Notifications
You must be signed in to change notification settings - Fork 2.2k
[Storage] Add support for storing some data in External EEPROM #5382
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: mega
Are you sure you want to change the base?
[Storage] Add support for storing some data in External EEPROM #5382
Conversation
…canner, code optimizations
…eprom Values page
@tonhuisman I got my EEPROMs today. Tell me when and what needs to be tested or how I can be of assistance. |
Ah, great 😃 You can of course test if the Task Values and Rules variables (writeEE,n,value / [readEE#n]) (NB: n = range 0..MAX-1 !) are restored correctly once you have enabled the corresponding settings on the Hardware page (see screenshot above). Restore should be successful after a power cycle 😄 to simulate the Cold boot situation. NB: I'm thinking of limiting the Rules vars to f.e. 1024 (less on smaller EEPROM sizes!), so more space will be available for Cache values, |
Ok... i am already in testing mode (I didn't wait for your reply :P ) Everything seems to work fine. (I have everything covered you mentioned)
|
I see no reason not to do it that way unless somebody really wants to write a lot of vars :) |
|
Would it be complicated to make the number of Rules var slots user selectable and put them at the end of the EEPROM and use the rest for C16? The ammount of user selectable slots could be also written to the EEPROM insted of storing it on the flash....
I get it. Would make a user-selectable amount of slots even more useful :) |
But for an analog reading of a LDR it still could mean 1 write per second |
I'll see where too put that extra checkbox per value 😅 I have already found a bit per value so I can store this setting 😎 Btw, I think it should be Enabled by default, and user can decide to turn it off Ah, and there's a particular reason not to skip values, as I'm also storing the Checksum for this data, and validating that against the calculated checksum, so when skipping a value the checksum won't be correct anymore 😱 |
Maybe it could also be stored on the EEPROM/FRAM? |
Hmm, not sure if that's such a good plan |
Me neither :) Just thinking out loud... |
What to do for Taskvalues that are not stored, store |
Hmmm.. very good question. I would make sense to use NaN. But that can not be represented (only when choosing a specific other value for it i guess?) Edit: ahhh since it is float 0xFFFFFFFF for NaN would be it right? |
I am probably stating the obvious by the memory layout could be like:
|
For GPIO pins we want to provide a way to store the states for MCP and PCF GPIOs, so 64 bits isn't going to cut it. And maybe we should store some more data, like PWM data and/or input/output, haven't coded anything for that yet. It's still slow-cooking in a background thread in my head 🤓 And the same is the case for |
It seems a value gets written no matter what, or there is an issue with the log. Log:
|
Since I can see the I2C working because SDA shares the GPIO with the internal LED of the ESP, I am confident something gets written for real. |
Yes, the checksum still gets written, I will fix that |
Hmm, that's not looking nice, 360 msec added on a PLUGIN_READ 😞 |
Saving of the UserVars to EEPROM is now handled in 'the background', though not in a RTOS task as using the I2C bus for a few-hundred milliseconds isn't easily made thread-safe (and quite undesirable too). |
This doesn't seem to be fixed 😳 But it is much faster :) |
The 0 is the number of bytes written, so... |
Ahhh... And I was wondering why there is zero success 😁 |
It's reading to compare data before writing, so there will always be activity on I2C. |
But still... if there is nothing to write, then there is no need to read and no need for I2C activity which then, even if it is only around 40ms, doesn't occupy the I2C bus. |
To be able to compare data, the current EEPROM-data must be read to compare to the new data. We don't want to (read: can't) keep a buffer in memory that reflects the EEPROM content. |
Sorry, I don't want to be a pain in the ass 😁 but it seems i don't get it. |
First thing that's done is a validity-check of the current EEPROM: https://github.com/letscontrolit/ESPEasy/pull/5382/files#diff-87033636f7a2095187789ef49c13c2e2767c2e1d8eb19618aa17d932dd58ab53R175-R182 That involves a 'couple of bytes' being read, but those are not counted, and even if the params are not OK, the writes to update the params are not counted. NB: AFAIK, reading from an EEPROM is harmless to the device, as opposed to writing, that will eventually wear out the chip. (Most EEPROMs are specced at ~106 writes per byte, though I haven't validated that.) |
There currently is scheduled only a single write action per task update, if a new update comes while the data is still being processed, the new write action is ignored, as it will be handled on the next 'run'. |
I know. It’s not so much about the cycles but about the time that the read occupies the I2C bus. If you have multiple tasks with a 1-sec interval and let this be multiple I2C devices, then there is a lot of stuff going on on the bus. I even have some tasks with a 100-ms (or was it 50ms...) interval getting the analog data of a light sensor (LDR)... I would think that theoretically could lead to issues. |
to get a better understanding.. what params are we talking about? |
|
Would it be a problem to treat a task, where all "Eeprom" fields are disabled as an disabled task? |
BTW: 0 is still not being displayed as a slot value in /eepromvars. |
Well, yes, that's the intention, but I now see that some improvements can be applied in the code. There's also the feature that I write a NaN value if the taskvalue is not enabled, but currently that's re-checked every time for an enabled task. Will fix that soon-ish. |
…feature/Storage-add-support-for-External-EEPROM
@chromoxdor and others that are building this PR locally: |
Thanks for the heads up! What’s the other setting? |
MQTT State Class per Value |
Resolves #1011
Forum requests: here here here here here here
Features:
float
resolution) usingWriteEE,<slot>,<value>
, limited to max. 1024 slots (less on smaller EEPROMs)WriteEE,erase,erase
[ReadEE#<slot>]
generic Rules variables syntax[ReadEE#max]
External EEPROM values
page (/eepromvars
endpoint), available from the Tools page, hiding currently stored Task Values by adding?tasks=0
and showing also disabled tasks by adding&enabled=1
to the page-url (advanced feature 😉) For 0-values no hex value display is included.WriteEE,Check,WP
to re-evaluate the write-ability of the EEPROM[ReadEE#WP]
, 1 = write-protectedEnabledDisabled by default, only visible if the EEPROM (or FRAM) is enabled and available.ESPEasy::eeprom
namespace for better structure and maintainability.TODO:
WriteEE
command)[ReadEE#<slot>]
)Hardware page configuration: (updated: 2025-08-31)
