Files
zstd-rs/rust/src/bits.rs
T
ddidderr 58a50db413 test(rust): make entropy tests portable to 32-bit
Use an explicitly 64-bit literal before narrowing it in the common-byte test,
and derive the FSE compression-bound expectation from `size_of::<usize>()`.
The tests now exercise the same public contracts on 32-bit and 64-bit targets
instead of embedding a 64-bit-only compile-time assumption.

Test Plan:
- cargo clippy; cargo clippy --benches; cargo clippy --tests
- cargo +nightly fmt, then repeat the Clippy checks
- cargo test --target i686-unknown-linux-gnu --lib
- cargo test --target i686-unknown-linux-gnu --lib --features \
  huf-force-decompress-x1
- cargo test --target i686-unknown-linux-gnu --lib --features \
  huf-force-decompress-x2

Refs: rust/README.md
2026-07-10 20:44:02 +02:00

122 lines
3.0 KiB
Rust

#![allow(non_snake_case)]
use crate::mem::*;
#[inline]
pub fn ZSTD_isPower2(u: usize) -> bool {
(u & (u.wrapping_sub(1))) == 0
}
#[inline]
pub fn ZSTD_countTrailingZeros32(val: U32) -> u32 {
assert!(val != 0);
val.trailing_zeros()
}
#[inline]
pub fn ZSTD_countLeadingZeros32(val: U32) -> u32 {
assert!(val != 0);
val.leading_zeros()
}
#[inline]
pub fn ZSTD_countTrailingZeros64(val: U64) -> u32 {
assert!(val != 0);
val.trailing_zeros()
}
#[inline]
pub fn ZSTD_countLeadingZeros64(val: U64) -> u32 {
assert!(val != 0);
val.leading_zeros()
}
#[inline]
pub fn ZSTD_NbCommonBytes(val: usize) -> u32 {
if MEM_isLittleEndian() {
if MEM_64bits() {
ZSTD_countTrailingZeros64(val as U64) >> 3
} else {
ZSTD_countTrailingZeros32(val as U32) >> 3
}
} else {
if MEM_64bits() {
ZSTD_countLeadingZeros64(val as U64) >> 3
} else {
ZSTD_countLeadingZeros32(val as U32) >> 3
}
}
}
#[inline]
pub fn ZSTD_highbit32(val: U32) -> u32 {
assert!(val != 0);
31 - ZSTD_countLeadingZeros32(val)
}
#[inline]
pub fn ZSTD_rotateRight_U64(value: U64, count: U32) -> U64 {
assert!(count < 64);
value.rotate_right(count)
}
#[inline]
pub fn ZSTD_rotateRight_U32(value: U32, count: U32) -> U32 {
assert!(count < 32);
value.rotate_right(count)
}
#[inline]
pub fn ZSTD_rotateRight_U16(value: U16, count: U32) -> U16 {
assert!(count < 16);
value.rotate_right(count)
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn power_of_two_matches_the_c_helper() {
assert!(ZSTD_isPower2(0));
assert!(ZSTD_isPower2(1));
assert!(ZSTD_isPower2(1 << 20));
assert!(!ZSTD_isPower2(3));
assert!(!ZSTD_isPower2((1 << 20) + 1));
}
#[test]
fn bit_counts_cover_both_ends() {
assert_eq!(ZSTD_countTrailingZeros32(1), 0);
assert_eq!(ZSTD_countTrailingZeros32(1 << 31), 31);
assert_eq!(ZSTD_countLeadingZeros32(1), 31);
assert_eq!(ZSTD_countLeadingZeros32(1 << 31), 0);
assert_eq!(ZSTD_countTrailingZeros64(1), 0);
assert_eq!(ZSTD_countTrailingZeros64(1 << 63), 63);
assert_eq!(ZSTD_countLeadingZeros64(1), 63);
assert_eq!(ZSTD_countLeadingZeros64(1 << 63), 0);
assert_eq!(ZSTD_highbit32(1), 0);
assert_eq!(ZSTD_highbit32(1 << 31), 31);
}
#[test]
fn common_bytes_are_counted_in_memory_order() {
if MEM_isLittleEndian() {
assert_eq!(ZSTD_NbCommonBytes(0x0000_0000_0001_0000), 2);
} else if MEM_64bits() {
assert_eq!(ZSTD_NbCommonBytes(0x0001_0000_0000_0000u64 as usize), 2);
} else {
assert_eq!(ZSTD_NbCommonBytes(0x0001_0000), 2);
}
}
#[test]
fn rotations_match_expected_wraparound() {
assert_eq!(ZSTD_rotateRight_U16(0x1234, 4), 0x4123);
assert_eq!(ZSTD_rotateRight_U32(0x1234_5678, 8), 0x7812_3456);
assert_eq!(
ZSTD_rotateRight_U64(0x0123_4567_89ab_cdef, 16),
0xcdef_0123_4567_89ab
);
}
}