RKTK API Docs RKTK Home Repo

rktk/
utils.rs

1//! Util types
2
3/// Print to the display
4#[macro_export]
5macro_rules! print {
6    ($literal:literal) => {{
7        use $crate::task::display::*;
8        let _ = DISPLAY_CONTROLLER.try_send(DisplayMessage::Message($literal));
9    }};
10    ($($arg:tt)*) => {{
11        use $crate::task::display::*;
12        use core::fmt::Write as _;
13
14        let mut str = $crate::reexports::heapless::String::<256>::new();
15        write!(str, $($arg)*).unwrap();
16        let _ = DISPLAY_DYNAMIC_MESSAGE_CONTROLLER.signal(str);
17    }};
18}
19
20/// Print to the display without formatting.
21///
22/// For string that does not require formatting, this macro is more efficient than `print!`.
23#[macro_export]
24macro_rules! print_str {
25    ($str:tt) => {{
26        use $crate::task::display::*;
27        let _ = DISPLAY_CONTROLLER.try_send(DisplayMessage::Message($str));
28    }};
29}
30
31macro_rules! display_state {
32    ($mes_type:ident,$val:expr) => {{
33        use $crate::task::display::*;
34        let _ = DISPLAY_CONTROLLER.try_send(DisplayMessage::$mes_type($val));
35    }};
36}
37
38pub(crate) use display_state;
39
40// Usually, we don't touch the interrupt code directly, so ThreadModeRawMutex is enough.
41#[cfg(target_arch = "arm")]
42pub type RawMutex = embassy_sync::blocking_mutex::raw::ThreadModeRawMutex;
43#[cfg(not(target_arch = "arm"))]
44pub type RawMutex = embassy_sync::blocking_mutex::raw::CriticalSectionRawMutex;
45
46pub type Mutex<T> = embassy_sync::mutex::Mutex<RawMutex, T>;
47pub type Channel<T, const N: usize> = embassy_sync::channel::Channel<RawMutex, T, N>;
48pub type Sender<'a, T, const N: usize> = embassy_sync::channel::Sender<'a, RawMutex, T, N>;
49pub type Receiver<'a, T, const N: usize> = embassy_sync::channel::Receiver<'a, RawMutex, T, N>;
50pub type Signal<T> = embassy_sync::signal::Signal<RawMutex, T>;
51
52/// sjoin or "spawn or join"
53pub(crate) mod sjoin {
54    macro_rules! join {
55        ($f1:expr, $($future:expr),* ) => {
56            $crate::utils::sjoin::join!(@alloc {$f1}, $($future),* );
57            $crate::utils::sjoin::join!(@no_alloc {$f1}, $($future),* );
58        };
59        (@alloc $f1:expr, $($future:expr),* ) => {
60            #[cfg(feature = "alloc")]
61            {
62                {
63                    use ::alloc::boxed::Box;
64                    let ex = embassy_executor::Spawner::for_current_executor().await;
65                    {
66                        $(
67                            let ts = Box::leak(Box::new(embassy_executor::raw::TaskStorage::new()));
68                            let st = ts.spawn(move || $future);
69                            ex.spawn(st).unwrap();
70                        )*
71                    }
72                }
73
74                $f1.await
75            };
76        };
77        (@no_alloc $f1:expr, $($future:expr),* ) => {
78            #[cfg(not(feature = "alloc"))]
79            futures::join!($f1, $($future),* );
80        };
81    }
82    pub(crate) use join;
83}
84
85#[macro_export]
86macro_rules! singleton {
87    ($val:expr, $type:ty) => {{
88        static STATIC_CELL: $crate::reexports::static_cell::StaticCell<$type> =
89            $crate::reexports::static_cell::StaticCell::new();
90        STATIC_CELL.init($val)
91    }};
92}