/// Peek at byte `n` ahead of cursor /// /// # Safety /// /// Caller must ensure that `n <= self.len()`, otherwise `self.cursor.add(n)` is UB. /// That means there are at least `n-1` bytes between `self.cursor` and `self.end` /// and `self.cursor.add(n)` is either `self.end` or points to a valid byte. #[inline] pubunsafefn peek_ahead(&self, n: usize) -> Option<u8> {
debug_assert!(n <= self.len()); // SAFETY: by preconditions let p = unsafe { self.cursor.add(n) }; if p < self.end { // SAFETY: by preconditions, if this is not `self.end`, // then it is safe to dereference
Some(unsafe { *p })
} else {
None
}
}
#[inline] pubfn peek_n<'b: 'a, U: TryFrom<&'a [u8]>>(&'b self, n: usize) -> Option<U> { // TODO: once we bump MSRC, use const generics to allow only [u8; N] reads // TODO: drop `n` arg in favour of const // let n = core::mem::size_of::<U>(); self.as_ref().get(..n)?.try_into().ok()
}
/// Advance by 1, equivalent to calling `advance(1)`. /// /// # Safety /// /// Caller must ensure that Bytes hasn't been advanced/bumped by more than [`Bytes::len()`]. #[inline] pubunsafefn bump(&mutself) { self.advance(1)
}
/// Advance cursor by `n` /// /// # Safety /// /// Caller must ensure that Bytes hasn't been advanced/bumped by more than [`Bytes::len()`]. #[inline] pubunsafefn advance(&mutself, n: usize) { self.cursor = self.cursor.add(n);
debug_assert!(self.cursor <= self.end, "overflow");
}
#[inline] pubfn len(&self) -> usize { self.end as usize - self.cursor as usize
}
#[inline] pubfn slice(&mutself) -> &'a [u8] { // SAFETY: not moving position at all, so it's safe let slice = unsafe { slice_from_ptr_range(self.start, self.cursor) }; self.commit();
slice
}
// TODO: this is an anti-pattern, should be removed /// Deprecated. Do not use! /// # Safety /// /// Caller must ensure that `skip` is at most the number of advances (i.e., `bytes.advance(3)` /// implies a skip of at most 3). #[inline] pubunsafefn slice_skip(&mutself, skip: usize) -> &'a [u8] {
debug_assert!(skip <= self.cursor.offset_from(self.start) as usize); let head = slice_from_ptr_range(self.start, self.cursor.sub(skip)); self.commit();
head
}
impl AsRef<[u8]> for Bytes<'_> { #[inline] fn as_ref(&self) -> &[u8] { // SAFETY: not moving position at all, so it's safe unsafe { slice_from_ptr_range(self.cursor, self.end) }
}
}
/// # Safety /// /// Must ensure start and end point to the same memory object to uphold memory safety. #[inline] unsafefn slice_from_ptr_range<'a>(start: *const u8, end: *const u8) -> &'a [u8] {
debug_assert!(start <= end);
core::slice::from_raw_parts(start, end as usize - start as usize)
}
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.