futures_util_io_peek/
lib_io.rs

1use core::{
2    ops::DerefMut,
3    pin::Pin,
4    task::{Context, Poll},
5};
6use std::io;
7
8// ref https://github.com/rust-lang/futures-rs/blob/0.3.5/futures-io/src/lib.rs#L50-L129
9pub trait AsyncPeek {
10    fn poll_peek(
11        self: Pin<&mut Self>,
12        cx: &mut Context<'_>,
13        buf: &mut [u8],
14    ) -> Poll<io::Result<usize>>;
15}
16
17// ref https://github.com/rust-lang/futures-rs/blob/0.3.5/futures-io/src/lib.rs#L321-L396
18macro_rules! deref_async_peek {
19    () => {
20        fn poll_peek(
21            mut self: Pin<&mut Self>,
22            cx: &mut Context<'_>,
23            buf: &mut [u8],
24        ) -> Poll<io::Result<usize>> {
25            Pin::new(&mut **self).poll_peek(cx, buf)
26        }
27    };
28}
29
30impl<T: ?Sized + AsyncPeek + Unpin> AsyncPeek for Box<T> {
31    deref_async_peek!();
32}
33
34impl<T: ?Sized + AsyncPeek + Unpin> AsyncPeek for &mut T {
35    deref_async_peek!();
36}
37
38impl<P> AsyncPeek for Pin<P>
39where
40    P: DerefMut + Unpin,
41    P::Target: AsyncPeek,
42{
43    fn poll_peek(
44        self: Pin<&mut Self>,
45        cx: &mut Context<'_>,
46        buf: &mut [u8],
47    ) -> Poll<io::Result<usize>> {
48        self.get_mut().as_mut().poll_peek(cx, buf)
49    }
50}
51
52// ref https://docs.rs/async-io
53#[cfg(feature = "async_io_async")]
54mod async_io_async {
55    use super::*;
56
57    use core::future::Future as _;
58    use std::net::{TcpStream, UdpSocket};
59
60    use async_io::Async;
61
62    // ref https://docs.rs/async-io/1.12.0/async_io/struct.Async.html#method.peek
63    impl AsyncPeek for Async<TcpStream> {
64        fn poll_peek(
65            self: Pin<&mut Self>,
66            cx: &mut Context<'_>,
67            buf: &mut [u8],
68        ) -> Poll<io::Result<usize>> {
69            let fut = self.peek(buf);
70            futures_util::pin_mut!(fut);
71            fut.poll(cx)
72        }
73    }
74
75    // ref https://docs.rs/async-io/1.12.0/async_io/struct.Async.html#method.peek-1
76    impl AsyncPeek for Async<UdpSocket> {
77        fn poll_peek(
78            self: Pin<&mut Self>,
79            cx: &mut Context<'_>,
80            buf: &mut [u8],
81        ) -> Poll<io::Result<usize>> {
82            let fut = self.peek(buf);
83            futures_util::pin_mut!(fut);
84            fut.poll(cx)
85        }
86    }
87}
88
89// ref https://docs.rs/tokio
90#[cfg(feature = "tokio_tcp_stream")]
91mod tokio_tcp_stream {
92    use super::*;
93
94    use tokio::{io::ReadBuf, net::TcpStream};
95
96    // https://docs.rs/tokio/1.25.0/tokio/net/struct.TcpStream.html#method.peek
97    impl AsyncPeek for TcpStream {
98        fn poll_peek(
99            self: Pin<&mut Self>,
100            cx: &mut Context<'_>,
101            buf: &mut [u8],
102        ) -> Poll<io::Result<usize>> {
103            TcpStream::poll_peek(&self, cx, &mut ReadBuf::new(buf))
104        }
105    }
106}