1
use std::{cell::RefCell, cmp::min, rc::Rc};
2

            
3
use anyhow::Result;
4

            
5
use crate::RwBuilder;
6

            
7
/// Type for building readers and writers on top of a `Vec` in memory.
8
/// It is itself an `RwBuilder`, but can't be created through one.
9
/// This is why we call it a source.
10
#[derive(Debug, Default)]
11
pub struct Builder {
12
    /// The inner `Vec` which is used to write data to and read data from
13
    /// It is shared between the reader and the writer
14
    buffer: Rc<RefCell<Vec<u8>>>,
15
}
16

            
17
impl RwBuilder for Builder {
18
    type Reader = Reader;
19
    type Writer = Writer;
20

            
21
7
    fn reader(&self) -> Result<Self::Reader> {
22
7
        Ok(Reader { buffer: Rc::clone(&self.buffer), bytes_read: 0 })
23
7
    }
24

            
25
7
    fn writer(&self) -> Result<Self::Writer> {
26
7
        Ok(Writer { buffer: Rc::clone(&self.buffer) })
27
7
    }
28
}
29

            
30
/// Reading from a `Vec`
31
#[derive(Debug)]
32
pub struct Reader {
33
    /// The buffer shared between the builder, reader and writer
34
    buffer: Rc<RefCell<Vec<u8>>>,
35
    /// The read position in the buffer
36
    bytes_read: usize,
37
}
38

            
39
impl std::io::Read for Reader {
40
9
    fn read(&mut self, buf: &mut [u8]) -> std::io::Result<usize> {
41
9
        let borrowed = self.buffer.borrow();
42
9
        let byte_count = min(borrowed.len() - self.bytes_read, buf.len());
43
9
        buf[..byte_count].copy_from_slice(&borrowed[self.bytes_read..self.bytes_read + byte_count]);
44
9
        self.bytes_read += byte_count;
45
9
        Ok(byte_count)
46
9
    }
47
}
48

            
49
impl std::io::Write for Writer {
50
13
    fn write(&mut self, buf: &[u8]) -> std::io::Result<usize> {
51
13
        let mut borrowed = self.buffer.borrow_mut();
52
13
        let byte_count = buf.len();
53
13
        borrowed.extend_from_slice(buf);
54
13
        Ok(byte_count)
55
13
    }
56

            
57
7
    fn flush(&mut self) -> std::io::Result<()> {
58
7
        Ok(())
59
7
    }
60
}
61

            
62
/// Writing to a `Vec`
63
#[derive(Debug)]
64
pub struct Writer {
65
    /// The buffer shared between the builder, reader and writer
66
    buffer: Rc<RefCell<Vec<u8>>>,
67
}