Browse Source

Initial commit

master
Colin Reeder 1 year ago
commit
e58a6ef5db
3 changed files with 63 additions and 0 deletions
  1. 3
    0
      .gitignore
  2. 6
    0
      Cargo.toml
  3. 54
    0
      src/lib.rs

+ 3
- 0
.gitignore View File

@@ -0,0 +1,3 @@
/target
**/*.rs.bk
Cargo.lock

+ 6
- 0
Cargo.toml View File

@@ -0,0 +1,6 @@
[package]
name = "peekaboo"
version = "0.1.0"
authors = ["Colin Reeder <vpzomtrrfrt@gmail.com>"]

[dependencies]

+ 54
- 0
src/lib.rs View File

@@ -0,0 +1,54 @@
pub struct Peekaboo<R: std::io::Read> {
reader: R,
buffer: Vec<u8>,
offset: usize,
}

impl<R: std::io::Read> Peekaboo<R> {
pub fn new(reader: R) -> Peekaboo<R> {
Peekaboo {
reader,
buffer: Vec::new(),
offset: 0,
}
}

pub fn peek(&mut self, len: usize) -> std::io::Result<&[u8]> {
let buffered = self.buffer.len() - self.offset;
if buffered < len {
let diff = len - buffered;
let mut buf = vec![0; diff];
self.reader.read_exact(&mut buf)?;
self.buffer.extend_from_slice(&buf);
}
Ok(&self.buffer[self.offset..])
}
}

impl<R: std::io::Read> std::io::Read for Peekaboo<R> {
fn read(&mut self, buf: &mut [u8]) -> std::io::Result<usize> {
let len = buf.len();
if len == 0 {
return Ok(0);
}

let buffered = self.buffer.len() - self.offset;
if buffered > 0 {
if len < buffered {
buf.copy_from_slice(&self.buffer[self.offset..(self.offset + len)]);
self.offset += len;
Ok(len)
}
else {
let (left, _right) = buf.split_at_mut(buffered);
left.copy_from_slice(&self.buffer[self.offset..]);
self.buffer.clear();
self.offset = 0;
Ok(buffered)
}
}
else {
self.reader.read(buf)
}
}
}

Loading…
Cancel
Save