EEPROM get&update promblem

Hi everyone. I'm new to coding in general and I'm working on a mass flow sensor using arduino. I'd like to save and update the run time of the system (tot_min in my code) through multiple power on-off clycles. This is the code I've kludged together and the other components is working ok-ish so far. Any suggestion would be greatly appreciated.
P.S: sorry if I didn't do the format correctly, will adjust/delete+repost if required.


#define pulse2liter 332
#define interval 1000.0
const byte intrPin = 2;
bool run_flag = false;
unsigned long startTime = millis();

#include <EEPROM.h>
#include <Wire.h>
#include <LiquidCrystal_I2C.h>
LiquidCrystal_I2C lcd(0X27, 16, 2);


int tot_cnt = 0;
int tot_sec = 0;
int tot_min = 0;
int TotLit = 0;


void setup() {
  Serial.begin(9600);
  pinMode(LED_BUILTIN, OUTPUT);
  pinMode(intrPin, INPUT_PULLUP);
  attachInterrupt(digitalPinToInterrupt(intrPin), Pulse_cnt, FALLING);


  tot_min = EEPROM.get(0, tot_min);

  lcd.init();
  lcd.backlight();
}
void Pulse_cnt() {

  tot_cnt++;
  run_flag = true;
}

void loop() {

  while (millis() - startTime <= interval)
    digitalWrite(LED_BUILTIN, LOW);
  if (run_flag) {
    digitalWrite(LED_BUILTIN, HIGH);
    run_flag = false;
  }



  tot_sec += interval / 1000;

  tot_min = round((tot_sec / 60));




  TotLit = round(tot_cnt / pulse2liter);



  Serial.print("Tong so lit:");
  Serial.println(TotLit);
  lcd.setCursor(0, 0);
  lcd.print("Tong so lit:");
  lcd.print(TotLit);

  Serial.print("Tong so phut:");
  Serial.println(tot_min);
  lcd.setCursor(0, 1);
  lcd.print("Tong so phut:");
  lcd.print(tot_min);

  EEPROM.update(0, tot_min);

  startTime = millis();
}

EEPROM.update() only writes one byte. Use EEPROM.put() instead to write any type of variable.

Nothing wrong with it. Thanks for using code tags in your first post :+1:

2 Likes

Hi, thank you for the quick respond. Glad to hear I got it on the 1st try forum format-wise. As for the code, I've just tried to changed to EEPROM.put() but after a restart it still start at 0 when I'd like for it to continue from when it was when the power was cut.

1 Like

Just keep in mind that writing to eeprom, eats away at its finite life.
Ideally, write only when shutting down, or just before power loss.

2 Likes

can not call a function out of setup setup only runs once try putting function at the end of the loop

1 Like

nvm i am wrong you call it in setup lol sorry

1 Like

You read tot_min from EEPROM in setup(), but then in loop() you ignore that value and set tot_min to a value calculated from tot_sec:

  tot_sec += interval / 1000;

  tot_min = round((tot_sec / 60));
1 Like

Thank you for the respond. Yes I've seen that the write/re-write lifespan of EEPROM is finite, but I think it's for 1 specific address yeah? So my current plan is to keep track of the address and move it to the next one once the one in use is getting to its limit. For your suggestion about write only when shutting down, could you give me some more tips please?

No worries, I have 0 experience in coding and these codes are the results of a few hours of looking things up on the internet, so I can't say that it's the easiest to troubleshoot. Much appreciate to you for looking at it.

Hi, thank you for the respond. I'm sorry that I can see the problem that you point out now but I have no idea how to remedy that, could you help me out with this? My thinking was that since I use EEPROM.put(0, tot_min) near the end of the block it should save the data.

You’ll need to check the data for the chip or EEPROM you’re using.

Often the memory is updated internally in blocks of 16 bytes. So you need to know what you’re writing.

Power failure detection and a capacitor to allow time for the memory writes is almost trivial.
then…
Power up, reload the current data from EEPPROM, and carry on like nothing happened.

1 Like

Thank you for the respond.
I've just check the doc from arduino page and it seems both of the data type I'm using and planning to use (int and unsigned long) is within the 16 bytes and there's only 1 value (tot_min) I'm keeping.
The spec of the website I bought this arduino uno R3 from said it has 1KB of EEPROM and from the result of my search its lifespan is suitable for my project.
The hardware for the system I think I can figure out from the information you gave, but I'm just stuck at actually saving the data I want to save to EEPROM.

Just keep in mind, your updates are within loop(), hence will be called thousands of times per second.

If as I believe. update() only writes if the specific block of bytes has changed, you’ll be ok, but 100k writes isn’t a lot of seconds.

If you check whether tot_mins has changed, you’ll only write once per minute… better than updating the same value in EEPROM hundreds of times per second.

1 Like

I see.
So what if I use an if/else command and make the value of tot_min changes as the condition to save it to EEPROM, would it be a better solution? Because I can make the time value to a block of 15', half and hour or 1 hour so it wouldn't matter much to space out the time it is saved if I can have a stable power supply.

yep, that’s the simplest way to change your existing code.

if you add other variables to EEPROM, you may need to rethink your writing strategy. It’s not hard, but you need to pay attention to details.

1 Like
  • add a diode in your power line. Use a Shottky diode if your input voltage is already very low.
  • add an electrolytic capacitor (for example 1000 µF) after the diode. This will buffer your power source for a very short time.
  • check with another pin, if the power before the diode is ok (= only the unbuffered power source). When the unbuffered power goes down to zero, switch off the LCD backlight and do your EEPROM put.
1 Like

Thank you for the suggestion. Yeah for this project I think I'll just need to save that 1 specific value and call it up every time the system run, other value can be reset without any problem.

Thank you for the information, I'll keep that in mind.

add on, I did some tests a while ago:

1 Like

Vielen Dank, my Deutsch is still kindergarten-level so this is great practice for me too.

1 Like