Skip to main content

glam/bool/sse2/
bvec4a.rs

1// Generated from vec_mask.rs.tera template. Edit the template, not the generated file.
2
3use core::fmt;
4use core::ops::*;
5
6#[cfg(target_arch = "x86")]
7use core::arch::x86::*;
8#[cfg(target_arch = "x86_64")]
9use core::arch::x86_64::*;
10
11#[repr(C)]
12union UnionCast {
13    a: [u32; 4],
14    v: BVec4A,
15}
16
17/// Creates a 4-dimensional `bool` vector mask.
18#[inline(always)]
19#[must_use]
20pub const fn bvec4a(x: bool, y: bool, z: bool, w: bool) -> BVec4A {
21    BVec4A::new(x, y, z, w)
22}
23
24/// A 4-dimensional SIMD vector mask.
25///
26/// This type is 16 byte aligned.
27#[derive(Clone, Copy)]
28#[repr(transparent)]
29pub struct BVec4A(pub(crate) __m128);
30
31const MASK: [u32; 2] = [0, 0xff_ff_ff_ff];
32
33impl BVec4A {
34    /// All false.
35    pub const FALSE: Self = Self::splat(false);
36
37    /// All true.
38    pub const TRUE: Self = Self::splat(true);
39
40    /// Creates a new vector mask.
41    #[inline(always)]
42    #[must_use]
43    pub const fn new(x: bool, y: bool, z: bool, w: bool) -> Self {
44        unsafe {
45            UnionCast {
46                a: [
47                    MASK[x as usize],
48                    MASK[y as usize],
49                    MASK[z as usize],
50                    MASK[w as usize],
51                ],
52            }
53            .v
54        }
55    }
56
57    /// Creates a vector mask with all elements set to `v`.
58    #[inline]
59    #[must_use]
60    pub const fn splat(v: bool) -> Self {
61        Self::new(v, v, v, v)
62    }
63
64    /// Creates a new vector mask from a bool array.
65    #[inline]
66    #[must_use]
67    pub const fn from_array(a: [bool; 4]) -> Self {
68        Self::new(a[0], a[1], a[2], a[3])
69    }
70
71    /// Returns a bitmask with the lowest 4 bits set from the elements of `self`.
72    ///
73    /// A true element results in a `1` bit and a false element in a `0` bit.  Element `x` goes
74    /// into the first lowest bit, element `y` into the second, etc.
75    #[inline]
76    #[must_use]
77    pub fn bitmask(self) -> u32 {
78        unsafe { _mm_movemask_ps(self.0) as u32 }
79    }
80
81    /// Returns true if any of the elements are true, false otherwise.
82    #[inline]
83    #[must_use]
84    pub fn any(self) -> bool {
85        self.bitmask() != 0
86    }
87
88    /// Returns true if all the elements are true, false otherwise.
89    #[inline]
90    #[must_use]
91    pub fn all(self) -> bool {
92        self.bitmask() == 0xf
93    }
94
95    /// Tests the value at `index`.
96    ///
97    /// Panics if `index` is greater than 3.
98    #[inline]
99    #[must_use]
100    #[track_caller]
101    pub fn test(self, index: usize) -> bool {
102        match index {
103            0 => (self.bitmask() & (1 << 0)) != 0,
104            1 => (self.bitmask() & (1 << 1)) != 0,
105            2 => (self.bitmask() & (1 << 2)) != 0,
106            3 => (self.bitmask() & (1 << 3)) != 0,
107            _ => panic!("index out of bounds"),
108        }
109    }
110
111    /// Sets the element at `index`.
112    ///
113    /// Panics if `index` is greater than 3.
114    #[inline]
115    #[track_caller]
116    pub fn set(&mut self, index: usize, value: bool) {
117        use crate::Vec4;
118        let mut v = Vec4(self.0);
119        v[index] = f32::from_bits(MASK[value as usize]);
120        self.0 = v.0;
121    }
122
123    #[inline]
124    #[must_use]
125    fn into_bool_array(self) -> [bool; 4] {
126        let bitmask = self.bitmask();
127        [
128            (bitmask & 1) != 0,
129            (bitmask & 2) != 0,
130            (bitmask & 4) != 0,
131            (bitmask & 8) != 0,
132        ]
133    }
134
135    #[inline]
136    #[must_use]
137    fn into_u32_array(self) -> [u32; 4] {
138        let bitmask = self.bitmask();
139        [
140            MASK[(bitmask & 1) as usize],
141            MASK[((bitmask >> 1) & 1) as usize],
142            MASK[((bitmask >> 2) & 1) as usize],
143            MASK[((bitmask >> 3) & 1) as usize],
144        ]
145    }
146}
147
148impl Default for BVec4A {
149    #[inline]
150    fn default() -> Self {
151        Self::FALSE
152    }
153}
154
155impl PartialEq for BVec4A {
156    #[inline]
157    fn eq(&self, rhs: &Self) -> bool {
158        self.bitmask().eq(&rhs.bitmask())
159    }
160}
161
162impl Eq for BVec4A {}
163
164impl core::hash::Hash for BVec4A {
165    #[inline]
166    fn hash<H: core::hash::Hasher>(&self, state: &mut H) {
167        self.bitmask().hash(state);
168    }
169}
170
171impl BitAnd for BVec4A {
172    type Output = Self;
173    #[inline]
174    fn bitand(self, rhs: Self) -> Self {
175        Self(unsafe { _mm_and_ps(self.0, rhs.0) })
176    }
177}
178
179impl BitAnd<&Self> for BVec4A {
180    type Output = Self;
181    #[inline]
182    fn bitand(self, rhs: &Self) -> Self {
183        self.bitand(*rhs)
184    }
185}
186
187impl BitAnd<&BVec4A> for &BVec4A {
188    type Output = BVec4A;
189    #[inline]
190    fn bitand(self, rhs: &BVec4A) -> BVec4A {
191        (*self).bitand(*rhs)
192    }
193}
194
195impl BitAnd<BVec4A> for &BVec4A {
196    type Output = BVec4A;
197    #[inline]
198    fn bitand(self, rhs: BVec4A) -> BVec4A {
199        (*self).bitand(rhs)
200    }
201}
202
203impl BitAndAssign for BVec4A {
204    #[inline]
205    fn bitand_assign(&mut self, rhs: Self) {
206        *self = self.bitand(rhs);
207    }
208}
209
210impl BitAndAssign<&Self> for BVec4A {
211    #[inline]
212    fn bitand_assign(&mut self, rhs: &Self) {
213        self.bitand_assign(*rhs);
214    }
215}
216
217impl BitOr for BVec4A {
218    type Output = Self;
219    #[inline]
220    fn bitor(self, rhs: Self) -> Self {
221        Self(unsafe { _mm_or_ps(self.0, rhs.0) })
222    }
223}
224
225impl BitOr<&Self> for BVec4A {
226    type Output = Self;
227    #[inline]
228    fn bitor(self, rhs: &Self) -> Self {
229        self.bitor(*rhs)
230    }
231}
232
233impl BitOr<&BVec4A> for &BVec4A {
234    type Output = BVec4A;
235    #[inline]
236    fn bitor(self, rhs: &BVec4A) -> BVec4A {
237        (*self).bitor(*rhs)
238    }
239}
240
241impl BitOr<BVec4A> for &BVec4A {
242    type Output = BVec4A;
243    #[inline]
244    fn bitor(self, rhs: BVec4A) -> BVec4A {
245        (*self).bitor(rhs)
246    }
247}
248
249impl BitOrAssign for BVec4A {
250    #[inline]
251    fn bitor_assign(&mut self, rhs: Self) {
252        *self = self.bitor(rhs);
253    }
254}
255
256impl BitOrAssign<&Self> for BVec4A {
257    #[inline]
258    fn bitor_assign(&mut self, rhs: &Self) {
259        self.bitor_assign(*rhs);
260    }
261}
262
263impl BitXor for BVec4A {
264    type Output = Self;
265    #[inline]
266    fn bitxor(self, rhs: Self) -> Self {
267        Self(unsafe { _mm_xor_ps(self.0, rhs.0) })
268    }
269}
270
271impl BitXor<&Self> for BVec4A {
272    type Output = Self;
273    #[inline]
274    fn bitxor(self, rhs: &Self) -> Self {
275        self.bitxor(*rhs)
276    }
277}
278
279impl BitXor<&BVec4A> for &BVec4A {
280    type Output = BVec4A;
281    #[inline]
282    fn bitxor(self, rhs: &BVec4A) -> BVec4A {
283        (*self).bitxor(*rhs)
284    }
285}
286
287impl BitXor<BVec4A> for &BVec4A {
288    type Output = BVec4A;
289    #[inline]
290    fn bitxor(self, rhs: BVec4A) -> BVec4A {
291        (*self).bitxor(rhs)
292    }
293}
294
295impl BitXorAssign for BVec4A {
296    #[inline]
297    fn bitxor_assign(&mut self, rhs: Self) {
298        *self = self.bitxor(rhs);
299    }
300}
301
302impl BitXorAssign<&Self> for BVec4A {
303    #[inline]
304    fn bitxor_assign(&mut self, rhs: &Self) {
305        self.bitxor_assign(*rhs);
306    }
307}
308
309impl Not for BVec4A {
310    type Output = Self;
311    #[inline]
312    fn not(self) -> Self {
313        Self(unsafe { _mm_andnot_ps(self.0, _mm_set_ps1(f32::from_bits(0xff_ff_ff_ff))) })
314    }
315}
316
317impl Not for &BVec4A {
318    type Output = BVec4A;
319    #[inline]
320    fn not(self) -> BVec4A {
321        (*self).not()
322    }
323}
324
325impl From<BVec4A> for __m128 {
326    #[inline]
327    fn from(t: BVec4A) -> Self {
328        t.0
329    }
330}
331
332impl fmt::Debug for BVec4A {
333    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
334        let arr = self.into_u32_array();
335        write!(
336            f,
337            "{}({:#x}, {:#x}, {:#x}, {:#x})",
338            stringify!(BVec4A),
339            arr[0],
340            arr[1],
341            arr[2],
342            arr[3]
343        )
344    }
345}
346
347impl fmt::Display for BVec4A {
348    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
349        let arr = self.into_bool_array();
350        write!(f, "[{}, {}, {}, {}]", arr[0], arr[1], arr[2], arr[3])
351    }
352}
353
354impl From<[bool; 4]> for BVec4A {
355    #[inline]
356    fn from(a: [bool; 4]) -> Self {
357        Self::from_array(a)
358    }
359}
360
361impl From<BVec4A> for [bool; 4] {
362    #[inline]
363    fn from(mask: BVec4A) -> Self {
364        mask.into_bool_array()
365    }
366}
367
368impl From<BVec4A> for [u32; 4] {
369    #[inline]
370    fn from(mask: BVec4A) -> Self {
371        mask.into_u32_array()
372    }
373}