cancel
Showing results for 
Search instead for 
Did you mean: 

Systick handler problems

xinjin
Associate II
Posted on March 01, 2013 at 04:44

Dear,

    I want to test the systick clock frequency. And use the systick as the RTOS system timer. It would be set to 1ms. And I use the configuration of the demo code as following:

 if (SysTick_Config(SystemCoreClock/1000))

 {

  /* Capture error */

  while (1);

And I add the LED toggler as following in the handler:

void SysTick_Handler(void)

{   

        STM_EVAL_LEDToggle(LED3);

}

I use oscilloscope to test, it would work only for serval time and stoped. On the other hand, I use USART3 to print the test information on PC, it would work continuously, but the frequency became 78Hz instead of 1KHz. Could anyone can tell me what is the problem? Appreciate.

B.R.

Jin
7 REPLIES 7
Posted on March 01, 2013 at 12:43

I suspect something else is going on if it stops. Perhaps you can confirm outside the RTOS.

You definitely don't want to be printing directly to a USART and blocking under such an interrupt. You could place such data in a buffer to be output a byte at a time via a USART interrupt, but if you're generating data at a higher rate than can be output you're still going to have some issues, or will need to lose some output.
Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..
xinjin
Associate II
Posted on March 04, 2013 at 04:09

Thanks for your suggestio. However, I still have two things do not understand, so I have no idea where to track my problem. One thing is that, depending on the vector table, there is no more higher priority exception than systick interrupt(I tracked all the exception higher than systick, found none), so which would stop it. Another thing is that, I can printf information in systick handler, it seems the interrupt is not stopped, but why the LED can't toggle?

I would add some information if it is useful for helping me found the bugs. There is no service in the main loop only endless service check called by the OS. When I put the LED togglling in the endless loop, it works at every us.

Posted on March 04, 2013 at 05:34

I guess I'd take a look at a few things.

Insure it's not in a Hard Fault state.

Check the stacks, and utilization.

Break out the debugger in the failing state and examine the peripheral state.

Breakpoint the SysTick code, confirm if it is running/functioning.
Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..
xinjin
Associate II
Posted on March 04, 2013 at 06:05

I made a debug following your instruction.

1. Track in the Hardfault_handler, no entry. Break the debug running, stop at the endless running loop.

2. Increase the stack size from 0x400 to 0x600, no changes.

3. Breakpoint the systick code and manually run it step by step. It can toggle the LED at every step.

Additionally, I reviewed my code again and found that there is time related service, it would use systick to drive. When I unregister this service, it works well. But if I register this service and do not use it. It fails.

xinjin
Associate II
Posted on March 04, 2013 at 06:59

I debugged again for my code and found that, the systick handler is entered for 24 times and stopped, even in step by step debugging mode manually. Is it related to 24-bit counter for systick or any ideas? Appreciate for any help.

xinjin
Associate II
Posted on March 04, 2013 at 08:44

I would like to update the progress of the debugging. I found that after systick interrupt for 24 times and stopped, the endless service checking is executed. Before that, the endless service checking loop would not run. It seems the code runs in turn instead of interrupt. I can't understand why.

xinjin
Associate II
Posted on March 05, 2013 at 08:02

Finally, I find the root cause. Because I use the following code to save and restore the interrupt status in OS.

 #define DISABLE_BLOCK_START { \

        t_irq_state_save _saved_istate = __get_PRIMASK(); \

        disable();

 #define DISABLE_BLOCK_END \

        __set_FAULTMASK(_saved_istate); \

        }

When I change it to

 #define DISABLE_BLOCK_START { \

        t_irq_state_save _saved_istate = __get_interrupt_state(); \

        disable();

 #define DISABLE_BLOCK_END \

        __set_interrupt_state(_saved_istate); \

        }

It works. But I still can't understand why it would disable the systick and do not restore.