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