Skip to content

Commit f55ca30

Browse files
Merge pull request #380 from rust-lang/bitmask-order
Fix bitmask vector bit order
2 parents 97007cc + 289c1d1 commit f55ca30

File tree

2 files changed

+48
-0
lines changed

2 files changed

+48
-0
lines changed

crates/core_simd/src/masks/full_masks.rs

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -156,6 +156,9 @@ where
156156
for x in bytes.as_mut() {
157157
*x = x.reverse_bits()
158158
}
159+
if N % 8 > 0 {
160+
bytes.as_mut()[N / 8] >>= 8 - N % 8;
161+
}
159162
}
160163

161164
bitmask.as_mut_array()[..bytes.as_ref().len()].copy_from_slice(bytes.as_ref());
@@ -179,6 +182,9 @@ where
179182
for x in bytes.as_mut() {
180183
*x = x.reverse_bits();
181184
}
185+
if N % 8 > 0 {
186+
bytes.as_mut()[N / 8] >>= 8 - N % 8;
187+
}
182188
}
183189

184190
// Compute the regular mask

crates/core_simd/tests/masks.rs

Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -99,6 +99,19 @@ macro_rules! test_mask_api {
9999
assert_eq!(Mask::<$type, 2>::from_bitmask(bitmask), mask);
100100
}
101101

102+
#[cfg(feature = "all_lane_counts")]
103+
#[test]
104+
fn roundtrip_bitmask_conversion_odd() {
105+
let values = [
106+
true, false, true, false, true, true, false, false, false, true, true,
107+
];
108+
let mask = Mask::<$type, 11>::from_array(values);
109+
let bitmask = mask.to_bitmask();
110+
assert_eq!(bitmask, 0b11000110101);
111+
assert_eq!(Mask::<$type, 11>::from_bitmask(bitmask), mask);
112+
}
113+
114+
102115
#[test]
103116
fn cast() {
104117
fn cast_impl<T: core_simd::simd::MaskElement>()
@@ -134,6 +147,35 @@ macro_rules! test_mask_api {
134147
assert_eq!(bitmask.resize::<2>(0).to_ne_bytes()[..2], [0b01001001, 0b10000011]);
135148
assert_eq!(Mask::<$type, 16>::from_bitmask_vector(bitmask), mask);
136149
}
150+
151+
// rust-lang/portable-simd#379
152+
#[test]
153+
fn roundtrip_bitmask_vector_conversion_small() {
154+
use core_simd::simd::ToBytes;
155+
let values = [
156+
true, false, true, true
157+
];
158+
let mask = Mask::<$type, 4>::from_array(values);
159+
let bitmask = mask.to_bitmask_vector();
160+
assert_eq!(bitmask.resize::<1>(0).to_ne_bytes()[0], 0b00001101);
161+
assert_eq!(Mask::<$type, 4>::from_bitmask_vector(bitmask), mask);
162+
}
163+
164+
/* FIXME doesn't work with non-powers-of-two, yet
165+
// rust-lang/portable-simd#379
166+
#[cfg(feature = "all_lane_counts")]
167+
#[test]
168+
fn roundtrip_bitmask_vector_conversion_odd() {
169+
use core_simd::simd::ToBytes;
170+
let values = [
171+
true, false, true, false, true, true, false, false, false, true, true,
172+
];
173+
let mask = Mask::<$type, 11>::from_array(values);
174+
let bitmask = mask.to_bitmask_vector();
175+
assert_eq!(bitmask.resize::<2>(0).to_ne_bytes()[..2], [0b00110101, 0b00000110]);
176+
assert_eq!(Mask::<$type, 11>::from_bitmask_vector(bitmask), mask);
177+
}
178+
*/
137179
}
138180
}
139181
}

0 commit comments

Comments
 (0)