Skip to content

Commit b6a73f8

Browse files
moved all const defintions inline
optimized micros() even more ...
1 parent 8ad4dd3 commit b6a73f8

File tree

1 file changed

+23
-28
lines changed

1 file changed

+23
-28
lines changed

cores/arduino/time.cpp

Lines changed: 23 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -3,9 +3,6 @@
33
#include "FspTimer.h"
44

55
// this file implements the following public funcions: delay, delayMicroseconds, yield, millis, micros
6-
// The millis and micros implementation uses timer AGT0 (24 HMz, 16-bits, count-down mode, 1 ms period)
7-
8-
volatile unsigned long agt_time_ms = 0;
96

107
__attribute__((weak)) void delay(uint32_t ms) {
118
R_BSP_SoftwareDelay(ms, BSP_DELAY_UNITS_MILLISECONDS);
@@ -18,29 +15,25 @@ void delayMicroseconds(unsigned int us) {
1815
__attribute__((weak)) void yield() {
1916
}
2017

21-
static FspTimer main_timer;
22-
const uint8_t _timer_type = AGT_TIMER;
23-
const uint8_t _timer_index = 0;
24-
inline uint8_t _timer_get_underflow_bit() { return R_AGT0->AGTCR_b.TUNDF; }
25-
inline uint16_t _timer_get_counter() { return R_AGT0->AGT; }
26-
// clock divider 8 works for the Uno R4 and Portenta C33 both because _timer_period is < 16-bit.
27-
// on the Uno R4 the AGT clock is 24 MHz / 8 -> 3000 ticks per ms
28-
// on the Portenta C33 the AGT clock is 50 Mhz / 8 -> 6250 ticks per ms
29-
const timer_source_div_t _timer_clock_divider = TIMER_SOURCE_DIV_8;
30-
uint32_t _timer_period;
31-
const uint8_t TIMER_PRIORITY = 8;
18+
static FspTimer agt_timer;
19+
volatile uint32_t agt_time_ms = 0;
3220

3321
static void timer_micros_callback(timer_callback_args_t __attribute((unused))* p_args) {
3422
agt_time_ms += 1;
3523
}
3624

3725
void startAgt() {
38-
const uint32_t _timer_clock_freq = R_FSP_SystemClockHzGet(_timer_type == AGT_TIMER ? FSP_PRIV_CLOCK_PCLKB : FSP_PRIV_CLOCK_PCLKD);
39-
_timer_period = _timer_clock_freq / ((1 << _timer_clock_divider) * 1000UL);
40-
main_timer.begin(TIMER_MODE_PERIODIC, _timer_type, _timer_index, _timer_period, 1, _timer_clock_divider, timer_micros_callback);;
41-
main_timer.setup_overflow_irq(TIMER_PRIORITY);
42-
main_timer.open();
43-
main_timer.start(); // bug in R4 1.0.2: calling start() is not necessary: open() starts the counter already !?
26+
// configure AGT timer 0 to generate an underflow interrupt every 1 ms
27+
// a clock divider 8 works for both the Uno R4 and Portenta C33 because number of clock ticks
28+
// in 1 ms (period) is an integer number and below the 16-bit counter limit
29+
// on the Uno R4 the AGT clock is 24 MHz / 8 -> 3000 ticks per ms
30+
// on the Portenta C33 the AGT clock is 50 Mhz / 8 -> 6250 ticks per ms
31+
const uint32_t clock_freq = R_FSP_SystemClockHzGet(FSP_PRIV_CLOCK_PCLKB);
32+
const uint32_t period = clock_freq / ((1 << TIMER_SOURCE_DIV_8) * 1000UL);
33+
agt_timer.begin(TIMER_MODE_PERIODIC, AGT_TIMER, 0, period, 1, TIMER_SOURCE_DIV_8, timer_micros_callback);;
34+
agt_timer.setup_overflow_irq(8);
35+
agt_timer.open();
36+
agt_timer.start(); // bug in R4 1.0.2: calling start() is not necessary: open() starts the counter already !?
4437
}
4538

4639
unsigned long millis()
@@ -54,15 +47,17 @@ unsigned long millis()
5447

5548
unsigned long micros() {
5649
// Return time in us
57-
NVIC_DisableIRQ(main_timer.get_cfg()->cycle_end_irq);
50+
const timer_cfg_t* cfg = agt_timer.get_cfg();
51+
NVIC_DisableIRQ(cfg->cycle_end_irq);
5852
uint32_t ms = agt_time_ms;
59-
uint32_t const down_counts = _timer_get_counter();
60-
if (_timer_get_underflow_bit() && (down_counts > (_timer_period / 2)))
61-
{
62-
// the counter wrapped around just before it was read
53+
// read from the R_AGT0 registers directly for performance reasons
54+
uint32_t const down_counts = R_AGT0->AGT; // get the counter value
55+
if (R_AGT0->AGTCR_b.TUNDF && (down_counts > (cfg->period_counts / 2))) {
56+
// if the TUNDF (underflow) bit is set, the counter wrapped around
57+
// just before down_counts was read and agt_time_ms was not yet updated
6358
++ms;
6459
}
65-
NVIC_EnableIRQ(main_timer.get_cfg()->cycle_end_irq);
66-
uint32_t const up_counts = (_timer_period - 1) - down_counts;
67-
return (ms * 1000) + ((up_counts * 1000) / _timer_period);
60+
NVIC_EnableIRQ(cfg->cycle_end_irq);
61+
uint32_t const up_counts = (cfg->period_counts - 1) - down_counts;
62+
return (ms * 1000) + ((up_counts * 1000) / cfg->period_counts);
6863
}

0 commit comments

Comments
 (0)