aboutsummaryrefslogtreecommitdiff
path: root/embassy-sync/src/blocking_mutex
diff options
context:
space:
mode:
Diffstat (limited to 'embassy-sync/src/blocking_mutex')
-rw-r--r--embassy-sync/src/blocking_mutex/mod.rs18
1 files changed, 18 insertions, 0 deletions
diff --git a/embassy-sync/src/blocking_mutex/mod.rs b/embassy-sync/src/blocking_mutex/mod.rs
index 8a4a4c642..a41bc3569 100644
--- a/embassy-sync/src/blocking_mutex/mod.rs
+++ b/embassy-sync/src/blocking_mutex/mod.rs
@@ -50,6 +50,23 @@ impl<R: RawMutex, T> Mutex<R, T> {
50 f(inner) 50 f(inner)
51 }) 51 })
52 } 52 }
53
54 /// Creates a critical section and grants temporary mutable access to the protected data.
55 ///
56 /// # Safety
57 ///
58 /// This method is marked unsafe because calling this method re-entrantly, i.e. within
59 /// another `lock_mut` or `lock` closure, violates Rust's aliasing rules. Calling this
60 /// method at the same time from different tasks is safe. For a safe alternative with
61 /// mutable access that never causes UB, use a `RefCell` in a `Mutex`.
62 pub unsafe fn lock_mut<U>(&self, f: impl FnOnce(&mut T) -> U) -> U {
63 self.raw.lock(|| {
64 let ptr = self.data.get() as *mut T;
65 // Safety: we have exclusive access to the data, as long as this mutex is not locked re-entrantly
66 let inner = unsafe { &mut *ptr };
67 f(inner)
68 })
69 }
53} 70}
54 71
55impl<R, T> Mutex<R, T> { 72impl<R, T> Mutex<R, T> {
@@ -104,6 +121,7 @@ impl<T> Mutex<raw::CriticalSectionRawMutex, T> {
104 121
105impl<T> Mutex<raw::NoopRawMutex, T> { 122impl<T> Mutex<raw::NoopRawMutex, T> {
106 /// Borrows the data 123 /// Borrows the data
124 #[allow(clippy::should_implement_trait)]
107 pub fn borrow(&self) -> &T { 125 pub fn borrow(&self) -> &T {
108 let ptr = self.data.get() as *const T; 126 let ptr = self.data.get() as *const T;
109 unsafe { &*ptr } 127 unsafe { &*ptr }