Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions src/block/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,7 @@ impl Block {
pub const NONE: Self = Self::from_usize_array([0; Self::USIZE_COUNT]);
pub const ALL: Self = Self::from_usize_array([usize::MAX; Self::USIZE_COUNT]);
pub const BITS: usize = core::mem::size_of::<Self>() * 8;
pub const BITS_LOG2: usize = usize::ilog2(Self::BITS) as usize;

#[inline]
pub fn into_usize_array(self) -> [usize; Self::USIZE_COUNT] {
Expand Down
39 changes: 24 additions & 15 deletions src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -40,15 +40,24 @@ use core::ptr::NonNull;
pub use range::IndexRange;

pub(crate) const BITS: usize = core::mem::size_of::<Block>() * 8;
pub const BITS_LOG2: usize = usize::ilog2(BITS) as usize;
#[cfg(feature = "serde")]
pub(crate) const BYTES: usize = core::mem::size_of::<Block>();

use block::Block as SimdBlock;
pub type Block = usize;

// #[inline]
// fn div_rem(x: usize, mut denominator: usize, _bitslog2: usize) -> (usize, usize) {
// denominator = usize::pow(2, denominator as u32) ;
// (x / denominator, x % denominator)
// }

#[inline]
fn div_rem(x: usize, denominator: usize) -> (usize, usize) {
(x / denominator, x % denominator)
fn div_rem(x: usize, bits: usize, bitslog2: usize) -> (usize, usize) {
let block = x >> bitslog2;
let i = x - (block * bits);
(block, i)
}

fn vec_into_parts<T>(vec: Vec<T>) -> (NonNull<T>, usize, usize) {
Expand Down Expand Up @@ -96,7 +105,7 @@ impl FixedBitSet {
/// Create a new **FixedBitSet** with a specific number of bits,
/// all initially clear.
pub fn with_capacity(bits: usize) -> Self {
let (mut blocks, rem) = div_rem(bits, SimdBlock::BITS);
let (mut blocks, rem) = div_rem(bits, SimdBlock::BITS, SimdBlock::BITS_LOG2);
blocks += (rem > 0) as usize;
Self::from_blocks_and_len(vec![SimdBlock::NONE; blocks], bits)
}
Expand Down Expand Up @@ -158,7 +167,7 @@ impl FixedBitSet {
let mut data = unsafe {
Vec::from_raw_parts(self.data.as_ptr(), self.simd_block_len(), self.capacity)
};
let (mut blocks, rem) = div_rem(bits, SimdBlock::BITS);
let (mut blocks, rem) = div_rem(bits, SimdBlock::BITS, SimdBlock::BITS_LOG2);
blocks += (rem > 0) as usize;
data.resize(blocks, fill);
let (data, capacity, _) = vec_into_parts(data);
Expand All @@ -179,14 +188,14 @@ impl FixedBitSet {

#[inline]
fn usize_len(&self) -> usize {
let (mut blocks, rem) = div_rem(self.length, BITS);
let (mut blocks, rem) = div_rem(self.length, BITS, BITS_LOG2);
blocks += (rem > 0) as usize;
blocks
}

#[inline]
fn simd_block_len(&self) -> usize {
let (mut blocks, rem) = div_rem(self.length, SimdBlock::BITS);
let (mut blocks, rem) = div_rem(self.length, SimdBlock::BITS, SimdBlock::BITS_LOG2);
blocks += (rem > 0) as usize;
blocks
}
Expand Down Expand Up @@ -233,7 +242,7 @@ impl FixedBitSet {
pub fn grow_and_insert(&mut self, bits: usize) {
self.grow(bits + 1);

let (blocks, rem) = div_rem(bits, BITS);
let (blocks, rem) = div_rem(bits, BITS, BITS_LOG2);
// SAFETY: The above grow ensures that the block is inside the Vec's allocation.
unsafe {
*self.get_unchecked_mut(blocks) |= 1 << rem;
Expand Down Expand Up @@ -406,7 +415,7 @@ impl FixedBitSet {
/// `bit` must be less than `self.len()`
#[inline]
pub unsafe fn contains_unchecked(&self, bit: usize) -> bool {
let (block, i) = div_rem(bit, BITS);
let (block, i) = div_rem(bit, BITS, BITS_LOG2);
(self.get_unchecked(block) & (1 << i)) != 0
}

Expand Down Expand Up @@ -441,7 +450,7 @@ impl FixedBitSet {
/// `bit` must be less than `self.len()`
#[inline]
pub unsafe fn insert_unchecked(&mut self, bit: usize) {
let (block, i) = div_rem(bit, BITS);
let (block, i) = div_rem(bit, BITS, BITS_LOG2);
// SAFETY: The above assertion ensures that the block is inside the Vec's allocation.
unsafe {
*self.get_unchecked_mut(block) |= 1 << i;
Expand Down Expand Up @@ -471,7 +480,7 @@ impl FixedBitSet {
/// `bit` must be less than `self.len()`
#[inline]
pub unsafe fn remove_unchecked(&mut self, bit: usize) {
let (block, i) = div_rem(bit, BITS);
let (block, i) = div_rem(bit, BITS, BITS_LOG2);
// SAFETY: The above assertion ensures that the block is inside the Vec's allocation.
unsafe {
*self.get_unchecked_mut(block) &= !(1 << i);
Expand Down Expand Up @@ -499,7 +508,7 @@ impl FixedBitSet {
/// `bit` must be less than `self.len()`
#[inline]
pub unsafe fn put_unchecked(&mut self, bit: usize) -> bool {
let (block, i) = div_rem(bit, BITS);
let (block, i) = div_rem(bit, BITS, BITS_LOG2);
// SAFETY: The above assertion ensures that the block is inside the Vec's allocation.
unsafe {
let word = self.get_unchecked_mut(block);
Expand Down Expand Up @@ -532,7 +541,7 @@ impl FixedBitSet {
/// `bit` must be less than `self.len()`
#[inline]
pub unsafe fn toggle_unchecked(&mut self, bit: usize) {
let (block, i) = div_rem(bit, BITS);
let (block, i) = div_rem(bit, BITS, BITS_LOG2);
// SAFETY: The above assertion ensures that the block is inside the Vec's allocation.
unsafe {
*self.get_unchecked_mut(block) ^= 1 << i;
Expand Down Expand Up @@ -562,7 +571,7 @@ impl FixedBitSet {
/// `bit` must be less than `self.len()`
#[inline]
pub unsafe fn set_unchecked(&mut self, bit: usize, enabled: bool) {
let (block, i) = div_rem(bit, BITS);
let (block, i) = div_rem(bit, BITS, BITS_LOG2);
// SAFETY: The above assertion ensures that the block is inside the Vec's allocation.
let elt = unsafe { self.get_unchecked_mut(block) };
if enabled {
Expand Down Expand Up @@ -1230,8 +1239,8 @@ impl Masks {
length
);

let (first_block, first_rem) = div_rem(start, BITS);
let (last_block, last_rem) = div_rem(end, BITS);
let (first_block, first_rem) = div_rem(start, BITS, BITS_LOG2);
let (last_block, last_rem) = div_rem(end, BITS, BITS_LOG2);

Masks {
first_block,
Expand Down
Loading