We’ve had a code review issue raised that our code could potentially suffer issues when the RTOS tick counter wraps around; at a tick interval of 100Hz with 32-bit ticks, this would be every 2^32 ticks, or 497 days – or 248.55 days if ticks are being subtracted (used in a signed fashion).
I’d like to increase the size of TickType_t to 64 bits, i.e. “unsigned long long”. Is this likely to have any adverse side effects which would need to be addressed?
Only if you need timers and time-outs that last longer that 497 days
(using 100 HZ), I would consider increasing the width.
…and even then it is not necessary as waking unnecessarily every 497
days in not going to impact battery life in any measurable way. You
just wake, see that you timed out rather than woke due to an event, then
go back to sleep for another 497 days.
Using a 64-bit tick type on a 32-bit architecture is possible, but it
requires a very minor code change. That is not the point though - at
the moment I don’t know what the OP wishes to make this change, and if
we knew that, we could provide a helpful answer.
The review stated there was an issue in our code, not FreeRTOS.
We use xTaskGetTickCount() in a few places, e.g. to find out if a set period has elapsed since the last time an event occurred, using a function called “isTimeAfter” which has been posted here previously.
The issue was that our implementation would fail roughly every 248.5 days, when the timer wrapped around.
While the correct fix is obviously to add some kind of background task to set a “timer has expired Y/N” flag which invalidates the event flag (or to rework the code to use FreeRTOS software timers – but there was a desire not to use these because it would involve enabling another FreeRTOS build option and there was a strong desire not to do this “just for one minor feature”).
The general air of the code review was that “by increasing the timer tick to 64 bits, we can avoid problems like this in the future.”
If you change the tick type to 64-bits then you will also need to edit
the portmacro.h file for your port to set portTICK_TYPE_IS_ATOMIC to 0.
However I would not recommend it, the tick type is used all over the
place and making it twice the natural word size of the architecture will
have a performance impact.
Apparently it was originally called timeAfter – we converted it from a function-like macro to an inline function (type checking is quite important for us from a software reliability POV) and renamed it.
I should also clarify: the specific case of this going wrong is that we were advised against using FreeRTOS Software Timers as it would require an additional Third Party Review to be done on that part of FreeRTOS, and we already had “timeAfter” reviewed.
This was suggested and implemented:
A global variable is set to xTaskGetTickCount() + 5 minutes when event “A” occurs
It’s reset to five minutes when further "event A"s occur
It stops waiting completely (set to zero) when a different type of event (“B”) occurs
Other things can poll to see if the five minutes has elapsed – that is to say, event “A” has elapsed, and five minutes have elapsed without either an event “A” resetting the counter to 5 minutes again, or an event “B” to say “done waiting, too late”.
In the review, this came up:
timeAfter() will return an incorrect return value when xTaskGetTickCount reaches half of its range, but event “A” hasn’t occurred yet (the global timer is still zero).