Review of External I2C Memory Chip AT24Cxx

In the development of electronic boards, it is often necessary to sign electronic boards with some kind of serial number. This is necessary to identify the board during mass production.

External memory chips are especially important since the firmware can be completely erased, so storing the serial number on the microcontroller inside the on-chip NOR-Flash of the microcontroller itself is unreliable.

In 2012, I had a task on four AT24C16 chips to organize a non-volatile log for storing time between failures in redundant refrigeration equipment. It was necessary to quickly read and write blocks of 16 bytes each. Then I wrote the blocks to a cyclic array on a 100kHz-I2C EEPROM. Each block contained a 4-byte timestamp from the RTC. For reading and searching, I used the binary search method to retrieve the desired entry. In 4-6 seconds I found any block in memory with a total size of 8kByte.

In this text I wrote which side to approach the external EEPROM chips from.

What do you need from the docks?

No.

Dock name

Number of pages

Vendor

1

AT24C02/04/08/16

13

Huaguan

2

AT24C02/04/08/16

14

Huaguan

3

Two-wire Serial EEPROM

27

Atmel

ASIC AT24C02M5/TR is a Chinese 256 byte EEPROM chip accessed via a two-wire I2C synchronous serial interface from Huaguan Semiconductor. The memory only supports 1 million entries. It’s a simple chip. His entire spec is only 14 pages.

The AT24C02M5/TR chip costs only 11 rubles.

It contains 256 bytes. It turns out that 0.042 RUR/Byte= 44 RUR/kByte=45056 RUR/Mbyte=46.1 MRUR/GByte. Yeah. There is definitely no point in building a hard drive on EEPROM chips. Otherwise it would cost as much as 2 apartments in Moscow.

What does the AT24C02M5/TR marking mean?

Hardware

This is the pinout of the microcircuit

You can connect up to 8 such chips on the I2C bus. In order to hit them with different I2C addresses, pins A were invented[3]. The highest nimble is always 0b1010=0xA=10

It turns out that on one I2C bus from these microcircuits you can assemble a memory strip of maximum 8*2kByte=16kByte. And if you consider that the average microcontroller usually has three I2C interfaces, it turns out that on this element base there can be a maximum of 48kByte EEPROM on one electronic board.

From a programmer’s point of view, the chip looks like this.

Inside the AT24Cxx chip you can see fields planted with transistors, a high voltage generator for erasing Flash cells, a hardware I2C transceiver, an I2C selection comparator and a bus address match comparator. It is also mentioned in the spec that there is a Schmitt trigger inside.

What equipment do you need?
To develop and debug the I2C-EEPROM driver you need the following equipment

No.

Equipment

Purpose

1

Logic analyzer

To record an electrical signal from the I2C bus

2

jumpers

for connecting the debug board and module

3

debug module with AT24C02 chip

to debug the driver

4

debug board with microcontroller and I2C interface

To execute C driver code

5

WAGO 3pin clamps

for connecting the logic analyzer and I2C bus wires

6

DMM, 2 probes, 9V battery for DMM

For measuring voltage on an electronic board

Software part

Bits are transmitted most significant bit first. Reading from memory looks like this. Here we should immediately note that WORD ADDRESS is 2 bytes, even despite what was shown in the datasheet as 8 bits. Apparently this is an error in the datasheet(s). Otherwise, unit tests fail.

reading

reading

In practice, reading looks like this. Here you can see that the number 0x34 was read from chip 0x50 at address 7. Here you can see two starts and one stop.

The number 0x34 was read from an I2C chip with address 0x50 to address 0x0007.

The number 0x34 was read from an I2C chip with address 0x50 to address 0x0007.

The memory entry looks like this. In the specification the reading is shown as follows.

Figure 6: Page Write

Figure 6: Page Write

In practice, it turns out that the address is also 2 bytes. However, in the spec the address again looks like one byte. Here is a working I2C oscillogram of writing to the 0x50 chip at address 7 of the value 0x34.

Write in I2C сhip 0x50, Addr 0x0007, Byte 0x34

Write in I2C сhip 0x50, Addr 0x0007, Byte 0x34

It’s worth noting here that the AT24C02 chip needs at least 5ms to complete writing to EEPROM cells.

You can write a maximum number of bytes in a page. For the AT24C02 chip this is 8 bytes. Otherwise, the internal receive buffer will overflow and no data will be written. Well, imagine where the data will go if you decide to immediately send a gigabyte-long train of bytes via I2C?

The simplest option is to write byte by byte. One I2C packet per byte. But only then will you have to wait 5ms for each byte to be written. The entire memory can be flashed in 1.5 seconds. Or write 32 pages and it will take only 0.19 seconds.

In general, you don’t always have to write. It may happen that in the memory area that you want to register there is already exactly the same data that you want to register. Then you need to do the so-called Lazy Write. First, read the memory area and if what we want is already there, what to tell the calling function that we wrote down, and not write it ourselves. In this software way you will save the life of the chip and it will last you longer.

This is what the API for the AT24CXX chip driver might look like. Functions for reading and functions for writing.

#ifndef AT24CXX_DRV_H
#define AT24CXX_DRV_H

#include <stdbool.h>
#include <stddef.h>
#include <stdint.h>

#include "at24cxx_config.h"
#include "at24cxx_types.h"

uint8_t at24cxx_read_byte_short(uint8_t num, uint16_t address);
bool at24cxx_read_byte(uint8_t num, uint16_t address, uint8_t* const data);
bool at24cxx_read(uint8_t num, uint16_t address, void* const data, size_t size);
bool at24cxx_read_address(uint8_t num, uint16_t* const address);
bool at24cxx_is_connected(uint8_t num);
bool at24cxx_init(void);
bool at24cxx_write_ctrl(uint8_t num, bool on_off);

bool at24cxx_write(uint8_t num, uint16_t address, 
                   const uint8_t* const data, size_t size);
bool at24cxx_write_byte(uint8_t num, uint16_t address, uint8_t data);
bool at24cxx_write_page(uint8_t num, uint16_t address, uint8_t* page);
bool at24cxx_erase(uint8_t num, uint16_t address, size_t size);
bool at24cxx_erase_chip(uint8_t num);

#endif /* AT24CXX_DRV_H */

Debugging the I2C-EEPROM driver

We applied power and in the UART boot log the microcontroller wrote that it detected an AT24Cxx chip.

It makes sense to add a CRC8 calculation function to the initialization function. One byte is easier to remember. This way it will be possible, for example, in a day to determine an unauthorized change in the I2C-EEPROM if the CRC8 in the boot log suddenly turns out to be different.

Here is the result of scanning the I2C bus on which the AT24C02 sits

This is who we found here

No.

Read reply address, hex

Reply to read address, Bin

1

0x50

0101_0000

2

0x58

0101_1000

3

0xD0

1101_0000

4

0xD8

1101_1000

GPIO pins for I2C must be connected to VCC.

Reading a byte at address 8. The value 0x55 was read.

writing byte 0x85 to address 8

Deleting is essentially setting the value 0xFF.

You can also periodically read the address of the I2C chip in a super loop. This will help to quickly detect a broken I2C bus connection before it is needed for writing or reading.

Testing the AT24Cxx driver

For the AT24C02 driver I have prepared these 9 tests.

Let’s run unit tests…

It can be seen that all tests passed!

Success!

Advantages of I2C-EEPROM based on AT24Cxx

1–Energy independence

2-EEPROM is good because you can register individual FFs.

3 – two wires for memory access

Flaws

1–Expensive memory for scaling.

2–You have to wait 5ms for the end of each recording.

3–The spec does not say that the address is two-byte.

4–Low memory. Total 256 bytes.

5–The register with the id revision number of the microcircuit is missing. Because of this, you can’t write a unit test to check the readability.

Results

While developing this driver, I encountered some counter-intuitive things. The spec does not say that the address is two-byte. Nevertheless, we managed to develop a driver for this ASIC.

UART-CLI and unit tests helped a lot in debugging the code. During driver development, I never even had to use JTAG step-by-step debugging.

If you need a C driver for the AT24Cxx family of microcircuits, then write in a personal message, I will send you the sources.

Dictionary

Acronym

Decoding

EEPROM

electrically erasable programmable read-only memory

I2C

Inter-Integrated Circuit

SCL

SERIAL CLOCK

S.D.A.

SERIAL DATA

ASIC

application-specific integrated circuit

Links
https://docs.google.com/spreadsheets/d/11aj3NdqWaDlz4OA9JxOmdXYTAaJEBaWIYc7GP2Ownq0/edit#gid=0

http://www.hgsemi.com.cn
https://www.youtube.com/watch?v=s7MYZamZ4hw

https://www.youtube.com/watch?v=urfhXmCd-uA

Control questions:

1–Which bit in the I2C address corresponds to data recording?

2–How to distinguish the error “cannot be read via I2C” from the error “cannot be written via I2C”?

3–What is Lazy Write?

4–How is I2C-EEPROM better than SPI-NOR Flash?

Similar Posts

Leave a Reply

Your email address will not be published. Required fields are marked *