AnsweredAssumed Answered

Interrupt generation on flash writes

Question asked by saviane.giorgio on Jun 20, 2013
I recently extended the eeprom emulation code provided by ST to perform asynchronous page transfer when a flash page has no more space left.
I need this feature because my embedded system runs in real time fashion (10 ms time slot or less), so when a page transfer occurred it would take too much time to synchronously copy one page into another and erase the old one.
So I implemented a page transfer state machine based on EOP interrupt letting other tasks to run.
All worked fine but most of the times the EOP interrupt wasn't generated on page erase operation. Thus the page transfer didn't closed correctly, leaving the pages structure corrupted.
I investigated more and more and now I can show the solution.
The library firmware functions FLASH_ErasePage() and FLASH_ProgramHalfWord() perform erase and programming setting bits PER and PG in FLASH_CR register respectively.
It sounds correct as stated in PM0075 but those functions take care only of their own operation bits leaving the other bits unaltered. So, what's happen when one use FLASH_ProgramHalfWord() first and FLASH_ErasePage() after?
The second function called has both PER and PG bits set, so the controller cannot distinguish what kind of operation has been requested, and may be the EOP interrupt  won't be generated.
Adding an instruction to clear the unwanted bits on the register did the things work as expected:


FLASH_ProgramHalfWord()
...
    /* if the previous operation is completed, proceed to program the new data */
    FLASH->CR &= (CR_MER_Reset & CR_PER_Reset); //<-- clear unwanted ops
    FLASH->CR |= CR_PG_Set;
 
    *(__IO uint16_t*)Address = Data;

FLASH_ErasePage()
...
    /* if the previous operation is completed, proceed to erase the page */
    FLASH->CR &= (CR_MER_Reset & CR_PG_Reset);  //<-- clear unwanted ops
    FLASH->CR|= CR_PER_Set;
    FLASH->AR = Page_Address;

Hope this could help someone had a similar problem.

Regards

Giorgio Saviane

Outcomes