1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
use compio_buf::{BufResult, IoBufMut};

use crate::{AsyncBufRead, AsyncRead, AsyncWrite, IoResult};

/// An empty reader and writer constructed via [`null`].
#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)]
pub struct Null {
    _p: (),
}

impl AsyncRead for Null {
    async fn read<B: IoBufMut>(&mut self, buf: B) -> compio_buf::BufResult<usize, B> {
        BufResult(Ok(0), buf)
    }
}

impl AsyncBufRead for Null {
    async fn fill_buf(&mut self) -> IoResult<&'_ [u8]> {
        Ok(&[])
    }

    fn consume(&mut self, _: usize) {}
}

impl AsyncWrite for Null {
    async fn write<T: compio_buf::IoBuf>(&mut self, buf: T) -> BufResult<usize, T> {
        BufResult(Ok(0), buf)
    }

    async fn write_vectored<T: compio_buf::IoVectoredBuf>(
        &mut self,
        buf: T,
    ) -> BufResult<usize, T> {
        BufResult(Ok(0), buf)
    }

    async fn flush(&mut self) -> IoResult<()> {
        Ok(())
    }

    async fn shutdown(&mut self) -> IoResult<()> {
        Ok(())
    }
}

/// Create a new [`Null`] reader and writer which acts like a black hole.
///
/// All reads from and writes to this reader will return
/// [`BufResult(Ok(0), buf)`] and leave the buffer unchanged.
///
/// # Examples
///
/// ```
/// use compio_io::{null, AsyncRead, AsyncWrite};
///
/// # compio_runtime::Runtime::new().unwrap().block_on(async {
/// let mut buf = Vec::with_capacity(10);
/// let mut null = null();
///
/// let (num_read, buf) = null.read(buf).await.unwrap();
///
/// assert_eq!(num_read, 0);
/// assert!(buf.is_empty());
///
/// let (num_written, buf) = null.write(buf).await.unwrap();
/// assert_eq!(num_written, 0);
/// # })
/// ```
///
/// [`BufResult(Ok(0), buf)`]: compio_buf::BufResult
#[inline(always)]
pub fn null() -> Null {
    Null { _p: () }
}