hermit/
time.rs

1use core::time::Duration;
2
3use crate::arch;
4
5#[allow(non_camel_case_types)]
6pub type time_t = i64;
7#[allow(non_camel_case_types)]
8pub type useconds_t = u32;
9#[allow(non_camel_case_types)]
10pub type suseconds_t = i32;
11
12/// Represent the number of seconds and microseconds since
13/// the Epoch (1970-01-01 00:00:00 +0000 (UTC))
14#[derive(Copy, Clone, Debug)]
15#[repr(C)]
16pub struct timeval {
17	/// seconds
18	pub tv_sec: time_t,
19	/// microseconds
20	pub tv_usec: suseconds_t,
21}
22
23impl timeval {
24	pub fn from_usec(microseconds: i64) -> Self {
25		Self {
26			tv_sec: (microseconds / 1_000_000),
27			tv_usec: (microseconds % 1_000_000) as i32,
28		}
29	}
30
31	pub fn into_usec(&self) -> Option<i64> {
32		self.tv_sec
33			.checked_mul(1_000_000)
34			.and_then(|usec| usec.checked_add(self.tv_usec.into()))
35	}
36}
37
38/// Represent the timer interval in seconds and microseconds
39#[derive(Copy, Clone, Debug)]
40#[repr(C)]
41pub struct itimerval {
42	pub it_interval: timeval,
43	pub it_value: timeval,
44}
45
46/// Represent the number of seconds and nanoseconds since
47/// the Epoch (1970-01-01 00:00:00 +0000 (UTC))
48#[derive(Copy, Clone, Debug, Default)]
49#[repr(C)]
50pub struct timespec {
51	/// seconds
52	pub tv_sec: time_t,
53	/// nanoseconds
54	pub tv_nsec: i32,
55}
56
57impl timespec {
58	pub fn from_usec(microseconds: i64) -> Self {
59		Self {
60			tv_sec: (microseconds / 1_000_000),
61			tv_nsec: ((microseconds % 1_000_000) * 1000) as i32,
62		}
63	}
64
65	pub fn into_usec(&self) -> Option<i64> {
66		self.tv_sec
67			.checked_mul(1_000_000)
68			.and_then(|usec| usec.checked_add((self.tv_nsec / 1000).into()))
69	}
70}
71
72#[derive(Copy, Clone, Debug, Default)]
73pub struct SystemTime(timespec);
74
75impl SystemTime {
76	pub const UNIX_EPOCH: SystemTime = Self(timespec {
77		tv_sec: 0,
78		tv_nsec: 0,
79	});
80
81	/// Returns the system time corresponding to "now".
82	pub fn now() -> Self {
83		Self(timespec::from_usec(
84			arch::kernel::systemtime::now_micros() as i64
85		))
86	}
87
88	/// Returns the amount of time elapsed from an earlier point in time.
89	pub fn duration_since(&self, earlier: SystemTime) -> Duration {
90		Duration::from_micros(
91			self.0
92				.into_usec()
93				.unwrap()
94				.checked_sub(earlier.0.into_usec().unwrap())
95				.unwrap()
96				.try_into()
97				.unwrap(),
98		)
99	}
100}
101
102impl From<timespec> for SystemTime {
103	fn from(t: timespec) -> Self {
104		Self(t)
105	}
106}
107
108impl From<SystemTime> for timespec {
109	fn from(value: SystemTime) -> Self {
110		value.0
111	}
112}