1use core::error::Error;
2use core::fmt::{Display, Formatter};
3
4#[repr(transparent)]
6#[derive(Debug, Clone, Copy, PartialEq, Eq)]
7#[must_use]
8pub struct Status(usize);
9
10impl Status {
11 pub const SUCCESS: Self = Self(0);
12 pub const UNSUPPORTED: Self = Self::error(3);
13 pub const BUFFER_TOO_SMALL: Self = Self::error(5);
14 pub const ABORTED: Self = Self::error(21);
15
16 #[cfg(target_pointer_width = "32")]
17 const fn error(v: usize) -> Self {
18 Self(0x80000000 | v)
19 }
20
21 #[cfg(target_pointer_width = "64")]
22 const fn error(v: usize) -> Self {
23 Self(0x8000000000000000 | v)
24 }
25
26 pub fn err_or<T>(self, success: T) -> Result<T, Self> {
27 if self == Self::SUCCESS {
28 Ok(success)
29 } else {
30 Err(self)
31 }
32 }
33
34 pub fn is_success(self) -> bool {
35 self == Self::SUCCESS
36 }
37}
38
39impl Error for Status {}
40
41impl Display for Status {
42 fn fmt(&self, f: &mut Formatter<'_>) -> core::fmt::Result {
43 match *self {
44 Self::SUCCESS => f.write_str("the operation completed successfully"),
45 Self::UNSUPPORTED => f.write_str("the operation is not supported"),
46 Self::BUFFER_TOO_SMALL => f.write_str("the buffer is not large enough"),
47 Self::ABORTED => f.write_str("the operation was aborted"),
48 v => write!(f, "{:#x}", v.0),
49 }
50 }
51}