diff --git a/fsrc-core/src/event_man.rs b/fsrc-core/src/event_man.rs index e72c0c4..c54cc2a 100644 --- a/fsrc-core/src/event_man.rs +++ b/fsrc-core/src/event_man.rs @@ -20,27 +20,41 @@ doc = ::embed_doc_image::embed_image!("event_man_arch", "images/event_man_arch.p //! //! ![Event flow][event_man_arch] //! +//! The event manager has a listener table abstracted by the [ListenerTable], which maps +//! listener groups identified by [ListenerKey]s to a [sender ID][SenderId]. +//! It also contains a sender table abstracted by the [SenderTable] which maps these sender IDs +//! to a concrete [SendEventProvider]. A simple approach would be to use one send event provider +//! for each OBSW thread and then subscribe for all interesting events for a particular thread +//! using the send event provider ID. +//! //! This can be done with the [EventManager] like this: //! -//! 1. Provide a concrete [SendEventProvider] implementation and a concrete [EventReceiver] -//! implementation. These abstraction allow to use different message queue backends. -//! A straightforward implementation where dynamic memory allocation is not a big concern could -//! use [std::sync::mpsc::channel] to do this. It is recommended that these implementations -//! derive [Clone]. -//! 2. Each event creator gets a (cloned) sender component which allows it to send events to the +//! 1. Provide a concrete [EventReceiver] implementation. This abstraction allow to use different +//! message queue backends. A straightforward implementation where dynamic memory allocation is +//! not a big concern could use [std::sync::mpsc::channel] to do this and is provided in +//! form of the [MpscEventSendProvider]. +//! 2. To set up event creators, create channel pairs using some message queue implementation. +//! Each event creator gets a (cloned) sender component which allows it to send events to the //! manager. //! 3. The event manager receives the receiver component so all events are routed to the //! manager. -//! 4. Additional channels are created for each event receiver and/or subscriber. -//! The sender component is used with the [SendEventProvider] trait and the subscription API -//! provided by the [EventManager] to subscribe for individual events, whole group of events or -//! all events. The receiver/subscribers can then receive all subscribed events via the receiver -//! end. +//! 4. Create the [send event providers][SendEventProvider]s which allow routing events to +//! subscribers. +//! Use can now use their [sender IDs][SendEventProvider::id] to subscribe for event groups, +//! for example by using the [EventManager::subscribe_single] method. +//! 5. Add the send provider as well using the [EventManager::add_sender] call so the event +//! manager can route listener groups to a the send provider. //! //! Some components like a PUS Event Service or PUS Event Action Service might require all //! events to package them as telemetry or start actions where applicable. //! Other components might only be interested in certain events. For example, a thermal system //! handler might only be interested in temperature events generated by a thermal sensor component. +//! +//! # Examples +//! +//! You can check [integration test](https://egit.irs.uni-stuttgart.de/rust/fsrc-launchpad/src/branch/event_man_table_impl/fsrc-core/tests/pus_events.rs) +//! for a concrete example using multi-threading where events are routed to +//! different threads. use crate::events::{EventU16, EventU32, GenericEvent, LargestEventRaw, LargestGroupIdRaw}; use crate::params::{Params, ParamsHeapless}; use alloc::boxed::Box; @@ -173,10 +187,12 @@ impl EventManager { self.listener_table.remove_duplicates(key) } + /// Subscribe for a unique event. pub fn subscribe_single(&mut self, event: &Event, sender_id: SenderId) { self.update_listeners(ListenerKey::Single(event.raw_as_largest_type()), sender_id); } + /// Subscribe for an event group. pub fn subscribe_group(&mut self, group_id: LargestGroupIdRaw, sender_id: SenderId) { self.update_listeners(ListenerKey::Group(group_id), sender_id); } @@ -367,9 +383,7 @@ impl id: &SenderId, ) -> Option<&mut Box>> { - self.senders - .get_mut(id) - .filter(|sender| sender.id() == *id) + self.senders.get_mut(id).filter(|sender| sender.id() == *id) } fn add_send_event_provider(