summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChromeOS Developer <dparker@chromium.org>2014-03-22 13:56:42 -0700
committerchrome-internal-fetch <chrome-internal-fetch@google.com>2014-03-26 19:28:54 +0000
commitd9bd95200f3252c141653a2e83f7580b00a4782d (patch)
tree8cb0501b36841e3fdd11941af98af6d6dc3a92bb
parent7895c278033acbb0f55020e5ac54fa8e6e669f14 (diff)
downloadchrome-ec-d9bd95200f3252c141653a2e83f7580b00a4782d.tar.gz
cortex-m: Add task_wait_event_mask() helper function
BUG=chrome-os-partner:27180 BRANCH=rambi TEST=Tested indirectly via subsequent patches to use this call in the adc and i2c handlers for the lm4. Change-Id: I53501fdf47d606ea6c7705facb66e945e25d9745 Signed-off-by: Dave Parker <dparker@chromium.org> Reviewed-on: https://chromium-review.googlesource.com/191300 Reviewed-by: Vincent Palatin <vpalatin@chromium.org> Reviewed-by: Randall Spangler <rspangler@chromium.org>
-rw-r--r--core/cortex-m/task.c29
-rw-r--r--include/task.h21
2 files changed, 49 insertions, 1 deletions
diff --git a/core/cortex-m/task.c b/core/cortex-m/task.c
index 5e309ef4cb..5d2f967693 100644
--- a/core/cortex-m/task.c
+++ b/core/cortex-m/task.c
@@ -380,6 +380,35 @@ uint32_t task_wait_event(int timeout_us)
return __wait_evt(timeout_us, TASK_ID_IDLE);
}
+uint32_t task_wait_event_mask(uint32_t event_mask, int timeout_us)
+{
+ uint64_t deadline = get_time().val + timeout_us;
+ uint32_t events = 0;
+ int time_remaining_us = timeout_us;
+
+ /* Add the timer event to the mask so we can indicate a timeout */
+ event_mask |= TASK_EVENT_TIMER;
+
+ while (!(events & event_mask)) {
+ /* Collect events to re-post later */
+ events |= __wait_evt(time_remaining_us, TASK_ID_IDLE);
+
+ time_remaining_us = deadline - get_time().val;
+ if (timeout_us > 0 && time_remaining_us <= 0) {
+ /* Ensure we return a TIMER event if we timeout */
+ events |= TASK_EVENT_TIMER;
+ break;
+ }
+ }
+
+ /* Re-post any other events collected */
+ if (events & ~event_mask)
+ atomic_or(task_get_event_bitmap(task_get_current()),
+ events & ~event_mask);
+
+ return events & event_mask;
+}
+
void task_enable_irq(int irq)
{
CPU_NVIC_EN(irq / 32) = 1 << (irq % 32);
diff --git a/include/task.h b/include/task.h
index 723c6f0ad6..6b10c649b1 100644
--- a/include/task.h
+++ b/include/task.h
@@ -95,10 +95,29 @@ uint32_t *task_get_event_bitmap(task_id_t tskid);
* @param timeout_us If > 0, sets a timer to produce the TASK_EVENT_TIMER
* event after the specified micro-second duration.
*
- * @return The bitmap of received events. */
+ * @return The bitmap of received events.
+ */
uint32_t task_wait_event(int timeout_us);
/**
+ * Wait for any event included in an event mask.
+ *
+ * If one or more events are already pending, returns immediately. Otherwise,
+ * it de-schedules the calling task and wakes up the next one in the priority
+ * order. Automatically clears the bitmap of received events before returning
+ * the events which are set.
+ *
+ * @param event_mask Bitmap of task events to wait for.
+ *
+ * @param timeout_us If > 0, sets a timer to produce the TASK_EVENT_TIMER
+ * event after the specified micro-second duration.
+ *
+ * @return The bitmap of received events. Includes
+ * TASK_EVENT_TIMER if the timeout is reached.
+ */
+uint32_t task_wait_event_mask(uint32_t event_mask, int timeout_us);
+
+/**
* Prints the list of tasks.
*
* Uses the command output channel. May be called from interrupt level.