Event Queues¶
An event queue allows a task to serialize incoming events and simplify event processing. Events are stored in a queue and a task removes and processes an event from the queue. An event is processed in the context of this task. Events may be generated by OS callouts, interrupt handlers, and other tasks.
Description¶
Mynewt’s event queue model uses callback functions to process events. Each event is associated with a callback function that is called to process the event. This model enables a library package, that uses events in its implementation but does not have real-time timing requirements, to use an application event queue instead of creating a dedicated event queue and task to process its events. The callback function executes in the context of the task that the application creates to manage the event queue. This model reduces an application’s memory requirement because memory must be allocated for the task’s stack when a task is created. A package that has real-time timing requirements and must run at a specific task priority should create a dedicated event queue and task to process its events.
In the Mynewt model, a package defines its events and implements the callback functions for the events. A package that does not have real-time timing requirements should use Mynewt’s default event queue for its events. The callback function for an event from the Mynewt default event queue is executed in the context of the application main task. A package can, optionally, export a function that allows an application to specify the event queue for the package to use. The application task handler that manages the event queue simply pulls events from the event queue and executes the event’s callback function in its context.
A common way that Mynewt applications or packages process events from an
event queue is to have a task that executes in an infinite loop and
calls the os_eventq_get()
function to dequeue and return the event
from the head of the event queue. The task then calls the event callback
function to process the event. The os_eventq_get()
function puts the
task in to the sleeping
state when there are no events on the queue.
(See Scheduler for more
information on task execution states.) Other tasks (or interrupts) call
the os_eventq_put()
function to add an event to the queue. The
os_eventq_put()
function determines whether a task is blocked
waiting for an event on the queue and puts the task into the
ready-to-run
state.
A task can use the os_eventq_run()
wrapper function that calls the
os_eventq_get()
function to dequeue an event from the queue and then
calls the event callback function to process the event.
Note:
Only one task should consume or block waiting for events from an event queue.
The OS callout subsystem uses events for timer expiration notification.
Example¶
Here is an example of using an event from the BLE host:
static void ble_hs_event_tx_notify(struct os_event *ev);
/** OS event - triggers tx of pending notifications and indications. */
static struct os_event ble_hs_ev_tx_notifications = {
.ev_cb = ble_hs_event_tx_notify,
};
API¶
-
void
os_eventq_init
(struct os_eventq*)¶ Initialize the event queue.
- Parameters
evq
: The event queue to initialize
-
int
os_eventq_inited
(const struct os_eventq *evq)¶ Check whether the event queue is initialized.
- Parameters
evq
: The event queue to check
-
void
os_eventq_put
(struct os_eventq*, struct os_event*)¶ Put an event on the event queue.
- Parameters
evq
: The event queue to put an event onev
: The event to put on the queue
-
struct os_event *
os_eventq_get_no_wait
(struct os_eventq *evq)¶ Poll an event from the event queue and return it immediately.
If no event is available, don’t block, just return NULL.
- Return
Event from the queue, or NULL if none available.
-
struct os_event *
os_eventq_get
(struct os_eventq*)¶ Pull a single item from an event queue.
This function blocks until there is an item on the event queue to read.
- Return
The event from the queue
- Parameters
evq
: The event queue to pull an event from
-
void
os_eventq_run
(struct os_eventq *evq)¶ Pull a single item off the event queue and call it’s event callback.
- Parameters
evq
: The event queue to pull the item off.
-
struct os_event *
os_eventq_poll
(struct os_eventq**, int, os_time_t)¶ Poll the list of event queues specified by the evq parameter (size nevqs), and return the “first” event available on any of the queues.
Event queues are searched in the order that they are passed in the array.
- Return
An event, or NULL if no events available
- Parameters
evq
: Array of event queuesnevqs
: Number of event queues in evqtimo
: Timeout, forever if OS_WAIT_FOREVER is passed to poll.
-
void
os_eventq_remove
(struct os_eventq*, struct os_event*)¶ Remove an event from the queue.
- Parameters
evq
: The event queue to remove the event fromev
: The event to remove from the queue
-
struct os_eventq *
os_eventq_dflt_get
(void)¶ Retrieves the default event queue processed by OS main task.
- Return
The default event queue.
-
OS_EVENT_QUEUED
(__ev)¶ Return whether or not the given event is queued.
-
struct
os_event
¶ - #include <os_eventq.h>
Structure representing an OS event.
OS events get placed onto the event queues and are consumed by tasks.
Public Members
-
uint8_t
ev_queued
¶ Whether this OS event is queued on an event queue.
-
os_event_fn *
ev_cb
¶ Callback to call when the event is taken off of an event queue.
APIs, except for os_eventq_run(), assume this callback will be called by the user.
-
void *
ev_arg
¶ Argument to pass to the event queue callback.
-
uint8_t
-
struct
os_eventq
¶ - #include <os_eventq.h>