Introduction: Simple EEPROM Module for Arduino or Other Microcontroller
EEPROMs come in handy if you want to store some data without losing it. Many microcontrollers come with some internal EEPROM, but as EEPROMs have a finite (though very large) number of writes before they start becoming faulty, my anal retentive character always had a problem with using that internal EEPROM.
There are other reasons too why you might want to use an external EEPROM: data logging in which you just want to swap an EEPROM rather than having to read out your microcontroller in the field.
Anyway, I just wanted to share a simple 5 minute build EEPROM module that is a bit simpler than a prior one i published.
BOM
1x 24LC256 EEPROM (or other size)
2x 4k7 resistors
stripboard 5 strips of 8
8 pin DIL IC socket (optional)
I am using a 24LC256. That is a 256 kiloBIT EEPROM so in fact only a 32kiloBYTE EEPROM in my traditional way of thinking. These are not to expensive. Can be had for around 80 ct USD.
Although the board can also be used for smaller EEPROMS, like a 24C32, I would advise against that. If that is what you need, buy a 50 ct DS1307 RTC module that includes a 24C32 (which is actually 4kByte).
Anyway, the 24LC256 is an I2C EEPROM, which is pretty standard and which makes use easy
Pins A0, A1 and A2 select the I2C addresses, (A0=pin1, A1=pin1, A2=pin3).
The adressing is as follows
1 | 0 | 1 | 0 | A2 | A1 | A0 | x |
So if you connect pins A0, A1, A2 to GND the I2C address will be 1010000 = 0x50 in hexadecimal.
If you connect them all to Vcc it will be 1010111=0x57.
As 0x50 is an address that is often used, I decided to connect A2 and A1 to ground and A0 to Vcc, which gives 0x51. It also made the design a tadd simpler.
Pin 7 is the 'WriteProtect' pin that needs to be pulled HIGH for ReadOnly and LOW for Read/Write. Obviously I connected it to ground.
The pull up resistors are both 4k7
You will find many EEPROM libraries in the Arduino Playground I tend to use the following code to read and write:
void writeData(int device, unsigned int addr, byte data) // writes a byte of data 'data' to the chip at I2C address 'device', // in memory location 'add' { if ( addr > 65535 ) addr = addr | B00001000; Wire.beginTransmission(device); Wire.write((int)(addr >> 8)); // left-part of pointer address Wire.write((int)(addr & 0xFF)); // and the right Wire.write(data); Wire.endTransmission(); delay(10); } byte readData(int device, unsigned int add) // reads a byte of data from memory location 'add' in chip at I2C address 'device' { byte result; // returned value Wire.beginTransmission(device); // these three lines set the pointer // position in the EEPROM Wire.write((int)(add >> 8)); // left-part of pointer address Wire.write((int)(add & 0xFF)); // and the right Wire.endTransmission(); Wire.requestFrom(device, 1); // now get the byte of data... result = Wire.read(); return result; // and return it as a result of the function readData }
Special Notes if using the 24LC1025
This board can also be used for larger EEPROMS, but......... if you use it for the 24LC1025, you need to make a small adaptation. With this chip A2 MUST be tied to Vcc for it to operate.
The 24LC1025 has an internal addressing boundary limitation that is divided into two segments of 512K bits. Block select bit ‘B0’ to control access to each segment.
The adressing is determined by 1010B0A1A0R/-W in which the 'Block select bit is used to address the lower or higher 512k Block The chip thus has 2 different addresses. with the A0A1 selection as in my board those are:
1010101 =0x55
1010001 =0x51
For memory access from 0..65535 the I2C address for the Memory Chip is 0x51. If you want to access memory between 65536..131071 the Chip address is 0x55
You cannot write across the 65535..65536 byte boundary with breaking the operation into two write() calls. One to chip 0x51, the other to chip 0x55.