STM8L001J3M3: another SOP-8 µC runs STM8 eForth

A project log for eForth for cheap STM8S gadgets

Turn cheap modules from AliExpress into interactive development kits!

ThomasThomas 09/22/2020 at 19:470 Comments

Flashing an STM8L001J3M3 never worked for me and I had given up - until debugging an STM8L101F3 with OpenOCD and stm8-gdb showed that I had been chasing a phantom.

I figured that clearing the chip might help but that didn't work, until now: the OpenOCD STM8L example target configuration had RESET ROP (Read-Out Protection) wrong!

EDIT: It's true that the reset routine in the STM8L152.cfg is wrong ... for the STM8L101 family, not for STM8L051 Low Density devices! A file stm8l101.cfg should simply use the stm8_clear_rop code in stm8_clear_rop and that's it.

Fortunately, OpenOCD uses Jim, a TCL subset, for configuration and writing a new "stm8_clear_rop" was quickly done:

#config script for STM8L101

set BLOCKSIZE 0x40

proc stm8_reset_rop {} {
   mwb 0x4800 0xaa
   mwb 0x4800 0xaa
   reset halt

proc stm8_clear_rop {} {
   mwb 0x4800 0x00
   reset halt

source [find target/stm8l.cfg]

After typing the new command on the OpenOCD telnet console programming just worked!

A STM8L001J3M3 is basically a STM8L101 chip in a SOP-8 package.

The problem with this thing is that there is

  1. a fair chance to lock the chip up by setting any of the GPIOs PA0, PC3 or PC4 to output mode after reset so that PA0/SWIM no longer works
  2. UART TX is on PC3 - this obviously means "output mode"
  3. there is no NRST to back you up if you made a mistake

The STM8L101F3 code works around this by *not* configuring PC3 to push pull -  the STM8L101F3 binary uses a weak pull-up and active low signaling. It's possible that the pull-up is too weak, but an external 4k7 pull-up will help.


I just tested a Forth console through the simulated serial interface: it works nicely! This means that at least the core functionality of GPIOs and TIM4 (interrupts, peripheral registers) are compatible with the STM8L051 STM8L Low Density devices.

I'm using the following UART section:

        HALF_DUPLEX      = 0    ; Use UART in half duplex mode
        HAS_TXUART       = 0    ; UART TXD, word TX!
        HAS_RXUART       = 0    ; UART RXD, word ?RX
        HAS_TXSIM        = 1    ; Enable TxD via GPIO/TIM4, word TXGP!
        HAS_RXSIM        = 1    ; Enable RxD via GPIO/TIM4, word ?RXGP
        PSIM     = PORTB        ; Port for UART simulation
        PNRX             = 6    ; Port GPIO# for HAS_RXDSIM
        PNTX             = 7    ; Port GPIO# for HAS_TXDSIM

It's also possible to use the simulated port half-duplex mode (which means that RX/TX and SWIM should get along fine on pin1.