Trait heph::net::BytesVectored [−][src]
pub trait BytesVectored { type Bufs: AsMut<[MaybeUninitSlice<'b>]>; fn as_bufs<'b>(&'b mut self) -> Self::Bufs; fn spare_capacity(&self) -> usize; unsafe fn update_lengths(&mut self, n: usize); fn has_spare_capacity(&self) -> bool { ... } fn limit(self, limit: usize) -> LimitedBytes<Self>
where
Self: Sized, { ... } }
Expand description
Trait to make easier to work with uninitialised buffers using vectored I/O.
This trait is implemented for arrays and tuples. When all of buffers are
homogeneous, i.e. of the same type, the array implementation is the
easiest to use along side with the Bytes
trait. If however the buffers
are heterogeneous, i.e. of different types, the tuple implementation can
be used. See the examples below.
Examples
Using the homogeneous array implementation.
use heph::net::BytesVectored; let mut buf1 = Vec::with_capacity(12); let mut buf2 = Vec::with_capacity(1); let mut buf3 = Vec::with_capacity(5); let mut buf4 = Vec::with_capacity(10); // Has extra capacity. let bufs = [&mut buf1, &mut buf2, &mut buf3, &mut buf4]; let text = b"Hello world. From mars!"; let bytes_written = write_vectored(bufs, text); assert_eq!(bytes_written, text.len()); assert_eq!(buf1, b"Hello world."); assert_eq!(buf2, b" "); assert_eq!(buf3, b"From "); assert_eq!(buf4, b"mars!"); /// Writes `text` to the `bufs`. fn write_vectored<B>(mut bufs: B, text: &[u8]) -> usize where B: BytesVectored, { // Implementation is not relevant to the example. }
Using the heterogeneous tuple implementation.
use std::mem::MaybeUninit; use heph::net::{Bytes, BytesVectored}; // Buffers of different types. let mut buf1 = Vec::with_capacity(12); let mut buf2 = StackBuf::new(); // Has extra capacity. // Using tuples we can use different kind of buffers. Here we use a `Vec` and // our own `StackBuf` type. let bufs = (&mut buf1, &mut buf2); let text = b"Hello world. From mars!"; let bytes_written = write_vectored(bufs, text); assert_eq!(bytes_written, text.len()); assert_eq!(buf1, b"Hello world."); assert_eq!(buf2.bytes(), b" From mars!"); /// Writes `text` to the `bufs`. fn write_vectored<B>(mut bufs: B, text: &[u8]) -> usize where B: BytesVectored, { // Implementation is not relevant to the example. } /// Custom stack buffer type that implements the `Bytes` trait. struct StackBuf { bytes: [MaybeUninit<u8>; 4096], initialised: usize, } impl StackBuf { fn new() -> StackBuf { StackBuf { bytes: MaybeUninit::uninit_array(), initialised: 0, } } fn bytes(&self) -> &[u8] { unsafe { MaybeUninit::slice_assume_init_ref(&self.bytes[..self.initialised]) } } } impl Bytes for StackBuf { fn as_bytes(&mut self) -> &mut [MaybeUninit<u8>] { &mut self.bytes[self.initialised..] } fn spare_capacity(&self) -> usize { self.bytes.len() - self.initialised } fn has_spare_capacity(&self) -> bool { self.bytes.len() != self.initialised } unsafe fn update_length(&mut self, n: usize) { self.initialised += n; } }
Associated Types
Required methods
Returns itself as a slice of MaybeUninitSlice
.
fn spare_capacity(&self) -> usize
fn spare_capacity(&self) -> usize
Returns the total length of the buffers as returned by as_bufs
.
unsafe fn update_lengths(&mut self, n: usize)
unsafe fn update_lengths(&mut self, n: usize)
Update the length of the buffers in the slice.
Safety
The caller must ensure that at least the first n
bytes returned by
as_bufs
are initialised, starting at the first buffer continuing
into the next one, etc.
Notes
If this method is not implemented correctly methods such as
TcpStream::recv_n_vectored
will not work correctly (as the buffer
will overwrite itself on successive reads).
Provided methods
fn has_spare_capacity(&self) -> bool
fn has_spare_capacity(&self) -> bool
Returns true
if (one of) the buffers has spare capacity.
fn limit(self, limit: usize) -> LimitedBytes<Self> where
Self: Sized,
fn limit(self, limit: usize) -> LimitedBytes<Self> where
Self: Sized,
Wrap the buffer in LimitedBytes
, which limits the amount of bytes used
to limit
.
LimitedBytes::into_inner
can be used to retrieve the buffer again,
or a mutable reference to the buffer can be used and the limited buffer
be dropped after usage.