2022-11-16 01:46 PM
Hello everyone,
My variable had a Runover even before it reached its range.
Currently, I am working with timer 2 with a frequency of 90MHz. When I retrieved the current time by `__HAL_TIM_GET_COUNTER()` and printed it by `printf("receive_time: %lu\n", (unsigned long)receive_time)`, the maximum the `receive_time` get is 16 bits although I declared it as 32 bits. I observed the printed value and it never exceeded 2^16 -1.
I also tried to print with `printf("%" PRIu32 "\n",a);` but it also returned the same.
I had another 32-bit variable `send_time` which is used later to subtract with `receive_time`. However, it gave me something in the order of 2*10^9 (2147482170 for example) besides some common values.
I want to ask what happen and if I do something wrong. If everything is correct, is there any way to handle the rollover besides having 2 timers starting at different times?
The code is here:
Radio::radio.tx_buf[0] = seq++; /* set payload */
printf("send a ready message\r\n");
Radio::Send(1, 0, 0, 0); /* begin transmission */
send_time = __HAL_TIM_GET_COUNTER(&htim2);
.
.
.
if (Radio::radio.rx_buf[0] == 100)
{
receive_time = __HAL_TIM_GET_COUNTER(&htim2);
printf("receive_time: %lu\n", (unsigned long)receive_time);
printf("send_time: %lu\n", (unsigned long)send_time);
time_difference = (receive_time - send_time)/2;
printf("time_difference: %lu\n", (unsigned long)time_difference);
uint32_t distance = time_difference * 10 / 3;
printf("Distance: %lu\n", (unsigned long)distance);
}
Thank you in advance,
Huy Nguyen.
Solved! Go to Solution.
2022-11-17 12:55 AM
Sorry I was wrong about the 32-bit timer. I didn't spot you specifying which stm32 you were using, and many are only 16-bit even for TIM2.
Looking at e.g. stm32f4xx_hal_tim.h, I see __HAL_TIM_GET_COUNTER expands to
((__HANDLE__)->Instance->CNT)
It might be worth looking at the code your compiler generates, to verify that it is doing a 32-bit access to htim2.Instance->CNT
And with a debugger seeing if the top 16-bits in TIM2->CNT ever get set.
How strongly do you know that htim2 refers to TIM2?
Regards,
Danish
2022-11-16 09:20 PM
The problem isn’t your variable.
The underlying hardware of stm32 timers is generally 16-bit. Have a look at the TIM section of the Reference Manual for your stm32 for a better understanding of the issues involved.
I strongly dislike ST’s HAL library because the documentation is inadequate. Although it helps users avoid “gotchas�?, users still need to understand the limitations of the underlying hardware, which is ONLY covered by the Reference Manual, Data Sheet and Programming Manual.
Hope this helps,
Danish
2022-11-16 11:24 PM
Hello @Danish
Thank you for your response. Before using the timer 2, I did check the manual about timer in the datasheet as below:
And timer 2 has a counter of 32-bit.
That is why I got confused a bit.
2022-11-17 12:55 AM
Sorry I was wrong about the 32-bit timer. I didn't spot you specifying which stm32 you were using, and many are only 16-bit even for TIM2.
Looking at e.g. stm32f4xx_hal_tim.h, I see __HAL_TIM_GET_COUNTER expands to
((__HANDLE__)->Instance->CNT)
It might be worth looking at the code your compiler generates, to verify that it is doing a 32-bit access to htim2.Instance->CNT
And with a debugger seeing if the top 16-bits in TIM2->CNT ever get set.
How strongly do you know that htim2 refers to TIM2?
Regards,
Danish
2022-11-17 01:03 AM
For the question "How strongly do you know that htim2 refers to TIM2?": it is in the initialization of timer 2. htim2 is just a name. And in the initialization function, the instance of htim2 is TIM2 (htim2.Instance = TIM2;)
As for your other suggestion, I will bear that in mind and check it. I think it is also about the maximum counter or Auto Reload Register (ARR).
I will update more.
2022-11-17 01:49 AM
The ARR value is the issue here. Earlier, I used the TIM10 and its maximum value is only 16 bits. Later I changed to TIM2 and its maximum value is 32 bits but I forgot to set the Period (ARR) value so the counter rolled over when it reached 16-bit. As I set the Period (ARR) value to the maximum possible (32 bits), it returned the values that I want.
Thank you for helping me.