From: Keith Packard Date: Sat, 31 Oct 2009 06:46:21 +0000 (-0700) Subject: Add ao_alarm X-Git-Tag: 0.6~15 X-Git-Url: https://git.gag.com/?p=fw%2Faltos;a=commitdiff_plain;h=73db30b2f9128c37dc7fa075793a8862814ce044 Add ao_alarm --- diff --git a/src/ao.h b/src/ao.h index 84e92f35..b90befe5 100644 --- a/src/ao.h +++ b/src/ao.h @@ -40,6 +40,7 @@ /* An AltOS task */ struct ao_task { __xdata void *wchan; /* current wait channel (NULL if running) */ + uint16_t alarm; /* abort ao_sleep time */ uint8_t stack_count; /* amount of saved stack */ uint8_t task_id; /* index in the task array */ __code char *name; /* task name */ @@ -55,8 +56,12 @@ extern __xdata struct ao_task *__data ao_cur_task; ao_task.c */ -/* Suspend the current task until wchan is awoken */ -void +/* Suspend the current task until wchan is awoken. + * returns: + * 0 on normal wake + * 1 on alarm + */ +uint8_t ao_sleep(__xdata void *wchan); /* Wake all tasks sleeping on wchan */ @@ -67,6 +72,10 @@ ao_wakeup(__xdata void *wchan); void ao_wake_task(__xdata struct ao_task *task); +/* set an alarm to go off in 'delay' ticks */ +void +ao_alarm(uint16_t delay); + /* Yield the processor to another task */ void ao_yield(void) _naked; diff --git a/src/ao_task.c b/src/ao_task.c index 136444b0..14aa84c8 100644 --- a/src/ao_task.c +++ b/src/ao_task.c @@ -129,6 +129,13 @@ ao_yield(void) _naked break; } + /* Check if the alarm is set for a time which has passed */ + if (ao_cur_task->alarm && + (int16_t) (ao_time() - ao_cur_task->alarm) >= 0) { + ao_cur_task_index = ao_next_task_index; + break; + } + /* Enter lower power mode when there isn't anything to do */ if (ao_next_task_index == ao_cur_task_index) PCON = PCON_IDLE; @@ -181,13 +188,20 @@ ao_yield(void) _naked _endasm; } -void +uint8_t ao_sleep(__xdata void *wchan) { __critical { ao_cur_task->wchan = wchan; } ao_yield(); + if (ao_cur_task->wchan) { + ao_cur_task->wchan = NULL; + ao_cur_task->alarm = 0; + return 1; + } + ao_cur_task->alarm = 0; + return 0; } void @@ -200,6 +214,13 @@ ao_wakeup(__xdata void *wchan) ao_tasks[i]->wchan = NULL; } +void +ao_alarm(uint16_t delay) +{ + if (!(ao_cur_task->alarm = ao_time() + delay)) + ao_cur_task->alarm = 1; +} + void ao_wake_task(__xdata struct ao_task *task) {