irox_tools/primitives/
mod.rs

1// SPDX-License-Identifier: MIT
2// Copyright 2025 IROX Contributors
3//
4
5pub mod f32;
6pub mod f64;
7mod u128;
8pub mod u16;
9pub mod u32;
10pub mod u64;
11pub mod u8;
12mod wrapping;
13
14use irox_bits::{Error, MutBits, WriteToBEBits};
15pub use wrapping::*;
16
17///
18/// An integer!
19#[derive(Copy, Clone, Debug, Eq, PartialEq, Ord, PartialOrd, Hash)]
20pub enum IntegerValue {
21    U8(u8),
22    U16(u16),
23    U32(u32),
24    U64(u64),
25    U128(u128),
26
27    I8(i8),
28    I16(i16),
29    I32(i32),
30    I64(i64),
31    I128(i128),
32}
33
34impl IntegerValue {
35    pub const fn to_be_u128(&self) -> u128 {
36        match self {
37            IntegerValue::U8(i) => *i as u128,
38            IntegerValue::U16(i) => *i as u128,
39            IntegerValue::U32(i) => *i as u128,
40            IntegerValue::U64(i) => *i as u128,
41            IntegerValue::U128(i) => *i,
42            IntegerValue::I8(i) => *i as u128,
43            IntegerValue::I16(i) => *i as u128,
44            IntegerValue::I32(i) => *i as u128,
45            IntegerValue::I64(i) => *i as u128,
46            IntegerValue::I128(i) => *i as u128,
47        }
48    }
49    pub const fn to_be_u64(&self) -> u64 {
50        match self {
51            IntegerValue::U8(i) => *i as u64,
52            IntegerValue::U16(i) => *i as u64,
53            IntegerValue::U32(i) => *i as u64,
54            IntegerValue::U64(i) => *i,
55            IntegerValue::U128(i) => *i as u64,
56            IntegerValue::I8(i) => *i as u64,
57            IntegerValue::I16(i) => *i as u64,
58            IntegerValue::I32(i) => *i as u64,
59            IntegerValue::I64(i) => *i as u64,
60            IntegerValue::I128(i) => *i as u64,
61        }
62    }
63    pub const fn to_be_u32(&self) -> u32 {
64        self.to_be_u64() as u32
65    }
66}
67impl WriteToBEBits for IntegerValue {
68    fn write_be_to<T: MutBits + ?Sized>(&self, bits: &mut T) -> Result<usize, Error> {
69        match self {
70            IntegerValue::U8(i) => i.write_be_to(bits),
71            IntegerValue::U16(i) => i.write_be_to(bits),
72            IntegerValue::U32(i) => i.write_be_to(bits),
73            IntegerValue::U64(i) => i.write_be_to(bits),
74            IntegerValue::U128(i) => i.write_be_to(bits),
75            IntegerValue::I8(i) => i.write_be_to(bits),
76            IntegerValue::I16(i) => i.write_be_to(bits),
77            IntegerValue::I32(i) => i.write_be_to(bits),
78            IntegerValue::I64(i) => i.write_be_to(bits),
79            IntegerValue::I128(i) => i.write_be_to(bits),
80        }
81    }
82}
83
84macro_rules! impl_from_integer {
85    ($typ:ty, $($elem:tt)+) => {
86        impl From<$typ> for IntegerValue {
87            fn from(value: $typ) -> Self {
88                $($elem)+(value)
89            }
90        }
91        impl From<&$typ> for IntegerValue {
92            fn from(value: &$typ) -> Self {
93                $($elem)+(*value)
94            }
95        }
96        impl From<&mut $typ> for IntegerValue {
97            fn from(value: &mut $typ) -> Self {
98                $($elem)+(*value)
99            }
100        }
101    };
102}
103impl_from_integer!(u8, IntegerValue::U8);
104impl_from_integer!(i8, IntegerValue::I8);
105impl_from_integer!(u16, IntegerValue::U16);
106impl_from_integer!(i16, IntegerValue::I16);
107impl_from_integer!(u32, IntegerValue::U32);
108impl_from_integer!(i32, IntegerValue::I32);
109impl_from_integer!(u64, IntegerValue::U64);
110impl_from_integer!(i64, IntegerValue::I64);
111impl_from_integer!(u128, IntegerValue::U128);
112impl_from_integer!(i128, IntegerValue::I128);
113
114///
115/// Converts this value into a F64 using the `as` cast operation.
116pub trait ToF64 {
117    fn to_f64(&self) -> f64;
118}
119
120///
121/// Converts this value to the signed version using the `as` cast operation.
122pub trait ToSigned {
123    type Output;
124    fn to_signed(self) -> Self::Output;
125    fn negative_one() -> Self::Output;
126}
127
128macro_rules! impl_to_signed {
129    ($src:ty, $dst:ty) => {
130        impl ToSigned for $src {
131            type Output = $dst;
132            fn to_signed(self) -> Self::Output {
133                self as $dst
134            }
135            fn negative_one() -> Self::Output {
136                -1 as $dst
137            }
138        }
139        impl ToSigned for $dst {
140            type Output = $dst;
141            fn to_signed(self) -> Self::Output {
142                self
143            }
144            fn negative_one() -> Self::Output {
145                -1 as $dst
146            }
147        }
148    };
149}
150impl_to_signed!(u8, i8);
151impl_to_signed!(u16, i16);
152impl_to_signed!(u32, i32);
153impl_to_signed!(u64, i64);
154impl_to_signed!(u128, i128);
155
156///
157/// Converts this value to the unsigned version using the `as` cast operation.
158pub trait ToUnsigned {
159    type Output;
160    fn to_unsigned(self) -> Self::Output;
161}
162
163macro_rules! impl_to_unsigned {
164    ($src:ty, $dst:ty) => {
165        impl ToUnsigned for $src {
166            type Output = $dst;
167            fn to_unsigned(self) -> Self::Output {
168                self as $dst
169            }
170        }
171        impl ToUnsigned for $dst {
172            type Output = $dst;
173            fn to_unsigned(self) -> Self::Output {
174                self
175            }
176        }
177    };
178}
179impl_to_unsigned!(i8, u8);
180impl_to_unsigned!(i16, u16);
181impl_to_unsigned!(i32, u32);
182impl_to_unsigned!(i64, u64);
183impl_to_unsigned!(i128, u128);
184
185pub trait ToU64 {
186    fn to_u64(&self) -> u64;
187}
188macro_rules! impl_to_u64 {
189    ($ty:ty) => {
190        impl ToU64 for $ty {
191            fn to_u64(&self) -> u64 {
192                *self as u64
193            }
194        }
195    };
196}
197impl_to_u64!(u8);
198impl_to_u64!(i8);
199impl_to_u64!(u16);
200impl_to_u64!(i16);
201impl_to_u64!(u32);
202impl_to_u64!(i32);
203impl_to_u64!(u64);
204impl_to_u64!(i64);
205impl_to_u64!(u128);
206impl_to_u64!(i128);
207impl_to_u64!(f32);
208impl_to_u64!(f64);
209impl_to_u64!(bool);
210impl_to_u64!(char);