Background
In some projects, there is a need for data storage, and read and write more frequently, and the amount of data read and written each time is not large (a few or dozens of bytes), in this case the use of EEPROM is a more convenient choice. But if you don’t want to hang an external eeprom on the hardware, you can also use the internal flash of the microcontroller to simulate the eeprom.
Principle
The following is a brief introduction of how to implement the emulated eeprom driver using the Geehy APM32F103 as an example.
The internal flash of APM32F103 can be operated in half-word unit for reading and writing. However, before writing, erasure is required. The unit of erase is a page size of 1024 bytes.
Therefore, simple erase and write cannot simulate the random read/write function of eeprom, and additional driver algorithms are needed to realize it.
Memory structure
We use two pages of internal flash to take turns erasing and writing to realize random read and write of data.
The first 4 bytes of each page are used to store the page status flag bits, there are three kinds: erased, pending transfer, valid.
At the same time, only one of the two pages is in the “valid” state, data read and write occur in the page.
4 bytes in the page as a unit of storage units. The first two bytes of each unit are the virtual address, and the last two bytes are the actual stored data.
When initializing for the first time, erase the two pages first and set the first page as “valid”.
When one of the pages is full, the status of the other page is set to “to be transferred”, and the data is copied from the valid page to the page to be transferred. After copying, the page to be transferred is set as the valid page, and the original valid page is erased and set to “Erased”.
After initialization, check the flag bits of the two pages, and if the conditions in point 2 above are not met, perform the operation in point 4. If one is a valid page and the other is a page to be transferred, perform the operation in point 5.
Write
After the internal flash page is erased, the data in each address of the page can be written only once. In order to realize the random writing of eeprom, we adopt the structure of virtual address+data to store each write operation in the order of physical address, and the latest operation will prevail. Similar to the log file system.
2 bytes of virtual address + 2 bytes of data are written each time.
In order to distinguish between valid data and invalid data, the 4-byte data cannot all be 0xFF. Therefore, the virtual address cannot be 0xFFFF.
All data are written in increasing order of physical address, with 4 byte address increments.
Before writing, you need to search for the next writable physical address on the current page, that is, find the physical address of the first invalid data (0xFFFFFFFF).
When the current page is full, process as in the previous section.
Read
The internal flash itself can be read randomly, but under the storage structure of our simulated eeprom driver, it is slightly different.
When reading, we search all the valid data in order of physical address, until we find the memory cell that matches with the virtual address to be read, then we can read out 2 bytes of data from this memory cell.
Project file
Based on the Geehy sdk, just implement the eeprom.c/.h file.
Interface
Notes:
- Virtual address does not correspond to actual flash address.
- Virtual address range is 00xFFFE
- The virtual address can be specified arbitrarily and does not correspond to the actual storage order.
- Each virtual address stores 16 bits of data
- Write and read operations are based on 16-bit data.
Address Assignment
- Modify
EE_BASE_ADDRESS
to specify the start address of eeprom data in flash.
- The end address is
EE_BASE_ADDRESS + EE_PAGE_SIZE * 2
.
- The maximum number of 16-bit data can be stored in
EE_PARA_MAX_NUMBER
.
- If space is not enough, modify
EE_SECTOR_NUM
to use more sectors.