blob: 471b40d43aad16437dfd514aee43cfd4b51743e1 [file] [log] [blame]
// Licensed to the Apache Software Foundation (ASF) under one
// or more contributor license agreements. See the NOTICE file
// distributed with this work for additional information
// regarding copyright ownership. The ASF licenses this file
// to you under the Apache License, Version 2.0 (the
// "License"); you may not use this file except in compliance
// with the License. You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing,
// software distributed under the License is distributed on an
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
// KIND, either express or implied. See the License for the
// specific language governing permissions and limitations
// under the License..
use crate::memchr;
use core::cmp;
use core::fmt;
use core::ptr;
use core::mem;
use core::ops::{Deref, DerefMut};
use alloc_crate::slice;
use alloc_crate::vec::Vec;
use alloc_crate::str;
use alloc_crate::string::String;
use crate::sys;
pub use self::buffered::IntoInnerError;
pub use self::buffered::{BufReader, BufWriter, LineWriter};
pub use self::cursor::Cursor;
pub use self::error::{Error, ErrorKind, Result};
pub use self::lazy::{Lazy};
pub use sys::os::{errno, set_errno, error_string};
#[cfg(feature = "stdio")]
pub use self::stdio::{stderr, stdin, stdout, Stderr, Stdin, Stdout};
#[cfg(feature = "stdio")]
pub use self::stdio::{StderrLock, StdinLock, StdoutLock};
#[cfg(feature = "stdio")]
pub use self::stdio::{_eprint, _print};
pub use self::util::{copy, empty, repeat, sink, Empty, Repeat, Sink};
pub mod prelude;
mod buffered;
mod cursor;
mod error;
mod impls;
mod lazy;
#[cfg(feature = "stdio")]
mod stdio;
mod util;
const DEFAULT_BUF_SIZE: usize = crate::sys_common::io::DEFAULT_BUF_SIZE;
struct Guard<'a> {
buf: &'a mut Vec<u8>,
len: usize,
}
impl Drop for Guard<'_> {
fn drop(&mut self) {
unsafe {
self.buf.set_len(self.len);
}
}
}
// A few methods below (read_to_string, read_line) will append data into a
// `String` buffer, but we need to be pretty careful when doing this. The
// implementation will just call `.as_mut_vec()` and then delegate to a
// byte-oriented reading method, but we must ensure that when returning we never
// leave `buf` in a state such that it contains invalid UTF-8 in its bounds.
//
// To this end, we use an RAII guard (to protect against panics) which updates
// the length of the string when it is dropped. This guard initially truncates
// the string to the prior length and only after we've validated that the
// new contents are valid UTF-8 do we allow it to set a longer length.
//
// The unsafety in this function is twofold:
//
// 1. We're looking at the raw bytes of `buf`, so we take on the burden of UTF-8
// checks.
// 2. We're passing a raw buffer to the function `f`, and it is expected that
// the function only *appends* bytes to the buffer. We'll get undefined
// behavior if existing bytes are overwritten to have non-UTF-8 data.
fn append_to_string<F>(buf: &mut String, f: F) -> Result<usize>
where
F: FnOnce(&mut Vec<u8>) -> Result<usize>,
{
unsafe {
let mut g = Guard { len: buf.len(), buf: buf.as_mut_vec() };
let ret = f(g.buf);
if str::from_utf8(&g.buf[g.len..]).is_err() {
ret.and_then(|_| {
Err(Error::new(ErrorKind::InvalidData, "stream did not contain valid UTF-8"))
})
} else {
g.len = g.buf.len();
ret
}
}
}
// This uses an adaptive system to extend the vector when it fills. We want to
// avoid paying to allocate and zero a huge chunk of memory if the reader only
// has 4 bytes while still making large reads if the reader does have a ton
// of data to return. Simply tacking on an extra DEFAULT_BUF_SIZE space every
// time is 4,500 times (!) slower than a default reservation size of 32 if the
// reader has a very small amount of data to return.
//
// Because we're extending the buffer with uninitialized data for trusted
// readers, we need to make sure to truncate that if any of this panics.
fn read_to_end<R: Read + ?Sized>(r: &mut R, buf: &mut Vec<u8>) -> Result<usize> {
read_to_end_with_reservation(r, buf, |_| 32)
}
fn read_to_end_with_reservation<R, F>(
r: &mut R,
buf: &mut Vec<u8>,
mut reservation_size: F,
) -> Result<usize>
where
R: Read + ?Sized,
F: FnMut(&R) -> usize,
{
let start_len = buf.len();
let mut g = Guard { len: buf.len(), buf };
let ret;
loop {
if g.len == g.buf.len() {
unsafe {
// FIXME(danielhenrymantilla): #42788
//
// - This creates a (mut) reference to a slice of
// _uninitialized_ integers, which is **undefined behavior**
//
// - Only the standard library gets to soundly "ignore" this,
// based on its privileged knowledge of unstable rustc
// internals;
g.buf.reserve(reservation_size(r));
let capacity = g.buf.capacity();
g.buf.set_len(capacity);
r.initializer().initialize(&mut g.buf[g.len..]);
}
}
match r.read(&mut g.buf[g.len..]) {
Ok(0) => {
ret = Ok(g.len - start_len);
break;
}
Ok(n) => g.len += n,
Err(ref e) if e.kind() == ErrorKind::Interrupted => {}
Err(e) => {
ret = Err(e);
break;
}
}
}
ret
}
pub(crate) fn default_read_vectored<F>(read: F, bufs: &mut [IoSliceMut<'_>]) -> Result<usize>
where
F: FnOnce(&mut [u8]) -> Result<usize>,
{
let buf = bufs.iter_mut().find(|b| !b.is_empty()).map_or(&mut [][..], |b| &mut **b);
read(buf)
}
pub(crate) fn default_write_vectored<F>(write: F, bufs: &[IoSlice<'_>]) -> Result<usize>
where
F: FnOnce(&[u8]) -> Result<usize>,
{
let buf = bufs.iter().find(|b| !b.is_empty()).map_or(&[][..], |b| &**b);
write(buf)
}
/// The `Read` trait allows for reading bytes from a source.
///
/// Implementors of the `Read` trait are called 'readers'.
///
/// Readers are defined by one required method, [`read()`]. Each call to [`read()`]
/// will attempt to pull bytes from this source into a provided buffer. A
/// number of other methods are implemented in terms of [`read()`], giving
/// implementors a number of ways to read bytes while only needing to implement
/// a single method.
///
/// Readers are intended to be composable with one another. Many implementors
/// throughout [`std::io`] take and provide types which implement the `Read`
/// trait.
///
/// Please note that each call to [`read()`] may involve a system call, and
/// therefore, using something that implements [`BufRead`], such as
/// [`BufReader`], will be more efficient.
///
pub trait Read {
/// Pull some bytes from this source into the specified buffer, returning
/// how many bytes were read.
///
/// This function does not provide any guarantees about whether it blocks
/// waiting for data, but if an object needs to block for a read and cannot,
/// it will typically signal this via an [`Err`] return value.
///
/// If the return value of this method is [`Ok(n)`], then it must be
/// guaranteed that `0 <= n <= buf.len()`. A nonzero `n` value indicates
/// that the buffer `buf` has been filled in with `n` bytes of data from this
/// source. If `n` is `0`, then it can indicate one of two scenarios:
///
/// 1. This reader has reached its "end of file" and will likely no longer
/// be able to produce bytes. Note that this does not mean that the
/// reader will *always* no longer be able to produce bytes.
/// 2. The buffer specified was 0 bytes in length.
///
/// No guarantees are provided about the contents of `buf` when this
/// function is called, implementations cannot rely on any property of the
/// contents of `buf` being true. It is recommended that *implementations*
/// only write data to `buf` instead of reading its contents.
///
/// Correspondingly, however, *callers* of this method may not assume any guarantees
/// about how the implementation uses `buf`. The trait is safe to implement,
/// so it is possible that the code that's supposed to write to the buffer might also read
/// from it. It is your responsibility to make sure that `buf` is initialized
/// before calling `read`. Calling `read` with an uninitialized `buf` (of the kind one
/// obtains via [`MaybeUninit<T>`]) is not safe, and can lead to undefined behavior.
///
/// [`MaybeUninit<T>`]: ../mem/union.MaybeUninit.html
///
/// # Errors
///
/// If this function encounters any form of I/O or other error, an error
/// variant will be returned. If an error is returned then it must be
/// guaranteed that no bytes were read.
///
/// An error of the [`ErrorKind::Interrupted`] kind is non-fatal and the read
/// operation should be retried if there is nothing else to do.
///
fn read(&mut self, buf: &mut [u8]) -> Result<usize>;
/// Like `read`, except that it reads into a slice of buffers.
///
/// Data is copied to fill each buffer in order, with the final buffer
/// written to possibly being only partially filled. This method must behave
/// as a single call to `read` with the buffers concatenated would.
///
/// The default implementation calls `read` with either the first nonempty
/// buffer provided, or an empty one if none exists.
fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result<usize> {
default_read_vectored(|b| self.read(b), bufs)
}
/// Determines if this `Read`er can work with buffers of uninitialized
/// memory.
///
/// The default implementation returns an initializer which will zero
/// buffers.
///
/// If a `Read`er guarantees that it can work properly with uninitialized
/// memory, it should call [`Initializer::nop()`]. See the documentation for
/// [`Initializer`] for details.
///
/// The behavior of this method must be independent of the state of the
/// `Read`er - the method only takes `&self` so that it can be used through
/// trait objects.
///
/// # Safety
///
/// This method is unsafe because a `Read`er could otherwise return a
/// non-zeroing `Initializer` from another `Read` type without an `unsafe`
/// block.
///
/// [`Initializer::nop()`]: ../../std/io/struct.Initializer.html#method.nop
/// [`Initializer`]: ../../std/io/struct.Initializer.html
#[inline]
unsafe fn initializer(&self) -> Initializer {
Initializer::zeroing()
}
/// Read all bytes until EOF in this source, placing them into `buf`.
///
/// All bytes read from this source will be appended to the specified buffer
/// `buf`. This function will continuously call [`read()`] to append more data to
/// `buf` until [`read()`] returns either [`Ok(0)`] or an error of
/// non-[`ErrorKind::Interrupted`] kind.
///
/// If successful, this function will return the total number of bytes read.
///
/// # Errors
///
/// If this function encounters an error of the kind
/// [`ErrorKind::Interrupted`] then the error is ignored and the operation
/// will continue.
///
/// If any other read error is encountered then this function immediately
/// returns. Any bytes which have already been read will be appended to
/// `buf`.
///
fn read_to_end(&mut self, buf: &mut Vec<u8>) -> Result<usize> {
read_to_end(self, buf)
}
/// Read all bytes until EOF in this source, appending them to `buf`.
///
/// If successful, this function returns the number of bytes which were read
/// and appended to `buf`.
///
/// # Errors
///
/// If the data in this stream is *not* valid UTF-8 then an error is
/// returned and `buf` is unchanged.
///
/// See [`read_to_end`][readtoend] for other error semantics.
///
/// [readtoend]: #method.read_to_end
///
fn read_to_string(&mut self, buf: &mut String) -> Result<usize> {
// Note that we do *not* call `.read_to_end()` here. We are passing
// `&mut Vec<u8>` (the raw contents of `buf`) into the `read_to_end`
// method to fill it up. An arbitrary implementation could overwrite the
// entire contents of the vector, not just append to it (which is what
// we are expecting).
//
// To prevent extraneously checking the UTF-8-ness of the entire buffer
// we pass it to our hardcoded `read_to_end` implementation which we
// know is guaranteed to only read data into the end of the buffer.
append_to_string(buf, |b| read_to_end(self, b))
}
/// Read the exact number of bytes required to fill `buf`.
///
/// This function reads as many bytes as necessary to completely fill the
/// specified buffer `buf`.
///
/// No guarantees are provided about the contents of `buf` when this
/// function is called, implementations cannot rely on any property of the
/// contents of `buf` being true. It is recommended that implementations
/// only write data to `buf` instead of reading its contents.
///
/// # Errors
///
/// If this function encounters an error of the kind
/// [`ErrorKind::Interrupted`] then the error is ignored and the operation
/// will continue.
///
/// If this function encounters an "end of file" before completely filling
/// the buffer, it returns an error of the kind [`ErrorKind::UnexpectedEof`].
/// The contents of `buf` are unspecified in this case.
///
/// If any other read error is encountered then this function immediately
/// returns. The contents of `buf` are unspecified in this case.
///
/// If this function returns an error, it is unspecified how many bytes it
/// has read, but it will never read more than would be necessary to
/// completely fill the buffer.
///
fn read_exact(&mut self, mut buf: &mut [u8]) -> Result<()> {
while !buf.is_empty() {
match self.read(buf) {
Ok(0) => break,
Ok(n) => {
let tmp = buf;
buf = &mut tmp[n..];
}
Err(ref e) if e.kind() == ErrorKind::Interrupted => {}
Err(e) => return Err(e),
}
}
if !buf.is_empty() {
Err(Error::new(ErrorKind::UnexpectedEof, "failed to fill whole buffer"))
} else {
Ok(())
}
}
/// Creates a "by reference" adaptor for this instance of `Read`.
///
/// The returned adaptor also implements `Read` and will simply borrow this
/// current reader.
///
fn by_ref(&mut self) -> &mut Self
where
Self: Sized,
{
self
}
/// Transforms this `Read` instance to an [`Iterator`] over its bytes.
///
/// The returned type implements [`Iterator`] where the `Item` is
/// [`Result`]`<`[`u8`]`, `[`io::Error`]`>`.
/// The yielded item is [`Ok`] if a byte was successfully read and [`Err`]
/// otherwise. EOF is mapped to returning [`None`] from this iterator.
///
fn bytes(self) -> Bytes<Self>
where
Self: Sized,
{
Bytes { inner: self }
}
/// Creates an adaptor which will chain this stream with another.
///
/// The returned `Read` instance will first read all bytes from this object
/// until EOF is encountered. Afterwards the output is equivalent to the
/// output of `next`.
///
fn chain<R: Read>(self, next: R) -> Chain<Self, R>
where
Self: Sized,
{
Chain { first: self, second: next, done_first: false }
}
/// Creates an adaptor which will read at most `limit` bytes from it.
///
/// This function returns a new instance of `Read` which will read at most
/// `limit` bytes, after which it will always return EOF ([`Ok(0)`]). Any
/// read errors will not count towards the number of bytes read and future
/// calls to [`read()`] may succeed.
///
fn take(self, limit: u64) -> Take<Self>
where
Self: Sized,
{
Take { inner: self, limit }
}
}
/// A buffer type used with `Read::read_vectored`.
///
/// It is semantically a wrapper around an `&mut [u8]`, but is guaranteed to be
/// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on
/// Windows.
#[repr(transparent)]
pub struct IoSliceMut<'a>(sys::io::IoSliceMut<'a>);
unsafe impl<'a> Send for IoSliceMut<'a> {}
unsafe impl<'a> Sync for IoSliceMut<'a> {}
impl<'a> fmt::Debug for IoSliceMut<'a> {
fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
fmt::Debug::fmt(self.0.as_slice(), fmt)
}
}
impl<'a> IoSliceMut<'a> {
/// Creates a new `IoSliceMut` wrapping a byte slice.
///
/// # Panics
///
/// Panics on Windows if the slice is larger than 4GB.
#[inline]
pub fn new(buf: &'a mut [u8]) -> IoSliceMut<'a> {
IoSliceMut(sys::io::IoSliceMut::new(buf))
}
/// Advance the internal cursor of the slice.
///
/// # Notes
///
/// Elements in the slice may be modified if the cursor is not advanced to
/// the end of the slice. For example if we have a slice of buffers with 2
/// `IoSliceMut`s, both of length 8, and we advance the cursor by 10 bytes
/// the first `IoSliceMut` will be untouched however the second will be
/// modified to remove the first 2 bytes (10 - 8).
///
#[inline]
pub fn advance<'b>(bufs: &'b mut [IoSliceMut<'a>], n: usize) -> &'b mut [IoSliceMut<'a>] {
// Number of buffers to remove.
let mut remove = 0;
// Total length of all the to be removed buffers.
let mut accumulated_len = 0;
for buf in bufs.iter() {
if accumulated_len + buf.len() > n {
break;
} else {
accumulated_len += buf.len();
remove += 1;
}
}
let bufs = &mut bufs[remove..];
if !bufs.is_empty() {
bufs[0].0.advance(n - accumulated_len)
}
bufs
}
}
impl<'a> Deref for IoSliceMut<'a> {
type Target = [u8];
#[inline]
fn deref(&self) -> &[u8] {
self.0.as_slice()
}
}
impl<'a> DerefMut for IoSliceMut<'a> {
#[inline]
fn deref_mut(&mut self) -> &mut [u8] {
self.0.as_mut_slice()
}
}
/// A buffer type used with `Write::write_vectored`.
///
/// It is semantically a wrapper around an `&[u8]`, but is guaranteed to be
/// ABI compatible with the `iovec` type on Unix platforms and `WSABUF` on
/// Windows.
#[derive(Copy, Clone)]
#[repr(transparent)]
pub struct IoSlice<'a>(sys::io::IoSlice<'a>);
unsafe impl<'a> Send for IoSlice<'a> {}
unsafe impl<'a> Sync for IoSlice<'a> {}
impl<'a> fmt::Debug for IoSlice<'a> {
fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
fmt::Debug::fmt(self.0.as_slice(), fmt)
}
}
impl<'a> IoSlice<'a> {
/// Creates a new `IoSlice` wrapping a byte slice.
///
/// # Panics
///
/// Panics on Windows if the slice is larger than 4GB.
#[inline]
pub fn new(buf: &'a [u8]) -> IoSlice<'a> {
IoSlice(sys::io::IoSlice::new(buf))
}
/// Advance the internal cursor of the slice.
///
/// # Notes
///
/// Elements in the slice may be modified if the cursor is not advanced to
/// the end of the slice. For example if we have a slice of buffers with 2
/// `IoSlice`s, both of length 8, and we advance the cursor by 10 bytes the
/// first `IoSlice` will be untouched however the second will be modified to
/// remove the first 2 bytes (10 - 8).
///
#[inline]
pub fn advance<'b>(bufs: &'b mut [IoSlice<'a>], n: usize) -> &'b mut [IoSlice<'a>] {
// Number of buffers to remove.
let mut remove = 0;
// Total length of all the to be removed buffers.
let mut accumulated_len = 0;
for buf in bufs.iter() {
if accumulated_len + buf.len() > n {
break;
} else {
accumulated_len += buf.len();
remove += 1;
}
}
let bufs = &mut bufs[remove..];
if !bufs.is_empty() {
bufs[0].0.advance(n - accumulated_len)
}
bufs
}
}
impl<'a> Deref for IoSlice<'a> {
type Target = [u8];
#[inline]
fn deref(&self) -> &[u8] {
self.0.as_slice()
}
}
/// A type used to conditionally initialize buffers passed to `Read` methods.
#[derive(Debug)]
pub struct Initializer(bool);
impl Initializer {
/// Returns a new `Initializer` which will zero out buffers.
#[inline]
pub fn zeroing() -> Initializer {
Initializer(true)
}
/// Returns a new `Initializer` which will not zero out buffers.
///
/// # Safety
///
/// This may only be called by `Read`ers which guarantee that they will not
/// read from buffers passed to `Read` methods, and that the return value of
/// the method accurately reflects the number of bytes that have been
/// written to the head of the buffer.
#[inline]
pub unsafe fn nop() -> Initializer {
Initializer(false)
}
/// Indicates if a buffer should be initialized.
#[inline]
pub fn should_initialize(&self) -> bool {
self.0
}
/// Initializes a buffer if necessary.
#[inline]
pub fn initialize(&self, buf: &mut [u8]) {
if self.should_initialize() {
unsafe { ptr::write_bytes(buf.as_mut_ptr(), 0, buf.len()) }
}
}
}
/// A trait for objects which are byte-oriented sinks.
///
/// Implementors of the `Write` trait are sometimes called 'writers'.
///
/// Writers are defined by two required methods, [`write`] and [`flush`]:
///
/// * The [`write`] method will attempt to write some data into the object,
/// returning how many bytes were successfully written.
///
/// * The [`flush`] method is useful for adaptors and explicit buffers
/// themselves for ensuring that all buffered data has been pushed out to the
/// 'true sink'.
///
/// Writers are intended to be composable with one another. Many implementors
/// throughout [`std::io`] take and provide types which implement the `Write`
/// trait.
///
/// [`write`]: #tymethod.write
/// [`flush`]: #tymethod.flush
/// [`std::io`]: index.html
///
pub trait Write {
/// Write a buffer into this writer, returning how many bytes were written.
///
/// This function will attempt to write the entire contents of `buf`, but
/// the entire write may not succeed, or the write may also generate an
/// error. A call to `write` represents *at most one* attempt to write to
/// any wrapped object.
///
/// Calls to `write` are not guaranteed to block waiting for data to be
/// written, and a write which would otherwise block can be indicated through
/// an [`Err`] variant.
///
/// If the return value is [`Ok(n)`] then it must be guaranteed that
/// `n <= buf.len()`. A return value of `0` typically means that the
/// underlying object is no longer able to accept bytes and will likely not
/// be able to in the future as well, or that the buffer provided is empty.
///
/// # Errors
///
/// Each call to `write` may generate an I/O error indicating that the
/// operation could not be completed. If an error is returned then no bytes
/// in the buffer were written to this writer.
///
/// It is **not** considered an error if the entire buffer could not be
/// written to this writer.
///
/// An error of the [`ErrorKind::Interrupted`] kind is non-fatal and the
/// write operation should be retried if there is nothing else to do.
///
/// [`Err`]: ../../std/result/enum.Result.html#variant.Err
/// [`Ok(n)`]: ../../std/result/enum.Result.html#variant.Ok
/// [`ErrorKind::Interrupted`]: ../../std/io/enum.ErrorKind.html#variant.Interrupted
///
fn write(&mut self, buf: &[u8]) -> Result<usize>;
/// Like `write`, except that it writes from a slice of buffers.
///
/// Data is copied from each buffer in order, with the final buffer
/// read from possibly being only partially consumed. This method must
/// behave as a call to `write` with the buffers concatenated would.
///
/// The default implementation calls `write` with either the first nonempty
/// buffer provided, or an empty one if none exists.
fn write_vectored(&mut self, bufs: &[IoSlice<'_>]) -> Result<usize> {
default_write_vectored(|b| self.write(b), bufs)
}
/// Flush this output stream, ensuring that all intermediately buffered
/// contents reach their destination.
///
/// # Errors
///
/// It is considered an error if not all bytes could be written due to
/// I/O errors or EOF being reached.
///
fn flush(&mut self) -> Result<()>;
/// Attempts to write an entire buffer into this writer.
///
/// This method will continuously call [`write`] until there is no more data
/// to be written or an error of non-[`ErrorKind::Interrupted`] kind is
/// returned. This method will not return until the entire buffer has been
/// successfully written or such an error occurs. The first error that is
/// not of [`ErrorKind::Interrupted`] kind generated from this method will be
/// returned.
///
/// If the buffer contains no data, this will never call [`write`].
///
/// # Errors
///
/// This function will return the first error of
/// non-[`ErrorKind::Interrupted`] kind that [`write`] returns.
///
/// [`ErrorKind::Interrupted`]: ../../std/io/enum.ErrorKind.html#variant.Interrupted
/// [`write`]: #tymethod.write
///
fn write_all(&mut self, mut buf: &[u8]) -> Result<()> {
while !buf.is_empty() {
match self.write(buf) {
Ok(0) => {
return Err(Error::new(ErrorKind::WriteZero, "failed to write whole buffer"));
}
Ok(n) => buf = &buf[n..],
Err(ref e) if e.kind() == ErrorKind::Interrupted => {}
Err(e) => return Err(e),
}
}
Ok(())
}
/// Attempts to write multiple buffers into this writer.
///
/// This method will continuously call [`write_vectored`] until there is no
/// more data to be written or an error of non-[`ErrorKind::Interrupted`]
/// kind is returned. This method will not return until all buffers have
/// been successfully written or such an error occurs. The first error that
/// is not of [`ErrorKind::Interrupted`] kind generated from this method
/// will be returned.
///
/// If the buffer contains no data, this will never call [`write_vectored`].
///
/// [`write_vectored`]: #method.write_vectored
/// [`ErrorKind::Interrupted`]: ../../std/io/enum.ErrorKind.html#variant.Interrupted
///
/// # Notes
///
///
/// Unlike `io::Write::write_vectored`, this takes a *mutable* reference to
/// a slice of `IoSlice`s, not an immutable one. That's because we need to
/// modify the slice to keep track of the bytes already written.
///
/// Once this function returns, the contents of `bufs` are unspecified, as
/// this depends on how many calls to `write_vectored` were necessary. It is
/// best to understand this function as taking ownership of `bufs` and to
/// not use `bufs` afterwards. The underlying buffers, to which the
/// `IoSlice`s point (but not the `IoSlice`s themselves), are unchanged and
/// can be reused.
///
fn write_all_vectored(&mut self, mut bufs: &mut [IoSlice<'_>]) -> Result<()> {
while !bufs.is_empty() {
match self.write_vectored(bufs) {
Ok(0) => {
return Err(Error::new(ErrorKind::WriteZero, "failed to write whole buffer"));
}
Ok(n) => bufs = IoSlice::advance(mem::take(&mut bufs), n),
Err(ref e) if e.kind() == ErrorKind::Interrupted => {}
Err(e) => return Err(e),
}
}
Ok(())
}
/// Writes a formatted string into this writer, returning any error
/// encountered.
///
/// This method is primarily used to interface with the
/// [`format_args!`][formatargs] macro, but it is rare that this should
/// explicitly be called. The [`write!`][write] macro should be favored to
/// invoke this method instead.
///
/// [formatargs]: ../macro.format_args.html
/// [write]: ../macro.write.html
///
/// This function internally uses the [`write_all`][writeall] method on
/// this trait and hence will continuously write data so long as no errors
/// are received. This also means that partial writes are not indicated in
/// this signature.
///
/// [writeall]: #method.write_all
///
/// # Errors
///
/// This function will return any I/O error reported while formatting.
///
fn write_fmt(&mut self, fmt: fmt::Arguments<'_>) -> Result<()> {
// Create a shim which translates a Write to a fmt::Write and saves
// off I/O errors. instead of discarding them
struct Adaptor<'a, T: ?Sized + 'a> {
inner: &'a mut T,
error: Result<()>,
}
impl<T: Write + ?Sized> fmt::Write for Adaptor<'_, T> {
fn write_str(&mut self, s: &str) -> fmt::Result {
match self.inner.write_all(s.as_bytes()) {
Ok(()) => Ok(()),
Err(e) => {
self.error = Err(e);
Err(fmt::Error)
}
}
}
}
let mut output = Adaptor { inner: self, error: Ok(()) };
match fmt::write(&mut output, fmt) {
Ok(()) => Ok(()),
Err(..) => {
// check if the error came from the underlying `Write` or not
if output.error.is_err() {
output.error
} else {
Err(Error::new(ErrorKind::Other, "formatter error"))
}
}
}
}
/// Creates a "by reference" adaptor for this instance of `Write`.
///
/// The returned adaptor also implements `Write` and will simply borrow this
/// current writer.
///
fn by_ref(&mut self) -> &mut Self
where
Self: Sized,
{
self
}
}
/// The `Seek` trait provides a cursor which can be moved within a stream of
/// bytes.
///
/// The stream typically has a fixed size, allowing seeking relative to either
/// end or the current offset.
///
pub trait Seek {
/// Seek to an offset, in bytes, in a stream.
///
/// A seek beyond the end of a stream is allowed, but behavior is defined
/// by the implementation.
///
/// If the seek operation completed successfully,
/// this method returns the new position from the start of the stream.
/// That position can be used later with [`SeekFrom::Start`].
///
/// # Errors
///
/// Seeking to a negative offset is considered an error.
///
/// [`SeekFrom::Start`]: enum.SeekFrom.html#variant.Start
fn seek(&mut self, pos: SeekFrom) -> Result<u64>;
/// Returns the length of this stream (in bytes).
///
/// This method is implemented using up to three seek operations. If this
/// method returns successfully, the seek position is unchanged (i.e. the
/// position before calling this method is the same as afterwards).
/// However, if this method returns an error, the seek position is
/// unspecified.
///
/// If you need to obtain the length of *many* streams and you don't care
/// about the seek position afterwards, you can reduce the number of seek
/// operations by simply calling `seek(SeekFrom::End(0))` and using its
/// return value (it is also the stream length).
///
/// Note that length of a stream can change over time (for example, when
/// data is appended to a file). So calling this method multiple times does
/// not necessarily return the same length each time.
///
fn stream_len(&mut self) -> Result<u64> {
let old_pos = self.stream_position()?;
let len = self.seek(SeekFrom::End(0))?;
// Avoid seeking a third time when we were already at the end of the
// stream. The branch is usually way cheaper than a seek operation.
if old_pos != len {
self.seek(SeekFrom::Start(old_pos))?;
}
Ok(len)
}
/// Returns the current seek position from the start of the stream.
///
/// This is equivalent to `self.seek(SeekFrom::Current(0))`.
///
fn stream_position(&mut self) -> Result<u64> {
self.seek(SeekFrom::Current(0))
}
}
/// Enumeration of possible methods to seek within an I/O object.
///
/// It is used by the [`Seek`] trait.
///
/// [`Seek`]: trait.Seek.html
#[derive(Copy, PartialEq, Eq, Clone, Debug)]
pub enum SeekFrom {
/// Sets the offset to the provided number of bytes.
Start(u64),
/// Sets the offset to the size of this object plus the specified number of
/// bytes.
///
/// It is possible to seek beyond the end of an object, but it's an error to
/// seek before byte 0.
End(i64),
/// Sets the offset to the current position plus the specified number of
/// bytes.
///
/// It is possible to seek beyond the end of an object, but it's an error to
/// seek before byte 0.
Current(i64),
}
fn read_until<R: BufRead + ?Sized>(r: &mut R, delim: u8, buf: &mut Vec<u8>) -> Result<usize> {
let mut read = 0;
loop {
let (done, used) = {
let available = match r.fill_buf() {
Ok(n) => n,
Err(ref e) if e.kind() == ErrorKind::Interrupted => continue,
Err(e) => return Err(e),
};
match memchr::memchr(delim, available) {
Some(i) => {
buf.extend_from_slice(&available[..=i]);
(true, i + 1)
}
None => {
buf.extend_from_slice(available);
(false, available.len())
}
}
};
r.consume(used);
read += used;
if done || used == 0 {
return Ok(read);
}
}
}
/// A `BufRead` is a type of `Read`er which has an internal buffer, allowing it
/// to perform extra ways of reading.
///
/// For example, reading line-by-line is inefficient without using a buffer, so
/// if you want to read by line, you'll need `BufRead`, which includes a
/// [`read_line`] method as well as a [`lines`] iterator.
///
pub trait BufRead: Read {
/// Returns the contents of the internal buffer, filling it with more data
/// from the inner reader if it is empty.
///
/// This function is a lower-level call. It needs to be paired with the
/// [`consume`] method to function properly. When calling this
/// method, none of the contents will be "read" in the sense that later
/// calling `read` may return the same contents. As such, [`consume`] must
/// be called with the number of bytes that are consumed from this buffer to
/// ensure that the bytes are never returned twice.
///
/// [`consume`]: #tymethod.consume
///
/// An empty buffer returned indicates that the stream has reached EOF.
///
/// # Errors
///
/// This function will return an I/O error if the underlying reader was
/// read, but returned an error.
///
fn fill_buf(&mut self) -> Result<&[u8]>;
/// Tells this buffer that `amt` bytes have been consumed from the buffer,
/// so they should no longer be returned in calls to `read`.
///
/// This function is a lower-level call. It needs to be paired with the
/// [`fill_buf`] method to function properly. This function does
/// not perform any I/O, it simply informs this object that some amount of
/// its buffer, returned from [`fill_buf`], has been consumed and should
/// no longer be returned. As such, this function may do odd things if
/// [`fill_buf`] isn't called before calling it.
///
/// The `amt` must be `<=` the number of bytes in the buffer returned by
/// [`fill_buf`].
///
fn consume(&mut self, amt: usize);
/// Read all bytes into `buf` until the delimiter `byte` or EOF is reached.
///
/// This function will read bytes from the underlying stream until the
/// delimiter or EOF is found. Once found, all bytes up to, and including,
/// the delimiter (if found) will be appended to `buf`.
///
/// If successful, this function will return the total number of bytes read.
///
/// # Errors
///
/// This function will ignore all instances of [`ErrorKind::Interrupted`] and
/// will otherwise return any errors returned by [`fill_buf`].
///
/// If an I/O error is encountered then all bytes read so far will be
/// present in `buf` and its length will have been adjusted appropriately.
///
/// [`fill_buf`]: #tymethod.fill_buf
/// [`ErrorKind::Interrupted`]: enum.ErrorKind.html#variant.Interrupted
///
fn read_until(&mut self, byte: u8, buf: &mut Vec<u8>) -> Result<usize> {
read_until(self, byte, buf)
}
/// Read all bytes until a newline (the 0xA byte) is reached, and append
/// them to the provided buffer.
///
/// This function will read bytes from the underlying stream until the
/// newline delimiter (the 0xA byte) or EOF is found. Once found, all bytes
/// up to, and including, the delimiter (if found) will be appended to
/// `buf`.
///
/// If successful, this function will return the total number of bytes read.
///
/// If this function returns `Ok(0)`, the stream has reached EOF.
///
/// # Errors
///
/// This function has the same error semantics as [`read_until`] and will
/// also return an error if the read bytes are not valid UTF-8. If an I/O
/// error is encountered then `buf` may contain some bytes already read in
/// the event that all data read so far was valid UTF-8.
///
/// [`read_until`]: #method.read_until
///
fn read_line(&mut self, buf: &mut String) -> Result<usize> {
// Note that we are not calling the `.read_until` method here, but
// rather our hardcoded implementation. For more details as to why, see
// the comments in `read_to_end`.
append_to_string(buf, |b| read_until(self, b'\n', b))
}
/// Returns an iterator over the contents of this reader split on the byte
/// `byte`.
///
/// The iterator returned from this function will return instances of
/// [`io::Result`]`<`[`Vec<u8>`]`>`. Each vector returned will *not* have
/// the delimiter byte at the end.
///
/// This function will yield errors whenever [`read_until`] would have
/// also yielded an error.
///
/// [`io::Result`]: type.Result.html
/// [`Vec<u8>`]: ../vec/struct.Vec.html
/// [`read_until`]: #method.read_until
///
fn split(self, byte: u8) -> Split<Self>
where
Self: Sized,
{
Split { buf: self, delim: byte }
}
/// Returns an iterator over the lines of this reader.
///
/// The iterator returned from this function will yield instances of
/// [`io::Result`]`<`[`String`]`>`. Each string returned will *not* have a newline
/// byte (the 0xA byte) or CRLF (0xD, 0xA bytes) at the end.
///
/// [`io::Result`]: type.Result.html
/// [`String`]: ../string/struct.String.html
///
/// # Errors
///
/// Each line of the iterator has the same error semantics as [`BufRead::read_line`].
///
/// [`BufRead::read_line`]: trait.BufRead.html#method.read_line
fn lines(self) -> Lines<Self>
where
Self: Sized,
{
Lines { buf: self }
}
}
/// Adaptor to chain together two readers.
///
/// This struct is generally created by calling [`chain`] on a reader.
/// Please see the documentation of [`chain`] for more details.
///
/// [`chain`]: trait.Read.html#method.chain
pub struct Chain<T, U> {
first: T,
second: U,
done_first: bool,
}
impl<T, U> Chain<T, U> {
/// Consumes the `Chain`, returning the wrapped readers.
///
pub fn into_inner(self) -> (T, U) {
(self.first, self.second)
}
/// Gets references to the underlying readers in this `Chain`.
///
pub fn get_ref(&self) -> (&T, &U) {
(&self.first, &self.second)
}
/// Gets mutable references to the underlying readers in this `Chain`.
///
/// Care should be taken to avoid modifying the internal I/O state of the
/// underlying readers as doing so may corrupt the internal state of this
/// `Chain`.
///
pub fn get_mut(&mut self) -> (&mut T, &mut U) {
(&mut self.first, &mut self.second)
}
}
impl<T: fmt::Debug, U: fmt::Debug> fmt::Debug for Chain<T, U> {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
f.debug_struct("Chain").field("t", &self.first).field("u", &self.second).finish()
}
}
impl<T: Read, U: Read> Read for Chain<T, U> {
fn read(&mut self, buf: &mut [u8]) -> Result<usize> {
if !self.done_first {
match self.first.read(buf)? {
0 if !buf.is_empty() => self.done_first = true,
n => return Ok(n),
}
}
self.second.read(buf)
}
fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result<usize> {
if !self.done_first {
match self.first.read_vectored(bufs)? {
0 if bufs.iter().any(|b| !b.is_empty()) => self.done_first = true,
n => return Ok(n),
}
}
self.second.read_vectored(bufs)
}
unsafe fn initializer(&self) -> Initializer {
let initializer = self.first.initializer();
if initializer.should_initialize() { initializer } else { self.second.initializer() }
}
}
impl<T: BufRead, U: BufRead> BufRead for Chain<T, U> {
fn fill_buf(&mut self) -> Result<&[u8]> {
if !self.done_first {
match self.first.fill_buf()? {
buf if buf.is_empty() => {
self.done_first = true;
}
buf => return Ok(buf),
}
}
self.second.fill_buf()
}
fn consume(&mut self, amt: usize) {
if !self.done_first { self.first.consume(amt) } else { self.second.consume(amt) }
}
}
/// Reader adaptor which limits the bytes read from an underlying reader.
///
/// This struct is generally created by calling [`take`] on a reader.
/// Please see the documentation of [`take`] for more details.
///
/// [`take`]: trait.Read.html#method.take
#[derive(Debug)]
pub struct Take<T> {
inner: T,
limit: u64,
}
impl<T> Take<T> {
/// Returns the number of bytes that can be read before this instance will
/// return EOF.
///
/// # Note
///
/// This instance may reach `EOF` after reading fewer bytes than indicated by
/// this method if the underlying [`Read`] instance reaches EOF.
///
/// [`Read`]: ../../std/io/trait.Read.html
///
pub fn limit(&self) -> u64 {
self.limit
}
/// Sets the number of bytes that can be read before this instance will
/// return EOF. This is the same as constructing a new `Take` instance, so
/// the amount of bytes read and the previous limit value don't matter when
/// calling this method.
///
pub fn set_limit(&mut self, limit: u64) {
self.limit = limit;
}
/// Consumes the `Take`, returning the wrapped reader.
///
pub fn into_inner(self) -> T {
self.inner
}
/// Gets a reference to the underlying reader.
///
pub fn get_ref(&self) -> &T {
&self.inner
}
/// Gets a mutable reference to the underlying reader.
///
/// Care should be taken to avoid modifying the internal I/O state of the
/// underlying reader as doing so may corrupt the internal limit of this
/// `Take`.
///
pub fn get_mut(&mut self) -> &mut T {
&mut self.inner
}
}
impl<T: Read> Read for Take<T> {
fn read(&mut self, buf: &mut [u8]) -> Result<usize> {
// Don't call into inner reader at all at EOF because it may still block
if self.limit == 0 {
return Ok(0);
}
let max = cmp::min(buf.len() as u64, self.limit) as usize;
let n = self.inner.read(&mut buf[..max])?;
self.limit -= n as u64;
Ok(n)
}
unsafe fn initializer(&self) -> Initializer {
self.inner.initializer()
}
fn read_to_end(&mut self, buf: &mut Vec<u8>) -> Result<usize> {
// Pass in a reservation_size closure that respects the current value
// of limit for each read. If we hit the read limit, this prevents the
// final zero-byte read from allocating again.
read_to_end_with_reservation(self, buf, |self_| cmp::min(self_.limit, 32) as usize)
}
}
impl<T: BufRead> BufRead for Take<T> {
fn fill_buf(&mut self) -> Result<&[u8]> {
// Don't call into inner reader at all at EOF because it may still block
if self.limit == 0 {
return Ok(&[]);
}
let buf = self.inner.fill_buf()?;
let cap = cmp::min(buf.len() as u64, self.limit) as usize;
Ok(&buf[..cap])
}
fn consume(&mut self, amt: usize) {
// Don't let callers reset the limit by passing an overlarge value
let amt = cmp::min(amt as u64, self.limit) as usize;
self.limit -= amt as u64;
self.inner.consume(amt);
}
}
/// An iterator over `u8` values of a reader.
///
/// This struct is generally created by calling [`bytes`] on a reader.
/// Please see the documentation of [`bytes`] for more details.
///
/// [`bytes`]: trait.Read.html#method.bytes
#[derive(Debug)]
pub struct Bytes<R> {
inner: R,
}
impl<R: Read> Iterator for Bytes<R> {
type Item = Result<u8>;
fn next(&mut self) -> Option<Result<u8>> {
let mut byte = 0;
loop {
return match self.inner.read(slice::from_mut(&mut byte)) {
Ok(0) => None,
Ok(..) => Some(Ok(byte)),
Err(ref e) if e.kind() == ErrorKind::Interrupted => continue,
Err(e) => Some(Err(e)),
};
}
}
}
/// An iterator over the contents of an instance of `BufRead` split on a
/// particular byte.
///
/// This struct is generally created by calling [`split`] on a `BufRead`.
/// Please see the documentation of [`split`] for more details.
///
/// [`split`]: trait.BufRead.html#method.split
#[derive(Debug)]
pub struct Split<B> {
buf: B,
delim: u8,
}
impl<B: BufRead> Iterator for Split<B> {
type Item = Result<Vec<u8>>;
fn next(&mut self) -> Option<Result<Vec<u8>>> {
let mut buf = Vec::new();
match self.buf.read_until(self.delim, &mut buf) {
Ok(0) => None,
Ok(_n) => {
if buf[buf.len() - 1] == self.delim {
buf.pop();
}
Some(Ok(buf))
}
Err(e) => Some(Err(e)),
}
}
}
/// An iterator over the lines of an instance of `BufRead`.
///
/// This struct is generally created by calling [`lines`] on a `BufRead`.
/// Please see the documentation of [`lines`] for more details.
///
/// [`lines`]: trait.BufRead.html#method.lines
#[derive(Debug)]
pub struct Lines<B> {
buf: B,
}
impl<B: BufRead> Iterator for Lines<B> {
type Item = Result<String>;
fn next(&mut self) -> Option<Result<String>> {
let mut buf = String::new();
match self.buf.read_line(&mut buf) {
Ok(0) => None,
Ok(_n) => {
if buf.ends_with('\n') {
buf.pop();
if buf.ends_with('\r') {
buf.pop();
}
}
Some(Ok(buf))
}
Err(e) => Some(Err(e)),
}
}
}