#[cfg(feature = "alloc")]
use alloc::vec::Vec;
#[cfg(not(feature = "std"))]
use core::fmt;
#[cfg(feature = "std")]
use std::io;
use crate::error;
#[cfg(not(feature = "unsealed_read_write"))]
pub trait Write: private::Sealed {
#[doc(hidden)]
type Error: Into<error::Error>;
#[doc(hidden)]
fn write_all(&mut self, buf: &[u8]) -> Result<(), Self::Error>;
}
#[cfg(feature = "unsealed_read_write")]
pub trait Write {
type Error: Into<error::Error>;
fn write_all(&mut self, buf: &[u8]) -> Result<(), Self::Error>;
}
#[cfg(not(feature = "unsealed_read_write"))]
mod private {
pub trait Sealed {}
}
impl<W> Write for &mut W
where
W: Write,
{
type Error = W::Error;
fn write_all(&mut self, buf: &[u8]) -> Result<(), Self::Error> {
(*self).write_all(buf)
}
}
#[cfg(not(feature = "unsealed_read_write"))]
impl<W> private::Sealed for &mut W where W: Write {}
#[cfg(feature = "std")]
#[derive(Debug)]
pub struct IoWrite<W>(W);
#[cfg(feature = "std")]
impl<W: io::Write> IoWrite<W> {
pub fn new(w: W) -> IoWrite<W> {
IoWrite(w)
}
}
#[cfg(feature = "std")]
impl<W: io::Write> Write for IoWrite<W> {
type Error = io::Error;
fn write_all(&mut self, buf: &[u8]) -> Result<(), Self::Error> {
self.0.write_all(buf)
}
}
#[cfg(all(feature = "std", not(feature = "unsealed_read_write")))]
impl<W> private::Sealed for IoWrite<W> where W: io::Write {}
#[cfg(any(feature = "std", feature = "alloc"))]
impl Write for Vec<u8> {
type Error = error::Error;
fn write_all(&mut self, buf: &[u8]) -> Result<(), Self::Error> {
self.extend_from_slice(buf);
Ok(())
}
}
#[cfg(all(
any(feature = "std", feature = "alloc"),
not(feature = "unsealed_read_write")
))]
impl private::Sealed for Vec<u8> {}
#[cfg(not(feature = "std"))]
#[derive(Debug)]
pub struct FmtWrite<'a, W: Write>(&'a mut W);
#[cfg(not(feature = "std"))]
impl<'a, W: Write> FmtWrite<'a, W> {
pub fn new(w: &'a mut W) -> FmtWrite<'a, W> {
FmtWrite(w)
}
}
#[cfg(not(feature = "std"))]
impl<'a, W: Write> fmt::Write for FmtWrite<'a, W> {
fn write_str(&mut self, s: &str) -> fmt::Result {
self.0.write_all(s.as_bytes()).map_err(|_| fmt::Error)
}
}
#[cfg(all(not(feature = "std"), not(feature = "unsealed_read_write")))]
impl<'a, W> private::Sealed for FmtWrite<'a, W> where W: Write {}
#[derive(Debug)]
pub struct SliceWrite<'a> {
slice: &'a mut [u8],
index: usize,
}
impl<'a> SliceWrite<'a> {
pub fn new(slice: &'a mut [u8]) -> SliceWrite<'a> {
SliceWrite { slice, index: 0 }
}
pub fn bytes_written(&self) -> usize {
self.index
}
pub fn into_inner(self) -> &'a mut [u8] {
self.slice
}
}
impl<'a> Write for SliceWrite<'a> {
type Error = error::Error;
fn write_all(&mut self, buf: &[u8]) -> Result<(), Self::Error> {
if self.slice.len() - self.index < buf.len() {
return Err(error::Error::scratch_too_small(self.index as u64));
}
let end = self.index + buf.len();
self.slice[self.index..end].copy_from_slice(buf);
self.index = end;
Ok(())
}
}
#[cfg(not(feature = "unsealed_read_write"))]
impl<'a> private::Sealed for SliceWrite<'a> {}