📄 microtimerm.nc
字号:
/** A micro-second interval timer, using clock1
* (Don't use at the same time as the radio...), or with LogicalTime
*/
module MicroTimerM
{
/** The interval in start is in microseconds, and it only supports
repeat timers. It does not support long intervals (max is about
10s on the mica2) */
provides interface MicroTimer;
}
implementation {
#ifdef PLATFORM_MICA2
enum { CYCLES_PER_MILLISECOND = 7373L };
#else
enum { CYCLES_PER_MILLISECOND = 4000L };
#endif
bool running;
command result_t MicroTimer.start(uint32_t interval) {
uint32_t overflow;
uint8_t prescaler;
bool wasRunning;
// Avoid overflow in calculations below. When we have large values
// of interval (close to a Hz), we drop the milliseconds to avoid
// overflow
if (interval > 0xffffffffUL / CYCLES_PER_MILLISECOND)
overflow = (interval / 1000) * CYCLES_PER_MILLISECOND;
else
overflow = (interval * CYCLES_PER_MILLISECOND) / 1000;
// Pick a prescaler
if (overflow >= 65536 * 1024)
return FAIL; // This is something like .1Hz on mica2s
else if (overflow >= 65536UL * 256)
{
prescaler = 5;
overflow /= 1024;
}
else if (overflow >= 65536UL * 64)
{
prescaler = 4;
overflow /= 256;
}
else if (overflow >= 65536UL * 8)
{
prescaler = 3;
overflow /= 64;
}
else if (overflow >= 65536UL)
{
overflow /= 8;
prescaler = 2;
}
else
prescaler = 1;
atomic
{
wasRunning = running;
running = TRUE;
}
if (wasRunning)
return FAIL;
outp(0, TCCR1A);
#if defined(PLATFORM_MICA2) || defined(PLATFORM_MICA2DOT)
#define CTC1 WGM12
#endif
outp(prescaler | 1 << CTC1, TCCR1B); // set prescaler and overflow value
outp(overflow >> 8, OCR1AH);
outp(overflow, OCR1AL);
outp(0, TCNT1H); // reset timer
outp(0, TCNT1L);
sbi(TIFR, OCF1A); // clear pending interrupt
sbi(TIMSK, OCIE1A); // enable overflow A interrupt
return SUCCESS;
}
async command result_t MicroTimer.stop() {
result_t ok = FAIL;
atomic
if (running)
{
cbi(TIMSK, OCIE1A); // disable overflow A interrupt
sbi(TIFR, OCF1A); // clear pending interrupt
running = FALSE;
ok = SUCCESS;
}
return ok;
}
TOSH_SIGNAL(SIG_OUTPUT_COMPARE1A) {
signal MicroTimer.fired();
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -