2019-02-11 08:45 AM
Hi,
I am struggling with HW timers when using FreeRTOS. Using H743ZI Nucleo Board and writing on FreeRTOS application examples.
I have changed ThreadCreation application a little bit: created another task that initializes LEDs and a timer, and creates other 2 tasks.
In the modified application, I have tried to setup a timer to get interrupts in every 4 us that only blinks an LED. None of LEDs were blinking and when debugging paused, system goes Default_Handler.
If I comment out timer part, FreeRTOS and tasks works fine; if osKernelStart() line is commented out, timer and interrupt works fine. But I need both so any help will be magnificent.
Here is some part of code:
int main(void)
{
/* Enable the CPU Cache */
CPU_CACHE_Enable();
HAL_Init();
/* Configure the system clock to 400 MHz */
SystemClock_Config();
/* Init thread definition */
osThreadDef(INIT, Init_Thread, osPriorityNormal, 0, configMINIMAL_STACK_SIZE);
/* Start thread 1 */
InitThreadHandle = osThreadCreate(osThread(INIT), NULL);
/* Start scheduler */
osKernelStart();
/* We should never get here as control is now taken by the scheduler */
for (;;);
}
And initialization thread (Other threads are same as example):
static void Init_Thread(void const *argument)
{
TIM_HandleTypeDef TimHandle;
uint8_t asdf;
/* Initialize LEDs */
BSP_LED_Init(LED1);
BSP_LED_Init(LED2);
__HAL_RCC_TIM3_CLK_ENABLE();
TimHandle.Instance = TIM3;
TimHandle.Init.Period = 560;
TimHandle.Init.Prescaler = 1;
TimHandle.Init.ClockDivision = 0;
TimHandle.Init.CounterMode = TIM_COUNTERMODE_UP;
TimHandle.Init.RepetitionCounter = 0;
TimHandle.Init.AutoReloadPreload = TIM_AUTORELOAD_PRELOAD_DISABLE;
/* TIM13 interrupt Init */
HAL_NVIC_SetPriority(TIM3_IRQn, 0, 0);
HAL_NVIC_EnableIRQ(TIM3_IRQn);
asdf = HAL_TIM_Base_Init(&TimHandle);
configASSERT(!asdf);
/*##-2- Start the TIM Base generation in interrupt mode ####################*/
/* Start Channel1 */
asdf = HAL_TIM_Base_Start_IT(&TimHandle);
configASSERT(!asdf);
/* Thread 1 definition */
osThreadDef(LED1, LED_Thread1, osPriorityNormal, 0, configMINIMAL_STACK_SIZE);
/* Thread 2 definition */
osThreadDef(LED2, LED_Thread2, osPriorityNormal, 0, configMINIMAL_STACK_SIZE);
/* Start thread 1 */
LEDThread1Handle = osThreadCreate(osThread(LED1), NULL);
/* Start thread 2 */
LEDThread2Handle = osThreadCreate(osThread(LED2), NULL);
for(;;) osThreadTerminate(NULL);
}
And the IRQHandler:
static void TIM3_IRQHandler(void)
{
BSP_LED_Toggle(LED3);
}
Solved! Go to Solution.
2019-02-12 02:21 PM
Minimally, since you have enabled the TIM Update event:
static void TIM3_IRQHandler(void)
{
__HAL_TIM_CLEAR_IT(&TimHandle, TIM_IT_UPDATE);
// clear TIM interrupt pending bit
BSP_LED_Toggle(LED3);
}
2019-02-11 08:50 AM
Unless your IRQ Handler clears the source it is going to be re-entering indefinitely.
2019-02-12 02:24 AM
Hi Clive, thank you for reply.
What do you mean by clearing sources? Is the problem about timer initialization? Can you show me an example?
2019-02-12 02:21 PM
Minimally, since you have enabled the TIM Update event:
static void TIM3_IRQHandler(void)
{
__HAL_TIM_CLEAR_IT(&TimHandle, TIM_IT_UPDATE);
// clear TIM interrupt pending bit
BSP_LED_Toggle(LED3);
}
2019-02-13 12:12 AM
Thank you both, my inattention.