#![warn(missing_docs)]
#![cfg_attr(not(feature = "std"), no_std)]
#[cfg(all(
feature = "internal_enhanced_float",
not(feature = "std"),
not(feature = "libm"),
not(feature = "micromath")
))]
compile_error!("internal_enhanced_float must only be enabled by another feature.");
#[cfg(feature = "std")]
use alloc::sync::Arc;
#[cfg(feature = "std")]
use std::sync::{Mutex, RwLock};
#[cfg(feature = "alloc")]
extern crate alloc;
#[cfg(feature = "alloc")]
use alloc::boxed::Box;
#[cfg(feature = "alloc")]
use alloc::rc::Rc;
#[cfg(feature = "alloc")]
use alloc::vec::Vec;
use core::cell::RefCell;
use core::fmt;
use core::marker::PhantomData;
use core::ops::{Add, AddAssign, Div, DivAssign, Mul, MulAssign, Neg, Not, Sub, SubAssign};
use fmt::Debug;
mod command;
pub mod compile_time_integer;
mod datum;
#[cfg(feature = "devices")]
pub mod devices;
pub mod dimensions;
#[cfg(feature = "internal_enhanced_float")]
mod enhanced_float;
pub use dimensions::*;
mod motion_profile;
mod state;
pub mod streams;
pub mod stulta;
pub use command::*;
pub use datum::*;
#[cfg(feature = "internal_enhanced_float")]
use enhanced_float::*;
pub use motion_profile::*;
pub use state::*;
pub mod error {
use super::*;
#[derive(Clone, Copy, Debug, PartialEq, Eq)]
pub struct CannotConvert;
#[derive(Clone, Copy, Debug, PartialEq, Eq)]
pub enum PossibleDoubleError<E> {
A(E),
B(E),
AB(E, E),
}
impl<E> PossibleDoubleError<E> {
#[inline]
pub fn from_options(a: Option<E>, b: Option<E>) -> Option<Self> {
match (a, b) {
(None, None) => None,
(Some(a), None) => Some(Self::A(a)),
(None, Some(b)) => Some(Self::B(b)),
(Some(a), Some(b)) => Some(Self::AB(a, b)),
}
}
}
}
#[derive(Clone, Copy, Debug, PartialEq)]
pub enum PositionDerivative {
Position,
Velocity,
Acceleration,
}
impl TryFrom<MotionProfilePiece> for PositionDerivative {
type Error = error::CannotConvert;
fn try_from(was: MotionProfilePiece) -> Result<Self, error::CannotConvert> {
match was {
MotionProfilePiece::BeforeStart | MotionProfilePiece::Complete => {
Err(error::CannotConvert)
}
MotionProfilePiece::InitialAcceleration | MotionProfilePiece::EndAcceleration => {
Ok(PositionDerivative::Acceleration)
}
MotionProfilePiece::ConstantVelocity => Ok(PositionDerivative::Velocity),
}
}
}
#[derive(Clone, Copy, Debug, PartialEq)]
pub struct PIDKValues {
pub kp: f32,
pub ki: f32,
pub kd: f32,
}
impl PIDKValues {
pub const fn new(kp: f32, ki: f32, kd: f32) -> Self {
Self { kp, ki, kd }
}
#[inline]
pub const fn evaluate(&self, error: f32, error_integral: f32, error_derivative: f32) -> f32 {
self.kp * error + self.ki * error_integral + self.kd * error_derivative
}
}
#[derive(Clone, Copy, Debug, PartialEq)]
pub struct PositionDerivativeDependentPIDKValues {
pub position: PIDKValues,
pub velocity: PIDKValues,
pub acceleration: PIDKValues,
}
impl PositionDerivativeDependentPIDKValues {
pub const fn new(position: PIDKValues, velocity: PIDKValues, acceleration: PIDKValues) -> Self {
Self {
position,
velocity,
acceleration,
}
}
#[inline]
pub const fn get_k_values(&self, position_derivative: PositionDerivative) -> PIDKValues {
match position_derivative {
PositionDerivative::Position => self.position,
PositionDerivative::Velocity => self.velocity,
PositionDerivative::Acceleration => self.acceleration,
}
}
#[inline]
pub const fn evaluate(
&self,
position_derivative: PositionDerivative,
error: f32,
error_integral: f32,
error_derivative: f32,
) -> f32 {
self.get_k_values(position_derivative)
.evaluate(error, error_integral, error_derivative)
}
}
pub type Output<T, E> = Result<Option<Datum<T>>, E>;
pub type TimeOutput<E> = Result<Time, E>;
pub type NothingOrError<E> = Result<(), E>;
pub trait NothingOrErrorExt<E> {
fn from_option(option: Option<E>) -> Self;
fn into_option(self) -> Option<E>;
}
impl<E> NothingOrErrorExt<E> for NothingOrError<E> {
fn from_option(option: Option<E>) -> Self {
match option {
None => Ok(()),
Some(x) => {
core::hint::cold_path();
Err(x)
}
}
}
fn into_option(self) -> Option<E> {
match self {
Ok(()) => None,
Err(x) => {
core::hint::cold_path();
Some(x)
}
}
}
}
pub trait TimeGetter<E: Clone + Debug>: Updatable<E> {
fn get(&self) -> TimeOutput<E>;
}
pub trait Chronology<T> {
fn get(&self, time: Time) -> Option<Datum<T>>;
}
pub trait Updatable<E: Clone + Debug> {
fn update(&mut self) -> NothingOrError<E>;
}
pub trait Getter<G, E: Clone + Debug>: Updatable<E> {
fn get(&self) -> Output<G, E>;
fn update_and_get(&mut self) -> Output<G, E> {
self.update()?;
self.get()
}
}
pub trait Settable<S, E: Clone + Debug>: Updatable<E> {
fn set(&mut self, value: S) -> NothingOrError<E>;
}
#[doc = include_str!("../feeder-flowchart.svg")]
#[doc = include_str!("../feeder-flowchart-2.svg")]
pub struct Feeder<T, G, S, E>
where
G: Getter<T, E>,
S: Settable<T, E>,
E: Clone + Debug,
{
getter: G,
settable: S,
phantom_t: PhantomData<T>,
phantom_e: PhantomData<E>,
}
impl<T, G, S, E> Feeder<T, G, S, E>
where
G: Getter<T, E>,
S: Settable<T, E>,
E: Clone + Debug,
{
pub const fn new(getter: G, settable: S) -> Self {
Self {
getter,
settable,
phantom_t: PhantomData,
phantom_e: PhantomData,
}
}
}
impl<T, G, S, E> Updatable<error::PossibleDoubleError<E>> for Feeder<T, G, S, E>
where
G: Getter<T, E>,
S: Settable<T, E>,
E: Clone + Debug,
{
fn update(&mut self) -> NothingOrError<error::PossibleDoubleError<E>> {
let gotten = self.getter.update_and_get();
let (gotten_ok, gotten_err) = match gotten {
Ok(Some(datum)) => (Some(datum.value), None),
Ok(None) => (None, None),
Err(err) => (None, Some(err)),
};
fn settable_side<Si, Ti, Ei>(settable: &mut Si, set_value: Option<Ti>) -> NothingOrError<Ei>
where
Si: Settable<Ti, Ei>,
Ei: Clone + Debug,
{
if let Some(value) = set_value {
settable.set(value)?;
}
settable.update()
}
let settable_out = settable_side(&mut self.settable, gotten_ok);
let settable_err = settable_out.err();
NothingOrError::from_option(error::PossibleDoubleError::from_options(
gotten_err,
settable_err,
))
}
}
pub struct TimeGetterFromGetter<T, G: Getter<T, E>, E: Clone + Debug> {
getter: G,
none_error: E,
phantom_t: PhantomData<T>,
}
impl<T, G: Getter<T, E>, E: Clone + Debug> TimeGetterFromGetter<T, G, E> {
pub const fn new(getter: G, none_error: E) -> Self {
Self {
getter,
none_error,
phantom_t: PhantomData,
}
}
}
impl<T, G: Getter<T, E>, E: Clone + Debug> TimeGetter<E> for TimeGetterFromGetter<T, G, E> {
fn get(&self) -> TimeOutput<E> {
match self.getter.get() {
Err(error) => Err(error),
Ok(None) => Err(self.none_error.clone()),
Ok(Some(datum)) => Ok(datum.time),
}
}
}
impl<T, G: Getter<T, E>, E: Clone + Debug> Updatable<E> for TimeGetterFromGetter<T, G, E> {
fn update(&mut self) -> NothingOrError<E> {
Ok(())
}
}
pub struct GetterFromChronology<T, C: Chronology<T>, TG: TimeGetter<E>, E: Clone + Debug> {
chronology: C,
time_getter: TG,
time_delta: Time,
phantom_t: PhantomData<T>,
phantom_e: PhantomData<E>,
}
impl<T, C: Chronology<T>, TG: TimeGetter<E>, E: Clone + Debug> GetterFromChronology<T, C, TG, E> {
pub const fn new_no_delta(chronology: C, time_getter: TG) -> Self {
Self {
chronology,
time_getter,
time_delta: Time::ZERO,
phantom_t: PhantomData,
phantom_e: PhantomData,
}
}
pub fn new_start_at_zero(chronology: C, time_getter: TG) -> Result<Self, E> {
let time_delta = -time_getter.get()?;
Ok(Self {
chronology,
time_getter,
time_delta,
phantom_t: PhantomData,
phantom_e: PhantomData,
})
}
pub fn new_custom_start(chronology: C, time_getter: TG, start: Time) -> Result<Self, E> {
let time_delta = start - time_getter.get()?;
Ok(Self {
chronology,
time_getter,
time_delta,
phantom_t: PhantomData,
phantom_e: PhantomData,
})
}
pub const fn new_custom_delta(chronology: C, time_getter: TG, time_delta: Time) -> Self {
Self {
chronology,
time_getter,
time_delta,
phantom_t: PhantomData,
phantom_e: PhantomData,
}
}
pub const fn set_delta(&mut self, time_delta: Time) {
self.time_delta = time_delta;
}
pub fn set_time(&mut self, time: Time) -> NothingOrError<E> {
let time_delta = time - self.time_getter.get()?;
self.time_delta = time_delta;
Ok(())
}
}
impl<T, C: Chronology<T>, TG: TimeGetter<E>, E: Clone + Debug> Updatable<E>
for GetterFromChronology<T, C, TG, E>
{
fn update(&mut self) -> NothingOrError<E> {
self.time_getter.update()?;
Ok(())
}
}
impl<T, C: Chronology<T>, TG: TimeGetter<E>, E: Clone + Debug> Getter<T, E>
for GetterFromChronology<T, C, TG, E>
{
fn get(&self) -> Output<T, E> {
let time = self.time_getter.get()?;
Ok(match self.chronology.get(time + self.time_delta) {
Some(datum) => Some(Datum::new(time, datum.value)),
None => None,
})
}
}
pub struct ConstantGetter<T, TG, E>
where
T: Clone,
TG: TimeGetter<E>,
E: Clone + Debug,
{
time_getter: TG,
value: T,
phantom_e: PhantomData<E>,
}
impl<T, TG, E> ConstantGetter<T, TG, E>
where
T: Clone,
TG: TimeGetter<E>,
E: Clone + Debug,
{
pub const fn new(time_getter: TG, value: T) -> Self {
Self {
time_getter,
value,
phantom_e: PhantomData,
}
}
}
impl<T, TG, E> Getter<T, E> for ConstantGetter<T, TG, E>
where
T: Clone,
TG: TimeGetter<E>,
E: Clone + Debug,
{
fn get(&self) -> Output<T, E> {
let time = self.time_getter.get()?;
Ok(Some(Datum::new(time, self.value.clone())))
}
}
impl<T, TG, E> Settable<T, E> for ConstantGetter<T, TG, E>
where
T: Clone,
TG: TimeGetter<E>,
E: Clone + Debug,
{
fn set(&mut self, value: T) -> NothingOrError<E> {
self.value = value;
Ok(())
}
}
impl<T, TG, E> Updatable<E> for ConstantGetter<T, TG, E>
where
T: Clone,
TG: TimeGetter<E>,
E: Clone + Debug,
{
fn update(&mut self) -> NothingOrError<E> {
self.time_getter.update()?;
Ok(())
}
}
#[derive(Default)]
pub struct NoneGetter;
impl NoneGetter {
pub const fn new() -> Self {
Self
}
}
impl<T, E: Clone + Debug> Getter<T, E> for NoneGetter {
fn get(&self) -> Output<T, E> {
Ok(None)
}
}
impl<E: Clone + Debug> Updatable<E> for NoneGetter {
fn update(&mut self) -> NothingOrError<E> {
Ok(())
}
}
impl<E: Clone + Debug> TimeGetter<E> for Time {
fn get(&self) -> TimeOutput<E> {
Ok(*self)
}
}
impl<E: Clone + Debug> Updatable<E> for Time {
fn update(&mut self) -> NothingOrError<E> {
Ok(())
}
}
pub fn latest<T>(dat1: Datum<T>, dat2: Datum<T>) -> Datum<T> {
if dat1.time >= dat2.time { dat1 } else { dat2 }
}
#[derive(Clone, Copy, Debug, PartialEq, Eq)]
#[repr(transparent)]
pub struct PointerDereferencer<P> {
pointer: P,
}
impl<P> PointerDereferencer<P> {
pub const unsafe fn new(pointer: P) -> Self {
Self { pointer }
}
#[inline]
pub fn into_ptr(self) -> P {
self.pointer
}
}
impl<P: Clone> PointerDereferencer<P> {
#[inline]
pub fn clone_ptr(&self) -> P {
self.pointer.clone()
}
}
impl<P: Copy> PointerDereferencer<P> {
#[inline]
pub const fn copy_ptr(&self) -> P {
self.pointer
}
}
macro_rules! as_dyn_updatable {
($return_type:ty) => {
#[allow(missing_docs)]
#[inline]
pub const fn as_dyn_updatable<E: Clone + Debug>(&self) -> PointerDereferencer<$return_type>
where
T: Updatable<E>,
{
let ptr = self.copy_ptr() as $return_type;
unsafe { PointerDereferencer::new(ptr) }
}
};
}
macro_rules! as_dyn_getter {
($return_type:ty) => {
#[allow(missing_docs)]
#[inline]
pub const fn as_dyn_getter<U, E: Clone + Debug>(&self) -> PointerDereferencer<$return_type>
where
T: Getter<U, E>,
{
let ptr = self.copy_ptr() as $return_type;
unsafe { PointerDereferencer::new(ptr) }
}
};
}
macro_rules! as_dyn_settable {
($return_type:ty) => {
#[allow(missing_docs)]
#[inline]
pub const fn as_dyn_settable<U, E: Clone + Debug>(
&self,
) -> PointerDereferencer<$return_type>
where
T: Settable<U, E>,
{
let ptr = self.copy_ptr() as $return_type;
unsafe { PointerDereferencer::new(ptr) }
}
};
}
macro_rules! as_dyn_time_getter {
($return_type:ty) => {
#[allow(missing_docs)]
#[inline]
pub const fn as_dyn_time_getter<E: Clone + Debug>(
&self,
) -> PointerDereferencer<$return_type>
where
T: TimeGetter<E>,
{
let ptr = self.copy_ptr() as $return_type;
unsafe { PointerDereferencer::new(ptr) }
}
};
}
macro_rules! as_dyn_chronology {
($return_type:ty) => {
#[allow(missing_docs)]
#[inline]
pub const fn as_dyn_chronology<U>(&self) -> PointerDereferencer<$return_type>
where
T: Chronology<U>,
{
let ptr = self.copy_ptr() as $return_type;
unsafe { PointerDereferencer::new(ptr) }
}
};
}
impl<T> PointerDereferencer<*mut T> {
as_dyn_updatable!(*mut (dyn Updatable<E> + '_));
as_dyn_getter!(*mut (dyn Getter<U, E> + '_));
as_dyn_settable!(*mut (dyn Settable<U, E> + '_));
as_dyn_time_getter!(*mut (dyn TimeGetter<E> + '_));
as_dyn_chronology!(*mut (dyn Chronology<U> + '_));
}
#[cfg(feature = "std")]
impl<T> PointerDereferencer<*const RwLock<T>> {
as_dyn_updatable!(*const RwLock<dyn Updatable<E> + '_>);
as_dyn_getter!(*const RwLock<dyn Getter<U, E> + '_>);
as_dyn_settable!(*const RwLock<dyn Settable<U, E> + '_>);
as_dyn_time_getter!(*const RwLock<dyn TimeGetter<E> + '_>);
}
#[cfg(feature = "std")]
impl<T> PointerDereferencer<*const Mutex<T>> {
as_dyn_updatable!(*const Mutex<dyn Updatable<E> + '_>);
as_dyn_getter!(*const Mutex<dyn Getter<U, E> + '_>);
as_dyn_settable!(*const Mutex<dyn Settable<U, E> + '_>);
as_dyn_time_getter!(*const Mutex<dyn TimeGetter<E> + '_>);
}
impl<T> PointerDereferencer<*const T> {
as_dyn_chronology!(*const (dyn Chronology<U> + '_));
}
impl<U: ?Sized + Updatable<E>, E: Clone + Debug> Updatable<E> for PointerDereferencer<*mut U> {
fn update(&mut self) -> NothingOrError<E> {
unsafe { (*self.pointer).update() }
}
}
impl<T, G: ?Sized + Getter<T, E>, E: Clone + Debug> Getter<T, E> for PointerDereferencer<*mut G> {
fn get(&self) -> Output<T, E> {
unsafe { (*self.pointer).get() }
}
}
impl<T, S: ?Sized + Settable<T, E>, E: Clone + Debug> Settable<T, E>
for PointerDereferencer<*mut S>
{
fn set(&mut self, value: T) -> NothingOrError<E> {
unsafe { (*self.pointer).set(value) }
}
}
impl<TG: ?Sized + TimeGetter<E>, E: Clone + Debug> TimeGetter<E> for PointerDereferencer<*mut TG> {
fn get(&self) -> TimeOutput<E> {
unsafe { (*self.pointer).get() }
}
}
impl<T, C: ?Sized + Chronology<T>> Chronology<T> for PointerDereferencer<*mut C> {
fn get(&self, time: Time) -> Option<Datum<T>> {
unsafe { (*self.pointer).get(time) }
}
}
impl<T, C: ?Sized + Chronology<T>> Chronology<T> for PointerDereferencer<*const C> {
fn get(&self, time: Time) -> Option<Datum<T>> {
unsafe { (*self.pointer).get(time) }
}
}
#[cfg(feature = "std")]
impl<U: ?Sized + Updatable<E>, E: Clone + Debug> Updatable<E>
for PointerDereferencer<*const RwLock<U>>
{
fn update(&mut self) -> NothingOrError<E> {
unsafe { (*self.pointer).write() }
.expect("RRTK failed to acquire RwLock write lock for Updatable")
.update()
}
}
#[cfg(feature = "std")]
impl<G: ?Sized + Getter<T, E>, T, E: Clone + Debug> Getter<T, E>
for PointerDereferencer<*const RwLock<G>>
{
fn get(&self) -> Output<T, E> {
unsafe { (*self.pointer).read() }
.expect("RRTK failed to acquire RwLock read lock for Getter")
.get()
}
}
#[cfg(feature = "std")]
impl<S: ?Sized + Settable<T, E>, T, E: Clone + Debug> Settable<T, E>
for PointerDereferencer<*const RwLock<S>>
{
fn set(&mut self, value: T) -> NothingOrError<E> {
unsafe { (*self.pointer).write() }
.expect("RRTK failed to acquire RwLock write lock for Settable")
.set(value)
}
}
#[cfg(feature = "std")]
impl<TG: ?Sized + TimeGetter<E>, E: Clone + Debug> TimeGetter<E>
for PointerDereferencer<*const RwLock<TG>>
{
fn get(&self) -> TimeOutput<E> {
unsafe { (*self.pointer).read() }
.expect("RRTK failed to acquire RwLock read lock for TimeGetter")
.get()
}
}
#[cfg(feature = "std")]
impl<U: ?Sized + Updatable<E>, E: Clone + Debug> Updatable<E>
for PointerDereferencer<*const Mutex<U>>
{
fn update(&mut self) -> NothingOrError<E> {
unsafe { (*self.pointer).lock() }
.expect("RRTK failed to acquire Mutex lock for Updatable")
.update()
}
}
#[cfg(feature = "std")]
impl<G: ?Sized + Getter<T, E>, T, E: Clone + Debug> Getter<T, E>
for PointerDereferencer<*const Mutex<G>>
{
fn get(&self) -> Output<T, E> {
unsafe { (*self.pointer).lock() }
.expect("RRTK failed to acquire Mutex lock for Getter")
.get()
}
}
#[cfg(feature = "std")]
impl<S: ?Sized + Settable<T, E>, T, E: Clone + Debug> Settable<T, E>
for PointerDereferencer<*const Mutex<S>>
{
fn set(&mut self, value: T) -> NothingOrError<E> {
unsafe { (*self.pointer).lock() }
.expect("RRTK failed to acquire Mutex lock for Settable")
.set(value)
}
}
#[cfg(feature = "std")]
impl<TG: ?Sized + TimeGetter<E>, E: Clone + Debug> TimeGetter<E>
for PointerDereferencer<*const Mutex<TG>>
{
fn get(&self) -> TimeOutput<E> {
unsafe { (*self.pointer).lock() }
.expect("RRTK failed to acquire Mutex lock for TimeGetter")
.get()
}
}
#[cfg(feature = "alloc")]
impl<U: ?Sized + Updatable<E>, E: Clone + Debug> Updatable<E> for Box<U> {
fn update(&mut self) -> NothingOrError<E> {
(**self).update()
}
}
#[cfg(feature = "alloc")]
impl<G: ?Sized + Getter<T, E>, T, E: Clone + Debug> Getter<T, E> for Box<G> {
fn get(&self) -> Output<T, E> {
(**self).get()
}
}
#[cfg(feature = "alloc")]
impl<S: ?Sized + Settable<T, E>, T, E: Clone + Debug> Settable<T, E> for Box<S> {
fn set(&mut self, value: T) -> NothingOrError<E> {
(**self).set(value)
}
}
#[cfg(feature = "alloc")]
impl<TG: ?Sized + TimeGetter<E>, E: Clone + Debug> TimeGetter<E> for Box<TG> {
fn get(&self) -> TimeOutput<E> {
(**self).get()
}
}
#[cfg(feature = "alloc")]
impl<T, C: ?Sized + Chronology<T>> Chronology<T> for Box<C> {
fn get(&self, time: Time) -> Option<Datum<T>> {
(**self).get(time)
}
}
#[cfg(feature = "alloc")]
impl<U: ?Sized + Updatable<E>, E: Clone + Debug> Updatable<E> for Rc<RefCell<U>> {
fn update(&mut self) -> NothingOrError<E> {
self.borrow_mut().update()
}
}
#[cfg(feature = "alloc")]
impl<G: ?Sized + Getter<T, E>, T, E: Clone + Debug> Getter<T, E> for Rc<RefCell<G>> {
fn get(&self) -> Output<T, E> {
self.borrow().get()
}
}
#[cfg(feature = "alloc")]
impl<S: ?Sized + Settable<T, E>, T, E: Clone + Debug> Settable<T, E> for Rc<RefCell<S>> {
fn set(&mut self, value: T) -> NothingOrError<E> {
self.borrow_mut().set(value)
}
}
#[cfg(feature = "alloc")]
impl<TG: ?Sized + TimeGetter<E>, E: Clone + Debug> TimeGetter<E> for Rc<RefCell<TG>> {
fn get(&self) -> TimeOutput<E> {
self.borrow().get()
}
}
#[cfg(feature = "std")]
impl<U: ?Sized + Updatable<E>, E: Clone + Debug> Updatable<E> for Arc<RwLock<U>> {
fn update(&mut self) -> NothingOrError<E> {
self.write()
.expect("RRTK failed to acquire RwLock write lock for Updatable")
.update()
}
}
#[cfg(feature = "std")]
impl<G: ?Sized + Getter<T, E>, T, E: Clone + Debug> Getter<T, E> for Arc<RwLock<G>> {
fn get(&self) -> Output<T, E> {
self.read()
.expect("RRTK failed to acquire RwLock read lock for Getter")
.get()
}
}
#[cfg(feature = "std")]
impl<S: ?Sized + Settable<T, E>, T, E: Clone + Debug> Settable<T, E> for Arc<RwLock<S>> {
fn set(&mut self, value: T) -> NothingOrError<E> {
self.write()
.expect("RRTK failed to acquire RwLock write lock for Settable")
.set(value)
}
}
#[cfg(feature = "std")]
impl<TG: ?Sized + TimeGetter<E>, E: Clone + Debug> TimeGetter<E> for Arc<RwLock<TG>> {
fn get(&self) -> TimeOutput<E> {
self.read()
.expect("RRTK failed to acquire RwLock read lock for TimeGetter")
.get()
}
}
#[cfg(feature = "std")]
impl<U: ?Sized + Updatable<E>, E: Clone + Debug> Updatable<E> for Arc<Mutex<U>> {
fn update(&mut self) -> NothingOrError<E> {
self.lock()
.expect("RRTK failed to acquire Mutex lock for Updatable")
.update()
}
}
#[cfg(feature = "std")]
impl<G: ?Sized + Getter<T, E>, T, E: Clone + Debug> Getter<T, E> for Arc<Mutex<G>> {
fn get(&self) -> Output<T, E> {
self.lock()
.expect("RRTK failed to acquire Mutex lock for Getter")
.get()
}
}
#[cfg(feature = "std")]
impl<S: ?Sized + Settable<T, E>, T, E: Clone + Debug> Settable<T, E> for Arc<Mutex<S>> {
fn set(&mut self, value: T) -> NothingOrError<E> {
self.lock()
.expect("RRTK failed to acquire Mutex lock for Settable")
.set(value)
}
}
#[cfg(feature = "std")]
impl<TG: ?Sized + TimeGetter<E>, E: Clone + Debug> TimeGetter<E> for Arc<Mutex<TG>> {
fn get(&self) -> TimeOutput<E> {
self.lock()
.expect("RRTK failed to acquire Mutex lock for TimeGetter")
.get()
}
}
#[cfg(feature = "alloc")]
impl<T, C: ?Sized + Chronology<T>> Chronology<T> for Rc<C> {
fn get(&self, time: Time) -> Option<Datum<T>> {
(**self).get(time)
}
}
#[cfg(feature = "std")]
impl<T, C: ?Sized + Chronology<T>> Chronology<T> for Arc<C> {
fn get(&self, time: Time) -> Option<Datum<T>> {
(**self).get(time)
}
}
impl<T, C: ?Sized + Chronology<T>> Chronology<T> for RefCell<C> {
fn get(&self, time: Time) -> Option<Datum<T>> {
self.borrow().get(time)
}
}
#[cfg(feature = "std")]
impl<T, C: ?Sized + Chronology<T>> Chronology<T> for RwLock<C> {
fn get(&self, time: Time) -> Option<Datum<T>> {
self.read()
.expect("RRTK failed to acquire RwLock read lock for Chronology")
.get(time)
}
}
#[cfg(feature = "std")]
impl<T, C: ?Sized + Chronology<T>> Chronology<T> for Mutex<C> {
fn get(&self, time: Time) -> Option<Datum<T>> {
self.lock()
.expect("RRTK failed to acquire Mutex lock for Chronology")
.get(time)
}
}