ahash/
convert.rs

1pub(crate) trait Convert<To> {
2    fn convert(self) -> To;
3}
4
5macro_rules! convert {
6    ($a:ty, $b:ty) => {
7        impl Convert<$b> for $a {
8            #[inline(always)]
9            fn convert(self) -> $b {
10                zerocopy::transmute!(self)
11            }
12        }
13        impl Convert<$a> for $b {
14            #[inline(always)]
15            fn convert(self) -> $a {
16                zerocopy::transmute!(self)
17            }
18        }
19    };
20}
21
22convert!([u128; 4], [u64; 8]);
23convert!([u128; 4], [u32; 16]);
24convert!([u128; 4], [u16; 32]);
25convert!([u128; 4], [u8; 64]);
26convert!([u128; 2], [u64; 4]);
27convert!([u128; 2], [u32; 8]);
28convert!([u128; 2], [u16; 16]);
29convert!([u128; 2], [u8; 32]);
30convert!(u128, [u64; 2]);
31convert!(u128, [u32; 4]);
32convert!(u128, [u16; 8]);
33convert!(u128, [u8; 16]);
34convert!([u64; 8], [u32; 16]);
35convert!([u64; 8], [u16; 32]);
36convert!([u64; 8], [u8; 64]);
37convert!([u64; 4], [u32; 8]);
38convert!([u64; 4], [u16; 16]);
39convert!([u64; 4], [u8; 32]);
40convert!([u64; 2], [u32; 4]);
41convert!([u64; 2], [u16; 8]);
42convert!([u64; 2], [u8; 16]);
43convert!([u32; 4], [u16; 8]);
44convert!([u32; 4], [u8; 16]);
45convert!([u16; 8], [u8; 16]);
46convert!(u64, [u32; 2]);
47convert!(u64, [u16; 4]);
48convert!(u64, [u8; 8]);
49convert!([u32; 2], [u16; 4]);
50convert!([u32; 2], [u8; 8]);
51convert!(u32, [u16; 2]);
52convert!(u32, [u8; 4]);
53convert!([u16; 2], [u8; 4]);
54convert!(u16, [u8; 2]);
55convert!([[u64; 4]; 2], [u8; 64]);
56
57convert!([f64; 2], [u8; 16]);
58convert!([f32; 4], [u8; 16]);
59convert!(f64, [u8; 8]);
60convert!([f32; 2], [u8; 8]);
61convert!(f32, [u8; 4]);
62
63macro_rules! as_array {
64    ($input:expr, $len:expr) => {{
65        {
66            #[inline(always)]
67            fn as_array<T>(slice: &[T]) -> &[T; $len] {
68                core::convert::TryFrom::try_from(slice).unwrap()
69            }
70            as_array($input)
71        }
72    }};
73}
74
75pub(crate) trait ReadFromSlice {
76    fn read_u16(&self) -> (u16, &[u8]);
77    fn read_u32(&self) -> (u32, &[u8]);
78    fn read_u64(&self) -> (u64, &[u8]);
79    fn read_u128(&self) -> (u128, &[u8]);
80    fn read_u128x2(&self) -> ([u128; 2], &[u8]);
81    fn read_u128x4(&self) -> ([u128; 4], &[u8]);
82    fn read_last_u16(&self) -> u16;
83    fn read_last_u32(&self) -> u32;
84    fn read_last_u64(&self) -> u64;
85    fn read_last_u128(&self) -> u128;
86    fn read_last_u128x2(&self) -> [u128; 2];
87    fn read_last_u128x4(&self) -> [u128; 4];
88}
89
90impl ReadFromSlice for [u8] {
91    #[inline(always)]
92    fn read_u16(&self) -> (u16, &[u8]) {
93        let (value, rest) = self.split_at(2);
94        (as_array!(value, 2).convert(), rest)
95    }
96
97    #[inline(always)]
98    fn read_u32(&self) -> (u32, &[u8]) {
99        let (value, rest) = self.split_at(4);
100        (as_array!(value, 4).convert(), rest)
101    }
102
103    #[inline(always)]
104    fn read_u64(&self) -> (u64, &[u8]) {
105        let (value, rest) = self.split_at(8);
106        (as_array!(value, 8).convert(), rest)
107    }
108
109    #[inline(always)]
110    fn read_u128(&self) -> (u128, &[u8]) {
111        let (value, rest) = self.split_at(16);
112        (as_array!(value, 16).convert(), rest)
113    }
114
115    #[inline(always)]
116    fn read_u128x2(&self) -> ([u128; 2], &[u8]) {
117        let (value, rest) = self.split_at(32);
118        (as_array!(value, 32).convert(), rest)
119    }
120
121    #[inline(always)]
122    fn read_u128x4(&self) -> ([u128; 4], &[u8]) {
123        let (value, rest) = self.split_at(64);
124        (as_array!(value, 64).convert(), rest)
125    }
126
127    #[inline(always)]
128    fn read_last_u16(&self) -> u16 {
129        let (_, value) = self.split_at(self.len() - 2);
130        as_array!(value, 2).convert()
131    }
132
133    #[inline(always)]
134    fn read_last_u32(&self) -> u32 {
135        let (_, value) = self.split_at(self.len() - 4);
136        as_array!(value, 4).convert()
137    }
138
139    #[inline(always)]
140    fn read_last_u64(&self) -> u64 {
141        let (_, value) = self.split_at(self.len() - 8);
142        as_array!(value, 8).convert()
143    }
144
145    #[inline(always)]
146    fn read_last_u128(&self) -> u128 {
147        let (_, value) = self.split_at(self.len() - 16);
148        as_array!(value, 16).convert()
149    }
150
151    #[inline(always)]
152    fn read_last_u128x2(&self) -> [u128; 2] {
153        let (_, value) = self.split_at(self.len() - 32);
154        as_array!(value, 32).convert()
155    }
156
157    #[inline(always)]
158    fn read_last_u128x4(&self) -> [u128; 4] {
159        let (_, value) = self.split_at(self.len() - 64);
160        as_array!(value, 64).convert()
161    }
162}