123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194 |
- /*
- * Copyright (c) 2020, Armink, <armink.ztl@gmail.com>
- *
- * SPDX-License-Identifier: Apache-2.0
- */
- #include <fal.h>
- #include <stm32f2xx.h>
- /* base address of the flash sectors */
- #define ADDR_FLASH_SECTOR_0 ((uint32_t)0x08000000) /* Base address of Sector 0, 16 K bytes */
- #define ADDR_FLASH_SECTOR_1 ((uint32_t)0x08004000) /* Base address of Sector 1, 16 K bytes */
- #define ADDR_FLASH_SECTOR_2 ((uint32_t)0x08008000) /* Base address of Sector 2, 16 K bytes */
- #define ADDR_FLASH_SECTOR_3 ((uint32_t)0x0800C000) /* Base address of Sector 3, 16 K bytes */
- #define ADDR_FLASH_SECTOR_4 ((uint32_t)0x08010000) /* Base address of Sector 4, 64 K bytes */
- #define ADDR_FLASH_SECTOR_5 ((uint32_t)0x08020000) /* Base address of Sector 5, 128 K bytes */
- #define ADDR_FLASH_SECTOR_6 ((uint32_t)0x08040000) /* Base address of Sector 6, 128 K bytes */
- #define ADDR_FLASH_SECTOR_7 ((uint32_t)0x08060000) /* Base address of Sector 7, 128 K bytes */
- #define ADDR_FLASH_SECTOR_8 ((uint32_t)0x08080000) /* Base address of Sector 8, 128 K bytes */
- #define ADDR_FLASH_SECTOR_9 ((uint32_t)0x080A0000) /* Base address of Sector 9, 128 K bytes */
- #define ADDR_FLASH_SECTOR_10 ((uint32_t)0x080C0000) /* Base address of Sector 10, 128 K bytes */
- #define ADDR_FLASH_SECTOR_11 ((uint32_t)0x080E0000) /* Base address of Sector 11, 128 K bytes */
- /**
- * Get the sector of a given address
- *
- * @param address flash address
- *
- * @return The sector of a given address
- */
- static uint32_t stm32_get_sector(uint32_t address)
- {
- uint32_t sector = 0;
- if ((address < ADDR_FLASH_SECTOR_1) && (address >= ADDR_FLASH_SECTOR_0))
- {
- sector = FLASH_Sector_0;
- }
- else if ((address < ADDR_FLASH_SECTOR_2) && (address >= ADDR_FLASH_SECTOR_1))
- {
- sector = FLASH_Sector_1;
- }
- else if ((address < ADDR_FLASH_SECTOR_3) && (address >= ADDR_FLASH_SECTOR_2))
- {
- sector = FLASH_Sector_2;
- }
- else if ((address < ADDR_FLASH_SECTOR_4) && (address >= ADDR_FLASH_SECTOR_3))
- {
- sector = FLASH_Sector_3;
- }
- else if ((address < ADDR_FLASH_SECTOR_5) && (address >= ADDR_FLASH_SECTOR_4))
- {
- sector = FLASH_Sector_4;
- }
- else if ((address < ADDR_FLASH_SECTOR_6) && (address >= ADDR_FLASH_SECTOR_5))
- {
- sector = FLASH_Sector_5;
- }
- else if ((address < ADDR_FLASH_SECTOR_7) && (address >= ADDR_FLASH_SECTOR_6))
- {
- sector = FLASH_Sector_6;
- }
- else if ((address < ADDR_FLASH_SECTOR_8) && (address >= ADDR_FLASH_SECTOR_7))
- {
- sector = FLASH_Sector_7;
- }
- else if ((address < ADDR_FLASH_SECTOR_9) && (address >= ADDR_FLASH_SECTOR_8))
- {
- sector = FLASH_Sector_8;
- }
- else if ((address < ADDR_FLASH_SECTOR_10) && (address >= ADDR_FLASH_SECTOR_9))
- {
- sector = FLASH_Sector_9;
- }
- else if ((address < ADDR_FLASH_SECTOR_11) && (address >= ADDR_FLASH_SECTOR_10))
- {
- sector = FLASH_Sector_10;
- }
- else
- {
- sector = FLASH_Sector_11;
- }
- return sector;
- }
- /**
- * Get the sector size
- *
- * @param sector sector
- *
- * @return sector size
- */
- static uint32_t stm32_get_sector_size(uint32_t sector) {
- assert(IS_FLASH_SECTOR(sector));
- switch (sector) {
- case FLASH_Sector_0: return 16 * 1024;
- case FLASH_Sector_1: return 16 * 1024;
- case FLASH_Sector_2: return 16 * 1024;
- case FLASH_Sector_3: return 16 * 1024;
- case FLASH_Sector_4: return 64 * 1024;
- case FLASH_Sector_5: return 128 * 1024;
- case FLASH_Sector_6: return 128 * 1024;
- case FLASH_Sector_7: return 128 * 1024;
- case FLASH_Sector_8: return 128 * 1024;
- case FLASH_Sector_9: return 128 * 1024;
- case FLASH_Sector_10: return 128 * 1024;
- case FLASH_Sector_11: return 128 * 1024;
- default : return 128 * 1024;
- }
- }
- static int init(void)
- {
- /* do nothing now */
- }
- static int read(long offset, uint8_t *buf, size_t size)
- {
- size_t i;
- uint32_t addr = stm32f2_onchip_flash.addr + offset;
- for (i = 0; i < size; i++, addr++, buf++)
- {
- *buf = *(uint8_t *) addr;
- }
- return size;
- }
- static int write(long offset, const uint8_t *buf, size_t size)
- {
- size_t i;
- uint32_t read_data;
- uint32_t addr = stm32f2_onchip_flash.addr + offset;
- FLASH_Unlock();
- FLASH_ClearFlag(
- FLASH_FLAG_EOP | FLASH_FLAG_OPERR | FLASH_FLAG_WRPERR | FLASH_FLAG_PGAERR | FLASH_FLAG_PGPERR
- | FLASH_FLAG_PGSERR);
- for (i = 0; i < size; i++, buf++, addr++)
- {
- /* write data */
- FLASH_ProgramByte(addr, *buf);
- read_data = *(uint8_t *) addr;
- /* check data */
- if (read_data != *buf)
- {
- return -1;
- }
- }
- FLASH_Lock();
- return size;
- }
- static int erase(long offset, size_t size)
- {
- FLASH_Status flash_status;
- size_t erased_size = 0;
- uint32_t cur_erase_sector;
- uint32_t addr = stm32f2_onchip_flash.addr + offset;
- /* start erase */
- FLASH_Unlock();
- FLASH_ClearFlag(
- FLASH_FLAG_EOP | FLASH_FLAG_OPERR | FLASH_FLAG_WRPERR | FLASH_FLAG_PGAERR | FLASH_FLAG_PGPERR
- | FLASH_FLAG_PGSERR);
- /* it will stop when erased size is greater than setting size */
- while (erased_size < size)
- {
- cur_erase_sector = stm32_get_sector(addr + erased_size);
- flash_status = FLASH_EraseSector(cur_erase_sector, VoltageRange_3);
- if (flash_status != FLASH_COMPLETE)
- {
- return -1;
- }
- erased_size += stm32_get_sector_size(cur_erase_sector);
- }
- FLASH_Lock();
- return size;
- }
- const struct fal_flash_dev stm32f2_onchip_flash =
- {
- .name = "stm32_onchip",
- .addr = 0x08000000,
- .len = 1024*1024,
- .blk_size = 128*1024,
- .ops = {init, read, write, erase},
- .write_gran = 8
- };
|