cancel
Showing results for 
Search instead for 
Did you mean: 

Not possible to use programmable alarm and periodic wakeup functions simultaneously on the STM8L051F3 MCU?

RDien
Associate III

IRET returns to nowhere from wakeup timer ISR as soon as programmable alarm interrupt is active!

Here is the STVD screen where programmable alarm and wakeup timer interrupts are enabled and wakeup timer ISR is just about to end. In the memory window at the bottom centered you can see a nonsense address stored in stack (highlighted with yellow).


_legacyfs_online_stmicro_images_0693W00000bjJREQA2.pngNext is the screen of the result of IRET instruction


_legacyfs_online_stmicro_images_0693W00000bjJRiQAM.pngAnd a screen with programmable alarm disabled where MCU exits correctly from the ISR


_legacyfs_online_stmicro_images_0693W00000bjJSHQA2.png 

What is it?  Any clues?

1 ACCEPTED SOLUTION

Accepted Solutions
AA1
Senior III

You have a problem with stack and this is not related with alarm and wakeup timer being both enable.

Do you use large buffers of local variables?

And it seems that you develop code in assembly, not in C.

How the program reaches ISR routine?

Show the ISR code and vector table.

View solution in original post

6 REPLIES 6
AA1
Senior III

You have a problem with stack and this is not related with alarm and wakeup timer being both enable.

Do you use large buffers of local variables?

And it seems that you develop code in assembly, not in C.

How the program reaches ISR routine?

Show the ISR code and vector table.

RDien
Associate III

Hello!

I use segments. The RAM is divided in two segments ram0 and ram1. All the variables are in ram0 segment which is in 00-FF address range. The total value of all my variables is 33 bytes, so there is enough space.

#define RAM0 1
#define ram0_segment_start 0
#define ram0_segment_end FF
#define RAM1 1
#define ram1_segment_start 100
#define ram1_segment_end 1FF
#define stack_segment_start 200
#define stack_segment_end 3FF

Yes, the program is written on assembler. Here is the code.

RDien
Associate III

stm8/
 
	extern main
 	#include "mapping.inc"
 	extern tim2_handler.l
 	extern tim4_handler.l
 	extern RTC_handler.l
 	extern key1_handler.l
 	extern key2_handler.l
 	extern key3_handler.l
 	extern key4_handler.l
 	
 	segment 'rom'
 reset.l
 	; initialize SP
 	ldw X,#$03ff
 	ldw SP,X
 	jp main
 	jra reset
 	
 	interrupt NonHandledInterrupt
 NonHandledInterrupt.l
 	iret
 	
 	segment 'vectit'
 	dc.l {$82000000+reset}								; reset
 	dc.l {$82000000+NonHandledInterrupt}	; trap
 	dc.l {$82000000+NonHandledInterrupt}	; irq0
 	dc.l {$82000000+NonHandledInterrupt}	; irq1
 	dc.l {$82000000+NonHandledInterrupt}	; irq2
 	dc.l {$82000000+NonHandledInterrupt}	; irq3
 	dc.l {$82000000+RTC_handler}					; irq4
 	dc.l {$82000000+NonHandledInterrupt}	; irq5
 	dc.l {$82000000+NonHandledInterrupt}	; irq6
 	dc.l {$82000000+NonHandledInterrupt}	; irq7
 	dc.l {$82000000+key4_handler}					; irq8
 	dc.l {$82000000+key1_handler}					; irq9
 	dc.l {$82000000+NonHandledInterrupt}	; irq10
 	dc.l {$82000000+NonHandledInterrupt}	; irq11
 	dc.l {$82000000+key3_handler}					; irq12
 	dc.l {$82000000+NonHandledInterrupt}	; irq13
 	dc.l {$82000000+NonHandledInterrupt}	; irq14
 	dc.l {$82000000+key2_handler}					; irq15
 	dc.l {$82000000+NonHandledInterrupt}	; irq16
 	dc.l {$82000000+NonHandledInterrupt}	; irq17
 	dc.l {$82000000+NonHandledInterrupt}	; irq18
 	dc.l {$82000000+tim2_handler}					; irq19
 	dc.l {$82000000+NonHandledInterrupt}	; irq20
 	dc.l {$82000000+NonHandledInterrupt}	; irq21
 	dc.l {$82000000+NonHandledInterrupt}	; irq22
 	dc.l {$82000000+NonHandledInterrupt}	; irq23
 	dc.l {$82000000+NonHandledInterrupt}	; irq24
 	dc.l {$82000000+tim4_handler}					; irq25
 	dc.l {$82000000+NonHandledInterrupt}	; irq26
 	dc.l {$82000000+NonHandledInterrupt}	; irq27
 	dc.l {$82000000+NonHandledInterrupt}	; irq28
 	dc.l {$82000000+NonHandledInterrupt}	; irq29
 	
 	end

RDien
Associate III

and the ISR code

RDien
Associate III

You were right! The problem was the stack overflow. I used to call a procedure from ISR and seems like next IRQ fired before previous ISR over, so stack was overflowed.

Thanks a lot for giving a hint!

RDien
Associate III

Alright, the real reason after all was an extra IRET which made stack pointer wrap around and counting down from the top.