Skip to content

Commit 3f1aa0b

Browse files
committed
Additional test for uN::{gather,scatter}_bits
1 parent 791c041 commit 3f1aa0b

File tree

1 file changed

+64
-0
lines changed

1 file changed

+64
-0
lines changed

library/coretests/tests/num/uint_macros.rs

Lines changed: 64 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -387,6 +387,70 @@ macro_rules! uint_module {
387387
}
388388
}
389389

390+
#[cfg(not(miri))] // Miri is too slow
391+
#[test]
392+
fn test_lots_of_gather_scatter() {
393+
// Generate a handful of bit patterns to use as inputs
394+
let xs = {
395+
let mut xs = vec![];
396+
let mut x: $T = !0;
397+
let mut w = $T::BITS;
398+
while w > 0 {
399+
w >>= 1;
400+
xs.push(x);
401+
xs.push(!x);
402+
x ^= x << w;
403+
}
404+
xs
405+
};
406+
if $T::BITS == 8 {
407+
assert_eq!(&xs, &[0xff, 0x00, 0x0f, 0xf0, 0x33, 0xcc, 0x55, 0xaa]);
408+
}
409+
410+
// `256 * BITS` masks
411+
let sparse_masks = (i8::MIN..=i8::MAX)
412+
.map(|i| (i as i128 as $T).rotate_right(4))
413+
.flat_map(|x| (0..$T::BITS).map(move |s| ((1 as $T) << s) ^ x));
414+
415+
for sparse in sparse_masks {
416+
// Collect the set bits to sequential low bits
417+
let dense = sparse.gather_bits(sparse);
418+
let count = sparse.count_ones();
419+
assert_eq!(count, dense.count_ones());
420+
assert_eq!(count, dense.trailing_ones());
421+
422+
let mut t = sparse;
423+
for k in 0..$T::BITS {
424+
let x = ((1 as $T) << k).scatter_bits(sparse);
425+
let y = t.isolate_lowest_one();
426+
assert_eq!(x, y);
427+
t ^= y;
428+
}
429+
430+
let mut t = sparse;
431+
for k in 0..count {
432+
let y = t.isolate_lowest_one();
433+
let x = y.gather_bits(sparse);
434+
assert_eq!(x, (1 as $T) << k);
435+
t ^= y;
436+
}
437+
438+
for &x in &xs {
439+
// Gather bits from `x & sparse` to `dense`
440+
let dx = x.gather_bits(sparse);
441+
assert_eq!(dx & !dense, 0);
442+
443+
// Scatter bits from `x & dense` to `sparse`
444+
let sx = x.scatter_bits(sparse);
445+
assert_eq!(sx & !sparse, 0);
446+
447+
// The other recovers the input (within the mask)
448+
assert_eq!(dx.scatter_bits(sparse), x & sparse);
449+
assert_eq!(sx.gather_bits(sparse), x & dense);
450+
}
451+
}
452+
}
453+
390454
test_runtime_and_compiletime! {
391455
fn test_div_floor() {
392456
assert_eq_const_safe!($T: (8 as $T).div_floor(3), 2);

0 commit comments

Comments
 (0)