diff options
| author | Ulf Lilleengen <[email protected]> | 2022-06-15 10:24:36 +0200 |
|---|---|---|
| committer | Ulf Lilleengen <[email protected]> | 2022-06-15 10:24:36 +0200 |
| commit | 72eb16b46dc9ff12ae38b9d9fb94e3ad7a4b2e65 (patch) | |
| tree | 6e1322cda8e6d51eaa0886aed00d5edf92ad7ba4 | |
| parent | aaebea00eb2078e717ef35a22f547cb83a5fe1d4 (diff) | |
Add missing documentation for all public modules and types
| -rw-r--r-- | embassy/src/blocking_mutex/mod.rs | 30 | ||||
| -rw-r--r-- | embassy/src/blocking_mutex/raw.rs | 23 | ||||
| -rw-r--r-- | embassy/src/channel/signal.rs | 1 | ||||
| -rw-r--r-- | embassy/src/mutex.rs | 24 | ||||
| -rw-r--r-- | embassy/src/util/steal.rs | 10 | ||||
| -rw-r--r-- | embassy/src/waitqueue/waker.rs | 9 |
6 files changed, 86 insertions, 11 deletions
diff --git a/embassy/src/blocking_mutex/mod.rs b/embassy/src/blocking_mutex/mod.rs index eb3cd9392..65daf15c4 100644 --- a/embassy/src/blocking_mutex/mod.rs +++ b/embassy/src/blocking_mutex/mod.rs | |||
| @@ -1,14 +1,23 @@ | |||
| 1 | //! Blocking mutex (not async) | 1 | //! Blocking mutex. |
| 2 | 2 | //! | |
| 3 | //! This module provides a blocking mutex that can be used to synchronize data. | ||
| 3 | pub mod raw; | 4 | pub mod raw; |
| 4 | 5 | ||
| 5 | use core::cell::UnsafeCell; | 6 | use core::cell::UnsafeCell; |
| 6 | 7 | ||
| 7 | use self::raw::RawMutex; | 8 | use self::raw::RawMutex; |
| 8 | 9 | ||
| 9 | /// Any object implementing this trait guarantees exclusive access to the data contained | 10 | /// Blocking mutex (not async) |
| 10 | /// within the mutex for the duration of the lock. | 11 | /// |
| 11 | /// Adapted from <https://github.com/rust-embedded/mutex-trait>. | 12 | /// Provides a blocking mutual exclusion primitive backed by an implementation of [`raw::RawMutex`]. |
| 13 | /// | ||
| 14 | /// Which implementation you select depends on the context in which you're using the mutex. | ||
| 15 | /// | ||
| 16 | /// Use [`CriticalSectionMutex`] when data can be shared between threads and interrupts. | ||
| 17 | /// | ||
| 18 | /// Use [`NoopMutex`] when data is only shared between tasks running on the same executor. | ||
| 19 | /// | ||
| 20 | /// Use [`ThreadModeMutex`] when data is shared between tasks running on the same executor but you want a global singleton. | ||
| 12 | pub struct Mutex<R, T: ?Sized> { | 21 | pub struct Mutex<R, T: ?Sized> { |
| 13 | // NOTE: `raw` must be FIRST, so when using ThreadModeMutex the "can't drop in non-thread-mode" gets | 22 | // NOTE: `raw` must be FIRST, so when using ThreadModeMutex the "can't drop in non-thread-mode" gets |
| 14 | // to run BEFORE dropping `data`. | 23 | // to run BEFORE dropping `data`. |
| @@ -78,7 +87,18 @@ impl<R, T> Mutex<R, T> { | |||
| 78 | } | 87 | } |
| 79 | } | 88 | } |
| 80 | 89 | ||
| 90 | /// A mutex that allows borrowing data across executors and interrupts. | ||
| 91 | /// | ||
| 92 | /// # Safety | ||
| 93 | /// | ||
| 94 | /// This mutex is safe to share between different executors and interrupts. | ||
| 81 | pub type CriticalSectionMutex<T> = Mutex<raw::CriticalSectionRawMutex, T>; | 95 | pub type CriticalSectionMutex<T> = Mutex<raw::CriticalSectionRawMutex, T>; |
| 96 | |||
| 97 | /// A mutex that allows borrowing data in the context of a single executor. | ||
| 98 | /// | ||
| 99 | /// # Safety | ||
| 100 | /// | ||
| 101 | /// **This Mutex is only safe within a single executor.** | ||
| 82 | pub type NoopMutex<T> = Mutex<raw::NoopRawMutex, T>; | 102 | pub type NoopMutex<T> = Mutex<raw::NoopRawMutex, T>; |
| 83 | 103 | ||
| 84 | impl<T> Mutex<raw::CriticalSectionRawMutex, T> { | 104 | impl<T> Mutex<raw::CriticalSectionRawMutex, T> { |
diff --git a/embassy/src/blocking_mutex/raw.rs b/embassy/src/blocking_mutex/raw.rs index f9d249b08..bdb443e4d 100644 --- a/embassy/src/blocking_mutex/raw.rs +++ b/embassy/src/blocking_mutex/raw.rs | |||
| @@ -1,11 +1,22 @@ | |||
| 1 | //! Mutex primitives. | ||
| 2 | //! | ||
| 3 | //! This module provides a trait for mutexes that can be used in different contexts. | ||
| 1 | use core::marker::PhantomData; | 4 | use core::marker::PhantomData; |
| 2 | 5 | ||
| 6 | /// Any object implementing this trait guarantees exclusive access to the data contained | ||
| 7 | /// within the mutex for the duration of the lock. | ||
| 8 | /// Adapted from <https://github.com/rust-embedded/mutex-trait>. | ||
| 3 | pub trait RawMutex { | 9 | pub trait RawMutex { |
| 4 | const INIT: Self; | 10 | const INIT: Self; |
| 5 | 11 | ||
| 6 | fn lock<R>(&self, f: impl FnOnce() -> R) -> R; | 12 | fn lock<R>(&self, f: impl FnOnce() -> R) -> R; |
| 7 | } | 13 | } |
| 8 | 14 | ||
| 15 | /// A mutex that allows borrowing data across executors and interrupts. | ||
| 16 | /// | ||
| 17 | /// # Safety | ||
| 18 | /// | ||
| 19 | /// This mutex is safe to share between different executors and interrupts. | ||
| 9 | pub struct CriticalSectionRawMutex { | 20 | pub struct CriticalSectionRawMutex { |
| 10 | _phantom: PhantomData<()>, | 21 | _phantom: PhantomData<()>, |
| 11 | } | 22 | } |
| @@ -28,6 +39,11 @@ impl RawMutex for CriticalSectionRawMutex { | |||
| 28 | 39 | ||
| 29 | // ================ | 40 | // ================ |
| 30 | 41 | ||
| 42 | /// A mutex that allows borrowing data in the context of a single executor. | ||
| 43 | /// | ||
| 44 | /// # Safety | ||
| 45 | /// | ||
| 46 | /// **This Mutex is only safe within a single executor.** | ||
| 31 | pub struct NoopRawMutex { | 47 | pub struct NoopRawMutex { |
| 32 | _phantom: PhantomData<*mut ()>, | 48 | _phantom: PhantomData<*mut ()>, |
| 33 | } | 49 | } |
| @@ -53,6 +69,13 @@ impl RawMutex for NoopRawMutex { | |||
| 53 | mod thread_mode { | 69 | mod thread_mode { |
| 54 | use super::*; | 70 | use super::*; |
| 55 | 71 | ||
| 72 | /// A "mutex" that only allows borrowing from thread mode. | ||
| 73 | /// | ||
| 74 | /// # Safety | ||
| 75 | /// | ||
| 76 | /// **This Mutex is only safe on single-core systems.** | ||
| 77 | /// | ||
| 78 | /// On multi-core systems, a `ThreadModeRawMutex` **is not sufficient** to ensure exclusive access. | ||
| 56 | pub struct ThreadModeRawMutex { | 79 | pub struct ThreadModeRawMutex { |
| 57 | _phantom: PhantomData<()>, | 80 | _phantom: PhantomData<()>, |
| 58 | } | 81 | } |
diff --git a/embassy/src/channel/signal.rs b/embassy/src/channel/signal.rs index 5a2c9d47a..cf78dad8b 100644 --- a/embassy/src/channel/signal.rs +++ b/embassy/src/channel/signal.rs | |||
| @@ -1,3 +1,4 @@ | |||
| 1 | //! A synchronization primitive for passing the latest value to a task. | ||
| 1 | use core::cell::UnsafeCell; | 2 | use core::cell::UnsafeCell; |
| 2 | use core::future::Future; | 3 | use core::future::Future; |
| 3 | use core::mem; | 4 | use core::mem; |
diff --git a/embassy/src/mutex.rs b/embassy/src/mutex.rs index 7b6bcb147..9cfaaa845 100644 --- a/embassy/src/mutex.rs +++ b/embassy/src/mutex.rs | |||
| @@ -1,9 +1,6 @@ | |||
| 1 | /// Async mutex. | 1 | //! Async mutex. |
| 2 | /// | 2 | //! |
| 3 | /// The mutex is generic over a blocking [`RawMutex`](crate::blocking_mutex::raw::RawMutex). | 3 | //! This module provides a mutex that can be used to synchronize data between asynchronous tasks. |
| 4 | /// The raw mutex is used to guard access to the internal "is locked" flag. It | ||
| 5 | /// is held for very short periods only, while locking and unlocking. It is *not* held | ||
| 6 | /// for the entire time the async Mutex is locked. | ||
| 7 | use core::cell::{RefCell, UnsafeCell}; | 4 | use core::cell::{RefCell, UnsafeCell}; |
| 8 | use core::ops::{Deref, DerefMut}; | 5 | use core::ops::{Deref, DerefMut}; |
| 9 | use core::task::Poll; | 6 | use core::task::Poll; |
| @@ -24,6 +21,21 @@ struct State { | |||
| 24 | waker: WakerRegistration, | 21 | waker: WakerRegistration, |
| 25 | } | 22 | } |
| 26 | 23 | ||
| 24 | /// Async mutex. | ||
| 25 | /// | ||
| 26 | /// The mutex is generic over a blocking [`RawMutex`](crate::blocking_mutex::raw::RawMutex). | ||
| 27 | /// The raw mutex is used to guard access to the internal "is locked" flag. It | ||
| 28 | /// is held for very short periods only, while locking and unlocking. It is *not* held | ||
| 29 | /// for the entire time the async Mutex is locked. | ||
| 30 | /// | ||
| 31 | /// Which implementation you select depends on the context in which you're using the mutex. | ||
| 32 | /// | ||
| 33 | /// Use [`CriticalSectionRawMutex`](crate::blocking_mutex::raw::CriticalSectionRawMutex) when data can be shared between threads and interrupts. | ||
| 34 | /// | ||
| 35 | /// Use [`NoopRawMutex`](crate::blocking_mutex::raw::NoopRawMutex) when data is only shared between tasks running on the same executor. | ||
| 36 | /// | ||
| 37 | /// Use [`ThreadModeRawMutex`](crate::blocking_mutex::raw::ThreadModeRawMutex) when data is shared between tasks running on the same executor but you want a singleton. | ||
| 38 | /// | ||
| 27 | pub struct Mutex<M, T> | 39 | pub struct Mutex<M, T> |
| 28 | where | 40 | where |
| 29 | M: RawMutex, | 41 | M: RawMutex, |
diff --git a/embassy/src/util/steal.rs b/embassy/src/util/steal.rs index a0d5f1359..07eb5fffd 100644 --- a/embassy/src/util/steal.rs +++ b/embassy/src/util/steal.rs | |||
| @@ -1,3 +1,13 @@ | |||
| 1 | /// A type that can retrieved unsafely from anywhere. | ||
| 1 | pub trait Steal { | 2 | pub trait Steal { |
| 3 | /// Retrieve and instance of this type. | ||
| 4 | /// | ||
| 5 | /// # Safety | ||
| 6 | /// | ||
| 7 | /// It is the responsibility of the application to ensure that the | ||
| 8 | /// usage of the returned instance is not in conflict with other uses | ||
| 9 | /// of this instance. | ||
| 10 | /// | ||
| 11 | /// The implementation may panic if the instance is already in use. | ||
| 2 | unsafe fn steal() -> Self; | 12 | unsafe fn steal() -> Self; |
| 3 | } | 13 | } |
diff --git a/embassy/src/waitqueue/waker.rs b/embassy/src/waitqueue/waker.rs index 1ac6054f9..da907300a 100644 --- a/embassy/src/waitqueue/waker.rs +++ b/embassy/src/waitqueue/waker.rs | |||
| @@ -6,6 +6,10 @@ use atomic_polyfill::{compiler_fence, AtomicPtr, Ordering}; | |||
| 6 | use crate::executor::raw::{task_from_waker, wake_task, TaskHeader}; | 6 | use crate::executor::raw::{task_from_waker, wake_task, TaskHeader}; |
| 7 | 7 | ||
| 8 | /// Utility struct to register and wake a waker. | 8 | /// Utility struct to register and wake a waker. |
| 9 | /// | ||
| 10 | /// # Safety | ||
| 11 | /// | ||
| 12 | /// This type is optimized for (and only works with) embassy tasks. | ||
| 9 | #[derive(Debug)] | 13 | #[derive(Debug)] |
| 10 | pub struct WakerRegistration { | 14 | pub struct WakerRegistration { |
| 11 | waker: Option<NonNull<TaskHeader>>, | 15 | waker: Option<NonNull<TaskHeader>>, |
| @@ -53,6 +57,11 @@ impl WakerRegistration { | |||
| 53 | unsafe impl Send for WakerRegistration {} | 57 | unsafe impl Send for WakerRegistration {} |
| 54 | unsafe impl Sync for WakerRegistration {} | 58 | unsafe impl Sync for WakerRegistration {} |
| 55 | 59 | ||
| 60 | /// Utility struct to atomically register and wake a waker. | ||
| 61 | /// | ||
| 62 | /// # Safety | ||
| 63 | /// | ||
| 64 | /// This type is optimized for (and only works with) embassy tasks. | ||
| 56 | pub struct AtomicWaker { | 65 | pub struct AtomicWaker { |
| 57 | waker: AtomicPtr<TaskHeader>, | 66 | waker: AtomicPtr<TaskHeader>, |
| 58 | } | 67 | } |
