Working with stm8 in Linux

I was ordering some uCs a while back and I saw that the STM8 Discovery and decided to pick it up, because I needed something to get free overnight shipping.

I’ve recently decided to look at it again and thought I’d try my hands at programming it. I found this guide and followed it’s instructions, but I ran into this problem:

main.c:1:19: fatal error: stm8s.h: No such file or directory
compilation terminated.
main.c:1: warning 190: ISO C forbids an empty source file

Nota Bene: the discovery uses the stm8s and not the stm8l

So, I thought that was weird that it wouldn’t compile. I made sure to install the libs, so let’s see if we can find the header:

find / -name stm8s.h 2>/dev/null

but that turned up nothing…

Let’s try again:

find / -name stm8.h 2>/dev/null
#For those who are beginners and are wondering what I'm doing the 2>/dev/null
#it is because I don't care about files or directories I don't have access to
#for example /root/

This did turn up something, but:


Which isn’t what we’re looking for…
Removing the #include statement only causes different errors.

Let’s take a look at something:

/usr/share/sdcc/include # ls
asm ds80c390.h limits.h pic16 stdbool.h stdnoreturn.h z180
assert.h errno.h malloc.h sdcc-lib.h stddef.h string.h
ctype.h float.h math.h setjmp.h stdint.h time.h
ds390 hc08 mcs51 stdalign.h stdio.h tinibios.h
ds400 iso646.h pic14 stdarg.h stdlib.h typeof.h

Oh…so there is no stm8s.h…Well, what does the part of sdcc source tree say? Answer: Nothing.

But wait a moment: lookie here: stm8.h

For right now, let’s just download it and compile with it..

sdcc -lstm8 -mstm8 --out-fmt-ihx main.c
stm8.h:176: syntax error: token -> 'machine' ; column 19

We are very close to solving this!

So it looks like the maintainer for this package might have goofed, but before we point the finger, let’s download the sdcc source and compile by hand:

svn co svn:// sdcc-code #This takes a while, so only do this if you want to..

cd ./sdcc-code

./configure #I was missing gputils, so you may need that as well.

make -j $((2 * `nproc`)) #I recommend 2 * the num cpus you have although you can just run make, but it takes a while since there are so many PIC uCs to compile for..

sudo make install

Alright! Let’s give this a try:

/usr/local/bin/sdcc -lstm8 -mstm8 --out-fmt-ihx main.c

main.c:1:18: fatal error: stm8.h: No such file or directory
compilation terminated.
main.c:1: warning 190: ISO C forbids an empty source file


Well, the install docs say to see sdccman.pdf (which of course sdccman.tex couldn't be found...) eventually I found myself on the sdcc wiki which referred me to this site and wouldn't you know it...they have a blinky LED as well; however, they aren't #include  or anything at all they just have a batch of defines at the top...lovely

// Source code under CC0 1.0

#define CLK_DIVR	(*(volatile uint8_t *)0x50c6)
#define CLK_PCKENR1	(*(volatile uint8_t *)0x50c7)

#define TIM1_CR1	(*(volatile uint8_t *)0x5250)
#define TIM1_CNTRH	(*(volatile uint8_t *)0x525e)
#define TIM1_CNTRL	(*(volatile uint8_t *)0x525f)
#define TIM1_PSCRH	(*(volatile uint8_t *)0x5260)
#define TIM1_PSCRL	(*(volatile uint8_t *)0x5261)

#define PD_ODR	(*(volatile uint8_t *)0x500f)
#define PD_DDR	(*(volatile uint8_t *)0x5011)
#define PD_CR1	(*(volatile uint8_t *)0x5012)

unsigned int clock(void)
	unsigned char h = TIM1_CNTRH;
	unsigned char l = TIM1_CNTRL;
	return((unsigned int)(h) << 8 | l);
void main(void)

	CLK_DIVR = 0x00; // Set the frequency to 16 MHz

	// Configure timer
	// 1000 ticks per second
	TIM1_PSCRH = 0x3e;
	TIM1_PSCRL = 0x80;
	// Enable timer
	TIM1_CR1 = 0x01;

	PD_DDR = 0x01;
	PD_CR1 = 0x01;

		PD_ODR = (clock() % 1000 < 500) & 1;

So, adding those defines works. However, let's just copy the above code, compile it, and flash it:

stm8flash -c stlink -p stm8s003k3 -w stm8_main.c

And of course it works...

Now something VERY important is that there is a difference between the stm8 value line discovery and the stm8 discovery. They use different uCs and while compiling the code will be the same, using stm8flash won't. So if it seems to take forever to flash your device, then double check your chip (-p option).

In conclusion, it isn't the maintainer that goofed, but instead there is something strange with the original tutorial. Maybe Debian based distributions of sdcc include that header, maybe the author wrote it, but didn't list it, or who knows?

I'd suggest putting that into a header file so you can just include it in future projects. My goal is to take this device and make a Nokia 5110 display work with it. And before you ask, I haven't forgotten about the dash-cam project. I have most of the stuff done, I just need to do some additional writing to show how I got to where I got.

Now I am not a fan of the setup for stm8flash. I may submit a patch so everything is done "correctly" with ./configure, make, make install, but that's for a different time.

2018/01/08 UPDATE:

I've submitted a pull request. My forked repo can be found here

This entry was posted in Computer Science, Engineering and tagged , , . Bookmark the permalink.

Leave a Reply

This site uses Akismet to reduce spam. Learn how your comment data is processed.