use core::time::Duration;
#[derive(Clone, Copy, Debug, Eq, Ord, PartialEq, PartialOrd)]
#[cfg_attr(feature = "serde", derive(serde::Deserialize, serde::Serialize))]
pub struct GenericTime {
#[cfg(feature = "std")]
_inner: std::time::SystemTime,
#[cfg(all(feature = "embassy-time", not(any(feature = "std"))))]
_inner: embassy_time::Instant,
#[cfg(not(any(feature = "std", feature = "embassy-time")))]
_inner: (),
}
impl GenericTime {
#[inline]
pub fn now() -> Self {
#[cfg(feature = "std")]
return Self { _inner: std::time::SystemTime::now() };
#[cfg(all(feature = "embassy-time", not(any(feature = "std"))))]
return Self { _inner: embassy_time::Instant::now() };
#[cfg(not(any(feature = "std", feature = "embassy-time")))]
return Self { _inner: () };
}
#[inline]
pub fn checked_add(&self, _duration: Duration) -> crate::Result<Self> {
#[cfg(feature = "std")]
return Ok(Self {
_inner: self._inner.checked_add(_duration).ok_or(crate::Error::InvalidTimeArithmetic)?,
});
#[cfg(all(feature = "embassy-time", not(any(feature = "std"))))]
return Ok(Self {
_inner: self
._inner
.checked_add(embassy_time::Duration::from_secs(_duration.as_secs()))
.ok_or(crate::Error::InvalidTimeArithmetic)?,
});
#[cfg(not(any(feature = "std", feature = "embassy-time")))]
return Err(crate::Error::GenericTimeNeedsBackend);
}
#[inline]
pub fn checked_sub(&self, _duration: Duration) -> crate::Result<Self> {
#[cfg(feature = "std")]
return Ok(Self {
_inner: self._inner.checked_sub(_duration).ok_or(crate::Error::InvalidTimeArithmetic)?,
});
#[cfg(all(feature = "embassy-time", not(any(feature = "std"))))]
return Ok(Self {
_inner: self
._inner
.checked_sub(embassy_time::Duration::from_secs(_duration.as_secs()))
.ok_or(crate::Error::InvalidTimeArithmetic)?,
});
#[cfg(not(any(feature = "std", feature = "embassy-time")))]
return Err(crate::Error::GenericTimeNeedsBackend);
}
#[inline]
pub fn duration_since(&self, _earlier: Self) -> crate::Result<Duration> {
#[cfg(feature = "std")]
return self
._inner
.duration_since(_earlier._inner)
.map_err(|_err| crate::Error::InvalidHardwareTime);
#[cfg(all(feature = "embassy-time", not(any(feature = "std"))))]
return Ok(Duration::from_micros(
self
._inner
.checked_duration_since(_earlier._inner)
.ok_or(crate::Error::InvalidTimeArithmetic)?
.as_micros(),
));
#[cfg(not(any(feature = "std", feature = "embassy-time")))]
return Err(crate::Error::GenericTimeNeedsBackend);
}
#[inline]
pub fn elapsed(&self) -> crate::Result<Duration> {
Self::now().duration_since(*self)
}
#[inline]
pub fn timestamp() -> crate::Result<Duration> {
#[cfg(feature = "std")]
return Self::now().duration_since(Self { _inner: std::time::UNIX_EPOCH });
#[cfg(all(feature = "embassy-time", not(any(feature = "std"))))]
return Self::now().duration_since(Self { _inner: embassy_time::Instant::from_secs(0) });
#[cfg(not(any(feature = "std", feature = "embassy-time")))]
return Err(crate::Error::GenericTimeNeedsBackend);
}
}