cancel
Showing results for 
Search instead for 
Did you mean: 

Timer Interrupt STM32F4

wkanew
Associate
Posted on June 13, 2013 at 05:44

I'm having difficulty getting a simple timer reload interupt system to work.

Once the initTimer() method is called the MCU appears to stop.  Even when I comment out ''

soloInd->flash();

''

Any help at all would be much appreciated.

#include ''stm32f4xx_tim.h''

Indicators *soloInd;

void Indicators::initTimer()

{

    // Use Timer 5

    TIMx = TIM5;

    NVIC_InitTypeDef NVIC_InitStructure;

    TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;

    RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM5, ENABLE);

    // Initialise TimeBaseStructure with default values.

    TIM_TimeBaseStructInit(&TIM_TimeBaseStructure);

    TIM_TimeBaseInit(TIMx, &TIM_TimeBaseStructure);

    /* Enable timer 5 capture compare Interrupt */

    register_interrupt(TIM5_IRQn, Indicators::IND_IRQ_Handler);

    NVIC_InitStructure.NVIC_IRQChannel = TIM5_IRQn;

    NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;

    NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;

    NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;

    NVIC_Init(&NVIC_InitStructure);

    TIM_ITConfig(TIMx, TIM_IT_Update, ENABLE);

}

void Indicators::IND_IRQ_Handler()

{

    TIM5->SR &= ~TIM_SR_UIF;

    soloInd->flash();

}

// Not sure how this method works, was already written.

inline void register_interrupt(uint8_t vector_offset,  void (*function)())

{

    ((uint32_t*)SCB->VTOR)[(uint16_t)vector_offset + 16] = (uint32_t)function;

}

2 REPLIES 2
Posted on June 13, 2013 at 09:13

>

    TIM5->SR &= ~TIM_SR_UIF;

No, you want

TIM5->SR = ~TIM_SR_UIF;

as all bits in TIMx_SR register are of rc_w0 type (look up in user manual what does that mean).

But this is not likely to be the root of your problem.

// Not sure how this method works, was already written.

This is your problem. ''was already written'' is no excuse - it's your responsibility to assure that things do work, isn't it. Once you know how this method works, you will probably know where's your problem, too.

The VTOR register determines, where is the interrupt vectors table located. And, as you want to write into it, it has to be located in RAM, whereas after reset it is located in FLASH. So, there has to be some code - explicit or implicit (from toolchain, libraries, RTOS, whatever) which changes it to point into RAM before you call this method the first time. Also, after you call this method, VTOR should not change.

JW

Posted on June 13, 2013 at 12:08

The purpose is not to change VTOR, but to index relative to it's current value, presumably in SRAM, to insert a vector into the table. This addresses two issues, a) that C++ mangles the function names, b) allows vectors to be changed.

The VTOR address would still need to fall on a 512-byte boundary.

Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..