2025-10-15 4:46 AM
Hi
I am using the function below to erase the flash, but am not able to do the same.
I have to erase from address 0x0803E000UL i.e. page 124
The function does basically
1. HAL_FLASH_Unlock
2. HAL_FLASHEx_Erase(&erase_init, &page_error) - where page is 124
3. reads the erased flash area
4. HAL_FLASH_Lock
Am I missing something? I would not prefer to run the function in ram
I have MCUboot running and my application running on slot 0 is based on FreeRTOS. I am trying to erase slot1.
#define SLOT1_BASE_ADDR 0x0803E000UL
void erase_slot1_flash(void)
{
HAL_StatusTypeDef status;
uint32_t page_error = 0;
FLASH_EraseInitTypeDef erase_init;
uint32_t page_index;
/* Determine actual flash size (in KB) from system memory register */
uint32_t flash_size_kb = *(uint16_t *)FLASHSIZE_BASE;
uint32_t flash_start = FLASH_BASE;
uint32_t flash_end_addr = FLASH_BASE + (flash_size_kb * 1024UL) - 1UL;
printf("SLOT1_BASE_ADDR = 0x%08lX\r\n", (unsigned long)SLOT1_BASE_ADDR);
printf("FLASH_BASE = 0x%08lX\r\n", (unsigned long)FLASH_BASE);
printf("FLASH_SIZE_KB = %lu\r\n", (unsigned long)flash_size_kb);
printf("FLASH_START_ADDR = 0x%08lX\r\n", (unsigned long)flash_start);
printf("FLASH_END_ADDR = 0x%08lX\r\n", (unsigned long)flash_end_addr);
/* Sanity check: make sure SLOT1 lies within flash */
if ((SLOT1_BASE_ADDR < flash_start) || (SLOT1_BASE_ADDR > flash_end_addr)) {
printf("Error: SLOT1_BASE_ADDR is outside internal flash range!\r\n");
return;
}
/* Compute which flash page the slot address belongs to */
page_index = (SLOT1_BASE_ADDR - FLASH_BASE) / FLASH_PAGE_SIZE;
HAL_FLASH_Unlock();
printf("Before erase: ");
for (uint8_t i = 0; i < 16; i++) {
uint8_t val = *(uint8_t *)(SLOT1_BASE_ADDR + i);
printf(" %02x", val);
}
printf("\n\r");
/* Prepare erase configuration */
erase_init.TypeErase = FLASH_TYPEERASE_PAGES;
erase_init.Page = page_index;
erase_init.NbPages = 1;
printf("Erasing page (index=%lu, address=0x%08lX)\r\n",
(unsigned long)page_index, (unsigned long)SLOT1_BASE_ADDR);
/* Optional: clear prior flash flags */
__HAL_FLASH_CLEAR_FLAG(FLASH_FLAG_OPTVERR |
FLASH_FLAG_RDERR |
FLASH_FLAG_FASTERR |
FLASH_FLAG_MISERR |
FLASH_FLAG_PGSERR |
FLASH_FLAG_WRPERR |
FLASH_FLAG_PROGERR |
FLASH_FLAG_OPERR);
status = HAL_FLASHEx_Erase(&erase_init, &page_error);
if (status != HAL_OK) {
printf("Erase failed! HAL status=%d Flash error=%lu\r\n",
status, HAL_FLASH_GetError());
} else {
printf("Erase successful.\r\n");
}
printf("-After erase: ");
for (uint8_t i = 0; i < 16; i++) {
uint8_t val = *(uint8_t *)(SLOT1_BASE_ADDR + i);
printf(" %02x", val);
}
printf("\n\r");
HAL_FLASH_Lock();
}
2025-10-15 6:29 AM
So what happens? What do your log functions output when it fails?
You should set the erase_init.Bank parameter to bank 1.
2025-10-15 6:36 AM
Missed it
I have some more observations
when #define SLOT1_BASE_ADDR 0x0803E000UL is
FLASH_START_ADDR = 0x08000000
FLASH_SIZE_KB = 512
FLASH_END_ADDR = 0x0807FFFF
SLOT1_BASE_ADDR = 0x0803E000
Before erase: 48 65 6c 6c 6f 20 66 72 6f 6d 20 46 72 65 65 52
Erasing page (index=124, address=0x0803E000)
Erase successful.
-After erase: 48 65 6c 6c 6f 20 66 72 6f 6d 20 46 72 65 65 52
Before write: 48 65 6c 6c 6f 20 66 72 6f 6d 20 46 72 65 65 52
Write failed @0x0803e000, err=8
As shown above, Line 8 and 9 should be FFs but not
When #define SLOT1_BASE_ADDR 0x08040000UL is
FLASH_START_ADDR = 0x08000000
FLASH_SIZE_KB = 512
FLASH_END_ADDR = 0x0807FFFF
SLOT1_BASE_ADDR = 0x08040000
Before erase: 70 72 61 6a 6f 73 68 20 64 69 64 20 74 68 69 73
Erasing page (index=128, address=0x08040000)
Erase successful.
-After erase: ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
Before write: ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
String written at 0x08040000
-After write: 70 72 61 6a 6f 73 68 20 64 69 64 20 74 68 69 73
The behavior is as expected.
2025-10-15 6:39 AM
Maybe my linker file also helps
/* Memories definition */
MEMORY
{
RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 144K
FLASH (rx) : ORIGIN = 0x800C200, LENGTH = (512K - 0xC200)
}