use futures_core::future::Future; use futures_core::ready; use futures_core::task::{Context, Poll}; use futures_io::AsyncRead; use std::io; use std::pin::Pin; use std::vec::Vec;
/// Future for the [`read_to_end`](super::AsyncReadExt::read_to_end) method. #[derive(Debug)] #[must_use = "futures do nothing unless you `.await` or poll them"] pubstruct ReadToEnd<'a, R: ?Sized> {
reader: &'a mut R,
buf: &'a mut Vec<u8>,
start_len: usize,
}
impl<R: ?Sized + Unpin> Unpin for ReadToEnd<'_, R> {}
impl Drop for Guard<'_> { fn drop(&mutself) { unsafe { self.buf.set_len(self.len);
}
}
}
// 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 this 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. pub(super) fn read_to_end_internal<R: AsyncRead + ?Sized>( mut rd: Pin<&mut R>,
cx: &mut Context<'_>,
buf: &mut Vec<u8>,
start_len: usize,
) -> Poll<io::Result<usize>> { letmut g = Guard { len: buf.len(), buf }; loop { if g.len == g.buf.len() { unsafe {
g.buf.reserve(32); let capacity = g.buf.capacity();
g.buf.set_len(capacity); super::initialize(&rd, &mut g.buf[g.len..]);
}
}
let buf = &mut g.buf[g.len..]; match ready!(rd.as_mut().poll_read(cx, buf)) {
Ok(0) => return Poll::Ready(Ok(g.len - start_len)),
Ok(n) => { // We can't allow bogus values from read. If it is too large, the returned vec could have its length // set past its capacity, or if it overflows the vec could be shortened which could create an invalid // string if this is called via read_to_string.
assert!(n <= buf.len());
g.len += n;
}
Err(e) => return Poll::Ready(Err(e)),
}
}
}
impl<A> Future for ReadToEnd<'_, A> where
A: AsyncRead + ?Sized + Unpin,
{ type Output = io::Result<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.0.1Bemerkung:
(vorverarbeitet am 2026-06-19)
¤
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.