cancel
Showing results for 
Search instead for 
Did you mean: 

Unable to erase flash in NUCLEO-G0B1RE board

jo512
Associate III

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();
}

 

20 REPLIES 20

This works and is more immune to errors and less ambiguous than a series of assignments:

FLASH_EraseInitTypeDef erase_init = {
    .TypeErase = FLASH_TYPEERASE_PAGES,
    .Banks     = FLASH_BANK_1,
    .Page      = page_index,
    .NbPages   = 1
};

 

My STM32 stuff on github - compact USB device stack and more: https://github.com/gbm-ii/gbmUSBdevice