use core::{
cell::RefCell,
ops::{Deref, DerefMut},
};
use bare_metal::{CriticalSection, Mutex};
pub struct Shared<T> {
inner: Mutex<RefCell<Option<T>>>,
}
impl <T> Shared<T> {
#[cfg(feature = "const-fn")]
pub const fn new() -> Self {
Shared {
inner: Mutex::new(RefCell::new(None)),
}
}
#[cfg(not(feature = "const-fn"))]
pub fn new() -> Self {
Shared {
inner: Mutex::new(RefCell::new(None)),
}
}
pub fn load(&mut self, cs: &CriticalSection, value: T) -> Option<T> {
self.inner.borrow(cs).replace(Some(value))
}
pub fn get<'a>(&'a self, cs: &'a CriticalSection) -> Option<core::cell::Ref<'a, T>> {
match self.inner.borrow(cs).try_borrow().ok() {
Some(inner) => match inner.deref() {
Some(_) => Some(core::cell::Ref::map(inner, |v| v.as_ref().unwrap())),
None => None,
}
None => None,
}
}
pub fn get_mut<'a>(&'a self, cs: &'a CriticalSection) -> Option<core::cell::RefMut<'a, T>> {
match self.inner.borrow(cs).try_borrow_mut().ok() {
Some(mut inner) => match inner.deref_mut() {
Some(_) => Some(core::cell::RefMut::map(inner, |v| v.as_mut().unwrap())),
None => None,
}
None => None,
}
}
}