Skip to main content

atomic_time/
lib.rs

1//! Atomic time types
2#![cfg_attr(not(feature = "std"), no_std)]
3#![cfg_attr(docsrs, feature(doc_cfg))]
4#![cfg_attr(docsrs, allow(unused_attributes))]
5#![deny(missing_docs, warnings)]
6#![forbid(unsafe_code)]
7
8pub use core::sync::atomic::Ordering;
9
10use portable_atomic::AtomicU128;
11
12mod duration;
13pub use duration::AtomicDuration;
14mod option_duration;
15pub use option_duration::AtomicOptionDuration;
16
17/// Utility functions for encoding/decoding [`Duration`] to other types.
18pub mod utils {
19  #[cfg(feature = "std")]
20  use std::time::{Duration, Instant, SystemTime};
21
22  #[cfg(feature = "std")]
23  fn init() -> (Duration, Instant) {
24    static ONCE: std::sync::OnceLock<(Duration, Instant)> = std::sync::OnceLock::new();
25
26    *ONCE.get_or_init(|| {
27      let epoch_dur = SystemTime::now()
28        .duration_since(SystemTime::UNIX_EPOCH)
29        .unwrap();
30      let instant_now = Instant::now();
31      (epoch_dur, instant_now)
32    })
33  }
34
35  /// Encode an [`Instant`] into a [`Duration`].
36  #[cfg(feature = "std")]
37  #[inline]
38  pub fn encode_instant_to_duration(instant: Instant) -> Duration {
39    let (epoch_dur, instant_now) = init();
40    if instant <= instant_now {
41      epoch_dur - (instant_now - instant)
42    } else {
43      epoch_dur + (instant - instant_now)
44    }
45  }
46
47  /// Decode an [`Instant`] from a [`Duration`].
48  #[cfg(feature = "std")]
49  #[inline]
50  pub fn decode_instant_from_duration(duration: Duration) -> Instant {
51    let (epoch_dur, instant_now) = init();
52    if duration >= epoch_dur {
53      instant_now + (duration - epoch_dur)
54    } else {
55      instant_now - (epoch_dur - duration)
56    }
57  }
58
59  pub use super::duration::{decode_duration, encode_duration};
60  pub use super::option_duration::{decode_option_duration, encode_option_duration};
61}
62
63#[cfg(feature = "std")]
64mod system_time;
65
66#[cfg(feature = "std")]
67#[cfg_attr(docsrs, doc(cfg(feature = "std")))]
68pub use system_time::AtomicSystemTime;
69
70#[cfg(feature = "std")]
71mod option_system_time;
72#[cfg(feature = "std")]
73#[cfg_attr(docsrs, doc(cfg(feature = "std")))]
74pub use option_system_time::AtomicOptionSystemTime;
75
76#[cfg(feature = "std")]
77mod instant;
78#[cfg(feature = "std")]
79#[cfg_attr(docsrs, doc(cfg(feature = "std")))]
80pub use instant::AtomicInstant;
81
82#[cfg(feature = "std")]
83mod option_instant;
84#[cfg(feature = "std")]
85#[cfg_attr(docsrs, doc(cfg(feature = "std")))]
86pub use option_instant::AtomicOptionInstant;
87
88#[cfg(feature = "std")]
89use utils::{decode_instant_from_duration, encode_instant_to_duration};