2025-10-28 10:51 AM - last edited on 2025-10-29 9:49 AM by mƎALLEm
Post edited by ST moderator to be inline with the community rules for the code sharing. In next time please use </> button to paste your code. Please read this post: How to insert source code.
Hey Folks,
I am writing firmware on a STM32U5A5ZJ-Q board, I am using FreeRTOS, and am running into some issues with SysTick, originally noticed when HAL_Delay() would just hang. I was also able to verify that uwTick does not change (this may be strange, because SysTick->Val does change as expected). I read in some other forums that
WARNING:
When RTOS is used, it is strongly recommended to use a HAL timebase source other than the SysTick. The HAL time base source can be changed from the Pinout tab under SYS.
My understanding is that an RTOS that has SysTick_Handler implemented overrides the __weak handler that exists in the generated code and thereby forces things using SysTick as their timing source to a low priority. Since I already have my code written, so can I just update my code to use a different time source? I'm not entirely sure how this works, although I did come across a STM32 FreeRTOS example that implements the following code
// located in stm32u5xx_it.c
void TIM6_IRQHandler(void) // TIM6 seems to be the go to alternative to SysTIck
{
HAL_TIM_IRQHandler(&htim6);
}
so I am hoping it is a relatively simple switch.
Please let me know if you need more details. Any assistance would be appreciated.
-Dylan
Solved! Go to Solution.
2025-10-29 4:55 PM - edited 2025-10-29 5:06 PM
Hi All,
I got the issue resolved. C++ was mangling my interrupt handler names so that no interrupts were firing. Originally, I had checked SysTick's counter, and that was incrementing, but the interrupt was not firing because the interrupt handler names were different under the hood. Once I updated all of my code the follow strictly C, it started working immediately. I am pretty sure there is a way to do this with C++ (I had my interrupts in extern "C" blocks to try to prevent mangling), but apparently it's somewhat tricky. Anyway, I appreciate the assistance.
2025-10-28 11:17 AM
When you create your FreeRTOS project with CubeMX, it suggests to choose another timer for HAL. TIM6/7 are obvious choices.
Anyway, it's definitely a very bad idea to use any HAL_Delay() in an RTOS-based application.
2025-10-28 11:21 AM - edited 2025-10-28 11:27 AM
Hi gbm,
Thank for the response.
I get that you should use a different timing source, but how difficult is that to work into code that is already written? My current code uses SysTick, and I want to change it to TIM6. I am assuming it's fairly doable, but I have never done embedded work before, so I am just trying to keep an eye out for gotchas.
Also, Why is it a bad idea to use HAL_Delay() in an RTOS based system? Is it just because they can cause timing issues? If so, that shouldn't be an issue, I am only using them during the system initialization and once it's up I do not use it anywhere.
2025-10-28 11:36 AM - edited 2025-10-28 11:37 AM
To efficiently use multithreading (that's what RTOS is made for) you should relinquish control to RTOS whenever you have nothing to do. That's how osDelay() works.
HAL_Delay() spends the thread's timeslice on waiting in a loop instead of telling the RTOS to switch to some useful task for a specified waiting time. If you call HAL_Delay(5) in two threads of the same priority, each of them will wait for 10 milliseconds or more.
2025-10-28 11:43 AM - edited 2025-10-28 11:46 AM
Hi gmb,
Understood, and I should be safe then since I don't use it after the firmware fully initializes and FreeRTOS has been started.
Back to my other question: does that sound like it might be the source of my issue? The issue is showing up before FreeRTOS? I am assuming it is relatively simple to just swap out some of my code to point to TIM6 instead.
2025-10-29 2:41 AM
Hello @drd1202
To select TIM6 as the HAL timebase in STM32CubeMX, simply open your project and navigate to the System Core section in the left panel, then click on SYS. In the right panel, you will find the Timebase Source dropdown menu—set this to TIM6. Once selected, CubeMX will automatically configure TIM6 to be used for the HAL timebase functions.
2025-10-29 9:44 AM
Hi @Saket_Om,
Thanks for the response.
I meant more changing it after the code is already generated, not regenerating through Cube. I made updates to the code as per this example, https://github.com/STMicroelectronics/x-cube-freertos, but TIM6 doesn't seem to be firing. I was just wondering if there were any gotchas I need to look out for if I'm making the manual change.
2025-10-29 9:58 AM - edited 2025-10-29 10:00 AM
@drd1202 wrote:
Hi gbm,
Why is it a bad idea to use HAL_Delay() in an RTOS based system? Is it just because they can cause timing issues? If so, that shouldn't be an issue, I am only using them during the system initialization and once it's up I do not use it anywhere.
If at the init stage before starting the scheduler, it's OK. But once you started the os scheduler, you should use the os delay service: for example in the tasks .
2025-10-29 4:55 PM - edited 2025-10-29 5:06 PM
Hi All,
I got the issue resolved. C++ was mangling my interrupt handler names so that no interrupts were firing. Originally, I had checked SysTick's counter, and that was incrementing, but the interrupt was not firing because the interrupt handler names were different under the hood. Once I updated all of my code the follow strictly C, it started working immediately. I am pretty sure there is a way to do this with C++ (I had my interrupts in extern "C" blocks to try to prevent mangling), but apparently it's somewhat tricky. Anyway, I appreciate the assistance.