#![cfg(all(unix, feature = "std-io"))]
use std::{marker::PhantomData, mem, slice};
use libc;
use super::BufError;
pub struct IoSlice<'data> {
vec: libc::iovec,
_ph: PhantomData<&'data [u8]>,
}
impl<'data> IoSlice<'data> {
#[inline(always)]
pub const fn new(buf: &'data [u8]) -> Self {
Self {
vec: libc::iovec {
iov_base: buf.as_ptr() as *mut u8 as *mut libc::c_void,
iov_len: buf.len(),
},
_ph: PhantomData,
}
}
#[inline]
pub fn advance(&mut self, n: usize) {
if self.vec.iov_len < n {
panic!("advancing IoSlice beyond its length");
}
unsafe {
self.vec.iov_len -= n;
self.vec.iov_base = self.vec.iov_base.add(n);
}
}
#[inline(always)]
pub const fn as_slice(&self) -> &'data [u8] {
unsafe { slice::from_raw_parts(self.vec.iov_base as *mut u8, self.vec.iov_len) }
}
}
pub trait WriteVecData {
type E: BufError;
fn write_vectored_data<'data>(
&mut self,
data: &'data [IoSlice<'data>],
) -> (usize, Option<Self::E>);
}
pub struct IoSliceMut<'buf> {
vec: libc::iovec,
_ph: PhantomData<&'buf mut [mem::MaybeUninit<u8>]>,
}
impl<'buf> IoSliceMut<'buf> {
#[inline(always)]
pub const fn new(buf: &'buf mut [u8]) -> Self {
Self {
vec: libc::iovec {
iov_base: buf.as_mut_ptr() as *mut libc::c_void,
iov_len: buf.len(),
},
_ph: PhantomData,
}
}
#[inline]
pub fn advance(&mut self, n: usize) {
if self.vec.iov_len < n {
panic!("advancing IoSliceMut beyond its length");
}
unsafe {
self.vec.iov_len -= n;
self.vec.iov_base = self.vec.iov_base.add(n);
}
}
#[inline(always)]
pub const fn as_slice(&self) -> &[mem::MaybeUninit<u8>] {
unsafe {
slice::from_raw_parts(
self.vec.iov_base as *mut mem::MaybeUninit<u8>,
self.vec.iov_len,
)
}
}
#[inline(always)]
pub const fn into_slice(self) -> &'buf mut [mem::MaybeUninit<u8>] {
unsafe {
slice::from_raw_parts_mut(
self.vec.iov_base as *mut mem::MaybeUninit<u8>,
self.vec.iov_len,
)
}
}
#[inline(always)]
pub const fn as_mut_slice(&mut self) -> &mut [mem::MaybeUninit<u8>] {
unsafe {
slice::from_raw_parts_mut(
self.vec.iov_base as *mut mem::MaybeUninit<u8>,
self.vec.iov_len,
)
}
}
}
pub trait ReadVecBuf {
type E: BufError;
fn read_vectored_buf<'buf>(
&mut self,
buf: &'buf mut [IoSliceMut<'buf>],
) -> (usize, Option<Self::E>);
}