ChibiOS  21.6.0
chevt.h
Go to the documentation of this file.
1 /*
2  ChibiOS - Copyright (C) 2006,2007,2008,2009,2010,2011,2012,2013,2014,
3  2015,2016,2017,2018,2019,2020,2021 Giovanni Di Sirio.
4 
5  This file is part of ChibiOS.
6 
7  ChibiOS is free software; you can redistribute it and/or modify
8  it under the terms of the GNU General Public License as published by
9  the Free Software Foundation version 3 of the License.
10 
11  ChibiOS is distributed in the hope that it will be useful,
12  but WITHOUT ANY WARRANTY; without even the implied warranty of
13  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14  GNU General Public License for more details.
15 
16  You should have received a copy of the GNU General Public License
17  along with this program. If not, see <http://www.gnu.org/licenses/>.
18 */
19 
20 /**
21  * @file nil/include/chevt.h
22  * @brief Nil RTOS events header file.
23  *
24  * @addtogroup NIL_EVENTS
25  * @{
26  */
27 
28 #ifndef CHEVT_H
29 #define CHEVT_H
30 
31 #if (CH_CFG_USE_EVENTS == TRUE) || defined(__DOXYGEN__)
32 
33 /*===========================================================================*/
34 /* Module constants. */
35 /*===========================================================================*/
36 
37 /*===========================================================================*/
38 /* Module pre-compile time settings. */
39 /*===========================================================================*/
40 
41 /*===========================================================================*/
42 /* Derived constants and error checks. */
43 /*===========================================================================*/
44 
45 /*===========================================================================*/
46 /* Module data structures and types. */
47 /*===========================================================================*/
48 
49 typedef struct event_listener event_listener_t;
50 
51 /**
52  * @brief Event Listener structure.
53  */
54 struct event_listener {
55  event_listener_t *next; /**< @brief Next Event Listener
56  registered on the event
57  source. */
58  thread_t *listener; /**< @brief Thread interested in the
59  event source. */
60  eventmask_t events; /**< @brief Events to be set in
61  the listening thread. */
62  eventflags_t flags; /**< @brief Flags added to the listener
63  by the event source. */
64  eventflags_t wflags; /**< @brief Flags that this listener
65  interested in. */
66 };
67 
68 /**
69  * @brief Event Source structure.
70  */
71 typedef struct event_source {
72  event_listener_t *next; /**< @brief First Event Listener
73  registered on the Event
74  Source. */
76 
77 /**
78  * @brief Event Handler callback function.
79  */
80 typedef void (*evhandler_t)(eventid_t id);
81 
82 /*===========================================================================*/
83 /* Module macros. */
84 /*===========================================================================*/
85 
86 /**
87  * @brief All events allowed mask.
88  */
89 #define ALL_EVENTS ((eventmask_t)-1)
90 
91 /**
92  * @brief Returns an event mask from an event identifier.
93  */
94 #define EVENT_MASK(eid) ((eventmask_t)1 << (eventmask_t)(eid))
95 
96 /**
97  * @brief Data part of a static event source initializer.
98  * @details This macro should be used when statically initializing an event
99  * source that is part of a bigger structure.
100  * @param name the name of the event source variable
101  */
102 #define _EVENTSOURCE_DATA(name) {(event_listener_t *)(&name)}
103 
104 /**
105  * @brief Static event source initializer.
106  * @details Statically initialized event sources require no explicit
107  * initialization using @p chEvtInit().
108  *
109  * @param name the name of the event source variable
110  */
111 #define EVENTSOURCE_DECL(name) event_source_t name = _EVENTSOURCE_DATA(name)
112 
113 /**
114  * @name Macro Functions
115  * @{
116  */
117 /**
118  * @brief Initializes an Event Source.
119  * @note This function can be invoked before the kernel is initialized
120  * because it just prepares a @p event_source_t structure.
121  *
122  * @param[in] esp pointer to the @p event_source_t structure
123  *
124  * @init
125  */
126 #define chEvtObjectInit(esp) do { \
127  (esp)->next = (event_listener_t *)(esp); \
128 } while (0)
129 
130 /**
131  * @brief Registers an Event Listener on an Event Source.
132  * @details Once a thread has registered as listener on an event source it
133  * will be notified of all events broadcasted there.
134  * @note Multiple Event Listeners can specify the same bits to be ORed to
135  * different threads.
136  *
137  * @param[in] esp pointer to the @p event_source_t structure
138  * @param[out] elp pointer to the @p event_listener_t structure
139  * @param[in] events the mask of events to be ORed to the thread when
140  * the event source is broadcasted
141  *
142  * @api
143  */
144 #define chEvtRegisterMask(esp, elp, events) \
145  chEvtRegisterMaskWithFlags(esp, elp, events, (eventflags_t)-1)
146 
147 /**
148  * @brief Registers an Event Listener on an Event Source.
149  * @note Multiple Event Listeners can use the same event identifier, the
150  * listener will share the callback function.
151  *
152  * @param[in] esp pointer to the @p event_source_t structure
153  * @param[out] elp pointer to the @p event_listener_t structure
154  * @param[in] event numeric identifier assigned to the Event Listener.
155  * The value must range between zero and the size, in bit,
156  * of the @p eventmask_t type minus one.
157  *
158  * @api
159  */
160 #define chEvtRegister(esp, elp, event) \
161  chEvtRegisterMask(esp, elp, EVENT_MASK(event))
162 
163 /**
164  * @brief Verifies if there is at least one @p event_listener_t registered.
165  *
166  * @param[in] esp pointer to the @p event_source_t structure
167  * @return The event source status.
168  *
169  * @iclass
170  */
171 #define chEvtIsListeningI(esp) (bool)((esp) != (event_source_t *)(esp)->next)
172 
173 /**
174  * @brief Signals all the Event Listeners registered on the specified Event
175  * Source.
176  *
177  * @param[in] esp pointer to the @p event_source_t structure
178  *
179  * @api
180  */
181 #define chEvtBroadcast(esp) chEvtBroadcastFlags(esp, (eventflags_t)0)
182 
183 /**
184  * @brief Signals all the Event Listeners registered on the specified Event
185  * Source.
186  * @post This function does not reschedule so a call to a rescheduling
187  * function must be performed before unlocking the kernel. Note that
188  * interrupt handlers always reschedule on exit so an explicit
189  * reschedule must not be performed in ISRs.
190  *
191  * @param[in] esp pointer to the @p event_source_t structure
192  *
193  * @iclass
194  */
195 #define chEvtBroadcastI(esp) chEvtBroadcastFlagsI(esp, (eventflags_t)0)
196 
197 /**
198  * @brief Adds (OR) a set of events to the current thread, this is
199  * @b much faster than using @p chEvtBroadcast() or @p chEvtSignal().
200  *
201  * @param[in] events the events to be added
202  * @return The mask of currently pending events.
203  *
204  * @iclass
205  */
206 #define chEvtAddEventsI(events) (nil.current->epmask |= events)
207 
208 /**
209  * @brief Returns the events mask.
210  * @details The pending events mask is returned but not altered in any way.
211  *
212  * @return The pending events mask.
213  *
214  * @api
215  */
216 #define chEvtGetEventsX(void) (nil.current->epmask)
217 
218 /**
219  * @brief Waits for exactly one of the specified events.
220  * @details The function waits for one event among those specified in
221  * @p events to become pending then the event is cleared and returned.
222  * @note One and only one event is served in the function, the one with the
223  * lowest event id. The function is meant to be invoked into a loop
224  * in order to serve all the pending events.<br>
225  * This means that Event Listeners with a lower event identifier have
226  * an higher priority.
227  *
228  * @param[in] events events that the function should wait
229  * for, @p ALL_EVENTS enables all the events
230  * @return The mask of the lowest event id served and cleared.
231  * @retval 0 if the operation has timed out.
232  *
233  * @api
234  */
235 #define chEvtWaitOne(events) chEvtWaitOneTimeout(events, TIME_INFINITE)
236 
237 /**
238  * @brief Waits for any of the specified events.
239  * @details The function waits for any event among those specified in
240  * @p mask to become pending then the events are cleared and
241  * returned.
242  *
243  * @param[in] events events that the function should wait
244  * for, @p ALL_EVENTS enables all the events
245  * @return The mask of the served and cleared events.
246  * @retval 0 if the operation has timed out.
247  *
248  * @api
249  */
250 #define chEvtWaitAny(events) chEvtWaitAnyTimeout(events, TIME_INFINITE)
251 
252 /**
253  * @brief Waits for all the specified events.
254  * @details The function waits for all the events specified in @p mask to
255  * become pending then the events are cleared and returned.
256  *
257  * @param[in] events events that the function should wait
258  * for, @p ALL_EVENTS enables all the events
259  * @return The mask of the served and cleared events.
260  * @retval 0 if the operation has timed out.
261  *
262  * @api
263  */
264 #define chEvtWaitAll(events) chEvtWaitAllTimeout(events, TIME_INFINITE)
265 
266 /** @} */
267 
268 /*===========================================================================*/
269 /* External declarations. */
270 /*===========================================================================*/
271 
272 #ifdef __cplusplus
273 extern "C" {
274 #endif
276  event_listener_t *elp,
277  eventmask_t events,
278  eventflags_t wflags);
285  void chEvtSignal(thread_t *tp, eventmask_t events);
286  void chEvtSignalI(thread_t *tp, eventmask_t events);
289  void chEvtDispatch(const evhandler_t *handlers, eventmask_t events);
293 #ifdef __cplusplus
294 }
295 #endif
296 
297 #endif /* CH_CFG_USE_EVENTS == TRUE */
298 
299 #endif /* CHEVT_H */
300 
301 /** @} */
chEvtGetAndClearEvents
eventmask_t chEvtGetAndClearEvents(eventmask_t events)
Clears the pending events specified in the events mask.
Definition: chevents.c:207
chEvtAddEvents
eventmask_t chEvtAddEvents(eventmask_t events)
Adds (OR) a set of events to the current thread, this is much faster than using chEvtBroadcast() or c...
Definition: chevents.c:226
chEvtSignalI
void chEvtSignalI(thread_t *tp, eventmask_t events)
Adds a set of event flags directly to the specified thread_t.
Definition: chevents.c:295
chEvtSignal
void chEvtSignal(thread_t *tp, eventmask_t events)
Adds a set of event flags directly to the specified thread_t.
Definition: chevents.c:319
evhandler_t
void(* evhandler_t)(eventid_t id)
Event Handler callback function.
Definition: chevt.h:80
event_source_t
struct event_source event_source_t
Event Source structure.
event_source
Event Source structure.
Definition: chevents.h:74
chEvtGetAndClearFlags
eventflags_t chEvtGetAndClearFlags(event_listener_t *elp)
Returns the flags associated to an event_listener_t.
Definition: chevents.c:270
chEvtBroadcastFlags
void chEvtBroadcastFlags(event_source_t *esp, eventflags_t flags)
Signals all the Event Listeners registered on the specified Event Source.
Definition: chevents.c:380
eventflags_t
uint32_t eventflags_t
Definition: chearly.h:91
chEvtWaitAllTimeout
eventmask_t chEvtWaitAllTimeout(eventmask_t events, sysinterval_t timeout)
Waits for all the specified events.
Definition: chevents.c:612
chEvtGetAndClearEventsI
eventmask_t chEvtGetAndClearEventsI(eventmask_t events)
Clears the pending events specified in the events mask.
Definition: chevents.c:187
eventmask_t
uint32_t eventmask_t
Definition: chearly.h:90
event_listener::flags
eventflags_t flags
Flags added to the listener by the event source.
Definition: chevents.h:65
event_listener::listener
thread_t * listener
Thread interested in the event source.
Definition: chevents.h:61
event_listener
Event Listener structure.
Definition: chevents.h:57
ch_thread
Structure representing a thread.
Definition: chobjects.h:156
eventid_t
int32_t eventid_t
Definition: chearly.h:89
chEvtUnregister
void chEvtUnregister(event_source_t *esp, event_listener_t *elp)
Unregisters an Event Listener from its Event Source.
Definition: chevents.c:158
chEvtWaitAnyTimeout
eventmask_t chEvtWaitAnyTimeout(eventmask_t events, sysinterval_t timeout)
Waits for any of the specified events.
Definition: chevents.c:571
event_listener::wflags
eventflags_t wflags
Flags that this listener interested in.
Definition: chevents.h:67
event_listener::events
eventmask_t events
Events to be set in the listening thread.
Definition: chevents.h:63
sysinterval_t
uint64_t sysinterval_t
Type of time interval.
Definition: chtime.h:119
chEvtBroadcastFlagsI
void chEvtBroadcastFlagsI(event_source_t *esp, eventflags_t flags)
Signals all the Event Listeners registered on the specified Event Source.
Definition: chevents.c:346
event_listener::next
event_listener_t * next
Next Event Listener registered on the event source.
Definition: chevents.h:58
chEvtRegisterMaskWithFlags
void chEvtRegisterMaskWithFlags(event_source_t *esp, event_listener_t *elp, eventmask_t events, eventflags_t wflags)
Registers an Event Listener on an Event Source.
Definition: chevents.c:135
chEvtGetAndClearFlagsI
eventflags_t chEvtGetAndClearFlagsI(event_listener_t *elp)
Returns the unmasked flags associated to an event_listener_t.
Definition: chevents.c:247
event_source::next
event_listener_t * next
First Event Listener registered on the Event Source.
Definition: chevents.h:75
chEvtDispatch
void chEvtDispatch(const evhandler_t *handlers, eventmask_t events)
Invokes the event handlers associated to an event flags mask.
Definition: chevents.c:397
chEvtWaitOneTimeout
eventmask_t chEvtWaitOneTimeout(eventmask_t events, sysinterval_t timeout)
Waits for exactly one of the specified events.
Definition: chevents.c:528