Skip to content

Commit 865f470

Browse files
committed
ncs36510: us ticker improvements
Do not ticker read in ISR, use reminder to schedule the next interrupt, this should make ticker much faster. read - disable Timer0 while reading it, if ISR is pending just reread the time again via read() function These 2 improvements should decrease time spent when reading/scheduling ticker events.
1 parent 9b082ff commit 865f470

File tree

1 file changed

+16
-26
lines changed

1 file changed

+16
-26
lines changed

targets/TARGET_ONSEMI/TARGET_NCS36510/ncs36510_us_ticker_api.c

Lines changed: 16 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@ static int us_ticker_inited = 0;
3838
static void us_timer_init(void);
3939

4040
static uint32_t us_ticker_target = 0;
41-
static volatile uint32_t msb_counter = 0;
41+
static volatile uint16_t msb_counter = 0;
4242

4343
void us_ticker_init(void)
4444
{
@@ -55,7 +55,6 @@ void us_ticker_init(void)
5555
* which is why a software timer is required to get 32-bit word length.
5656
******************************************************************************/
5757
/* TODO - Need some sort of load value/prescale calculation for non-32MHz clock */
58-
/* TODO - Add msb_counter rollover protection at 16 bits count? */
5958
/* TODO - How is overflow handled? */
6059

6160
/* Timer 0 for free running time */
@@ -108,22 +107,21 @@ static void us_timer_init(void)
108107
/* Reads 32 bit timer's current value (16 bit s/w timer | 16 bit h/w timer) */
109108
uint32_t us_ticker_read()
110109
{
111-
uint32_t retval, tim0cval;
112110

113111
if (!us_ticker_inited) {
114112
us_timer_init();
115113
}
116114

115+
NVIC_DisableIRQ(Tim0_IRQn);
116+
uint32_t retval, tim0cval;
117117
/* Get the current tick from the hw and sw timers */
118118
tim0cval = TIM0REG->VALUE; /* read current time */
119119
retval = (0xFFFF - tim0cval); /* subtract down count */
120120

121-
NVIC_DisableIRQ(Tim0_IRQn);
122121
if (TIM0REG->CONTROL.BITS.INT) {
123-
TIM0REG->CLEAR = 0;
124-
msb_counter++;
125-
tim0cval = TIM0REG->VALUE; /* read current time again after interrupt */
126-
retval = (0xFFFF - tim0cval);
122+
us_timer_isr(); /* handle ISR again */
123+
NVIC_ClearPendingIRQ(Tim0_IRQn);
124+
retval = (0xFFFF - TIM0REG->VALUE);
127125
}
128126
retval |= msb_counter << 16; /* add software bits */
129127
NVIC_EnableIRQ(Tim0_IRQn);
@@ -168,25 +166,21 @@ extern void us_ticker_isr(void)
168166
/* Clear IRQ flag */
169167
TIM1REG->CLEAR = 0;
170168

171-
int32_t delta = us_ticker_target - us_ticker_read();
172-
if (delta <= 0) {
173-
TIM1REG->CONTROL.BITS.ENABLE = False;
174-
us_ticker_irq_handler();
169+
if (us_ticker_target > 0) {
170+
--us_ticker_target;
171+
ticker_set(0xFFFF);
175172
} else {
176-
// Clamp at max value of timer
177-
if (delta > 0xFFFF) {
178-
delta = 0xFFFF;
179-
}
180-
181-
ticker_set(delta);
173+
us_ticker_irq_handler();
182174
}
183175
}
184176

185177
/* Set timer 1 ticker interrupt */
186178
void us_ticker_set_interrupt(timestamp_t timestamp)
187179
{
188-
us_ticker_target = (uint32_t)timestamp;
189-
int32_t delta = us_ticker_target - us_ticker_read();
180+
int32_t delta = timestamp - us_ticker_read();
181+
// we got 16 bit timer, use upper 16bit as a simple counter how many times
182+
// we need to schedule full range ticker count
183+
us_ticker_target = (uint32_t)delta >> 16;
190184

191185
if (delta <= 0) {
192186
/* This event was in the past */
@@ -200,10 +194,6 @@ void us_ticker_set_interrupt(timestamp_t timestamp)
200194
return;
201195
}
202196

203-
// Clamp at max value of timer
204-
if (delta > 0xFFFF) {
205-
delta = 0xFFFF;
206-
}
207-
208-
ticker_set(delta);
197+
// we set the full reminder of 16 bit, the next ISR will do the upper part
198+
ticker_set(delta & 0xFFFF);
209199
}

0 commit comments

Comments
 (0)