/rust/registry/src/index.crates.io-1949cf8c6b5b557f/bitvec-1.0.1/src/slice.rs
Line | Count | Source |
1 | | #![doc = include_str!("../doc/slice.md")] |
2 | | |
3 | | #[cfg(feature = "alloc")] |
4 | | use alloc::vec::Vec; |
5 | | use core::{ |
6 | | marker::PhantomData, |
7 | | ops::RangeBounds, |
8 | | }; |
9 | | |
10 | | use funty::Integral; |
11 | | use tap::Pipe; |
12 | | #[cfg(feature = "alloc")] |
13 | | use tap::Tap; |
14 | | use wyz::{ |
15 | | bidi::BidiIterator, |
16 | | comu::{ |
17 | | Const, |
18 | | Mut, |
19 | | }, |
20 | | range::RangeExt, |
21 | | }; |
22 | | |
23 | | #[cfg(feature = "alloc")] |
24 | | use crate::vec::BitVec; |
25 | | use crate::{ |
26 | | domain::{ |
27 | | BitDomain, |
28 | | Domain, |
29 | | }, |
30 | | mem, |
31 | | order::{ |
32 | | BitOrder, |
33 | | Lsb0, |
34 | | Msb0, |
35 | | }, |
36 | | ptr::{ |
37 | | self as bv_ptr, |
38 | | BitPtr, |
39 | | BitPtrRange, |
40 | | BitSpan, |
41 | | BitSpanError, |
42 | | }, |
43 | | store::BitStore, |
44 | | }; |
45 | | |
46 | | mod api; |
47 | | mod iter; |
48 | | mod ops; |
49 | | mod specialization; |
50 | | mod tests; |
51 | | mod traits; |
52 | | |
53 | | pub use self::{ |
54 | | api::*, |
55 | | iter::*, |
56 | | }; |
57 | | |
58 | | #[repr(transparent)] |
59 | | #[doc = include_str!("../doc/slice/BitSlice.md")] |
60 | | pub struct BitSlice<T = usize, O = Lsb0> |
61 | | where |
62 | | T: BitStore, |
63 | | O: BitOrder, |
64 | | { |
65 | | /// The ordering of bits within a `T` register. |
66 | | _ord: PhantomData<O>, |
67 | | /// The register type used for storage. |
68 | | _typ: PhantomData<[T]>, |
69 | | /// Indicate that this is a newtype wrapper over a wholly-untyped slice. |
70 | | /// |
71 | | /// This is necessary in order for the Rust compiler to remove restrictions |
72 | | /// on the possible values of reference handles to this type. Any other |
73 | | /// slice type here (such as `[u8]` or `[T]`) would require that `&/mut |
74 | | /// BitSlice` handles have values that correctly describe the region, and |
75 | | /// the encoding *does not* do this. As such, reference handles to |
76 | | /// `BitSlice` must not be even implicitly dereferenceäble to real memory, |
77 | | /// and the slice must be a ZST. |
78 | | /// |
79 | | /// References to a ZST have no restrictions about what the values can be, |
80 | | /// as they are never able to dereference real memory and thus both |
81 | | /// addresses and lengths are meaningless to the memory inspector. |
82 | | /// |
83 | | /// See `ptr::span` for more information on the encoding scheme used in |
84 | | /// references to `BitSlice`. |
85 | | _mem: [()], |
86 | | } |
87 | | |
88 | | /// Constructors. |
89 | | impl<T, O> BitSlice<T, O> |
90 | | where |
91 | | T: BitStore, |
92 | | O: BitOrder, |
93 | | { |
94 | | /// Produces an empty bit-slice with an arbitrary lifetime. |
95 | | /// |
96 | | /// ## Original |
97 | | /// |
98 | | /// This is equivalent to the `&[]` literal. |
99 | | /// |
100 | | /// ## Examples |
101 | | /// |
102 | | /// ```rust |
103 | | /// use bitvec::prelude::*; |
104 | | /// |
105 | | /// assert!(BitSlice::<u16, LocalBits>::empty().is_empty()); |
106 | | /// assert_eq!(bits![], BitSlice::<u8, Msb0>::empty()); |
107 | | /// ``` |
108 | | #[inline] |
109 | 0 | pub fn empty<'a>() -> &'a Self { |
110 | 0 | unsafe { BitSpan::<Const, T, O>::EMPTY.into_bitslice_ref() } |
111 | 0 | } |
112 | | |
113 | | /// Produces an empty bit-slice with an arbitrary lifetime. |
114 | | /// |
115 | | /// ## Original |
116 | | /// |
117 | | /// This is equivalent to the `&mut []` literal. |
118 | | /// |
119 | | /// ## Examples |
120 | | /// |
121 | | /// ```rust |
122 | | /// use bitvec::prelude::*; |
123 | | /// |
124 | | /// assert!(BitSlice::<u16, LocalBits>::empty_mut().is_empty()); |
125 | | /// assert_eq!(bits![mut], BitSlice::<u8, Msb0>::empty_mut()); |
126 | | /// ``` |
127 | | #[inline] |
128 | 210k | pub fn empty_mut<'a>() -> &'a mut Self { |
129 | 210k | unsafe { BitSpan::<Mut, T, O>::EMPTY.into_bitslice_mut() } |
130 | 210k | } Unexecuted instantiation: <bitvec::slice::BitSlice<bitvec::access::BitSafeU8>>::empty_mut <bitvec::slice::BitSlice<bitvec::access::BitSafeU8, bitvec::order::Msb0>>::empty_mut Line | Count | Source | 128 | 210k | pub fn empty_mut<'a>() -> &'a mut Self { | 129 | 210k | unsafe { BitSpan::<Mut, T, O>::EMPTY.into_bitslice_mut() } | 130 | 210k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::empty_mut |
131 | | |
132 | | /// Constructs a shared `&BitSlice` reference over a shared element. |
133 | | /// |
134 | | /// The [`BitView`] trait, implemented on all [`BitStore`] implementors, |
135 | | /// provides a [`.view_bits::<O>()`] method which delegates to this function |
136 | | /// and may be more convenient for you to write. |
137 | | /// |
138 | | /// ## Parameters |
139 | | /// |
140 | | /// - `elem`: A shared reference to a memory element. |
141 | | /// |
142 | | /// ## Returns |
143 | | /// |
144 | | /// A shared `&BitSlice` over `elem`. |
145 | | /// |
146 | | /// ## Examples |
147 | | /// |
148 | | /// ```rust |
149 | | /// use bitvec::prelude::*; |
150 | | /// |
151 | | /// let elem = 0u8; |
152 | | /// let bits = BitSlice::<_, Lsb0>::from_element(&elem); |
153 | | /// assert_eq!(bits.len(), 8); |
154 | | /// |
155 | | /// let bits = elem.view_bits::<Lsb0>(); |
156 | | /// ``` |
157 | | /// |
158 | | /// [`BitStore`]: crate::store::BitStore |
159 | | /// [`BitView`]: crate::view::BitView |
160 | | /// [`.view_bits::<O>()`]: crate::view::BitView::view_bits |
161 | | #[inline] |
162 | 0 | pub fn from_element(elem: &T) -> &Self { |
163 | | unsafe { |
164 | 0 | BitPtr::from_ref(elem) |
165 | 0 | .span_unchecked(mem::bits_of::<T::Mem>()) |
166 | 0 | .into_bitslice_ref() |
167 | | } |
168 | 0 | } |
169 | | |
170 | | /// Constructs an exclusive `&mut BitSlice` reference over an element. |
171 | | /// |
172 | | /// The [`BitView`] trait, implemented on all [`BitStore`] implementors, |
173 | | /// provides a [`.view_bits_mut::<O>()`] method which delegates to this |
174 | | /// function and may be more convenient for you to write. |
175 | | /// |
176 | | /// ## Parameters |
177 | | /// |
178 | | /// - `elem`: An exclusive reference to a memory element. |
179 | | /// |
180 | | /// ## Returns |
181 | | /// |
182 | | /// An exclusive `&mut BitSlice` over `elem`. |
183 | | /// |
184 | | /// Note that the original `elem` reference will be inaccessible for the |
185 | | /// duration of the returned bit-slice handle’s lifetime. |
186 | | /// |
187 | | /// ## Examples |
188 | | /// |
189 | | /// ```rust |
190 | | /// use bitvec::prelude::*; |
191 | | /// |
192 | | /// let mut elem = 0u8; |
193 | | /// let bits = BitSlice::<_, Lsb0>::from_element_mut(&mut elem); |
194 | | /// bits.set(1, true); |
195 | | /// assert!(bits[1]); |
196 | | /// assert_eq!(elem, 2); |
197 | | /// |
198 | | /// let bits = elem.view_bits_mut::<Lsb0>(); |
199 | | /// ``` |
200 | | /// |
201 | | /// [`BitStore`]: crate::store::BitStore |
202 | | /// [`BitView`]: crate::view::BitView |
203 | | /// [`.view_bits_mut::<O>()`]: crate::view::BitView::view_bits_mut |
204 | | #[inline] |
205 | 0 | pub fn from_element_mut(elem: &mut T) -> &mut Self { |
206 | 0 | unsafe { |
207 | 0 | BitPtr::from_mut(elem) |
208 | 0 | .span_unchecked(mem::bits_of::<T::Mem>()) |
209 | 0 | .into_bitslice_mut() |
210 | 0 | } |
211 | 0 | } |
212 | | |
213 | | /// Constructs a shared `&BitSlice` reference over a slice of elements. |
214 | | /// |
215 | | /// The [`BitView`] trait, implemented on all `[T]` slices, provides a |
216 | | /// [`.view_bits::<O>()`] method which delegates to this function and may be |
217 | | /// more convenient for you to write. |
218 | | /// |
219 | | /// ## Parameters |
220 | | /// |
221 | | /// - `slice`: A shared reference to a slice of memory elements. |
222 | | /// |
223 | | /// ## Returns |
224 | | /// |
225 | | /// A shared `BitSlice` reference over all of `slice`. |
226 | | /// |
227 | | /// ## Panics |
228 | | /// |
229 | | /// This will panic if `slice` is too long to encode as a bit-slice view. |
230 | | /// |
231 | | /// ## Examples |
232 | | /// |
233 | | /// ```rust |
234 | | /// use bitvec::prelude::*; |
235 | | /// |
236 | | /// let data = [0u16, 1]; |
237 | | /// let bits = BitSlice::<_, Lsb0>::from_slice(&data); |
238 | | /// assert!(bits[16]); |
239 | | /// |
240 | | /// let bits = data.view_bits::<Lsb0>(); |
241 | | /// ``` |
242 | | /// |
243 | | /// [`BitView`]: crate::view::BitView |
244 | | /// [`.view_bits::<O>()`]: crate::view::BitView::view_bits |
245 | | #[inline] |
246 | 136k | pub fn from_slice(slice: &[T]) -> &Self { |
247 | 136k | Self::try_from_slice(slice).unwrap() |
248 | 136k | } <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::from_slice Line | Count | Source | 246 | 136k | pub fn from_slice(slice: &[T]) -> &Self { | 247 | 136k | Self::try_from_slice(slice).unwrap() | 248 | 136k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::from_slice |
249 | | |
250 | | /// Attempts to construct a shared `&BitSlice` reference over a slice of |
251 | | /// elements. |
252 | | /// |
253 | | /// The [`BitView`], implemented on all `[T]` slices, provides a |
254 | | /// [`.try_view_bits::<O>()`] method which delegates to this function and |
255 | | /// may be more convenient for you to write. |
256 | | /// |
257 | | /// This is *very hard*, if not impossible, to cause to fail. Rust will not |
258 | | /// create excessive arrays on 64-bit architectures. |
259 | | /// |
260 | | /// ## Parameters |
261 | | /// |
262 | | /// - `slice`: A shared reference to a slice of memory elements. |
263 | | /// |
264 | | /// ## Returns |
265 | | /// |
266 | | /// A shared `&BitSlice` over `slice`. If `slice` is longer than can be |
267 | | /// encoded into a `&BitSlice` (see [`MAX_ELTS`]), this will fail and return |
268 | | /// the original `slice` as an error. |
269 | | /// |
270 | | /// ## Examples |
271 | | /// |
272 | | /// ```rust |
273 | | /// use bitvec::prelude::*; |
274 | | /// |
275 | | /// let data = [0u8, 1]; |
276 | | /// let bits = BitSlice::<_, Msb0>::try_from_slice(&data).unwrap(); |
277 | | /// assert!(bits[15]); |
278 | | /// |
279 | | /// let bits = data.try_view_bits::<Msb0>().unwrap(); |
280 | | /// ``` |
281 | | /// |
282 | | /// [`BitView`]: crate::view::BitView |
283 | | /// [`MAX_ELTS`]: Self::MAX_ELTS |
284 | | /// [`.try_view_bits::<O>()`]: crate::view::BitView::try_view_bits |
285 | | #[inline] |
286 | 136k | pub fn try_from_slice(slice: &[T]) -> Result<&Self, BitSpanError<T>> { |
287 | 136k | let elts = slice.len(); |
288 | 136k | if elts >= Self::MAX_ELTS { |
289 | 0 | elts.saturating_mul(mem::bits_of::<T::Mem>()) |
290 | 0 | .pipe(BitSpanError::TooLong) |
291 | 0 | .pipe(Err) |
292 | | } |
293 | | else { |
294 | 136k | Ok(unsafe { Self::from_slice_unchecked(slice) }) |
295 | | } |
296 | 136k | } <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::try_from_slice Line | Count | Source | 286 | 136k | pub fn try_from_slice(slice: &[T]) -> Result<&Self, BitSpanError<T>> { | 287 | 136k | let elts = slice.len(); | 288 | 136k | if elts >= Self::MAX_ELTS { | 289 | 0 | elts.saturating_mul(mem::bits_of::<T::Mem>()) | 290 | 0 | .pipe(BitSpanError::TooLong) | 291 | 0 | .pipe(Err) | 292 | | } | 293 | | else { | 294 | 136k | Ok(unsafe { Self::from_slice_unchecked(slice) }) | 295 | | } | 296 | 136k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::try_from_slice |
297 | | |
298 | | /// Constructs an exclusive `&mut BitSlice` reference over a slice of |
299 | | /// elements. |
300 | | /// |
301 | | /// The [`BitView`] trait, implemented on all `[T]` slices, provides a |
302 | | /// [`.view_bits_mut::<O>()`] method which delegates to this function and |
303 | | /// may be more convenient for you to write. |
304 | | /// |
305 | | /// ## Parameters |
306 | | /// |
307 | | /// - `slice`: An exclusive reference to a slice of memory elements. |
308 | | /// |
309 | | /// ## Returns |
310 | | /// |
311 | | /// An exclusive `&mut BitSlice` over all of `slice`. |
312 | | /// |
313 | | /// ## Panics |
314 | | /// |
315 | | /// This panics if `slice` is too long to encode as a bit-slice view. |
316 | | /// |
317 | | /// ## Examples |
318 | | /// |
319 | | /// ```rust |
320 | | /// use bitvec::prelude::*; |
321 | | /// |
322 | | /// let mut data = [0u16; 2]; |
323 | | /// let bits = BitSlice::<_, Lsb0>::from_slice_mut(&mut data); |
324 | | /// bits.set(0, true); |
325 | | /// bits.set(17, true); |
326 | | /// assert_eq!(data, [1, 2]); |
327 | | /// |
328 | | /// let bits = data.view_bits_mut::<Lsb0>(); |
329 | | /// ``` |
330 | | /// |
331 | | /// [`BitView`]: crate::view::BitView |
332 | | /// [`.view_bits_mut::<O>()`]: crate::view::BitView::view_bits_mut |
333 | | #[inline] |
334 | 164k | pub fn from_slice_mut(slice: &mut [T]) -> &mut Self { |
335 | 164k | Self::try_from_slice_mut(slice).unwrap() |
336 | 164k | } <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::from_slice_mut Line | Count | Source | 334 | 164k | pub fn from_slice_mut(slice: &mut [T]) -> &mut Self { | 335 | 164k | Self::try_from_slice_mut(slice).unwrap() | 336 | 164k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::from_slice_mut |
337 | | |
338 | | /// Attempts to construct an exclusive `&mut BitSlice` reference over a |
339 | | /// slice of elements. |
340 | | /// |
341 | | /// The [`BitView`] trait, implemented on all `[T]` slices, provides a |
342 | | /// [`.try_view_bits_mut::<O>()`] method which delegates to this function |
343 | | /// and may be more convenient for you to write. |
344 | | /// |
345 | | /// ## Parameters |
346 | | /// |
347 | | /// - `slice`: An exclusive reference to a slice of memory elements. |
348 | | /// |
349 | | /// ## Returns |
350 | | /// |
351 | | /// An exclusive `&mut BitSlice` over `slice`. If `slice` is longer than can |
352 | | /// be encoded into a `&mut BitSlice` (see [`MAX_ELTS`]), this will fail and |
353 | | /// return the original `slice` as an error. |
354 | | /// |
355 | | /// ## Examples |
356 | | /// |
357 | | /// ```rust |
358 | | /// use bitvec::prelude::*; |
359 | | /// |
360 | | /// let mut data = [0u8; 2]; |
361 | | /// let bits = BitSlice::<_, Msb0>::try_from_slice_mut(&mut data).unwrap(); |
362 | | /// bits.set(7, true); |
363 | | /// bits.set(15, true); |
364 | | /// assert_eq!(data, [1; 2]); |
365 | | /// |
366 | | /// let bits = data.try_view_bits_mut::<Msb0>().unwrap(); |
367 | | /// ``` |
368 | | /// |
369 | | /// [`BitView`]: crate::view::BitView |
370 | | /// [`MAX_ELTS`]: Self::MAX_ELTS |
371 | | /// [`.try_view_bits_mut::<O>()`]: crate::view::BitView::try_view_bits_mut |
372 | | #[inline] |
373 | 164k | pub fn try_from_slice_mut( |
374 | 164k | slice: &mut [T], |
375 | 164k | ) -> Result<&mut Self, BitSpanError<T>> { |
376 | 164k | let elts = slice.len(); |
377 | 164k | if elts >= Self::MAX_ELTS { |
378 | 0 | elts.saturating_mul(mem::bits_of::<T::Mem>()) |
379 | 0 | .pipe(BitSpanError::TooLong) |
380 | 0 | .pipe(Err) |
381 | | } |
382 | | else { |
383 | 164k | Ok(unsafe { Self::from_slice_unchecked_mut(slice) }) |
384 | | } |
385 | 164k | } <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::try_from_slice_mut Line | Count | Source | 373 | 164k | pub fn try_from_slice_mut( | 374 | 164k | slice: &mut [T], | 375 | 164k | ) -> Result<&mut Self, BitSpanError<T>> { | 376 | 164k | let elts = slice.len(); | 377 | 164k | if elts >= Self::MAX_ELTS { | 378 | 0 | elts.saturating_mul(mem::bits_of::<T::Mem>()) | 379 | 0 | .pipe(BitSpanError::TooLong) | 380 | 0 | .pipe(Err) | 381 | | } | 382 | | else { | 383 | 164k | Ok(unsafe { Self::from_slice_unchecked_mut(slice) }) | 384 | | } | 385 | 164k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::try_from_slice_mut |
386 | | |
387 | | /// Constructs a shared `&BitSlice` over an element slice, without checking |
388 | | /// its length. |
389 | | /// |
390 | | /// If `slice` is too long to encode into a `&BitSlice`, then the produced |
391 | | /// bit-slice’s length is unspecified. |
392 | | /// |
393 | | /// ## Safety |
394 | | /// |
395 | | /// You must ensure that `slice.len() < BitSlice::MAX_ELTS`. |
396 | | /// |
397 | | /// Calling this function with an over-long slice is **library-level** |
398 | | /// undefined behavior. You may not assume anything about its implementation |
399 | | /// or behavior, and must conservatively assume that over-long slices cause |
400 | | /// compiler UB. |
401 | | #[inline] |
402 | 136k | pub unsafe fn from_slice_unchecked(slice: &[T]) -> &Self { |
403 | 136k | let bits = slice.len().wrapping_mul(mem::bits_of::<T::Mem>()); |
404 | 136k | BitPtr::from_slice(slice) |
405 | 136k | .span_unchecked(bits) |
406 | 136k | .into_bitslice_ref() |
407 | 136k | } <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::from_slice_unchecked Line | Count | Source | 402 | 136k | pub unsafe fn from_slice_unchecked(slice: &[T]) -> &Self { | 403 | 136k | let bits = slice.len().wrapping_mul(mem::bits_of::<T::Mem>()); | 404 | 136k | BitPtr::from_slice(slice) | 405 | 136k | .span_unchecked(bits) | 406 | 136k | .into_bitslice_ref() | 407 | 136k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::from_slice_unchecked |
408 | | |
409 | | /// Constructs an exclusive `&mut BitSlice` over an element slice, without |
410 | | /// checking its length. |
411 | | /// |
412 | | /// If `slice` is too long to encode into a `&mut BitSlice`, then the |
413 | | /// produced bit-slice’s length is unspecified. |
414 | | /// |
415 | | /// ## Safety |
416 | | /// |
417 | | /// You must ensure that `slice.len() < BitSlice::MAX_ELTS`. |
418 | | /// |
419 | | /// Calling this function with an over-long slice is **library-level** |
420 | | /// undefined behavior. You may not assume anything about its implementation |
421 | | /// or behavior, and must conservatively assume that over-long slices cause |
422 | | /// compiler UB. |
423 | | #[inline] |
424 | 164k | pub unsafe fn from_slice_unchecked_mut(slice: &mut [T]) -> &mut Self { |
425 | 164k | let bits = slice.len().wrapping_mul(mem::bits_of::<T::Mem>()); |
426 | 164k | BitPtr::from_slice_mut(slice) |
427 | 164k | .span_unchecked(bits) |
428 | 164k | .into_bitslice_mut() |
429 | 164k | } <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::from_slice_unchecked_mut Line | Count | Source | 424 | 164k | pub unsafe fn from_slice_unchecked_mut(slice: &mut [T]) -> &mut Self { | 425 | 164k | let bits = slice.len().wrapping_mul(mem::bits_of::<T::Mem>()); | 426 | 164k | BitPtr::from_slice_mut(slice) | 427 | 164k | .span_unchecked(bits) | 428 | 164k | .into_bitslice_mut() | 429 | 164k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::from_slice_unchecked_mut |
430 | | } |
431 | | |
432 | | /// Alternates of standard APIs. |
433 | | impl<T, O> BitSlice<T, O> |
434 | | where |
435 | | T: BitStore, |
436 | | O: BitOrder, |
437 | | { |
438 | | /// Gets a raw pointer to the zeroth bit of the bit-slice. |
439 | | /// |
440 | | /// ## Original |
441 | | /// |
442 | | /// [`slice::as_ptr`](https://doc.rust-lang.org/std/primitive.slice.html#method.as_ptr) |
443 | | /// |
444 | | /// ## API Differences |
445 | | /// |
446 | | /// This is renamed in order to indicate that it is returning a `bitvec` |
447 | | /// structure, not a raw pointer. |
448 | | #[inline] |
449 | 164k | pub fn as_bitptr(&self) -> BitPtr<Const, T, O> { |
450 | 164k | self.as_bitspan().to_bitptr() |
451 | 164k | } Unexecuted instantiation: <bitvec::slice::BitSlice<u8>>::as_bitptr <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::as_bitptr Line | Count | Source | 449 | 164k | pub fn as_bitptr(&self) -> BitPtr<Const, T, O> { | 450 | 164k | self.as_bitspan().to_bitptr() | 451 | 164k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::as_bitptr |
452 | | |
453 | | /// Gets a raw, write-capable pointer to the zeroth bit of the bit-slice. |
454 | | /// |
455 | | /// ## Original |
456 | | /// |
457 | | /// [`slice::as_mut_ptr`](https://doc.rust-lang.org/std/primitive.slice.html#method.as_mut_ptr) |
458 | | /// |
459 | | /// ## API Differences |
460 | | /// |
461 | | /// This is renamed in order to indicate that it is returning a `bitvec` |
462 | | /// structure, not a raw pointer. |
463 | | #[inline] |
464 | 169k | pub fn as_mut_bitptr(&mut self) -> BitPtr<Mut, T, O> { |
465 | 169k | self.as_mut_bitspan().to_bitptr() |
466 | 169k | } Unexecuted instantiation: <bitvec::slice::BitSlice<bitvec::access::BitSafeU8>>::as_mut_bitptr <bitvec::slice::BitSlice<bitvec::access::BitSafeU8, bitvec::order::Msb0>>::as_mut_bitptr Line | Count | Source | 464 | 124k | pub fn as_mut_bitptr(&mut self) -> BitPtr<Mut, T, O> { | 465 | 124k | self.as_mut_bitspan().to_bitptr() | 466 | 124k | } |
<bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::as_mut_bitptr Line | Count | Source | 464 | 44.2k | pub fn as_mut_bitptr(&mut self) -> BitPtr<Mut, T, O> { | 465 | 44.2k | self.as_mut_bitspan().to_bitptr() | 466 | 44.2k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::as_mut_bitptr |
467 | | |
468 | | /// Views the bit-slice as a half-open range of bit-pointers, to its first |
469 | | /// bit *in* the bit-slice and first bit *beyond* it. |
470 | | /// |
471 | | /// ## Original |
472 | | /// |
473 | | /// [`slice::as_ptr_range`](https://doc.rust-lang.org/std/primitive.slice.html#method.as_ptr_range) |
474 | | /// |
475 | | /// ## API Differences |
476 | | /// |
477 | | /// This is renamed to indicate that it returns a `bitvec` structure, rather |
478 | | /// than an ordinary `Range`. |
479 | | /// |
480 | | /// ## Notes |
481 | | /// |
482 | | /// `BitSlice` does define a [`.as_ptr_range()`], which returns a |
483 | | /// `Range<BitPtr>`. `BitPtrRange` has additional capabilities that |
484 | | /// `Range<*const T>` and `Range<BitPtr>` do not. |
485 | | /// |
486 | | /// [`.as_ptr_range()`]: Self::as_ptr_range |
487 | | #[inline] |
488 | 0 | pub fn as_bitptr_range(&self) -> BitPtrRange<Const, T, O> { |
489 | 0 | self.as_bitspan().to_bitptr_range() |
490 | 0 | } Unexecuted instantiation: <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::as_bitptr_range Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::as_bitptr_range |
491 | | |
492 | | /// Views the bit-slice as a half-open range of write-capable bit-pointers, |
493 | | /// to its first bit *in* the bit-slice and the first bit *beyond* it. |
494 | | /// |
495 | | /// ## Original |
496 | | /// |
497 | | /// [`slice::as_mut_ptr_range`](https://doc.rust-lang.org/std/primitive.slice.html#method.as_mut_ptr_range) |
498 | | /// |
499 | | /// ## API Differences |
500 | | /// |
501 | | /// This is renamed to indicate that it returns a `bitvec` structure, rather |
502 | | /// than an ordinary `Range`. |
503 | | /// |
504 | | /// ## Notes |
505 | | /// |
506 | | /// `BitSlice` does define a [`.as_mut_ptr_range()`], which returns a |
507 | | /// `Range<BitPtr>`. `BitPtrRange` has additional capabilities that |
508 | | /// `Range<*mut T>` and `Range<BitPtr>` do not. |
509 | | #[inline] |
510 | 0 | pub fn as_mut_bitptr_range(&mut self) -> BitPtrRange<Mut, T, O> { |
511 | 0 | self.as_mut_bitspan().to_bitptr_range() |
512 | 0 | } Unexecuted instantiation: <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::as_mut_bitptr_range Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::as_mut_bitptr_range |
513 | | |
514 | | /// Copies the bits from `src` into `self`. |
515 | | /// |
516 | | /// `self` and `src` must have the same length. |
517 | | /// |
518 | | /// ## Performance |
519 | | /// |
520 | | /// If `src` has the same type arguments as `self`, it will use the same |
521 | | /// implementation as [`.copy_from_bitslice()`]; if you know that this will |
522 | | /// always be the case, you should prefer to use that method directly. |
523 | | /// |
524 | | /// Only `.copy_from_bitslice()` is *able* to perform acceleration; this |
525 | | /// method is *always* required to perform a bit-by-bit crawl over both |
526 | | /// bit-slices. |
527 | | /// |
528 | | /// ## Original |
529 | | /// |
530 | | /// [`slice::clone_from_slice`](https://doc.rust-lang.org/std/primitive.slice.html#method.clone_from_slice) |
531 | | /// |
532 | | /// ## API Differences |
533 | | /// |
534 | | /// This is renamed to reflect that it copies from another bit-slice, not |
535 | | /// from an element slice. |
536 | | /// |
537 | | /// In order to support general usage, it allows `src` to have different |
538 | | /// type parameters than `self`, at the cost of performance optimizations. |
539 | | /// |
540 | | /// ## Panics |
541 | | /// |
542 | | /// This panics if the two bit-slices have different lengths. |
543 | | /// |
544 | | /// ## Examples |
545 | | /// |
546 | | /// ```rust |
547 | | /// use bitvec::prelude::*; |
548 | | /// ``` |
549 | | /// |
550 | | /// [`.copy_from_bitslice()`]: Self::copy_from_bitslice |
551 | | #[inline] |
552 | 0 | pub fn clone_from_bitslice<T2, O2>(&mut self, src: &BitSlice<T2, O2>) |
553 | 0 | where |
554 | 0 | T2: BitStore, |
555 | 0 | O2: BitOrder, |
556 | | { |
557 | 0 | assert_eq!( |
558 | 0 | self.len(), |
559 | 0 | src.len(), |
560 | 0 | "cloning between bit-slices requires equal lengths", |
561 | | ); |
562 | | |
563 | 0 | if let Some(that) = src.coerce::<T, O>() { |
564 | 0 | self.copy_from_bitslice(that); |
565 | 0 | } |
566 | | // TODO(myrrlyn): Test if `<T::Mem, O>` matches `<T2::Mem, O>` and |
567 | | // specialize cloning. |
568 | | else { |
569 | 0 | for (to, bit) in self.as_mut_bitptr_range().zip(src.iter().by_vals()) |
570 | | { |
571 | 0 | unsafe { |
572 | 0 | to.write(bit); |
573 | 0 | } |
574 | | } |
575 | | } |
576 | 0 | } |
577 | | |
578 | | /// Copies all bits from `src` into `self`, using batched acceleration when |
579 | | /// possible. |
580 | | /// |
581 | | /// `self` and `src` must have the same length. |
582 | | /// |
583 | | /// ## Original |
584 | | /// |
585 | | /// [`slice::copy_from_slice`](https://doc.rust-lang.org/std/primitive.slice.html#method.copy_from_slice) |
586 | | /// |
587 | | /// ## Panics |
588 | | /// |
589 | | /// This panics if the two bit-slices have different lengths. |
590 | | /// |
591 | | /// ## Examples |
592 | | /// |
593 | | /// ```rust |
594 | | /// use bitvec::prelude::*; |
595 | | /// ``` |
596 | | #[inline] |
597 | 85.9k | pub fn copy_from_bitslice(&mut self, src: &Self) { |
598 | 85.9k | assert_eq!( |
599 | 85.9k | self.len(), |
600 | 85.9k | src.len(), |
601 | 0 | "copying between bit-slices requires equal lengths", |
602 | | ); |
603 | | |
604 | 85.9k | let (to_head, from_head) = |
605 | 85.9k | (self.as_bitspan().head(), src.as_bitspan().head()); |
606 | 85.9k | if to_head == from_head { |
607 | 38.8k | match (self.domain_mut(), src.domain()) { |
608 | 0 | (Domain::Enclave(mut to), Domain::Enclave(from)) => { |
609 | 0 | to.store_value(from.load_value()); |
610 | 0 | }, |
611 | | ( |
612 | | Domain::Region { |
613 | 38.8k | head: to_head, |
614 | 38.8k | body: to_body, |
615 | 38.8k | tail: to_tail, |
616 | | }, |
617 | | Domain::Region { |
618 | 38.8k | head: from_head, |
619 | 38.8k | body: from_body, |
620 | 38.8k | tail: from_tail, |
621 | | }, |
622 | | ) => { |
623 | 38.8k | if let (Some(mut to), Some(from)) = (to_head, from_head) { |
624 | 38.8k | to.store_value(from.load_value()); |
625 | 38.8k | } |
626 | 543k | for (to, from) in to_body.iter_mut().zip(from_body) { |
627 | 543k | to.store_value(from.load_value()); |
628 | 543k | } |
629 | 38.8k | if let (Some(mut to), Some(from)) = (to_tail, from_tail) { |
630 | 0 | to.store_value(from.load_value()); |
631 | 38.8k | } |
632 | | }, |
633 | 0 | _ => unreachable!( |
634 | | "bit-slices with equal type parameters, lengths, and heads \ |
635 | | will always have equal domains" |
636 | | ), |
637 | | } |
638 | 47.0k | } |
639 | 0 | if let (Some(this), Some(that)) = |
640 | 85.9k | (self.coerce_mut::<T, Lsb0>(), src.coerce::<T, Lsb0>()) |
641 | | { |
642 | 0 | return this.sp_copy_from_bitslice(that); |
643 | 85.9k | } |
644 | 85.9k | if let (Some(this), Some(that)) = |
645 | 85.9k | (self.coerce_mut::<T, Msb0>(), src.coerce::<T, Msb0>()) |
646 | | { |
647 | 85.9k | return this.sp_copy_from_bitslice(that); |
648 | 0 | } |
649 | 0 | for (to, bit) in self.as_mut_bitptr_range().zip(src.iter().by_vals()) { |
650 | 0 | unsafe { |
651 | 0 | to.write(bit); |
652 | 0 | } |
653 | | } |
654 | 85.9k | } <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::copy_from_bitslice Line | Count | Source | 597 | 85.9k | pub fn copy_from_bitslice(&mut self, src: &Self) { | 598 | 85.9k | assert_eq!( | 599 | 85.9k | self.len(), | 600 | 85.9k | src.len(), | 601 | 0 | "copying between bit-slices requires equal lengths", | 602 | | ); | 603 | | | 604 | 85.9k | let (to_head, from_head) = | 605 | 85.9k | (self.as_bitspan().head(), src.as_bitspan().head()); | 606 | 85.9k | if to_head == from_head { | 607 | 38.8k | match (self.domain_mut(), src.domain()) { | 608 | 0 | (Domain::Enclave(mut to), Domain::Enclave(from)) => { | 609 | 0 | to.store_value(from.load_value()); | 610 | 0 | }, | 611 | | ( | 612 | | Domain::Region { | 613 | 38.8k | head: to_head, | 614 | 38.8k | body: to_body, | 615 | 38.8k | tail: to_tail, | 616 | | }, | 617 | | Domain::Region { | 618 | 38.8k | head: from_head, | 619 | 38.8k | body: from_body, | 620 | 38.8k | tail: from_tail, | 621 | | }, | 622 | | ) => { | 623 | 38.8k | if let (Some(mut to), Some(from)) = (to_head, from_head) { | 624 | 38.8k | to.store_value(from.load_value()); | 625 | 38.8k | } | 626 | 543k | for (to, from) in to_body.iter_mut().zip(from_body) { | 627 | 543k | to.store_value(from.load_value()); | 628 | 543k | } | 629 | 38.8k | if let (Some(mut to), Some(from)) = (to_tail, from_tail) { | 630 | 0 | to.store_value(from.load_value()); | 631 | 38.8k | } | 632 | | }, | 633 | 0 | _ => unreachable!( | 634 | | "bit-slices with equal type parameters, lengths, and heads \ | 635 | | will always have equal domains" | 636 | | ), | 637 | | } | 638 | 47.0k | } | 639 | 0 | if let (Some(this), Some(that)) = | 640 | 85.9k | (self.coerce_mut::<T, Lsb0>(), src.coerce::<T, Lsb0>()) | 641 | | { | 642 | 0 | return this.sp_copy_from_bitslice(that); | 643 | 85.9k | } | 644 | 85.9k | if let (Some(this), Some(that)) = | 645 | 85.9k | (self.coerce_mut::<T, Msb0>(), src.coerce::<T, Msb0>()) | 646 | | { | 647 | 85.9k | return this.sp_copy_from_bitslice(that); | 648 | 0 | } | 649 | 0 | for (to, bit) in self.as_mut_bitptr_range().zip(src.iter().by_vals()) { | 650 | 0 | unsafe { | 651 | 0 | to.write(bit); | 652 | 0 | } | 653 | | } | 654 | 85.9k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::copy_from_bitslice |
655 | | |
656 | | /// Swaps the contents of two bit-slices. |
657 | | /// |
658 | | /// `self` and `other` must have the same length. |
659 | | /// |
660 | | /// ## Original |
661 | | /// |
662 | | /// [`slice::swap_with_slice`](https://doc.rust-lang.org/std/primitive.slice.html#method.swap_with_slice) |
663 | | /// |
664 | | /// ## API Differences |
665 | | /// |
666 | | /// This method is renamed, as it takes a bit-slice rather than an element |
667 | | /// slice. |
668 | | /// |
669 | | /// ## Panics |
670 | | /// |
671 | | /// This panics if the two bit-slices have different lengths. |
672 | | /// |
673 | | /// ## Examples |
674 | | /// |
675 | | /// ```rust |
676 | | /// use bitvec::prelude::*; |
677 | | /// |
678 | | /// let mut one = [0xA5u8, 0x69]; |
679 | | /// let mut two = 0x1234u16; |
680 | | /// let one_bits = one.view_bits_mut::<Msb0>(); |
681 | | /// let two_bits = two.view_bits_mut::<Lsb0>(); |
682 | | /// |
683 | | /// one_bits.swap_with_bitslice(two_bits); |
684 | | /// |
685 | | /// assert_eq!(one, [0x2C, 0x48]); |
686 | | /// # if cfg!(target_endian = "little") { |
687 | | /// assert_eq!(two, 0x96A5); |
688 | | /// # } |
689 | | /// ``` |
690 | | #[inline] |
691 | 0 | pub fn swap_with_bitslice<T2, O2>(&mut self, other: &mut BitSlice<T2, O2>) |
692 | 0 | where |
693 | 0 | T2: BitStore, |
694 | 0 | O2: BitOrder, |
695 | | { |
696 | 0 | assert_eq!( |
697 | 0 | self.len(), |
698 | 0 | other.len(), |
699 | 0 | "swapping between bit-slices requires equal lengths", |
700 | | ); |
701 | | |
702 | 0 | if let (Some(this), Some(that)) = |
703 | 0 | (self.coerce_mut::<T, Lsb0>(), other.coerce_mut::<T, Lsb0>()) |
704 | | { |
705 | 0 | return this.sp_swap_with_bitslice(that); |
706 | 0 | } |
707 | 0 | if let (Some(this), Some(that)) = |
708 | 0 | (self.coerce_mut::<T, Msb0>(), other.coerce_mut::<T, Msb0>()) |
709 | | { |
710 | 0 | return this.sp_swap_with_bitslice(that); |
711 | 0 | } |
712 | 0 | self.as_mut_bitptr_range() |
713 | 0 | .zip(other.as_mut_bitptr_range()) |
714 | 0 | .for_each(|(a, b)| unsafe { |
715 | 0 | bv_ptr::swap(a, b); |
716 | 0 | }); |
717 | 0 | } |
718 | | } |
719 | | |
720 | | /// Extensions of standard APIs. |
721 | | impl<T, O> BitSlice<T, O> |
722 | | where |
723 | | T: BitStore, |
724 | | O: BitOrder, |
725 | | { |
726 | | /// Writes a new value into a single bit. |
727 | | /// |
728 | | /// This is the replacement for `*slice[index] = value;`, as `bitvec` is not |
729 | | /// able to express that under the current `IndexMut` API signature. |
730 | | /// |
731 | | /// ## Parameters |
732 | | /// |
733 | | /// - `&mut self` |
734 | | /// - `index`: The bit-index to set. It must be in `0 .. self.len()`. |
735 | | /// - `value`: The new bit-value to write into the bit at `index`. |
736 | | /// |
737 | | /// ## Panics |
738 | | /// |
739 | | /// This panics if `index` is out of bounds. |
740 | | /// |
741 | | /// ## Examples |
742 | | /// |
743 | | /// ```rust |
744 | | /// use bitvec::prelude::*; |
745 | | /// |
746 | | /// let bits = bits![mut 0, 1]; |
747 | | /// bits.set(0, true); |
748 | | /// bits.set(1, false); |
749 | | /// |
750 | | /// assert_eq!(bits, bits![1, 0]); |
751 | | /// ``` |
752 | | #[inline] |
753 | 44.2k | pub fn set(&mut self, index: usize, value: bool) { |
754 | 44.2k | self.replace(index, value); |
755 | 44.2k | } <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::set Line | Count | Source | 753 | 44.2k | pub fn set(&mut self, index: usize, value: bool) { | 754 | 44.2k | self.replace(index, value); | 755 | 44.2k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::set |
756 | | |
757 | | /// Writes a new value into a single bit, without bounds checking. |
758 | | /// |
759 | | /// ## Parameters |
760 | | /// |
761 | | /// - `&mut self` |
762 | | /// - `index`: The bit-index to set. It must be in `0 .. self.len()`. |
763 | | /// - `value`: The new bit-value to write into the bit at `index`. |
764 | | /// |
765 | | /// ## Safety |
766 | | /// |
767 | | /// You must ensure that `index` is in the range `0 .. self.len()`. |
768 | | /// |
769 | | /// This performs bit-pointer offset arithmetic without doing any bounds |
770 | | /// checks. If `index` is out of bounds, then this will issue an |
771 | | /// out-of-bounds access and will trigger memory unsafety. |
772 | | /// |
773 | | /// ## Examples |
774 | | /// |
775 | | /// ```rust |
776 | | /// use bitvec::prelude::*; |
777 | | /// |
778 | | /// let mut data = 0u8; |
779 | | /// let bits = &mut data.view_bits_mut::<Lsb0>()[.. 2]; |
780 | | /// assert_eq!(bits.len(), 2); |
781 | | /// unsafe { |
782 | | /// bits.set_unchecked(3, true); |
783 | | /// } |
784 | | /// assert_eq!(data, 8); |
785 | | /// ``` |
786 | | #[inline] |
787 | 0 | pub unsafe fn set_unchecked(&mut self, index: usize, value: bool) { |
788 | 0 | self.replace_unchecked(index, value); |
789 | 0 | } |
790 | | |
791 | | /// Writes a new value into a bit, and returns its previous value. |
792 | | /// |
793 | | /// ## Panics |
794 | | /// |
795 | | /// This panics if `index` is not less than `self.len()`. |
796 | | /// |
797 | | /// ## Examples |
798 | | /// |
799 | | /// ```rust |
800 | | /// use bitvec::prelude::*; |
801 | | /// |
802 | | /// let bits = bits![mut 0]; |
803 | | /// assert!(!bits.replace(0, true)); |
804 | | /// assert!(bits[0]); |
805 | | /// ``` |
806 | | #[inline] |
807 | 44.2k | pub fn replace(&mut self, index: usize, value: bool) -> bool { |
808 | 44.2k | self.assert_in_bounds(index, 0 .. self.len()); |
809 | 44.2k | unsafe { self.replace_unchecked(index, value) } |
810 | 44.2k | } <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::replace Line | Count | Source | 807 | 44.2k | pub fn replace(&mut self, index: usize, value: bool) -> bool { | 808 | 44.2k | self.assert_in_bounds(index, 0 .. self.len()); | 809 | 44.2k | unsafe { self.replace_unchecked(index, value) } | 810 | 44.2k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::replace |
811 | | |
812 | | /// Writes a new value into a bit, returning the previous value, without |
813 | | /// bounds checking. |
814 | | /// |
815 | | /// ## Safety |
816 | | /// |
817 | | /// `index` must be less than `self.len()`. |
818 | | /// |
819 | | /// ## Examples |
820 | | /// |
821 | | /// ```rust |
822 | | /// use bitvec::prelude::*; |
823 | | /// |
824 | | /// let bits = bits![mut 0, 0]; |
825 | | /// let old = unsafe { |
826 | | /// let a = &mut bits[.. 1]; |
827 | | /// a.replace_unchecked(1, true) |
828 | | /// }; |
829 | | /// assert!(!old); |
830 | | /// assert!(bits[1]); |
831 | | /// ``` |
832 | | #[inline] |
833 | 44.2k | pub unsafe fn replace_unchecked( |
834 | 44.2k | &mut self, |
835 | 44.2k | index: usize, |
836 | 44.2k | value: bool, |
837 | 44.2k | ) -> bool { |
838 | 44.2k | self.as_mut_bitptr().add(index).replace(value) |
839 | 44.2k | } <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::replace_unchecked Line | Count | Source | 833 | 44.2k | pub unsafe fn replace_unchecked( | 834 | 44.2k | &mut self, | 835 | 44.2k | index: usize, | 836 | 44.2k | value: bool, | 837 | 44.2k | ) -> bool { | 838 | 44.2k | self.as_mut_bitptr().add(index).replace(value) | 839 | 44.2k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::replace_unchecked |
840 | | |
841 | | /// Swaps two bits in a bit-slice, without bounds checking. |
842 | | /// |
843 | | /// See [`.swap()`] for documentation. |
844 | | /// |
845 | | /// ## Safety |
846 | | /// |
847 | | /// You must ensure that `a` and `b` are both in the range `0 .. |
848 | | /// self.len()`. |
849 | | /// |
850 | | /// This method performs bit-pointer offset arithmetic without doing any |
851 | | /// bounds checks. If `a` or `b` are out of bounds, then this will issue an |
852 | | /// out-of-bounds access and will trigger memory unsafety. |
853 | | /// |
854 | | /// [`.swap()`]: Self::swap |
855 | | #[inline] |
856 | 0 | pub unsafe fn swap_unchecked(&mut self, a: usize, b: usize) { |
857 | 0 | let a = self.as_mut_bitptr().add(a); |
858 | 0 | let b = self.as_mut_bitptr().add(b); |
859 | 0 | bv_ptr::swap(a, b); |
860 | 0 | } |
861 | | |
862 | | /// Splits a bit-slice at an index, without bounds checking. |
863 | | /// |
864 | | /// See [`.split_at()`] for documentation. |
865 | | /// |
866 | | /// ## Safety |
867 | | /// |
868 | | /// You must ensure that `mid` is in the range `0 ..= self.len()`. |
869 | | /// |
870 | | /// This method produces new bit-slice references. If `mid` is out of |
871 | | /// bounds, its behavior is **library-level** undefined. You must |
872 | | /// conservatively assume that an out-of-bounds split point produces |
873 | | /// compiler-level UB. |
874 | | /// |
875 | | /// [`.split_at()`]: Self::split_at |
876 | | #[inline] |
877 | 124k | pub unsafe fn split_at_unchecked(&self, mid: usize) -> (&Self, &Self) { |
878 | 124k | let len = self.len(); |
879 | 124k | let left = self.as_bitptr(); |
880 | 124k | let right = left.add(mid); |
881 | 124k | let left = left.span_unchecked(mid); |
882 | 124k | let right = right.span_unchecked(len - mid); |
883 | 124k | let left = left.into_bitslice_ref(); |
884 | 124k | let right = right.into_bitslice_ref(); |
885 | 124k | (left, right) |
886 | 124k | } Unexecuted instantiation: <bitvec::slice::BitSlice<u8>>::split_at_unchecked <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::split_at_unchecked Line | Count | Source | 877 | 124k | pub unsafe fn split_at_unchecked(&self, mid: usize) -> (&Self, &Self) { | 878 | 124k | let len = self.len(); | 879 | 124k | let left = self.as_bitptr(); | 880 | 124k | let right = left.add(mid); | 881 | 124k | let left = left.span_unchecked(mid); | 882 | 124k | let right = right.span_unchecked(len - mid); | 883 | 124k | let left = left.into_bitslice_ref(); | 884 | 124k | let right = right.into_bitslice_ref(); | 885 | 124k | (left, right) | 886 | 124k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::split_at_unchecked |
887 | | |
888 | | /// Splits a mutable bit-slice at an index, without bounds checking. |
889 | | /// |
890 | | /// See [`.split_at_mut()`] for documentation. |
891 | | /// |
892 | | /// ## Safety |
893 | | /// |
894 | | /// You must ensure that `mid` is in the range `0 ..= self.len()`. |
895 | | /// |
896 | | /// This method produces new bit-slice references. If `mid` is out of |
897 | | /// bounds, its behavior is **library-level** undefined. You must |
898 | | /// conservatively assume that an out-of-bounds split point produces |
899 | | /// compiler-level UB. |
900 | | /// |
901 | | /// [`.split_at_mut()`]: Self::split_at_mut |
902 | | #[inline] |
903 | 124k | pub unsafe fn split_at_unchecked_mut( |
904 | 124k | &mut self, |
905 | 124k | mid: usize, |
906 | 124k | ) -> (&mut BitSlice<T::Alias, O>, &mut BitSlice<T::Alias, O>) { |
907 | 124k | let len = self.len(); |
908 | 124k | let left = self.alias_mut().as_mut_bitptr(); |
909 | 124k | let right = left.add(mid); |
910 | 124k | ( |
911 | 124k | left.span_unchecked(mid).into_bitslice_mut(), |
912 | 124k | right.span_unchecked(len - mid).into_bitslice_mut(), |
913 | 124k | ) |
914 | 124k | } Unexecuted instantiation: <bitvec::slice::BitSlice<bitvec::access::BitSafeU8>>::split_at_unchecked_mut <bitvec::slice::BitSlice<bitvec::access::BitSafeU8, bitvec::order::Msb0>>::split_at_unchecked_mut Line | Count | Source | 903 | 124k | pub unsafe fn split_at_unchecked_mut( | 904 | 124k | &mut self, | 905 | 124k | mid: usize, | 906 | 124k | ) -> (&mut BitSlice<T::Alias, O>, &mut BitSlice<T::Alias, O>) { | 907 | 124k | let len = self.len(); | 908 | 124k | let left = self.alias_mut().as_mut_bitptr(); | 909 | 124k | let right = left.add(mid); | 910 | 124k | ( | 911 | 124k | left.span_unchecked(mid).into_bitslice_mut(), | 912 | 124k | right.span_unchecked(len - mid).into_bitslice_mut(), | 913 | 124k | ) | 914 | 124k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::split_at_unchecked_mut |
915 | | |
916 | | /// Copies bits from one region of the bit-slice to another region of |
917 | | /// itself, without doing bounds checks. |
918 | | /// |
919 | | /// The regions are allowed to overlap. |
920 | | /// |
921 | | /// ## Parameters |
922 | | /// |
923 | | /// - `&mut self` |
924 | | /// - `src`: The range within `self` from which to copy. |
925 | | /// - `dst`: The starting index within `self` at which to paste. |
926 | | /// |
927 | | /// ## Effects |
928 | | /// |
929 | | /// `self[src]` is copied to `self[dest .. dest + src.len()]`. The bits of |
930 | | /// `self[src]` are in an unspecified, but initialized, state. |
931 | | /// |
932 | | /// ## Safety |
933 | | /// |
934 | | /// `src.end()` and `dest + src.len()` must be entirely within bounds. |
935 | | /// |
936 | | /// ## Examples |
937 | | /// |
938 | | /// ```rust |
939 | | /// use bitvec::prelude::*; |
940 | | /// |
941 | | /// let mut data = 0b1011_0000u8; |
942 | | /// let bits = data.view_bits_mut::<Msb0>(); |
943 | | /// |
944 | | /// unsafe { |
945 | | /// bits.copy_within_unchecked(.. 4, 2); |
946 | | /// } |
947 | | /// assert_eq!(data, 0b1010_1100); |
948 | | /// ``` |
949 | | #[inline] |
950 | 0 | pub unsafe fn copy_within_unchecked<R>(&mut self, src: R, dest: usize) |
951 | 0 | where R: RangeExt<usize> { |
952 | 0 | if let Some(this) = self.coerce_mut::<T, Lsb0>() { |
953 | 0 | return this.sp_copy_within_unchecked(src, dest); |
954 | 0 | } |
955 | 0 | if let Some(this) = self.coerce_mut::<T, Msb0>() { |
956 | 0 | return this.sp_copy_within_unchecked(src, dest); |
957 | 0 | } |
958 | 0 | let source = src.normalize(0, self.len()); |
959 | 0 | let source_len = source.len(); |
960 | 0 | let rev = source.contains(&dest); |
961 | 0 | let dest = dest .. dest + source_len; |
962 | 0 | for (from, to) in self |
963 | 0 | .get_unchecked(source) |
964 | 0 | .as_bitptr_range() |
965 | 0 | .zip(self.get_unchecked_mut(dest).as_mut_bitptr_range()) |
966 | 0 | .bidi(rev) |
967 | 0 | { |
968 | 0 | to.write(from.read()); |
969 | 0 | } |
970 | 0 | } |
971 | | |
972 | | #[inline] |
973 | | #[doc(hidden)] |
974 | | #[cfg(not(tarpaulin_include))] |
975 | | #[deprecated = "use `.iter_mut().enumerate()`"] |
976 | 0 | pub fn for_each(&mut self, mut func: impl FnMut(usize, bool) -> bool) { |
977 | 0 | for (idx, ptr) in self.as_mut_bitptr_range().enumerate() { |
978 | 0 | unsafe { |
979 | 0 | ptr.write(func(idx, ptr.read())); |
980 | 0 | } |
981 | | } |
982 | 0 | } |
983 | | } |
984 | | |
985 | | /// Views of underlying memory. |
986 | | impl<T, O> BitSlice<T, O> |
987 | | where |
988 | | T: BitStore, |
989 | | O: BitOrder, |
990 | | { |
991 | | /// Partitions a bit-slice into maybe-contended and known-uncontended parts. |
992 | | /// |
993 | | /// The documentation of `BitDomain` goes into this in more detail. In |
994 | | /// short, this produces a `&BitSlice` that is as large as possible without |
995 | | /// requiring alias protection, as well as any bits that were not able to be |
996 | | /// included in the unaliased bit-slice. |
997 | | #[inline] |
998 | | #[cfg(not(tarpaulin_include))] |
999 | 0 | pub fn bit_domain(&self) -> BitDomain<Const, T, O> { |
1000 | 0 | self.domain().into_bit_domain() |
1001 | 0 | } |
1002 | | |
1003 | | /// Partitions a mutable bit-slice into maybe-contended and |
1004 | | /// known-uncontended parts. |
1005 | | /// |
1006 | | /// The documentation of `BitDomain` goes into this in more detail. In |
1007 | | /// short, this produces a `&mut BitSlice` that is as large as possible |
1008 | | /// without requiring alias protection, as well as any bits that were not |
1009 | | /// able to be included in the unaliased bit-slice. |
1010 | | #[inline] |
1011 | | #[cfg(not(tarpaulin_include))] |
1012 | 0 | pub fn bit_domain_mut(&mut self) -> BitDomain<Mut, T, O> { |
1013 | 0 | self.domain_mut().into_bit_domain() |
1014 | 0 | } |
1015 | | |
1016 | | /// Views the underlying memory of a bit-slice, removing alias protections |
1017 | | /// where possible. |
1018 | | /// |
1019 | | /// The documentation of `Domain` goes into this in more detail. In short, |
1020 | | /// this produces a `&[T]` slice with alias protections removed, covering |
1021 | | /// all elements that `self` completely fills. Partially-used elements on |
1022 | | /// either the front or back edge of the slice are returned separately. |
1023 | | #[inline] |
1024 | | #[cfg(not(tarpaulin_include))] |
1025 | 222k | pub fn domain(&self) -> Domain<Const, T, O> { |
1026 | 222k | Domain::new(self) |
1027 | 222k | } Unexecuted instantiation: <bitvec::slice::BitSlice<u8>>::domain <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::domain Line | Count | Source | 1025 | 222k | pub fn domain(&self) -> Domain<Const, T, O> { | 1026 | 222k | Domain::new(self) | 1027 | 222k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::domain |
1028 | | |
1029 | | /// Views the underlying memory of a bit-slice, removing alias protections |
1030 | | /// where possible. |
1031 | | /// |
1032 | | /// The documentation of `Domain` goes into this in more detail. In short, |
1033 | | /// this produces a `&mut [T]` slice with alias protections removed, |
1034 | | /// covering all elements that `self` completely fills. Partially-used |
1035 | | /// elements on the front or back edge of the slice are returned separately. |
1036 | | #[inline] |
1037 | | #[cfg(not(tarpaulin_include))] |
1038 | 281k | pub fn domain_mut(&mut self) -> Domain<Mut, T, O> { |
1039 | 281k | Domain::new(self) |
1040 | 281k | } Unexecuted instantiation: <bitvec::slice::BitSlice<u8>>::domain_mut <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::domain_mut Line | Count | Source | 1038 | 281k | pub fn domain_mut(&mut self) -> Domain<Mut, T, O> { | 1039 | 281k | Domain::new(self) | 1040 | 281k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::domain_mut |
1041 | | } |
1042 | | |
1043 | | /// Bit-value queries. |
1044 | | impl<T, O> BitSlice<T, O> |
1045 | | where |
1046 | | T: BitStore, |
1047 | | O: BitOrder, |
1048 | | { |
1049 | | /// Counts the number of bits set to `1` in the bit-slice contents. |
1050 | | /// |
1051 | | /// ## Examples |
1052 | | /// |
1053 | | /// ```rust |
1054 | | /// use bitvec::prelude::*; |
1055 | | /// |
1056 | | /// let bits = bits![1, 1, 0, 0]; |
1057 | | /// assert_eq!(bits[.. 2].count_ones(), 2); |
1058 | | /// assert_eq!(bits[2 ..].count_ones(), 0); |
1059 | | /// assert_eq!(bits![].count_ones(), 0); |
1060 | | /// ``` |
1061 | | #[inline] |
1062 | 0 | pub fn count_ones(&self) -> usize { |
1063 | 0 | match self.domain() { |
1064 | 0 | Domain::Enclave(elem) => elem.load_value().count_ones() as usize, |
1065 | 0 | Domain::Region { head, body, tail } => { |
1066 | 0 | head.map_or(0, |elem| elem.load_value().count_ones() as usize) |
1067 | 0 | + body |
1068 | 0 | .iter() |
1069 | 0 | .map(BitStore::load_value) |
1070 | 0 | .map(|elem| elem.count_ones() as usize) |
1071 | 0 | .sum::<usize>() + tail |
1072 | 0 | .map_or(0, |elem| elem.load_value().count_ones() as usize) |
1073 | | }, |
1074 | | } |
1075 | 0 | } |
1076 | | |
1077 | | /// Counts the number of bits cleared to `0` in the bit-slice contents. |
1078 | | /// |
1079 | | /// ## Examples |
1080 | | /// |
1081 | | /// ```rust |
1082 | | /// use bitvec::prelude::*; |
1083 | | /// |
1084 | | /// let bits = bits![1, 1, 0, 0]; |
1085 | | /// assert_eq!(bits[.. 2].count_zeros(), 0); |
1086 | | /// assert_eq!(bits[2 ..].count_zeros(), 2); |
1087 | | /// assert_eq!(bits![].count_zeros(), 0); |
1088 | | /// ``` |
1089 | | #[inline] |
1090 | 5.70k | pub fn count_zeros(&self) -> usize { |
1091 | 5.70k | match self.domain() { |
1092 | 5.70k | Domain::Enclave(elem) => (elem.load_value() |
1093 | 5.70k | | !elem.mask().into_inner()) |
1094 | 5.70k | .count_zeros() as usize, |
1095 | 0 | Domain::Region { head, body, tail } => { |
1096 | 0 | head.map_or(0, |elem| { |
1097 | 0 | (elem.load_value() | !elem.mask().into_inner()).count_zeros() |
1098 | 0 | as usize |
1099 | 0 | }) + body Unexecuted instantiation: <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::count_zeros::{closure#0}Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::count_zeros::{closure#0} |
1100 | 0 | .iter() |
1101 | 0 | .map(BitStore::load_value) |
1102 | 0 | .map(|elem| elem.count_zeros() as usize) Unexecuted instantiation: <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::count_zeros::{closure#1}Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::count_zeros::{closure#1} |
1103 | 0 | .sum::<usize>() + tail.map_or(0, |elem| { |
1104 | 0 | (elem.load_value() | !elem.mask().into_inner()).count_zeros() |
1105 | 0 | as usize |
1106 | 0 | }) Unexecuted instantiation: <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::count_zeros::{closure#2}Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::count_zeros::{closure#2} |
1107 | | }, |
1108 | | } |
1109 | 5.70k | } <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::count_zeros Line | Count | Source | 1090 | 5.70k | pub fn count_zeros(&self) -> usize { | 1091 | 5.70k | match self.domain() { | 1092 | 5.70k | Domain::Enclave(elem) => (elem.load_value() | 1093 | 5.70k | | !elem.mask().into_inner()) | 1094 | 5.70k | .count_zeros() as usize, | 1095 | 0 | Domain::Region { head, body, tail } => { | 1096 | 0 | head.map_or(0, |elem| { | 1097 | | (elem.load_value() | !elem.mask().into_inner()).count_zeros() | 1098 | | as usize | 1099 | 0 | }) + body | 1100 | 0 | .iter() | 1101 | 0 | .map(BitStore::load_value) | 1102 | 0 | .map(|elem| elem.count_zeros() as usize) | 1103 | 0 | .sum::<usize>() + tail.map_or(0, |elem| { | 1104 | | (elem.load_value() | !elem.mask().into_inner()).count_zeros() | 1105 | | as usize | 1106 | | }) | 1107 | | }, | 1108 | | } | 1109 | 5.70k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::count_zeros |
1110 | | |
1111 | | /// Enumerates the index of each bit in a bit-slice set to `1`. |
1112 | | /// |
1113 | | /// This is a shorthand for a `.enumerate().filter_map()` iterator that |
1114 | | /// selects the index of each `true` bit; however, its implementation is |
1115 | | /// eligible for optimizations that the individual-bit iterator is not. |
1116 | | /// |
1117 | | /// Specializations for the `Lsb0` and `Msb0` orderings allow processors |
1118 | | /// with instructions that seek particular bits within an element to operate |
1119 | | /// on whole elements, rather than on each bit individually. |
1120 | | /// |
1121 | | /// ## Examples |
1122 | | /// |
1123 | | /// This example uses `.iter_ones()`, a `.filter_map()` that finds the index |
1124 | | /// of each set bit, and the known indices, in order to show that they have |
1125 | | /// equivalent behavior. |
1126 | | /// |
1127 | | /// ```rust |
1128 | | /// use bitvec::prelude::*; |
1129 | | /// |
1130 | | /// let bits = bits![0, 1, 0, 0, 1, 0, 0, 0, 1]; |
1131 | | /// |
1132 | | /// let iter_ones = bits.iter_ones(); |
1133 | | /// let known_indices = [1, 4, 8].iter().copied(); |
1134 | | /// let filter = bits.iter() |
1135 | | /// .by_vals() |
1136 | | /// .enumerate() |
1137 | | /// .filter_map(|(idx, bit)| if bit { Some(idx) } else { None }); |
1138 | | /// let all = iter_ones.zip(known_indices).zip(filter); |
1139 | | /// |
1140 | | /// for ((iter_one, known), filtered) in all { |
1141 | | /// assert_eq!(iter_one, known); |
1142 | | /// assert_eq!(known, filtered); |
1143 | | /// } |
1144 | | /// ``` |
1145 | | #[inline] |
1146 | 0 | pub fn iter_ones(&self) -> IterOnes<T, O> { |
1147 | 0 | IterOnes::new(self) |
1148 | 0 | } |
1149 | | |
1150 | | /// Enumerates the index of each bit in a bit-slice cleared to `0`. |
1151 | | /// |
1152 | | /// This is a shorthand for a `.enumerate().filter_map()` iterator that |
1153 | | /// selects the index of each `false` bit; however, its implementation is |
1154 | | /// eligible for optimizations that the individual-bit iterator is not. |
1155 | | /// |
1156 | | /// Specializations for the `Lsb0` and `Msb0` orderings allow processors |
1157 | | /// with instructions that seek particular bits within an element to operate |
1158 | | /// on whole elements, rather than on each bit individually. |
1159 | | /// |
1160 | | /// ## Examples |
1161 | | /// |
1162 | | /// This example uses `.iter_zeros()`, a `.filter_map()` that finds the |
1163 | | /// index of each cleared bit, and the known indices, in order to show that |
1164 | | /// they have equivalent behavior. |
1165 | | /// |
1166 | | /// ```rust |
1167 | | /// use bitvec::prelude::*; |
1168 | | /// |
1169 | | /// let bits = bits![1, 0, 1, 1, 0, 1, 1, 1, 0]; |
1170 | | /// |
1171 | | /// let iter_zeros = bits.iter_zeros(); |
1172 | | /// let known_indices = [1, 4, 8].iter().copied(); |
1173 | | /// let filter = bits.iter() |
1174 | | /// .by_vals() |
1175 | | /// .enumerate() |
1176 | | /// .filter_map(|(idx, bit)| if !bit { Some(idx) } else { None }); |
1177 | | /// let all = iter_zeros.zip(known_indices).zip(filter); |
1178 | | /// |
1179 | | /// for ((iter_zero, known), filtered) in all { |
1180 | | /// assert_eq!(iter_zero, known); |
1181 | | /// assert_eq!(known, filtered); |
1182 | | /// } |
1183 | | /// ``` |
1184 | | #[inline] |
1185 | 0 | pub fn iter_zeros(&self) -> IterZeros<T, O> { |
1186 | 0 | IterZeros::new(self) |
1187 | 0 | } |
1188 | | |
1189 | | /// Finds the index of the first bit in the bit-slice set to `1`. |
1190 | | /// |
1191 | | /// Returns `None` if there is no `true` bit in the bit-slice. |
1192 | | /// |
1193 | | /// ## Examples |
1194 | | /// |
1195 | | /// ```rust |
1196 | | /// use bitvec::prelude::*; |
1197 | | /// |
1198 | | /// assert!(bits![].first_one().is_none()); |
1199 | | /// assert!(bits![0].first_one().is_none()); |
1200 | | /// assert_eq!(bits![0, 1].first_one(), Some(1)); |
1201 | | /// ``` |
1202 | | #[inline] |
1203 | 0 | pub fn first_one(&self) -> Option<usize> { |
1204 | 0 | self.iter_ones().next() |
1205 | 0 | } |
1206 | | |
1207 | | /// Finds the index of the first bit in the bit-slice cleared to `0`. |
1208 | | /// |
1209 | | /// Returns `None` if there is no `false` bit in the bit-slice. |
1210 | | /// |
1211 | | /// ## Examples |
1212 | | /// |
1213 | | /// ```rust |
1214 | | /// use bitvec::prelude::*; |
1215 | | /// |
1216 | | /// assert!(bits![].first_zero().is_none()); |
1217 | | /// assert!(bits![1].first_zero().is_none()); |
1218 | | /// assert_eq!(bits![1, 0].first_zero(), Some(1)); |
1219 | | /// ``` |
1220 | | #[inline] |
1221 | 0 | pub fn first_zero(&self) -> Option<usize> { |
1222 | 0 | self.iter_zeros().next() |
1223 | 0 | } |
1224 | | |
1225 | | /// Finds the index of the last bit in the bit-slice set to `1`. |
1226 | | /// |
1227 | | /// Returns `None` if there is no `true` bit in the bit-slice. |
1228 | | /// |
1229 | | /// ## Examples |
1230 | | /// |
1231 | | /// ```rust |
1232 | | /// use bitvec::prelude::*; |
1233 | | /// |
1234 | | /// assert!(bits![].last_one().is_none()); |
1235 | | /// assert!(bits![0].last_one().is_none()); |
1236 | | /// assert_eq!(bits![1, 0].last_one(), Some(0)); |
1237 | | /// ``` |
1238 | | #[inline] |
1239 | 0 | pub fn last_one(&self) -> Option<usize> { |
1240 | 0 | self.iter_ones().next_back() |
1241 | 0 | } |
1242 | | |
1243 | | /// Finds the index of the last bit in the bit-slice cleared to `0`. |
1244 | | /// |
1245 | | /// Returns `None` if there is no `false` bit in the bit-slice. |
1246 | | /// |
1247 | | /// ## Examples |
1248 | | /// |
1249 | | /// ```rust |
1250 | | /// use bitvec::prelude::*; |
1251 | | /// |
1252 | | /// assert!(bits![].last_zero().is_none()); |
1253 | | /// assert!(bits![1].last_zero().is_none()); |
1254 | | /// assert_eq!(bits![0, 1].last_zero(), Some(0)); |
1255 | | /// ``` |
1256 | | #[inline] |
1257 | 0 | pub fn last_zero(&self) -> Option<usize> { |
1258 | 0 | self.iter_zeros().next_back() |
1259 | 0 | } |
1260 | | |
1261 | | /// Counts the number of bits from the start of the bit-slice to the first |
1262 | | /// bit set to `0`. |
1263 | | /// |
1264 | | /// This returns `0` if the bit-slice is empty. |
1265 | | /// |
1266 | | /// ## Examples |
1267 | | /// |
1268 | | /// ```rust |
1269 | | /// use bitvec::prelude::*; |
1270 | | /// |
1271 | | /// assert_eq!(bits![].leading_ones(), 0); |
1272 | | /// assert_eq!(bits![0].leading_ones(), 0); |
1273 | | /// assert_eq!(bits![1, 0].leading_ones(), 1); |
1274 | | /// ``` |
1275 | | #[inline] |
1276 | 0 | pub fn leading_ones(&self) -> usize { |
1277 | 0 | self.first_zero().unwrap_or_else(|| self.len()) |
1278 | 0 | } |
1279 | | |
1280 | | /// Counts the number of bits from the start of the bit-slice to the first |
1281 | | /// bit set to `1`. |
1282 | | /// |
1283 | | /// This returns `0` if the bit-slice is empty. |
1284 | | /// |
1285 | | /// ## Examples |
1286 | | /// |
1287 | | /// ```rust |
1288 | | /// use bitvec::prelude::*; |
1289 | | /// |
1290 | | /// assert_eq!(bits![].leading_zeros(), 0); |
1291 | | /// assert_eq!(bits![1].leading_zeros(), 0); |
1292 | | /// assert_eq!(bits![0, 1].leading_zeros(), 1); |
1293 | | /// ``` |
1294 | | #[inline] |
1295 | 0 | pub fn leading_zeros(&self) -> usize { |
1296 | 0 | self.first_one().unwrap_or_else(|| self.len()) |
1297 | 0 | } |
1298 | | |
1299 | | /// Counts the number of bits from the end of the bit-slice to the last bit |
1300 | | /// set to `0`. |
1301 | | /// |
1302 | | /// This returns `0` if the bit-slice is empty. |
1303 | | /// |
1304 | | /// ## Examples |
1305 | | /// |
1306 | | /// ```rust |
1307 | | /// use bitvec::prelude::*; |
1308 | | /// |
1309 | | /// assert_eq!(bits![].trailing_ones(), 0); |
1310 | | /// assert_eq!(bits![0].trailing_ones(), 0); |
1311 | | /// assert_eq!(bits![0, 1].trailing_ones(), 1); |
1312 | | /// ``` |
1313 | | #[inline] |
1314 | 0 | pub fn trailing_ones(&self) -> usize { |
1315 | 0 | let len = self.len(); |
1316 | 0 | self.last_zero().map(|idx| len - 1 - idx).unwrap_or(len) |
1317 | 0 | } |
1318 | | |
1319 | | /// Counts the number of bits from the end of the bit-slice to the last bit |
1320 | | /// set to `1`. |
1321 | | /// |
1322 | | /// This returns `0` if the bit-slice is empty. |
1323 | | /// |
1324 | | /// ## Examples |
1325 | | /// |
1326 | | /// ```rust |
1327 | | /// use bitvec::prelude::*; |
1328 | | /// |
1329 | | /// assert_eq!(bits![].trailing_zeros(), 0); |
1330 | | /// assert_eq!(bits![1].trailing_zeros(), 0); |
1331 | | /// assert_eq!(bits![1, 0].trailing_zeros(), 1); |
1332 | | /// ``` |
1333 | | #[inline] |
1334 | 0 | pub fn trailing_zeros(&self) -> usize { |
1335 | 0 | let len = self.len(); |
1336 | 0 | self.last_one().map(|idx| len - 1 - idx).unwrap_or(len) |
1337 | 0 | } |
1338 | | |
1339 | | /// Tests if there is at least one bit set to `1` in the bit-slice. |
1340 | | /// |
1341 | | /// Returns `false` when `self` is empty. |
1342 | | /// |
1343 | | /// ## Examples |
1344 | | /// |
1345 | | /// ```rust |
1346 | | /// use bitvec::prelude::*; |
1347 | | /// |
1348 | | /// assert!(!bits![].any()); |
1349 | | /// assert!(!bits![0].any()); |
1350 | | /// assert!(bits![0, 1].any()); |
1351 | | /// ``` |
1352 | | #[inline] |
1353 | 0 | pub fn any(&self) -> bool { |
1354 | 0 | self.count_ones() > 0 |
1355 | 0 | } |
1356 | | |
1357 | | /// Tests if every bit is set to `1` in the bit-slice. |
1358 | | /// |
1359 | | /// Returns `true` when `self` is empty. |
1360 | | /// |
1361 | | /// ## Examples |
1362 | | /// |
1363 | | /// ```rust |
1364 | | /// use bitvec::prelude::*; |
1365 | | /// |
1366 | | /// assert!( bits![].all()); |
1367 | | /// assert!(!bits![0].all()); |
1368 | | /// assert!( bits![1].all()); |
1369 | | /// ``` |
1370 | | #[inline] |
1371 | 5.70k | pub fn all(&self) -> bool { |
1372 | 5.70k | self.count_zeros() == 0 |
1373 | 5.70k | } <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::all Line | Count | Source | 1371 | 5.70k | pub fn all(&self) -> bool { | 1372 | 5.70k | self.count_zeros() == 0 | 1373 | 5.70k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::all |
1374 | | |
1375 | | /// Tests if every bit is cleared to `0` in the bit-slice. |
1376 | | /// |
1377 | | /// Returns `true` when `self` is empty. |
1378 | | /// |
1379 | | /// ## Examples |
1380 | | /// |
1381 | | /// ```rust |
1382 | | /// use bitvec::prelude::*; |
1383 | | /// |
1384 | | /// assert!( bits![].not_any()); |
1385 | | /// assert!(!bits![1].not_any()); |
1386 | | /// assert!( bits![0].not_any()); |
1387 | | /// ``` |
1388 | | #[inline] |
1389 | 0 | pub fn not_any(&self) -> bool { |
1390 | 0 | self.count_ones() == 0 |
1391 | 0 | } |
1392 | | |
1393 | | /// Tests if at least one bit is cleared to `0` in the bit-slice. |
1394 | | /// |
1395 | | /// Returns `false` when `self` is empty. |
1396 | | /// |
1397 | | /// ## Examples |
1398 | | /// |
1399 | | /// ```rust |
1400 | | /// use bitvec::prelude::*; |
1401 | | /// |
1402 | | /// assert!(!bits![].not_all()); |
1403 | | /// assert!(!bits![1].not_all()); |
1404 | | /// assert!( bits![0].not_all()); |
1405 | | /// ``` |
1406 | | #[inline] |
1407 | 0 | pub fn not_all(&self) -> bool { |
1408 | 0 | self.count_zeros() > 0 |
1409 | 0 | } |
1410 | | |
1411 | | /// Tests if at least one bit is set to `1`, and at least one bit is cleared |
1412 | | /// to `0`, in the bit-slice. |
1413 | | /// |
1414 | | /// Returns `false` when `self` is empty. |
1415 | | /// |
1416 | | /// ## Examples |
1417 | | /// |
1418 | | /// ```rust |
1419 | | /// use bitvec::prelude::*; |
1420 | | /// |
1421 | | /// assert!(!bits![].some()); |
1422 | | /// assert!(!bits![0].some()); |
1423 | | /// assert!(!bits![1].some()); |
1424 | | /// assert!( bits![0, 1].some()); |
1425 | | /// ``` |
1426 | | #[inline] |
1427 | 0 | pub fn some(&self) -> bool { |
1428 | 0 | self.any() && self.not_all() |
1429 | 0 | } |
1430 | | } |
1431 | | |
1432 | | /// Buffer manipulation. |
1433 | | impl<T, O> BitSlice<T, O> |
1434 | | where |
1435 | | T: BitStore, |
1436 | | O: BitOrder, |
1437 | | { |
1438 | | /// Shifts the contents of a bit-slice “left” (towards the zero-index), |
1439 | | /// clearing the “right” bits to `0`. |
1440 | | /// |
1441 | | /// This is a strictly-worse analogue to taking `bits = &bits[by ..]`: it |
1442 | | /// has to modify the entire memory region that `bits` governs, and destroys |
1443 | | /// contained information. Unless the actual memory layout and contents of |
1444 | | /// your bit-slice matters to your program, you should *probably* prefer to |
1445 | | /// munch your way forward through a bit-slice handle. |
1446 | | /// |
1447 | | /// Note also that the “left” here is semantic only, and **does not** |
1448 | | /// necessarily correspond to a left-shift instruction applied to the |
1449 | | /// underlying integer storage. |
1450 | | /// |
1451 | | /// This has no effect when `by` is `0`. When `by` is `self.len()`, the |
1452 | | /// bit-slice is entirely cleared to `0`. |
1453 | | /// |
1454 | | /// ## Panics |
1455 | | /// |
1456 | | /// This panics if `by` is not less than `self.len()`. |
1457 | | /// |
1458 | | /// ## Examples |
1459 | | /// |
1460 | | /// ```rust |
1461 | | /// use bitvec::prelude::*; |
1462 | | /// |
1463 | | /// let bits = bits![mut 1, 1, 1, 1, 0, 0, 1, 0, 1, 1, 1, 1]; |
1464 | | /// // these bits are retained ^--------------------------^ |
1465 | | /// bits.shift_left(2); |
1466 | | /// assert_eq!(bits, bits![1, 1, 0, 0, 1, 0, 1, 1, 1, 1, 0, 0]); |
1467 | | /// // and move here ^--------------------------^ |
1468 | | /// |
1469 | | /// let bits = bits![mut 1; 2]; |
1470 | | /// bits.shift_left(2); |
1471 | | /// assert_eq!(bits, bits![0; 2]); |
1472 | | /// ``` |
1473 | | #[inline] |
1474 | 0 | pub fn shift_left(&mut self, by: usize) { |
1475 | 0 | if by == 0 { |
1476 | 0 | return; |
1477 | 0 | } |
1478 | | |
1479 | 0 | let len = self.len(); |
1480 | 0 | if by == len { |
1481 | 0 | return self.fill(false); |
1482 | 0 | } |
1483 | 0 | assert!( |
1484 | 0 | by <= len, |
1485 | 0 | "shift must be less than the length of the bit-slice: {} >= {}", |
1486 | | by, |
1487 | | len, |
1488 | | ); |
1489 | | |
1490 | 0 | unsafe { |
1491 | 0 | self.copy_within_unchecked(by .., 0); |
1492 | 0 | self.get_unchecked_mut(len - by ..).fill(false); |
1493 | 0 | } |
1494 | 0 | } |
1495 | | |
1496 | | /// Shifts the contents of a bit-slice “right” (away from the zero-index), |
1497 | | /// clearing the “left” bits to `0`. |
1498 | | /// |
1499 | | /// This is a strictly-worse analogue to taking `bits = &bits[.. bits.len() |
1500 | | /// - by]`: it must modify the entire memory region that `bits` governs, and |
1501 | | /// destroys contained information. Unless the actual memory layout and |
1502 | | /// contents of your bit-slice matters to your program, you should |
1503 | | /// *probably* prefer to munch your way backward through a bit-slice handle. |
1504 | | /// |
1505 | | /// Note also that the “right” here is semantic only, and **does not** |
1506 | | /// necessarily correspond to a right-shift instruction applied to the |
1507 | | /// underlying integer storage. |
1508 | | /// |
1509 | | /// This has no effect when `by` is `0`. When `by` is `self.len()`, the |
1510 | | /// bit-slice is entirely cleared to `0`. |
1511 | | /// |
1512 | | /// ## Panics |
1513 | | /// |
1514 | | /// This panics if `by` is not less than `self.len()`. |
1515 | | /// |
1516 | | /// ## Examples |
1517 | | /// |
1518 | | /// ```rust |
1519 | | /// use bitvec::prelude::*; |
1520 | | /// |
1521 | | /// let bits = bits![mut 1, 1, 1, 1, 0, 0, 1, 0, 1, 1, 1, 1]; |
1522 | | /// // these bits stay ^--------------------------^ |
1523 | | /// bits.shift_right(2); |
1524 | | /// assert_eq!(bits, bits![0, 0, 1, 1, 1, 1, 0, 0, 1, 0, 1, 1]); |
1525 | | /// // and move here ^--------------------------^ |
1526 | | /// |
1527 | | /// let bits = bits![mut 1; 2]; |
1528 | | /// bits.shift_right(2); |
1529 | | /// assert_eq!(bits, bits![0; 2]); |
1530 | | /// ``` |
1531 | | #[inline] |
1532 | 0 | pub fn shift_right(&mut self, by: usize) { |
1533 | 0 | if by == 0 { |
1534 | 0 | return; |
1535 | 0 | } |
1536 | | |
1537 | 0 | let len = self.len(); |
1538 | 0 | if by == len { |
1539 | 0 | return self.fill(false); |
1540 | 0 | } |
1541 | 0 | assert!( |
1542 | 0 | by <= len, |
1543 | 0 | "shift must be less than the length of the bit-slice: {} >= {}", |
1544 | | by, |
1545 | | len, |
1546 | | ); |
1547 | | |
1548 | 0 | unsafe { |
1549 | 0 | self.copy_within_unchecked(.. len - by, by); |
1550 | 0 | self.get_unchecked_mut(.. by).fill(false); |
1551 | 0 | } |
1552 | 0 | } |
1553 | | } |
1554 | | |
1555 | | /// Crate internals. |
1556 | | impl<T, O> BitSlice<T, O> |
1557 | | where |
1558 | | T: BitStore, |
1559 | | O: BitOrder, |
1560 | | { |
1561 | | /// Gets the structural form of the encoded reference. |
1562 | 2.37M | pub(crate) fn as_bitspan(&self) -> BitSpan<Const, T, O> { |
1563 | 2.37M | BitSpan::from_bitslice_ptr(self) |
1564 | 2.37M | } Unexecuted instantiation: <bitvec::slice::BitSlice<bitvec::access::BitSafeU8>>::as_bitspan <bitvec::slice::BitSlice<bitvec::access::BitSafeU8, bitvec::order::Msb0>>::as_bitspan Line | Count | Source | 1562 | 335k | pub(crate) fn as_bitspan(&self) -> BitSpan<Const, T, O> { | 1563 | 335k | BitSpan::from_bitslice_ptr(self) | 1564 | 335k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<u8>>::as_bitspan <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::as_bitspan Line | Count | Source | 1562 | 2.03M | pub(crate) fn as_bitspan(&self) -> BitSpan<Const, T, O> { | 1563 | 2.03M | BitSpan::from_bitslice_ptr(self) | 1564 | 2.03M | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::as_bitspan |
1565 | | |
1566 | | /// Gets the structural form of the encoded reference. |
1567 | 842k | pub(crate) fn as_mut_bitspan(&mut self) -> BitSpan<Mut, T, O> { |
1568 | 842k | BitSpan::from_bitslice_ptr_mut(self) |
1569 | 842k | } Unexecuted instantiation: <bitvec::slice::BitSlice<bitvec::access::BitSafeU8>>::as_mut_bitspan <bitvec::slice::BitSlice<bitvec::access::BitSafeU8, bitvec::order::Msb0>>::as_mut_bitspan Line | Count | Source | 1567 | 623k | pub(crate) fn as_mut_bitspan(&mut self) -> BitSpan<Mut, T, O> { | 1568 | 623k | BitSpan::from_bitslice_ptr_mut(self) | 1569 | 623k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<u8>>::as_mut_bitspan <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::as_mut_bitspan Line | Count | Source | 1567 | 218k | pub(crate) fn as_mut_bitspan(&mut self) -> BitSpan<Mut, T, O> { | 1568 | 218k | BitSpan::from_bitslice_ptr_mut(self) | 1569 | 218k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::as_mut_bitspan |
1570 | | |
1571 | | /// Asserts that `index` is within the given bounds. |
1572 | | /// |
1573 | | /// ## Parameters |
1574 | | /// |
1575 | | /// - `&self` |
1576 | | /// - `index`: The bit index to test against the bit-slice. |
1577 | | /// - `bounds`: The bounds to check. cannot exceed `0 ..= self.len()`. |
1578 | | /// |
1579 | | /// ## Panics |
1580 | | /// |
1581 | | /// This panics if `bounds` is outside `index`. |
1582 | 44.2k | pub(crate) fn assert_in_bounds<R>(&self, index: usize, bounds: R) |
1583 | 44.2k | where R: RangeExt<usize> { |
1584 | 44.2k | let bounds = bounds.normalize(0, self.len()); |
1585 | 44.2k | assert!( |
1586 | 44.2k | bounds.contains(&index), |
1587 | 0 | "index {} out of range: {:?}", |
1588 | | index, |
1589 | 0 | bounds.end_bound() |
1590 | | ); |
1591 | 44.2k | } <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::assert_in_bounds::<core::ops::range::Range<usize>> Line | Count | Source | 1582 | 44.2k | pub(crate) fn assert_in_bounds<R>(&self, index: usize, bounds: R) | 1583 | 44.2k | where R: RangeExt<usize> { | 1584 | 44.2k | let bounds = bounds.normalize(0, self.len()); | 1585 | 44.2k | assert!( | 1586 | 44.2k | bounds.contains(&index), | 1587 | 0 | "index {} out of range: {:?}", | 1588 | | index, | 1589 | 0 | bounds.end_bound() | 1590 | | ); | 1591 | 44.2k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::assert_in_bounds::<_> |
1592 | | |
1593 | | /// Marks an exclusive bit-slice as covering an aliased memory region. |
1594 | 210k | pub(crate) fn alias_mut(&mut self) -> &mut BitSlice<T::Alias, O> { |
1595 | 210k | unsafe { self.as_mut_bitspan().cast::<T::Alias>().into_bitslice_mut() } |
1596 | 210k | } Unexecuted instantiation: <bitvec::slice::BitSlice<bitvec::access::BitSafeU8>>::alias_mut <bitvec::slice::BitSlice<bitvec::access::BitSafeU8, bitvec::order::Msb0>>::alias_mut Line | Count | Source | 1594 | 124k | pub(crate) fn alias_mut(&mut self) -> &mut BitSlice<T::Alias, O> { | 1595 | 124k | unsafe { self.as_mut_bitspan().cast::<T::Alias>().into_bitslice_mut() } | 1596 | 124k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<u8>>::alias_mut <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::alias_mut Line | Count | Source | 1594 | 85.9k | pub(crate) fn alias_mut(&mut self) -> &mut BitSlice<T::Alias, O> { | 1595 | 85.9k | unsafe { self.as_mut_bitspan().cast::<T::Alias>().into_bitslice_mut() } | 1596 | 85.9k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::alias_mut |
1597 | | |
1598 | | /// Removes an aliasing marker from an exclusive bit-slice handle. |
1599 | | /// |
1600 | | /// ## Safety |
1601 | | /// |
1602 | | /// This may only be used when the bit-slice is either known to be |
1603 | | /// unaliased, or this call is combined with an operation that adds an |
1604 | | /// aliasing marker and the total number of aliasing markers remains |
1605 | | /// unchanged. |
1606 | 374k | pub(crate) unsafe fn unalias_mut( |
1607 | 374k | this: &mut BitSlice<T::Alias, O>, |
1608 | 374k | ) -> &mut Self { |
1609 | 374k | this.as_mut_bitspan().cast::<T>().into_bitslice_mut() |
1610 | 374k | } Unexecuted instantiation: <bitvec::slice::BitSlice<bitvec::access::BitSafeU8>>::unalias_mut <bitvec::slice::BitSlice<bitvec::access::BitSafeU8, bitvec::order::Msb0>>::unalias_mut Line | Count | Source | 1606 | 249k | pub(crate) unsafe fn unalias_mut( | 1607 | 249k | this: &mut BitSlice<T::Alias, O>, | 1608 | 249k | ) -> &mut Self { | 1609 | 249k | this.as_mut_bitspan().cast::<T>().into_bitslice_mut() | 1610 | 249k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<u8>>::unalias_mut <bitvec::slice::BitSlice<u8, bitvec::order::Msb0>>::unalias_mut Line | Count | Source | 1606 | 124k | pub(crate) unsafe fn unalias_mut( | 1607 | 124k | this: &mut BitSlice<T::Alias, O>, | 1608 | 124k | ) -> &mut Self { | 1609 | 124k | this.as_mut_bitspan().cast::<T>().into_bitslice_mut() | 1610 | 124k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::unalias_mut |
1611 | | |
1612 | | /// Splits a mutable bit-slice at a midpoint, without either doing bounds |
1613 | | /// checks or adding an alias marker to the returned sections. |
1614 | | /// |
1615 | | /// This method has the same behavior as [`.split_at_unchecked_mut()`], |
1616 | | /// except that it does not apply an aliasing marker to the partitioned |
1617 | | /// subslices. |
1618 | | /// |
1619 | | /// ## Safety |
1620 | | /// |
1621 | | /// See `split_at_unchecked_mut`. Additionally, this is only safe when `T` |
1622 | | /// is alias-safe. |
1623 | | /// |
1624 | | /// [`.split_at_unchecked_mut()`]: Self::split_at_unchecked_mut |
1625 | 124k | pub(crate) unsafe fn split_at_unchecked_mut_noalias( |
1626 | 124k | &mut self, |
1627 | 124k | mid: usize, |
1628 | 124k | ) -> (&mut Self, &mut Self) { |
1629 | | // Split the slice at the requested midpoint, adding an alias layer |
1630 | 124k | let (head, tail) = self.split_at_unchecked_mut(mid); |
1631 | | // Remove the new alias layer. |
1632 | 124k | (Self::unalias_mut(head), Self::unalias_mut(tail)) |
1633 | 124k | } Unexecuted instantiation: <bitvec::slice::BitSlice<bitvec::access::BitSafeU8>>::split_at_unchecked_mut_noalias <bitvec::slice::BitSlice<bitvec::access::BitSafeU8, bitvec::order::Msb0>>::split_at_unchecked_mut_noalias Line | Count | Source | 1625 | 124k | pub(crate) unsafe fn split_at_unchecked_mut_noalias( | 1626 | 124k | &mut self, | 1627 | 124k | mid: usize, | 1628 | 124k | ) -> (&mut Self, &mut Self) { | 1629 | | // Split the slice at the requested midpoint, adding an alias layer | 1630 | 124k | let (head, tail) = self.split_at_unchecked_mut(mid); | 1631 | | // Remove the new alias layer. | 1632 | 124k | (Self::unalias_mut(head), Self::unalias_mut(tail)) | 1633 | 124k | } |
Unexecuted instantiation: <bitvec::slice::BitSlice<_, _>>::split_at_unchecked_mut_noalias |
1634 | | } |
1635 | | |
1636 | | /// Methods available only when `T` allows shared mutability. |
1637 | | impl<T, O> BitSlice<T, O> |
1638 | | where |
1639 | | T: BitStore + radium::Radium, |
1640 | | O: BitOrder, |
1641 | | { |
1642 | | /// Writes a new value into a single bit, using alias-safe operations. |
1643 | | /// |
1644 | | /// This is equivalent to [`.set()`], except that it does not require an |
1645 | | /// `&mut` reference, and allows bit-slices with alias-safe storage to share |
1646 | | /// write permissions. |
1647 | | /// |
1648 | | /// ## Parameters |
1649 | | /// |
1650 | | /// - `&self`: This method only exists on bit-slices with alias-safe |
1651 | | /// storage, and so does not require exclusive access. |
1652 | | /// - `index`: The bit index to set. It must be in `0 .. self.len()`. |
1653 | | /// - `value`: The new bit-value to write into the bit at `index`. |
1654 | | /// |
1655 | | /// ## Panics |
1656 | | /// |
1657 | | /// This panics if `index` is out of bounds. |
1658 | | /// |
1659 | | /// ## Examples |
1660 | | /// |
1661 | | /// ```rust |
1662 | | /// use bitvec::prelude::*; |
1663 | | /// use core::cell::Cell; |
1664 | | /// |
1665 | | /// let bits: &BitSlice<_, _> = bits![Cell<usize>, Lsb0; 0, 1]; |
1666 | | /// bits.set_aliased(0, true); |
1667 | | /// bits.set_aliased(1, false); |
1668 | | /// |
1669 | | /// assert_eq!(bits, bits![1, 0]); |
1670 | | /// ``` |
1671 | | /// |
1672 | | /// [`.set()`]: Self::set |
1673 | | #[inline] |
1674 | 0 | pub fn set_aliased(&self, index: usize, value: bool) { |
1675 | 0 | self.assert_in_bounds(index, 0 .. self.len()); |
1676 | 0 | unsafe { |
1677 | 0 | self.set_aliased_unchecked(index, value); |
1678 | 0 | } |
1679 | 0 | } |
1680 | | |
1681 | | /// Writes a new value into a single bit, using alias-safe operations and |
1682 | | /// without bounds checking. |
1683 | | /// |
1684 | | /// This is equivalent to [`.set_unchecked()`], except that it does not |
1685 | | /// require an `&mut` reference, and allows bit-slices with alias-safe |
1686 | | /// storage to share write permissions. |
1687 | | /// |
1688 | | /// ## Parameters |
1689 | | /// |
1690 | | /// - `&self`: This method only exists on bit-slices with alias-safe |
1691 | | /// storage, and so does not require exclusive access. |
1692 | | /// - `index`: The bit index to set. It must be in `0 .. self.len()`. |
1693 | | /// - `value`: The new bit-value to write into the bit at `index`. |
1694 | | /// |
1695 | | /// ## Safety |
1696 | | /// |
1697 | | /// The caller must ensure that `index` is not out of bounds. |
1698 | | /// |
1699 | | /// ## Examples |
1700 | | /// |
1701 | | /// ```rust |
1702 | | /// use bitvec::prelude::*; |
1703 | | /// use core::cell::Cell; |
1704 | | /// |
1705 | | /// let data = Cell::new(0u8); |
1706 | | /// let bits = &data.view_bits::<Lsb0>()[.. 2]; |
1707 | | /// unsafe { |
1708 | | /// bits.set_aliased_unchecked(3, true); |
1709 | | /// } |
1710 | | /// assert_eq!(data.get(), 8); |
1711 | | /// ``` |
1712 | | /// |
1713 | | /// [`.set_unchecked()`]: Self::set_unchecked |
1714 | | #[inline] |
1715 | 0 | pub unsafe fn set_aliased_unchecked(&self, index: usize, value: bool) { |
1716 | 0 | self.as_bitptr().add(index).freeze().frozen_write_bit(value); |
1717 | 0 | } |
1718 | | } |
1719 | | |
1720 | | /// Miscellaneous information. |
1721 | | impl<T, O> BitSlice<T, O> |
1722 | | where |
1723 | | T: BitStore, |
1724 | | O: BitOrder, |
1725 | | { |
1726 | | /// The inclusive maximum length of a `BitSlice<_, T>`. |
1727 | | /// |
1728 | | /// As `BitSlice` is zero-indexed, the largest possible *index* is one less |
1729 | | /// than this value. |
1730 | | /// |
1731 | | /// |CPU word width| Value | |
1732 | | /// |-------------:|----------------------:| |
1733 | | /// | 32 bits | `0x1fff_ffff` | |
1734 | | /// | 64 bits |`0x1fff_ffff_ffff_ffff`| |
1735 | | pub const MAX_BITS: usize = BitSpan::<Const, T, O>::REGION_MAX_BITS; |
1736 | | /// The inclusive maximum length that a `[T]` slice can be for |
1737 | | /// `BitSlice<_, T>` to cover it. |
1738 | | /// |
1739 | | /// A `BitSlice<_, T>` that begins in the interior of an element and |
1740 | | /// contains the maximum number of bits will extend one element past the |
1741 | | /// cutoff that would occur if the bit-slice began at the zeroth bit. Such a |
1742 | | /// bit-slice is difficult to manually construct, but would not otherwise |
1743 | | /// fail. |
1744 | | /// |
1745 | | /// |Type Bits|Max Elements (32-bit)| Max Elements (64-bit) | |
1746 | | /// |--------:|--------------------:|----------------------:| |
1747 | | /// | 8| `0x0400_0001` |`0x0400_0000_0000_0001`| |
1748 | | /// | 16| `0x0200_0001` |`0x0200_0000_0000_0001`| |
1749 | | /// | 32| `0x0100_0001` |`0x0100_0000_0000_0001`| |
1750 | | /// | 64| `0x0080_0001` |`0x0080_0000_0000_0001`| |
1751 | | pub const MAX_ELTS: usize = BitSpan::<Const, T, O>::REGION_MAX_ELTS; |
1752 | | } |
1753 | | |
1754 | | #[cfg(feature = "alloc")] |
1755 | | impl<T, O> BitSlice<T, O> |
1756 | | where |
1757 | | T: BitStore, |
1758 | | O: BitOrder, |
1759 | | { |
1760 | | /// Copies a bit-slice into an owned bit-vector. |
1761 | | /// |
1762 | | /// Since the new vector is freshly owned, this gets marked as `::Unalias` |
1763 | | /// to remove any guards that may have been inserted by the bit-slice’s |
1764 | | /// history. |
1765 | | /// |
1766 | | /// It does *not* use the underlying memory type, so that a `BitSlice<_, |
1767 | | /// Cell<_>>` will produce a `BitVec<_, Cell<_>>`. |
1768 | | /// |
1769 | | /// ## Original |
1770 | | /// |
1771 | | /// [`slice::to_vec`](https://doc.rust-lang.org/std/primitive.slice.html#method.to_vec) |
1772 | | /// |
1773 | | /// ## Examples |
1774 | | /// |
1775 | | /// ```rust |
1776 | | /// use bitvec::prelude::*; |
1777 | | /// |
1778 | | /// let bits = bits![0, 1, 0, 1]; |
1779 | | /// let bv = bits.to_bitvec(); |
1780 | | /// assert_eq!(bits, bv); |
1781 | | /// ``` |
1782 | | #[inline] |
1783 | 0 | pub fn to_bitvec(&self) -> BitVec<T::Unalias, O> { |
1784 | 0 | self.domain() |
1785 | 0 | .map(<T::Unalias as BitStore>::new) |
1786 | 0 | .collect::<Vec<_>>() |
1787 | 0 | .pipe(BitVec::from_vec) |
1788 | 0 | .tap_mut(|bv| unsafe { |
1789 | 0 | bv.set_head(self.as_bitspan().head()); |
1790 | 0 | bv.set_len(self.len()); |
1791 | 0 | }) |
1792 | 0 | } |
1793 | | } |
1794 | | |
1795 | | #[inline] |
1796 | | #[doc = include_str!("../doc/slice/from_raw_parts_unchecked.md")] |
1797 | 0 | pub unsafe fn from_raw_parts_unchecked<'a, T, O>( |
1798 | 0 | ptr: BitPtr<Const, T, O>, |
1799 | 0 | len: usize, |
1800 | 0 | ) -> &'a BitSlice<T, O> |
1801 | 0 | where |
1802 | 0 | O: BitOrder, |
1803 | 0 | T: 'a + BitStore, |
1804 | | { |
1805 | 0 | ptr.span_unchecked(len).into_bitslice_ref() |
1806 | 0 | } |
1807 | | |
1808 | | #[inline] |
1809 | | #[doc = include_str!("../doc/slice/from_raw_parts_unchecked_mut.md")] |
1810 | 0 | pub unsafe fn from_raw_parts_unchecked_mut<'a, T, O>( |
1811 | 0 | ptr: BitPtr<Mut, T, O>, |
1812 | 0 | len: usize, |
1813 | 0 | ) -> &'a mut BitSlice<T, O> |
1814 | 0 | where |
1815 | 0 | O: BitOrder, |
1816 | 0 | T: 'a + BitStore, |
1817 | | { |
1818 | 0 | ptr.span_unchecked(len).into_bitslice_mut() |
1819 | 0 | } |