diff --git a/src/reader.rs b/src/reader.rs index fe3217de..f074634f 100644 --- a/src/reader.rs +++ b/src/reader.rs @@ -48,14 +48,18 @@ impl Seek for Reader { #[cfg(feature = "logging")] log::trace!("seek: {pos:?}"); - // clear leftover - self.leftover = None; - - let new_pos = self.inner.seek(pos)?; - self.bits_read = usize::try_from(new_pos) - .unwrap_or(usize::MAX) - .saturating_mul(8); - Ok(new_pos) + if pos == SeekFrom::Current(0) { + self.inner.seek(pos) + } else { + // clear leftover + self.leftover = None; + + let new_pos = self.inner.seek(pos)?; + self.bits_read = usize::try_from(new_pos) + .unwrap_or(usize::MAX) + .saturating_mul(8); + Ok(new_pos) + } } } @@ -935,4 +939,26 @@ mod tests { Some(bitvec![u8, Msb0; 0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 0, 0, 1, 0]) ); } + + #[cfg(all(feature = "alloc", feature = "bits"))] + #[test] + // Issue #678 + fn test_regression_stream_position() { + use alloc::vec; + + let input = vec![0x0F, 0xFF, 0xF0]; + let mut reader = Reader::new(Cursor::new(&input)); + + let first_bits = reader.read_bits(4, Order::Msb0).unwrap(); + assert_eq!(first_bits, Some(bitvec!(u8, Msb0; 0, 0, 0, 0))); + + let pos = reader.stream_position().unwrap(); + assert_eq!(pos, 1); + + let second_bits = reader.read_bits(16, Order::Msb0).unwrap(); + assert_eq!( + second_bits, + Some(bitvec![u8, Msb0; 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1]) + ); + } } diff --git a/src/writer.rs b/src/writer.rs index 0a6c6411..d743dbc4 100644 --- a/src/writer.rs +++ b/src/writer.rs @@ -32,9 +32,9 @@ impl Seek for Writer { #[cfg(feature = "logging")] log::trace!("seek: {pos:?}"); - // clear leftover + // clear leftover if the position changes #[cfg(feature = "bits")] - { + if pos != SeekFrom::Current(0) { self.leftover.0.clear(); self.leftover.1 = Order::Msb0; } @@ -551,4 +551,26 @@ mod tests { writer.finalize().unwrap(); assert_eq!(out_buf.into_inner(), [0b1001_0101, 0b0000_1010]); } + + #[cfg(all(feature = "alloc", feature = "bits"))] + #[test] + // Issue #678 + fn test_regression_stream_position() { + let mut target = vec![]; + let mut writer = Writer::new(Cursor::new(&mut target)); + + writer + .write_bits_order(&bitvec![u8, Msb0; 1, 1, 1, 1], Order::Msb0) + .unwrap(); + + let pos = writer.stream_position().unwrap(); + assert_eq!(pos, 0); + + writer + .write_bits_order(&bitvec![u8, Msb0; 1, 1, 1, 1], Order::Msb0) + .unwrap(); + + writer.finalize().unwrap(); + assert_eq!(target, [0xFF]); + } }