1use core::mem::transmute;
2
3#[cfg(feature = "unstable")]
6item_group! {
7 use core::simd::{u8x16, u8x32, u8x64, u8x8};
8
9 #[derive(Debug, Clone, Copy)]
10 #[repr(transparent)]
11 pub struct V64(u8x8);
12
13 #[derive(Debug, Clone, Copy)]
14 #[repr(transparent)]
15 pub struct V128(u8x16);
16
17 #[derive(Debug, Clone, Copy)]
18 #[repr(transparent)]
19 pub struct V256(u8x32);
20
21 #[derive(Debug, Clone, Copy)]
22 #[repr(transparent)]
23 pub struct V512(u8x64);
24}
25
26#[cfg(all(not(feature = "unstable"), any(target_arch = "x86", target_arch = "x86_64")))]
27item_group! {
28 #[cfg(target_arch = "x86")]
29 use core::arch::x86::*;
30
31 #[cfg(target_arch = "x86_64")]
32 use core::arch::x86_64::*;
33
34 #[derive(Debug, Clone, Copy)]
35 #[repr(transparent)]
36 pub struct V64(u64);
37
38 #[derive(Debug, Clone, Copy)]
39 #[repr(transparent)]
40 pub struct V128(__m128i);
41
42 #[derive(Debug, Clone, Copy)]
43 #[repr(transparent)]
44 pub struct V256(__m256i);
45
46 #[derive(Debug, Clone, Copy)]
47 #[repr(C, align(64))]
48 pub struct V512(__m256i, __m256i);
49}
50
51#[cfg(all(not(feature = "unstable"), target_arch = "aarch64"))]
52item_group! {
53 use core::arch::aarch64::*;
54
55 #[derive(Debug, Clone, Copy)]
56 #[repr(transparent)]
57 pub struct V64(uint8x8_t);
58
59 #[derive(Debug, Clone, Copy)]
60 #[repr(transparent)]
61 pub struct V128(uint8x16_t);
62
63 #[derive(Debug, Clone, Copy)]
64 #[repr(transparent)]
65 pub struct V256(uint8x16x2_t);
66
67 #[derive(Debug, Clone, Copy)]
68 #[repr(transparent)]
69 pub struct V512(uint8x16x4_t);
70}
71
72#[cfg(all(not(feature = "unstable"), target_arch = "wasm32"))]
73item_group! {
74 #[cfg(target_arch = "wasm32")]
75 use core::arch::wasm32::*;
76
77 #[derive(Debug, Clone, Copy)]
78 #[repr(transparent)]
79 pub struct V64(u64);
80
81 #[derive(Debug, Clone, Copy)]
82 #[repr(transparent)]
83 pub struct V128(v128);
84
85 #[derive(Debug, Clone, Copy)]
86 #[repr(C, align(32))]
87 pub struct V256(v128, v128);
88
89 #[derive(Debug, Clone, Copy)]
90 #[repr(C, align(64))]
91 pub struct V512(v128, v128, v128, v128);
92}
93
94#[cfg(all(
95 not(feature = "unstable"),
96 not(any(
97 any(target_arch = "x86", target_arch = "x86_64"),
98 target_arch = "aarch64",
99 target_arch = "wasm32"
100 ))
101))]
102item_group! {
103 #[derive(Debug, Clone, Copy)]
104 #[repr(C, align(8))]
105 pub struct V64([u8; 8]);
106
107 #[derive(Debug, Clone, Copy)]
108 #[repr(C, align(16))]
109 pub struct V128([u8; 16]);
110
111 #[derive(Debug, Clone, Copy)]
112 #[repr(C, align(32))]
113 pub struct V256([u8; 32]);
114
115 #[derive(Debug, Clone, Copy)]
116 #[repr(C, align(64))]
117 pub struct V512([u8; 64]);
118}
119
120impl V64 {
121 #[inline(always)]
122 #[must_use]
123 pub const fn from_bytes(bytes: [u8; 8]) -> Self {
124 unsafe { transmute(bytes) }
125 }
126
127 #[inline(always)]
128 #[must_use]
129 pub const fn as_bytes(&self) -> &[u8; 8] {
130 unsafe { transmute(self) }
131 }
132
133 #[inline(always)]
134 #[must_use]
135 pub fn to_u64(self) -> u64 {
136 unsafe { transmute(self) }
137 }
138}
139
140impl V128 {
141 #[inline(always)]
142 #[must_use]
143 pub const fn from_bytes(bytes: [u8; 16]) -> Self {
144 unsafe { transmute(bytes) }
145 }
146
147 #[inline(always)]
148 #[must_use]
149 pub const fn as_bytes(&self) -> &[u8; 16] {
150 unsafe { transmute(self) }
151 }
152
153 #[inline(always)]
154 #[must_use]
155 pub const fn to_v64x2(self) -> (V64, V64) {
156 let x: [V64; 2] = unsafe { transmute(self) };
157 (x[0], x[1])
158 }
159
160 #[inline(always)]
161 #[must_use]
162 pub const fn x2(self) -> V256 {
163 unsafe { transmute([self, self]) }
164 }
165}
166
167impl V256 {
168 #[inline(always)]
169 #[must_use]
170 pub const fn from_bytes(bytes: [u8; 32]) -> Self {
171 unsafe { transmute(bytes) }
172 }
173
174 #[inline(always)]
175 #[must_use]
176 pub const fn as_bytes(&self) -> &[u8; 32] {
177 unsafe { transmute(self) }
178 }
179
180 #[inline(always)]
181 #[must_use]
182 pub const fn from_v128x2(x: (V128, V128)) -> Self {
183 unsafe { transmute([x.0, x.1]) }
184 }
185
186 #[inline(always)]
187 #[must_use]
188 pub const fn to_v128x2(self) -> (V128, V128) {
189 let x: [V128; 2] = unsafe { transmute(self) };
190 (x[0], x[1])
191 }
192
193 #[inline(always)]
194 #[must_use]
195 pub const fn double_bytes(bytes: [u8; 16]) -> Self {
196 unsafe { transmute([bytes, bytes]) }
197 }
198
199 #[inline(always)]
200 #[must_use]
201 pub const fn x2(self) -> V512 {
202 unsafe { transmute([self, self]) }
203 }
204}
205
206impl V512 {
207 #[inline(always)]
208 #[must_use]
209 pub const fn from_bytes(bytes: [u8; 64]) -> Self {
210 unsafe { transmute(bytes) }
211 }
212
213 #[inline(always)]
214 #[must_use]
215 pub const fn as_bytes(&self) -> &[u8; 64] {
216 unsafe { transmute(self) }
217 }
218
219 #[inline(always)]
220 #[must_use]
221 pub const fn from_v256x2(x: (V256, V256)) -> Self {
222 unsafe { transmute([x.0, x.1]) }
223 }
224
225 #[inline(always)]
226 #[must_use]
227 pub const fn to_v256x2(self) -> (V256, V256) {
228 let x: [V256; 2] = unsafe { transmute(self) };
229 (x[0], x[1])
230 }
231
232 #[inline(always)]
233 #[must_use]
234 pub const fn double_bytes(bytes: [u8; 32]) -> Self {
235 unsafe { transmute([bytes, bytes]) }
236 }
237}