Home Learning EEPROM Storage Use Cases in Arduino Projects (With Examples)

EEPROM Storage Use Cases in Arduino Projects (With Examples)

by shedboy71
[lebox id="1"]

One of the most misunderstood parts of Arduino projects is EEPROM (Electrically Erasable Programmable Read-Only Memory).

Beginners often either ignore it or use it wrong by writing too often, which wears out the memory too soon.

EEPROM is not a substitute for SRAM or Flash. It has one very specific job: to keep small amounts of data safe even when the power goes out or the system is reset.

This tutorial explains:

  • What EEPROM is and how it differs from other memory
  • When EEPROM should and should not be used
  • Real-world EEPROM storage use cases
  • Safe write strategies
  • Many practical code examples
  • Common mistakes and best practices

 

What EEPROM Is and Is Not

EEPROM Characteristics

  • Non-volatile (data survives power loss)
  • Byte-addressable
  • Limited write endurance (~100,000 writes per cell)
  • Slower than SRAM
  • Small capacity (typically 512–4096 bytes depending on board)

EEPROM Is Best For

  • Configuration settings
  • Calibration values
  • User preferences
  • Counters and flags
  • Last-known system state

EEPROM Is NOT For

  • Frequently changing sensor data
  • Logging large datasets
  • Temporary variables
  • High-speed writes

EEPROM vs SRAM vs Flash (Quick Reminder)

Memory Volatile Speed Size Typical Use
SRAM Yes Fast Very small Variables
Flash No Fast Large Code, constants
EEPROM No Slow Small Persistent data

Basic EEPROM Access

Including the EEPROM Library

#include <EEPROM.h>

Reading a Byte

byte value = EEPROM.read(0);

Writing a Byte

EEPROM.write(0, 42);

This always writes, even if the value didn’t change.

Safer Alternative: update()

EEPROM.update(0, 42);

update() only writes if the stored value is different, preserving EEPROM lifespan.

Use Case 1: Saving User Settings

Example: Storing a Brightness Setting

const int EEPROM_ADDR = 0;
int brightness = 128;

void setup() {
  EEPROM.get(EEPROM_ADDR, brightness);
  analogWrite(9, brightness);
}

void loop() {
  // imagine brightness changes via buttons
  EEPROM.update(EEPROM_ADDR, brightness);
}

Why EEPROM Works Here

  • Changes infrequently
  • Must persist across power cycles
  • Small data size

Use Case 2: Device Calibration Data

Calibration is a perfect EEPROM use case.

Example: Sensor Calibration Offset

struct CalibrationData {
  float offset;
  float scale;
};

CalibrationData calib;

void setup() {
  EEPROM.get(0, calib);

  if (isnan(calib.offset)) {
    calib.offset = 0.0;
    calib.scale = 1.0;
    EEPROM.put(0, calib);
  }
}

EEPROM ensures calibration is retained even after firmware updates.

Use Case 3: Remembering Last System State

Example: Restore Last Mode on Startup

enum Mode { MODE_IDLE, MODE_RUN, MODE_ERROR };

Mode lastMode;

void setup() {
  EEPROM.get(0, lastMode);

  if (lastMode > MODE_ERROR) {
    lastMode = MODE_IDLE;
  }
}

void loop() {
  // when mode changes
  EEPROM.update(0, lastMode);
}

This allows systems to resume gracefully after power failure.

Use Case 4: Persistent Counters

Example: Power-On Counter

unsigned long bootCount;

void setup() {
  EEPROM.get(0, bootCount);
  bootCount++;
  EEPROM.put(0, bootCount);
}

Caution

Writing on every boot is acceptable. Writing every loop is not.

Use Case 5: Feature Flags and Unlocks

Example: Feature Enabled Flag

bool featureEnabled;

void setup() {
  EEPROM.get(0, featureEnabled);

  if (!featureEnabled) {
    // limited mode
  }
}

This is commonly used in:

  • Trial features
  • Configuration locks
  • Setup-complete flags

Use Case 6: Storing Small Data Structures

Example: Settings Struct

struct Settings {
  int threshold;
  byte mode;
  bool enabled;
};

Settings settings;

void setup() {
  EEPROM.get(0, settings);

  if (settings.threshold == 0xFFFF) {
    settings.threshold = 500;
    settings.mode = 1;
    settings.enabled = true;
    EEPROM.put(0, settings);
  }
}

EEPROM.put() automatically handles multi-byte writes safely.

Use Case 7: Menu-Based Configuration Systems

EEPROM is ideal for menu-driven devices.

Example: Save Menu Selection

byte menuSelection;

void setup() {
  EEPROM.get(10, menuSelection);
}

void loop() {
  // user changes menu
  EEPROM.update(10, menuSelection);
}

Use Case 8: Storing Error Codes

Example: Last Error Code

byte lastError;

void logError(byte code) {
  EEPROM.update(20, code);
}

On restart, diagnostics can report the last failure.

Managing EEPROM Wear (Very Important)

EEPROM Write Limits

  • Typical endurance: ~100,000 writes per address
  • Writing every second = worn out in ~28 hours
  • Writing every minute = years of lifespan

Strategy 1: Write Only When Necessary

if (newValue != oldValue) {
  EEPROM.update(addr, newValue);
}

Strategy 2: Delayed Writes

unsigned long lastSave = 0;

if (millis() - lastSave > 5000) {
  EEPROM.put(addr, settings);
  lastSave = millis();
}

Strategy 3: Wear Leveling (Advanced)

Rotate storage locations.

int baseAddr = (counter % 10) * sizeof(Settings);
EEPROM.put(baseAddr, settings);

This spreads wear across cells.

Common EEPROM Mistakes

Mistake 1: Writing Inside loop()

void loop() {
  EEPROM.write(0, sensorValue); // dangerous
}

Fix: write only on change or on events.

Mistake 2: Using EEPROM Like RAM

EEPROM is slow and wears out. Treat it like permanent storage, not workspace.

Mistake 3: Not Validating Stored Data

Always validate loaded EEPROM values.

if (value < MIN || value > MAX) {
  value = DEFAULT;
}

EEPROM Capacity Awareness

Example on Arduino Uno:

  • EEPROM size: 1024 bytes
  • Address range: 0–1023

Always ensure data fits.

if (sizeof(Settings) > EEPROM.length()) {
  // error
}

EEPROM Alternatives

Sometimes EEPROM is not the best solution:

  • Flash: large constants
  • External EEPROM: more space
  • FRAM: unlimited writes
  • SD card: logs and datasets

EEPROM is best for small, critical data.

Practical Design Checklist

Before using EEPROM, ask:

  • Does the data need to persist?
  • Does it change infrequently?
  • Is the size small?
  • Can I tolerate limited write cycles?

If yes → EEPROM is appropriate.

Final Thoughts

When used correctly, EEPROM is one of the most useful tools for Arduino projects. It lets devices act like real products by remembering settings, recovering from power loss, and keeping their calibration.

If you use it wrong, it can make your memory wear out and cause strange behaviour.

When used correctly, it greatly improves reliability and the user experience.

Share
[lebox id="2"]

You may also like