1mod test_faketime;
3mod test_realtime;
4
5#[cfg(feature = "enable_faketime")]
6use std::sync::atomic::{AtomicBool, AtomicU64, Ordering};
7#[cfg(not(target_family = "wasm"))]
8pub use std::time::{Duration, Instant, SystemTime};
9#[cfg(all(target_family = "wasm", target_os = "unknown"))]
10pub use web_time::{Duration, Instant, SystemTime};
11
12#[cfg(feature = "enable_faketime")]
14static FAKETIME: AtomicU64 = AtomicU64::new(0);
15
16#[cfg(feature = "enable_faketime")]
18static FAKETIME_ENABLED: AtomicBool = AtomicBool::new(false);
19
20fn system_time_as_millis() -> u64 {
22 let duration = SystemTime::now()
23 .duration_since(SystemTime::UNIX_EPOCH)
24 .expect("SystemTime before UNIX EPOCH!");
25 duration.as_secs() * 1000 + u64::from(duration.subsec_millis())
26}
27
28#[cfg(not(feature = "enable_faketime"))]
30pub fn unix_time_as_millis() -> u64 {
31 system_time_as_millis()
32}
33
34#[cfg(feature = "enable_faketime")]
36pub fn faketime() -> FaketimeGuard {
37 FaketimeGuard {}
38}
39
40#[cfg(feature = "enable_faketime")]
42pub fn unix_time_as_millis() -> u64 {
43 if FAKETIME_ENABLED.load(Ordering::SeqCst) {
44 return FAKETIME.load(Ordering::SeqCst);
45 }
46 system_time_as_millis()
47}
48
49pub fn unix_time() -> Duration {
51 Duration::from_millis(unix_time_as_millis())
52}
53
54#[cfg(feature = "enable_faketime")]
57pub struct FaketimeGuard {}
58
59#[cfg(feature = "enable_faketime")]
60impl FaketimeGuard {
61 #[cfg(feature = "enable_faketime")]
63 pub fn set_faketime(&self, time: u64) {
64 FAKETIME.store(time, Ordering::Release);
65 FAKETIME_ENABLED.store(true, Ordering::SeqCst);
66 }
67
68 #[cfg(feature = "enable_faketime")]
70 pub fn disable_faketime(&self) {
71 FAKETIME_ENABLED.store(false, Ordering::Release);
72 }
73}
74
75#[cfg(feature = "enable_faketime")]
76impl Drop for FaketimeGuard {
77 fn drop(&mut self) {
78 self.disable_faketime()
79 }
80}