Note! This project has moved to github.com/armmbed/mbed-events
This repository has been superceded
This project has moved to mbed-events
Composable event loops combine the cheap synchronicity of event loops with the composability of preempted threads.
Two modular event queue classes are provided:
- EventLoop - for loops coupled with a c++ managed thread
- EventQueue - for manually managed event queues
The Event class takes advantage of the extensibility of FuncPtr to allow an event to be passed through APIs as a normal function.
More information on composable event loops.
EventQueue.h
- Committer:
- Christopher Haster
- Date:
- 2016-05-10
- Revision:
- 14:5abf2ccf2dbf
- Parent:
- 10:62767e708bb6
- Child:
- 15:92d7c0b8a0f5
File content as of revision 14:5abf2ccf2dbf:
/* EventQueue * * Flexible queue for managing events */ #ifndef EVENT_QUEUE_H #define EVENT_QUEUE_H #include "Timer.h" #include "Ticker.h" #include "FuncPtr.h" #include "Binder.h" /** Flexible queue for managing events */ class EventQueue { public: /** Create an event queue * @param event_count Number of events to allow enqueueing at once * @param event_context Max size of arguments passed with an event */ EventQueue(unsigned event_count=32, unsigned event_context=0); virtual ~EventQueue(); /** Dispatch pending events * @param ms Time to wait for events in milliseconds, * 0 indicates to return immediately if no events are pending */ void dispatch(int ms=-1); /** Get current tick of the event queue * @return Number of milliseconds since the queue was instantiated, * this count intentionally overflows to 0 after 2^32-1 */ unsigned get_tick(); private: struct event { struct event *volatile next; unsigned target; int period; void (*dispatch)(void *p); // data follows }; struct event *alloc(unsigned size, int ms=-1); void dealloc(struct event *); void trigger(struct event *e, int delay); template <typename F> bool trigger(F func, int delay, int period, int tolerance, int ms=-1) { struct event *e = alloc(sizeof(F), ms); if (!e) { return false; } e->period = period; (void)tolerance; // unused e->dispatch = &F::thunk; *reinterpret_cast<F*>(e+1) = func; trigger(e, delay); return true; } void tick(); void wakeup(); unsigned _event_count; unsigned _event_context; struct event *volatile _queue; struct event *volatile _free; void *_mem; unsigned _tick; mbed::Ticker _ticker; mbed::Timer _timer; template <typename F> friend class Event; }; #endif