From ad35fbef035da3bc0b18b2042ae19cf7358fec6e Mon Sep 17 00:00:00 2001 From: Carl Lerche Date: Mon, 3 Sep 2018 10:23:00 -0700 Subject: [PATCH] implement `Buf` and `BufMut` for `Either` (#225) --- .travis.yml | 3 ++ Cargo.toml | 1 + src/either.rs | 89 +++++++++++++++++++++++++++++++++++++++++++++++++++ src/lib.rs | 4 +++ 4 files changed, 97 insertions(+) create mode 100644 src/either.rs diff --git a/.travis.yml b/.travis.yml index 3deb61f..2e8ab18 100644 --- a/.travis.yml +++ b/.travis.yml @@ -39,6 +39,9 @@ matrix: # 128 bit numbers - env: EXTRA_ARGS="--features i128" + # `Either` impls + - env: EXTRA_ARGS="--features either" + # WASM support - rust: beta script: diff --git a/Cargo.toml b/Cargo.toml index 9cfed61..af9a794 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -26,6 +26,7 @@ features = ["i128"] byteorder = "1.1.0" iovec = "0.1" serde = { version = "1.0", optional = true } +either = { version = "1.5", default-features = false, optional = true } [dev-dependencies] serde_test = "1.0" diff --git a/src/either.rs b/src/either.rs new file mode 100644 index 0000000..53a2775 --- /dev/null +++ b/src/either.rs @@ -0,0 +1,89 @@ +extern crate either; + +use {Buf, BufMut}; + +use self::either::Either; +use self::either::Either::*; +use iovec::IoVec; + +impl Buf for Either +where + L: Buf, + R: Buf, +{ + fn remaining(&self) -> usize { + match *self { + Left(ref b) => b.remaining(), + Right(ref b) => b.remaining(), + } + } + + fn bytes(&self) -> &[u8] { + match *self { + Left(ref b) => b.bytes(), + Right(ref b) => b.bytes(), + } + } + + fn bytes_vec<'a>(&'a self, dst: &mut [&'a IoVec]) -> usize { + match *self { + Left(ref b) => b.bytes_vec(dst), + Right(ref b) => b.bytes_vec(dst), + } + } + + fn advance(&mut self, cnt: usize) { + match *self { + Left(ref mut b) => b.advance(cnt), + Right(ref mut b) => b.advance(cnt), + } + } + + fn copy_to_slice(&mut self, dst: &mut [u8]) { + match *self { + Left(ref mut b) => b.copy_to_slice(dst), + Right(ref mut b) => b.copy_to_slice(dst), + } + } +} + +impl BufMut for Either +where + L: BufMut, + R: BufMut, +{ + fn remaining_mut(&self) -> usize { + match *self { + Left(ref b) => b.remaining_mut(), + Right(ref b) => b.remaining_mut(), + } + } + + unsafe fn bytes_mut(&mut self) -> &mut [u8] { + match *self { + Left(ref mut b) => b.bytes_mut(), + Right(ref mut b) => b.bytes_mut(), + } + } + + unsafe fn bytes_vec_mut<'a>(&'a mut self, dst: &mut [&'a mut IoVec]) -> usize { + match *self { + Left(ref mut b) => b.bytes_vec_mut(dst), + Right(ref mut b) => b.bytes_vec_mut(dst), + } + } + + unsafe fn advance_mut(&mut self, cnt: usize) { + match *self { + Left(ref mut b) => b.advance_mut(cnt), + Right(ref mut b) => b.advance_mut(cnt), + } + } + + fn put_slice(&mut self, src: &[u8]) { + match *self { + Left(ref mut b) => b.put_slice(src), + Right(ref mut b) => b.put_slice(src), + } + } +} diff --git a/src/lib.rs b/src/lib.rs index eccb8a3..b007940 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -99,3 +99,7 @@ pub use byteorder::{ByteOrder, BigEndian, LittleEndian}; #[cfg(feature = "serde")] #[doc(hidden)] pub mod serde; + +// Optional `Either` support +#[cfg(feature = "either")] +mod either;