Skip to main content

mcproto_codec/
io.rs

1use std::io::{self, Read, Write};
2
3use crate::error::{CodecError, CodecKind};
4
5#[inline]
6pub fn read_exact_counted<R: Read + ?Sized>(
7    reader: &mut R,
8    buffer: &mut [u8],
9    codec: CodecKind,
10    bytes_processed: usize,
11) -> Result<(), CodecError> {
12    let mut current = 0;
13
14    while current < buffer.len() {
15        match reader.read(&mut buffer[current..]) {
16            Ok(0) => {
17                let error = io::Error::new(
18                    io::ErrorKind::UnexpectedEof,
19                    "failed to fill the whole buffer",
20                );
21                return Err(CodecError::from_read_error(
22                    codec,
23                    bytes_processed + current,
24                    error,
25                ));
26            }
27            Ok(read) => current += read,
28            Err(error) if error.kind() == io::ErrorKind::Interrupted => {}
29            Err(error) => {
30                return Err(CodecError::from_read_error(
31                    codec,
32                    bytes_processed + current,
33                    error,
34                ));
35            }
36        }
37    }
38
39    Ok(())
40}
41
42#[inline]
43pub fn write_all_counted<W: Write + ?Sized>(
44    writer: &mut W,
45    buffer: &[u8],
46    codec: CodecKind,
47    bytes_processed: usize,
48) -> Result<(), CodecError> {
49    let mut current = 0;
50
51    while current < buffer.len() {
52        match writer.write(&buffer[current..]) {
53            Ok(0) => {
54                let error =
55                    io::Error::new(io::ErrorKind::WriteZero, "failed to write the whole buffer");
56                return Err(CodecError::from_write_error(
57                    codec,
58                    bytes_processed + current,
59                    error,
60                ));
61            }
62            Ok(written) => current += written,
63            Err(error) if error.kind() == io::ErrorKind::Interrupted => {}
64            Err(error) => {
65                return Err(CodecError::from_write_error(
66                    codec,
67                    bytes_processed + current,
68                    error,
69                ));
70            }
71        }
72    }
73
74    Ok(())
75}