Skip to content

Commit de915a0

Browse files
committed
Correct SysTimer absolute time calculations
`SysTimer::set_wake_time` incorrectly assumed that the `SysTimer`s tick count and the underlying HAL timer had the same zero base. This normally holds, at least approximately, in RTOS builds where the HAL timer starts from zero at the same time the SysTimer is initialised. But in bare metal builds, the HAL timer could be started some time before the SysTimer, giving a significant discrepancy. Beyond that, there's no requirement for HAL timers to start from zero in the spec. Record the HAL timer start time to get the conversion right.
1 parent ee1d998 commit de915a0

File tree

2 files changed

+6
-3
lines changed

2 files changed

+6
-3
lines changed

platform/source/SysTimer.cpp

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,8 @@ SysTimer<US_IN_TICK, IRQ>::SysTimer() :
5252
#else
5353
TimerEvent(get_us_ticker_data()),
5454
#endif
55-
_time_us(ticker_read_us(_ticker_data)),
55+
_epoch(ticker_read_us(_ticker_data)),
56+
_time_us(_epoch),
5657
_tick(0),
5758
_unacknowledged_ticks(0),
5859
_wake_time_set(false),
@@ -66,7 +67,8 @@ SysTimer<US_IN_TICK, IRQ>::SysTimer() :
6667
template<uint32_t US_IN_TICK, bool IRQ>
6768
SysTimer<US_IN_TICK, IRQ>::SysTimer(const ticker_data_t *data) :
6869
TimerEvent(data),
69-
_time_us(ticker_read_us(_ticker_data)),
70+
_epoch(ticker_read_us(_ticker_data)),
71+
_time_us(_epoch),
7072
_tick(0),
7173
_unacknowledged_ticks(0),
7274
_wake_time_set(false),
@@ -104,7 +106,7 @@ void SysTimer<US_IN_TICK, IRQ>::set_wake_time(uint64_t at)
104106
}
105107

106108
uint64_t ticks_to_sleep = at - _tick;
107-
uint64_t wake_time = at * US_IN_TICK;
109+
uint64_t wake_time = _epoch + at * US_IN_TICK;
108110

109111
/* Set this first, before attaching the interrupt that can unset it */
110112
_wake_time_set = true;

platform/source/SysTimer.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -225,6 +225,7 @@ class SysTimer: private mbed::TimerEvent, private mbed::NonCopyable<SysTimer<US_
225225
uint64_t _elapsed_ticks() const;
226226
static void _set_irq_pending();
227227
static void _clear_irq_pending();
228+
const us_timestamp_t _epoch;
228229
us_timestamp_t _time_us;
229230
uint64_t _tick;
230231
uint8_t _unacknowledged_ticks;

0 commit comments

Comments
 (0)