STM8L: ULOCKF/NVM freeze when bootloader enabled (known errata)
yumkam opened this issue · 1 comments
According to, "STM8AL3xx6/8 STM8Lx5xx4/6 Errata sheet", section 1.2.6, "Program memory are write unprotected after reset when embedded bootloader enabled", if bootloader is enabled, it
- leaves flash unprotected upon reset/boot;
- writes incorrect sequence into
FLASH_PUKR
register;
And once you write incorrect sequence intoFLASH_PUKR
, it is not possible to recover till reset (correct sequence will be ignored).
As a result,LOCKF ULOCKF
(orNVM RAM NVM
) results in freeze (flash is unprotected upon reset --- unlock sequence is ignored, but initiallyFLASH_IAPSR.PUL==1
, so firstNVM
succeeds, thenLOCKF
protects flash, thenULOCKF
cannot unprotect it again, and waits forever forFLASH_IAPSR.PUL
).
(I verified this on STM8L151K6, rev.Y)
Possible workarounds:
- suggest to disable bootloader (use stlink/SWIM instead, etc) in documentation;
- turn
LOCKF
into no-op (for affected parts);
2a) remember previous state inULOCKF
and keep it unprotected inLOCKF
if saved state was unprotected: on affected parts flash is unprotected upon reset/boot, and it will remain unprotected; on unaffected parts,ULOCKF ... LOCKF
will work as before. - ignore: it is stm8l bootloader firmware issue, not a stm8ef bug;
@yumkam I've never worked with the serial bootloader, so thanks for analyzing and reporting this issue!
Since it extends the current use-case (initial flashing through SWIM) but works around a bug in the STM8L "Medium density" boot-ROM, I classify it as an "enhancement".
Regarding the proposed workarounds:
- accepted, I'll add that to the docs
- possibly, see below
- rejected, your work shall not be in vain :-)
Regarding 2: maybe there are even more solution options:
- quick fix: tentatively write a
RET
toLOCKF
after flashing by entering "$81 ' LOCKF C!
" (this can be reversed by writing$72
). - upon reset check if the flash is unlocked and issue a reset, e.g.:
\ ?fix#409 resets a device when Flash is hard-unlocked by STM8L boot-ROM
\res MCU: STM8L151
\res export FLASH_IAPSR
#require ]B@IF
: ?fix#409 ( -- ) [ FLASH_IAPSR 1 ]B@IF [ 0 C, ] THEN ;
It's of course possible to anchor ?fix#409
in the startup chain, e.g. (: init ?fix#409 hi ; ' init 'BOOT
).
- It would also be possible to put reset code in
BOARDINIT
(inboardcore.inc
in the board configuration folder) - detecting and saving the unlocked state during cold start is possible but it would require some more considerations. Please check if one of the solutions above would be viable.
@yumkam please check if one of the options works for someone who uses the boot-ROM.