osom_tools_runtime/
length.rs1#![allow(clippy::cast_possible_truncation, clippy::cast_possible_wrap, clippy::cast_sign_loss)]
2
3#[derive(Copy, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
13#[repr(transparent)]
14#[must_use]
15pub struct Length {
16 value: i32,
17}
18
19impl core::fmt::Debug for Length {
20 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
21 write!(f, "{}", self.value())
22 }
23}
24
25#[derive(Debug, Clone, PartialEq, Eq, Hash)]
27#[repr(u8)]
28pub enum LengthError {
29 TooLarge,
31
32 Negative,
34}
35
36impl Length {
37 pub const MAX: usize = (i32::MAX - 1024) as usize;
38 pub const ZERO: Self = unsafe { Self::new_unchecked(0) };
39
40 pub const fn try_from_usize(len: usize) -> Result<Self, LengthError> {
46 if len > Self::MAX {
47 return Err(LengthError::TooLarge);
48 }
49
50 Ok(unsafe { Self::new_unchecked(len as i32) })
51 }
52
53 pub const fn try_from_i32(len: i32) -> Result<Self, LengthError> {
59 if len < 0 {
60 return Err(LengthError::Negative);
61 }
62
63 Ok(unsafe { Self::new_unchecked(len) })
64 }
65
66 #[inline(always)]
72 pub const unsafe fn new_unchecked(len: i32) -> Self {
73 Self { value: len }
74 }
75
76 #[inline(always)]
78 #[must_use]
79 pub const fn value(&self) -> i32 {
80 unsafe { core::hint::assert_unchecked(self.value >= 0) };
81 self.value
82 }
83
84 #[inline(always)]
86 pub const fn inc(&mut self, value: i32) {
87 self.value += value;
88 }
89
90 #[inline(always)]
92 pub const fn dec(&mut self, value: i32) {
93 self.value -= value;
94 }
95}
96
97impl TryFrom<usize> for Length {
98 type Error = LengthError;
99
100 fn try_from(value: usize) -> Result<Self, Self::Error> {
101 Self::try_from_usize(value)
102 }
103}
104
105impl TryFrom<i32> for Length {
106 type Error = LengthError;
107
108 fn try_from(value: i32) -> Result<Self, Self::Error> {
109 Self::try_from_i32(value)
110 }
111}
112
113impl From<Length> for usize {
114 fn from(value: Length) -> Self {
115 value.value() as usize
116 }
117}
118
119impl From<Length> for i32 {
120 fn from(value: Length) -> Self {
121 value.value()
122 }
123}
124
125impl From<Length> for u32 {
126 fn from(value: Length) -> Self {
127 value.value() as u32
128 }
129}