mirror of https://git.sr.ht/~stygianentity/bincode
Make Reader and Writer generic on Endianness (#103)
* Make Reader and Writer generic on Endianness * make alternate API modules * add test asserting that big endian encoding is different from little endian encoding * clean up tests
This commit is contained in:
parent
42a8164756
commit
1631cb2d80
58
src/lib.rs
58
src/lib.rs
|
|
@ -43,7 +43,63 @@ extern crate serde as serde_crate;
|
||||||
pub mod refbox;
|
pub mod refbox;
|
||||||
mod serde;
|
mod serde;
|
||||||
|
|
||||||
pub use serde::*;
|
pub mod endian_choice {
|
||||||
|
pub use super::serde::{serialize, serialize_into, deserialize, deserialize_from};
|
||||||
|
}
|
||||||
|
|
||||||
|
use std::io::{Read, Write};
|
||||||
|
|
||||||
|
pub use serde::{Deserializer, Serializer, ErrorKind, Error, Result, serialized_size, serialized_size_bounded};
|
||||||
|
|
||||||
|
/// Deserializes a slice of bytes into an object.
|
||||||
|
///
|
||||||
|
/// This method does not have a size-limit because if you already have the bytes
|
||||||
|
/// in memory, then you don't gain anything by having a limiter.
|
||||||
|
pub fn deserialize<T>(bytes: &[u8]) -> serde::Result<T>
|
||||||
|
where T: serde_crate::Deserialize,
|
||||||
|
{
|
||||||
|
serde::deserialize::<_, byteorder::LittleEndian>(bytes)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Deserializes an object directly from a `Buffer`ed Reader.
|
||||||
|
///
|
||||||
|
/// If the provided `SizeLimit` is reached, the deserialization will bail immediately.
|
||||||
|
/// A SizeLimit can help prevent an attacker from flooding your server with
|
||||||
|
/// a neverending stream of values that runs your server out of memory.
|
||||||
|
///
|
||||||
|
/// If this returns an `Error`, assume that the buffer that you passed
|
||||||
|
/// in is in an invalid state, as the error could be returned during any point
|
||||||
|
/// in the reading.
|
||||||
|
pub fn deserialize_from<R: ?Sized, T>(reader: &mut R, size_limit: SizeLimit) -> serde::Result<T>
|
||||||
|
where R: Read,
|
||||||
|
T: serde_crate::Deserialize,
|
||||||
|
{
|
||||||
|
serde::deserialize_from::<_, _, byteorder::LittleEndian>(reader, size_limit)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Serializes an object directly into a `Writer`.
|
||||||
|
///
|
||||||
|
/// If the serialization would take more bytes than allowed by `size_limit`, an error
|
||||||
|
/// is returned and *no bytes* will be written into the `Writer`.
|
||||||
|
///
|
||||||
|
/// If this returns an `Error` (other than SizeLimit), assume that the
|
||||||
|
/// writer is in an invalid state, as writing could bail out in the middle of
|
||||||
|
/// serializing.
|
||||||
|
pub fn serialize_into<W: ?Sized, T: ?Sized>(writer: &mut W, value: &T, size_limit: SizeLimit) -> serde::Result<()>
|
||||||
|
where W: Write, T: serde_crate::Serialize
|
||||||
|
{
|
||||||
|
serde::serialize_into::<_, _, byteorder::LittleEndian>(writer, value, size_limit)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Serializes a serializable object into a `Vec` of bytes.
|
||||||
|
///
|
||||||
|
/// If the serialization would take more bytes than allowed by `size_limit`,
|
||||||
|
/// an error is returned.
|
||||||
|
pub fn serialize<T: ?Sized>(value: &T, size_limit: SizeLimit) -> serde::Result<Vec<u8>>
|
||||||
|
where T: serde_crate::Serialize
|
||||||
|
{
|
||||||
|
serde::serialize::<_, byteorder::LittleEndian>(value, size_limit)
|
||||||
|
}
|
||||||
|
|
||||||
/// A limit on the amount of bytes that can be read or written.
|
/// A limit on the amount of bytes that can be read or written.
|
||||||
///
|
///
|
||||||
|
|
|
||||||
|
|
@ -6,6 +6,7 @@ use std::io::{Write, Read};
|
||||||
use std::io::Error as IoError;
|
use std::io::Error as IoError;
|
||||||
use std::{error, fmt, result};
|
use std::{error, fmt, result};
|
||||||
use ::SizeLimit;
|
use ::SizeLimit;
|
||||||
|
use byteorder::{ByteOrder};
|
||||||
|
|
||||||
pub use self::reader::{
|
pub use self::reader::{
|
||||||
Deserializer,
|
Deserializer,
|
||||||
|
|
@ -118,9 +119,8 @@ impl serde::ser::Error for Error {
|
||||||
/// If this returns an `Error` (other than SizeLimit), assume that the
|
/// If this returns an `Error` (other than SizeLimit), assume that the
|
||||||
/// writer is in an invalid state, as writing could bail out in the middle of
|
/// writer is in an invalid state, as writing could bail out in the middle of
|
||||||
/// serializing.
|
/// serializing.
|
||||||
pub fn serialize_into<W: ?Sized, T: ?Sized>(writer: &mut W, value: &T, size_limit: SizeLimit) -> Result<()>
|
pub fn serialize_into<W: ?Sized, T: ?Sized, E>(writer: &mut W, value: &T, size_limit: SizeLimit) -> Result<()>
|
||||||
where W: Write,
|
where W: Write, T: serde::Serialize, E: ByteOrder
|
||||||
T: serde::Serialize,
|
|
||||||
{
|
{
|
||||||
match size_limit {
|
match size_limit {
|
||||||
SizeLimit::Infinite => { }
|
SizeLimit::Infinite => { }
|
||||||
|
|
@ -130,7 +130,7 @@ pub fn serialize_into<W: ?Sized, T: ?Sized>(writer: &mut W, value: &T, size_limi
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
let mut serializer = Serializer::new(writer);
|
let mut serializer = Serializer::<_, E>::new(writer);
|
||||||
serde::Serialize::serialize(value, &mut serializer)
|
serde::Serialize::serialize(value, &mut serializer)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -138,7 +138,7 @@ pub fn serialize_into<W: ?Sized, T: ?Sized>(writer: &mut W, value: &T, size_limi
|
||||||
///
|
///
|
||||||
/// If the serialization would take more bytes than allowed by `size_limit`,
|
/// If the serialization would take more bytes than allowed by `size_limit`,
|
||||||
/// an error is returned.
|
/// an error is returned.
|
||||||
pub fn serialize<T: ?Sized>(value: &T, size_limit: SizeLimit) -> Result<Vec<u8>>
|
pub fn serialize<T: ?Sized, E: ByteOrder>(value: &T, size_limit: SizeLimit) -> Result<Vec<u8>>
|
||||||
where T: serde::Serialize
|
where T: serde::Serialize
|
||||||
{
|
{
|
||||||
// Since we are putting values directly into a vector, we can do size
|
// Since we are putting values directly into a vector, we can do size
|
||||||
|
|
@ -152,7 +152,7 @@ pub fn serialize<T: ?Sized>(value: &T, size_limit: SizeLimit) -> Result<Vec<u8>>
|
||||||
SizeLimit::Infinite => Vec::new()
|
SizeLimit::Infinite => Vec::new()
|
||||||
};
|
};
|
||||||
|
|
||||||
try!(serialize_into(&mut writer, value, SizeLimit::Infinite));
|
try!(serialize_into::<_, _, E>(&mut writer, value, SizeLimit::Infinite));
|
||||||
Ok(writer)
|
Ok(writer)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -190,11 +190,11 @@ pub fn serialized_size_bounded<T: ?Sized>(value: &T, max: u64) -> Option<u64>
|
||||||
/// If this returns an `Error`, assume that the buffer that you passed
|
/// If this returns an `Error`, assume that the buffer that you passed
|
||||||
/// in is in an invalid state, as the error could be returned during any point
|
/// in is in an invalid state, as the error could be returned during any point
|
||||||
/// in the reading.
|
/// in the reading.
|
||||||
pub fn deserialize_from<R: ?Sized, T>(reader: &mut R, size_limit: SizeLimit) -> Result<T>
|
pub fn deserialize_from<R: ?Sized, T, E: ByteOrder>(reader: &mut R, size_limit: SizeLimit) -> Result<T>
|
||||||
where R: Read,
|
where R: Read,
|
||||||
T: serde::Deserialize,
|
T: serde::Deserialize,
|
||||||
{
|
{
|
||||||
let mut deserializer = Deserializer::new(reader, size_limit);
|
let mut deserializer = Deserializer::<_, E>::new(reader, size_limit);
|
||||||
serde::Deserialize::deserialize(&mut deserializer)
|
serde::Deserialize::deserialize(&mut deserializer)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -202,9 +202,9 @@ pub fn deserialize_from<R: ?Sized, T>(reader: &mut R, size_limit: SizeLimit) ->
|
||||||
///
|
///
|
||||||
/// This method does not have a size-limit because if you already have the bytes
|
/// This method does not have a size-limit because if you already have the bytes
|
||||||
/// in memory, then you don't gain anything by having a limiter.
|
/// in memory, then you don't gain anything by having a limiter.
|
||||||
pub fn deserialize<T>(bytes: &[u8]) -> Result<T>
|
pub fn deserialize<T, E: ByteOrder>(bytes: &[u8]) -> Result<T>
|
||||||
where T: serde::Deserialize,
|
where T: serde::Deserialize,
|
||||||
{
|
{
|
||||||
let mut reader = bytes;
|
let mut reader = bytes;
|
||||||
deserialize_from(&mut reader, SizeLimit::Infinite)
|
deserialize_from::<_, _, E>(&mut reader, SizeLimit::Infinite)
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,7 @@
|
||||||
use std::io::Read;
|
use std::io::Read;
|
||||||
|
use std::marker::PhantomData;
|
||||||
|
|
||||||
use byteorder::{BigEndian, ReadBytesExt};
|
use byteorder::{ReadBytesExt, ByteOrder};
|
||||||
use serde_crate as serde;
|
use serde_crate as serde;
|
||||||
use serde_crate::de::value::ValueDeserializer;
|
use serde_crate::de::value::ValueDeserializer;
|
||||||
use serde_crate::de::Error as DeError;
|
use serde_crate::de::Error as DeError;
|
||||||
|
|
@ -17,18 +18,20 @@ use super::{Result, Error, ErrorKind};
|
||||||
/// serde::Deserialize::deserialize(&mut deserializer);
|
/// serde::Deserialize::deserialize(&mut deserializer);
|
||||||
/// let bytes_read = d.bytes_read();
|
/// let bytes_read = d.bytes_read();
|
||||||
/// ```
|
/// ```
|
||||||
pub struct Deserializer<R> {
|
pub struct Deserializer<R, E: ByteOrder> {
|
||||||
reader: R,
|
reader: R,
|
||||||
size_limit: SizeLimit,
|
size_limit: SizeLimit,
|
||||||
read: u64
|
read: u64,
|
||||||
|
_phantom: PhantomData<E>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<R: Read> Deserializer<R> {
|
impl<R: Read, E: ByteOrder> Deserializer<R, E> {
|
||||||
pub fn new(r: R, size_limit: SizeLimit) -> Deserializer<R> {
|
pub fn new(r: R, size_limit: SizeLimit) -> Deserializer<R, E> {
|
||||||
Deserializer {
|
Deserializer {
|
||||||
reader: r,
|
reader: r,
|
||||||
size_limit: size_limit,
|
size_limit: size_limit,
|
||||||
read: 0
|
read: 0,
|
||||||
|
_phantom: PhantomData
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -78,14 +81,13 @@ macro_rules! impl_nums {
|
||||||
where V: serde::de::Visitor,
|
where V: serde::de::Visitor,
|
||||||
{
|
{
|
||||||
try!(self.read_type::<$ty>());
|
try!(self.read_type::<$ty>());
|
||||||
let value = try!(self.reader.$reader_method::<BigEndian>());
|
let value = try!(self.reader.$reader_method::<E>());
|
||||||
visitor.$visitor_method(value)
|
visitor.$visitor_method(value)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl<'a, R: Read, E: ByteOrder> serde::Deserializer for &'a mut Deserializer<R, E> {
|
||||||
impl<'a, R: Read> serde::Deserializer for &'a mut Deserializer<R> {
|
|
||||||
type Error = Error;
|
type Error = Error;
|
||||||
|
|
||||||
#[inline]
|
#[inline]
|
||||||
|
|
@ -212,7 +214,7 @@ impl<'a, R: Read> serde::Deserializer for &'a mut Deserializer<R> {
|
||||||
visitor: V) -> Result<V::Value>
|
visitor: V) -> Result<V::Value>
|
||||||
where V: serde::de::Visitor,
|
where V: serde::de::Visitor,
|
||||||
{
|
{
|
||||||
impl<'a, R: Read + 'a> serde::de::EnumVisitor for &'a mut Deserializer<R> {
|
impl<'a, R: Read + 'a, E: ByteOrder> serde::de::EnumVisitor for &'a mut Deserializer<R, E> {
|
||||||
type Error = Error;
|
type Error = Error;
|
||||||
type Variant = Self;
|
type Variant = Self;
|
||||||
|
|
||||||
|
|
@ -233,9 +235,9 @@ impl<'a, R: Read> serde::Deserializer for &'a mut Deserializer<R> {
|
||||||
visitor: V) -> Result<V::Value>
|
visitor: V) -> Result<V::Value>
|
||||||
where V: serde::de::Visitor,
|
where V: serde::de::Visitor,
|
||||||
{
|
{
|
||||||
struct TupleVisitor<'a, R: Read + 'a>(&'a mut Deserializer<R>);
|
struct TupleVisitor<'a, R: Read + 'a, E: ByteOrder + 'a>(&'a mut Deserializer<R, E>);
|
||||||
|
|
||||||
impl<'a, 'b: 'a, R: Read + 'b> serde::de::SeqVisitor for TupleVisitor<'a, R> {
|
impl<'a, 'b: 'a, R: Read + 'b, E: ByteOrder> serde::de::SeqVisitor for TupleVisitor<'a, R, E> {
|
||||||
type Error = Error;
|
type Error = Error;
|
||||||
|
|
||||||
fn visit_seed<T>(&mut self, seed: T) -> Result<Option<T::Value>>
|
fn visit_seed<T>(&mut self, seed: T) -> Result<Option<T::Value>>
|
||||||
|
|
@ -254,12 +256,12 @@ impl<'a, R: Read> serde::Deserializer for &'a mut Deserializer<R> {
|
||||||
visitor: V) -> Result<V::Value>
|
visitor: V) -> Result<V::Value>
|
||||||
where V: serde::de::Visitor,
|
where V: serde::de::Visitor,
|
||||||
{
|
{
|
||||||
struct SeqVisitor<'a, R: Read + 'a> {
|
struct SeqVisitor<'a, R: Read + 'a, E: ByteOrder + 'a> {
|
||||||
deserializer: &'a mut Deserializer<R>,
|
deserializer: &'a mut Deserializer<R, E>,
|
||||||
len: usize,
|
len: usize,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, 'b: 'a, R: Read + 'b> serde::de::SeqVisitor for SeqVisitor<'a, R> {
|
impl<'a, 'b: 'a, R: Read + 'b, E: ByteOrder> serde::de::SeqVisitor for SeqVisitor<'a, R, E> {
|
||||||
type Error = Error;
|
type Error = Error;
|
||||||
|
|
||||||
fn visit_seed<T>(&mut self, seed: T) -> Result<Option<T::Value>>
|
fn visit_seed<T>(&mut self, seed: T) -> Result<Option<T::Value>>
|
||||||
|
|
@ -303,12 +305,12 @@ impl<'a, R: Read> serde::Deserializer for &'a mut Deserializer<R> {
|
||||||
fn deserialize_map<V>(self, visitor: V) -> Result<V::Value>
|
fn deserialize_map<V>(self, visitor: V) -> Result<V::Value>
|
||||||
where V: serde::de::Visitor,
|
where V: serde::de::Visitor,
|
||||||
{
|
{
|
||||||
struct MapVisitor<'a, R: Read + 'a> {
|
struct MapVisitor<'a, R: Read + 'a, E: ByteOrder + 'a> {
|
||||||
deserializer: &'a mut Deserializer<R>,
|
deserializer: &'a mut Deserializer<R, E>,
|
||||||
len: usize,
|
len: usize,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, 'b: 'a, R: Read + 'b> serde::de::MapVisitor for MapVisitor<'a, R> {
|
impl<'a, 'b: 'a, R: Read + 'b, E: ByteOrder> serde::de::MapVisitor for MapVisitor<'a, R, E> {
|
||||||
type Error = Error;
|
type Error = Error;
|
||||||
|
|
||||||
fn visit_key_seed<K>(&mut self, seed: K) -> Result<Option<K::Value>>
|
fn visit_key_seed<K>(&mut self, seed: K) -> Result<Option<K::Value>>
|
||||||
|
|
@ -387,7 +389,7 @@ impl<'a, R: Read> serde::Deserializer for &'a mut Deserializer<R> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, R: Read> serde::de::VariantVisitor for &'a mut Deserializer<R> {
|
impl<'a, R: Read, E: ByteOrder> serde::de::VariantVisitor for &'a mut Deserializer<R, E> {
|
||||||
type Error = Error;
|
type Error = Error;
|
||||||
|
|
||||||
fn visit_unit(self) -> Result<()> {
|
fn visit_unit(self) -> Result<()> {
|
||||||
|
|
|
||||||
|
|
@ -1,9 +1,10 @@
|
||||||
use std::io::Write;
|
use std::io::Write;
|
||||||
use std::u32;
|
use std::u32;
|
||||||
|
use std::marker::PhantomData;
|
||||||
|
|
||||||
use serde_crate as serde;
|
use serde_crate as serde;
|
||||||
|
|
||||||
use byteorder::{BigEndian, WriteBytesExt};
|
use byteorder::{WriteBytesExt, ByteOrder};
|
||||||
|
|
||||||
use super::{Result, Error, ErrorKind};
|
use super::{Result, Error, ErrorKind};
|
||||||
|
|
||||||
|
|
@ -11,14 +12,16 @@ use super::{Result, Error, ErrorKind};
|
||||||
///
|
///
|
||||||
/// This struct should not be used often.
|
/// This struct should not be used often.
|
||||||
/// For most cases, prefer the `encode_into` function.
|
/// For most cases, prefer the `encode_into` function.
|
||||||
pub struct Serializer<W> {
|
pub struct Serializer<W, E: ByteOrder> {
|
||||||
writer: W,
|
writer: W,
|
||||||
|
_phantom: PhantomData<E>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<W: Write> Serializer<W> {
|
impl<W: Write, E: ByteOrder> Serializer<W, E> {
|
||||||
pub fn new(w: W) -> Serializer<W> {
|
pub fn new(w: W) -> Serializer<W, E> {
|
||||||
Serializer {
|
Serializer {
|
||||||
writer: w,
|
writer: w,
|
||||||
|
_phantom: PhantomData,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -31,16 +34,16 @@ impl<W: Write> Serializer<W> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, W: Write> serde::Serializer for &'a mut Serializer<W> {
|
impl<'a, W: Write, E: ByteOrder> serde::Serializer for &'a mut Serializer<W, E> {
|
||||||
type Ok = ();
|
type Ok = ();
|
||||||
type Error = Error;
|
type Error = Error;
|
||||||
type SerializeSeq = Compound<'a, W>;
|
type SerializeSeq = Compound<'a, W, E>;
|
||||||
type SerializeTuple = Compound<'a, W>;
|
type SerializeTuple = Compound<'a, W, E>;
|
||||||
type SerializeTupleStruct = Compound<'a, W>;
|
type SerializeTupleStruct = Compound<'a, W, E>;
|
||||||
type SerializeTupleVariant = Compound<'a, W>;
|
type SerializeTupleVariant = Compound<'a, W, E>;
|
||||||
type SerializeMap = Compound<'a, W>;
|
type SerializeMap = Compound<'a, W, E>;
|
||||||
type SerializeStruct = Compound<'a, W>;
|
type SerializeStruct = Compound<'a, W, E>;
|
||||||
type SerializeStructVariant = Compound<'a, W>;
|
type SerializeStructVariant = Compound<'a, W, E>;
|
||||||
|
|
||||||
fn serialize_unit(self) -> Result<()> { Ok(()) }
|
fn serialize_unit(self) -> Result<()> { Ok(()) }
|
||||||
|
|
||||||
|
|
@ -55,15 +58,15 @@ impl<'a, W: Write> serde::Serializer for &'a mut Serializer<W> {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn serialize_u16(self, v: u16) -> Result<()> {
|
fn serialize_u16(self, v: u16) -> Result<()> {
|
||||||
self.writer.write_u16::<BigEndian>(v).map_err(Into::into)
|
self.writer.write_u16::<E>(v).map_err(Into::into)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn serialize_u32(self, v: u32) -> Result<()> {
|
fn serialize_u32(self, v: u32) -> Result<()> {
|
||||||
self.writer.write_u32::<BigEndian>(v).map_err(Into::into)
|
self.writer.write_u32::<E>(v).map_err(Into::into)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn serialize_u64(self, v: u64) -> Result<()> {
|
fn serialize_u64(self, v: u64) -> Result<()> {
|
||||||
self.writer.write_u64::<BigEndian>(v).map_err(Into::into)
|
self.writer.write_u64::<E>(v).map_err(Into::into)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn serialize_i8(self, v: i8) -> Result<()> {
|
fn serialize_i8(self, v: i8) -> Result<()> {
|
||||||
|
|
@ -71,23 +74,23 @@ impl<'a, W: Write> serde::Serializer for &'a mut Serializer<W> {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn serialize_i16(self, v: i16) -> Result<()> {
|
fn serialize_i16(self, v: i16) -> Result<()> {
|
||||||
self.writer.write_i16::<BigEndian>(v).map_err(Into::into)
|
self.writer.write_i16::<E>(v).map_err(Into::into)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn serialize_i32(self, v: i32) -> Result<()> {
|
fn serialize_i32(self, v: i32) -> Result<()> {
|
||||||
self.writer.write_i32::<BigEndian>(v).map_err(Into::into)
|
self.writer.write_i32::<E>(v).map_err(Into::into)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn serialize_i64(self, v: i64) -> Result<()> {
|
fn serialize_i64(self, v: i64) -> Result<()> {
|
||||||
self.writer.write_i64::<BigEndian>(v).map_err(Into::into)
|
self.writer.write_i64::<E>(v).map_err(Into::into)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn serialize_f32(self, v: f32) -> Result<()> {
|
fn serialize_f32(self, v: f32) -> Result<()> {
|
||||||
self.writer.write_f32::<BigEndian>(v).map_err(Into::into)
|
self.writer.write_f32::<E>(v).map_err(Into::into)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn serialize_f64(self, v: f64) -> Result<()> {
|
fn serialize_f64(self, v: f64) -> Result<()> {
|
||||||
self.writer.write_f64::<BigEndian>(v).map_err(Into::into)
|
self.writer.write_f64::<E>(v).map_err(Into::into)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn serialize_str(self, v: &str) -> Result<()> {
|
fn serialize_str(self, v: &str) -> Result<()> {
|
||||||
|
|
@ -384,12 +387,12 @@ impl<'a> serde::Serializer for &'a mut SizeChecker {
|
||||||
}
|
}
|
||||||
|
|
||||||
#[doc(hidden)]
|
#[doc(hidden)]
|
||||||
pub struct Compound<'a, W: 'a> {
|
pub struct Compound<'a, W: 'a, E: ByteOrder + 'a> {
|
||||||
ser: &'a mut Serializer<W>,
|
ser: &'a mut Serializer<W, E>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, W> serde::ser::SerializeSeq for Compound<'a, W>
|
impl<'a, W, E> serde::ser::SerializeSeq for Compound<'a, W, E>
|
||||||
where W: Write
|
where W: Write, E: ByteOrder
|
||||||
{
|
{
|
||||||
type Ok = ();
|
type Ok = ();
|
||||||
type Error = Error;
|
type Error = Error;
|
||||||
|
|
@ -407,8 +410,8 @@ impl<'a, W> serde::ser::SerializeSeq for Compound<'a, W>
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, W> serde::ser::SerializeTuple for Compound<'a, W>
|
impl<'a, W, E> serde::ser::SerializeTuple for Compound<'a, W, E>
|
||||||
where W: Write
|
where W: Write, E: ByteOrder
|
||||||
{
|
{
|
||||||
type Ok = ();
|
type Ok = ();
|
||||||
type Error = Error;
|
type Error = Error;
|
||||||
|
|
@ -426,8 +429,8 @@ impl<'a, W> serde::ser::SerializeTuple for Compound<'a, W>
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, W> serde::ser::SerializeTupleStruct for Compound<'a, W>
|
impl<'a, W, E> serde::ser::SerializeTupleStruct for Compound<'a, W, E>
|
||||||
where W: Write
|
where W: Write, E: ByteOrder
|
||||||
{
|
{
|
||||||
type Ok = ();
|
type Ok = ();
|
||||||
type Error = Error;
|
type Error = Error;
|
||||||
|
|
@ -445,8 +448,8 @@ impl<'a, W> serde::ser::SerializeTupleStruct for Compound<'a, W>
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, W> serde::ser::SerializeTupleVariant for Compound<'a, W>
|
impl<'a, W, E> serde::ser::SerializeTupleVariant for Compound<'a, W, E>
|
||||||
where W: Write
|
where W: Write, E: ByteOrder
|
||||||
{
|
{
|
||||||
type Ok = ();
|
type Ok = ();
|
||||||
type Error = Error;
|
type Error = Error;
|
||||||
|
|
@ -464,8 +467,8 @@ impl<'a, W> serde::ser::SerializeTupleVariant for Compound<'a, W>
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, W> serde::ser::SerializeMap for Compound<'a, W>
|
impl<'a, W, E> serde::ser::SerializeMap for Compound<'a, W, E>
|
||||||
where W: Write
|
where W: Write, E: ByteOrder
|
||||||
{
|
{
|
||||||
type Ok = ();
|
type Ok = ();
|
||||||
type Error = Error;
|
type Error = Error;
|
||||||
|
|
@ -490,8 +493,8 @@ impl<'a, W> serde::ser::SerializeMap for Compound<'a, W>
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, W> serde::ser::SerializeStruct for Compound<'a, W>
|
impl<'a, W, E> serde::ser::SerializeStruct for Compound<'a, W, E>
|
||||||
where W: Write
|
where W: Write, E: ByteOrder
|
||||||
{
|
{
|
||||||
type Ok = ();
|
type Ok = ();
|
||||||
type Error = Error;
|
type Error = Error;
|
||||||
|
|
@ -509,8 +512,8 @@ impl<'a, W> serde::ser::SerializeStruct for Compound<'a, W>
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, W> serde::ser::SerializeStructVariant for Compound<'a, W>
|
impl<'a, W, E> serde::ser::SerializeStructVariant for Compound<'a, W, E>
|
||||||
where W: Write
|
where W: Write, E: ByteOrder
|
||||||
{
|
{
|
||||||
type Ok = ();
|
type Ok = ();
|
||||||
type Error = Error;
|
type Error = Error;
|
||||||
|
|
|
||||||
148
tests/test.rs
148
tests/test.rs
|
|
@ -3,6 +3,7 @@ extern crate serde_derive;
|
||||||
|
|
||||||
extern crate bincode;
|
extern crate bincode;
|
||||||
extern crate serde;
|
extern crate serde;
|
||||||
|
extern crate byteorder;
|
||||||
|
|
||||||
use std::fmt::Debug;
|
use std::fmt::Debug;
|
||||||
use std::collections::HashMap;
|
use std::collections::HashMap;
|
||||||
|
|
@ -10,29 +11,13 @@ use std::ops::Deref;
|
||||||
|
|
||||||
use bincode::refbox::{RefBox, StrBox, SliceBox};
|
use bincode::refbox::{RefBox, StrBox, SliceBox};
|
||||||
|
|
||||||
use bincode::SizeLimit::{self, Infinite, Bounded};
|
use bincode::SizeLimit::{Infinite, Bounded};
|
||||||
use bincode::{serialize, serialized_size, deserialize, deserialize_from, ErrorKind, Result};
|
use bincode::{serialized_size, ErrorKind, Result};
|
||||||
|
use bincode::endian_choice::{serialize, deserialize};
|
||||||
|
|
||||||
fn proxy_encode<V>(element: &V, size_limit: SizeLimit) -> Vec<u8>
|
use bincode::serialize as serialize_little;
|
||||||
where V: serde::Serialize + serde::Deserialize + PartialEq + Debug + 'static
|
use bincode::deserialize as deserialize_little;
|
||||||
{
|
use bincode::deserialize_from as deserialize_from_little;
|
||||||
let v2 = serialize(element, size_limit).unwrap();
|
|
||||||
v2
|
|
||||||
}
|
|
||||||
|
|
||||||
fn proxy_decode<V>(slice: &[u8]) -> V
|
|
||||||
where V: serde::Serialize + serde::Deserialize + PartialEq + Debug + 'static
|
|
||||||
{
|
|
||||||
let e2 = deserialize(slice).unwrap();
|
|
||||||
e2
|
|
||||||
}
|
|
||||||
|
|
||||||
fn proxy_encoded_size<V>(element: &V) -> u64
|
|
||||||
where V: serde::Serialize + PartialEq + Debug + 'static
|
|
||||||
{
|
|
||||||
let serde_size = serialized_size(element);
|
|
||||||
serde_size
|
|
||||||
}
|
|
||||||
|
|
||||||
fn the_same<V>(element: V)
|
fn the_same<V>(element: V)
|
||||||
where V: serde::Serialize+serde::Deserialize+PartialEq+Debug+'static
|
where V: serde::Serialize+serde::Deserialize+PartialEq+Debug+'static
|
||||||
|
|
@ -42,20 +27,35 @@ fn the_same<V>(element: V)
|
||||||
where V: serde::Serialize + serde::Deserialize + PartialEq + Debug + 'static
|
where V: serde::Serialize + serde::Deserialize + PartialEq + Debug + 'static
|
||||||
{
|
{
|
||||||
let rf = RefBox::new(v);
|
let rf = RefBox::new(v);
|
||||||
let encoded = serialize(&rf, Infinite).unwrap();
|
let encoded = serialize_little(&rf, Infinite).unwrap();
|
||||||
let decoded: RefBox<'static, V> = deserialize(&encoded[..]).unwrap();
|
let decoded: RefBox<'static, V> = deserialize_little(&encoded[..]).unwrap();
|
||||||
|
|
||||||
decoded.take().deref() == v
|
decoded.take().deref() == v
|
||||||
}
|
}
|
||||||
|
|
||||||
let size = proxy_encoded_size(&element);
|
let size = serialized_size(&element);
|
||||||
|
|
||||||
let encoded = proxy_encode(&element, Infinite);
|
{
|
||||||
let decoded = proxy_decode(&encoded[..]);
|
let encoded = serialize_little(&element, Infinite);
|
||||||
|
let encoded = encoded.unwrap();
|
||||||
|
let decoded = deserialize_little(&encoded[..]);
|
||||||
|
let decoded = decoded.unwrap();
|
||||||
|
|
||||||
assert_eq!(element, decoded);
|
assert_eq!(element, decoded);
|
||||||
assert_eq!(size, encoded.len() as u64);
|
assert_eq!(size, encoded.len() as u64);
|
||||||
assert!(ref_box_correct(&element));
|
assert!(ref_box_correct(&element));
|
||||||
|
}
|
||||||
|
|
||||||
|
{
|
||||||
|
let encoded = serialize::<_, byteorder::BigEndian>(&element, Infinite);
|
||||||
|
let encoded = encoded.unwrap();
|
||||||
|
let decoded = deserialize::<_, byteorder::BigEndian>(&encoded[..]);
|
||||||
|
let decoded = decoded.unwrap();
|
||||||
|
|
||||||
|
assert_eq!(element, decoded);
|
||||||
|
assert_eq!(size, encoded.len() as u64);
|
||||||
|
assert!(ref_box_correct(&element));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
|
|
@ -220,26 +220,26 @@ fn deserializing_errors() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
isize_invalid_deserialize(deserialize::<bool>(&vec![0xA][..]));
|
isize_invalid_deserialize(deserialize_little::<bool>(&vec![0xA][..]));
|
||||||
isize_invalid_deserialize(deserialize::<String>(&vec![0, 0, 0, 0, 0, 0, 0, 1, 0xFF][..]));
|
isize_invalid_deserialize(deserialize_little::<String>(&vec![0, 0, 0, 0, 0, 0, 0, 1, 0xFF][..]));
|
||||||
// Out-of-bounds variant
|
// Out-of-bounds variant
|
||||||
#[derive(Serialize, Deserialize, Debug)]
|
#[derive(Serialize, Deserialize, Debug)]
|
||||||
enum Test {
|
enum Test {
|
||||||
One,
|
One,
|
||||||
Two,
|
Two,
|
||||||
};
|
};
|
||||||
isize_invalid_deserialize(deserialize::<Test>(&vec![0, 0, 0, 5][..]));
|
isize_invalid_deserialize(deserialize_little::<Test>(&vec![0, 0, 0, 5][..]));
|
||||||
isize_invalid_deserialize(deserialize::<Option<u8>>(&vec![5, 0][..]));
|
isize_invalid_deserialize(deserialize_little::<Option<u8>>(&vec![5, 0][..]));
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn too_big_deserialize() {
|
fn too_big_deserialize() {
|
||||||
let serialized = vec![0,0,0,3];
|
let serialized = vec![0,0,0,3];
|
||||||
let deserialized: Result<u32> = deserialize_from(&mut &serialized[..], Bounded(3));
|
let deserialized: Result<u32> = deserialize_from_little::<_, _>(&mut &serialized[..], Bounded(3));
|
||||||
assert!(deserialized.is_err());
|
assert!(deserialized.is_err());
|
||||||
|
|
||||||
let serialized = vec![0,0,0,3];
|
let serialized = vec![0,0,0,3];
|
||||||
let deserialized: Result<u32> = deserialize_from(&mut &serialized[..], Bounded(4));
|
let deserialized: Result<u32> = deserialize_from_little::<_, _>(&mut &serialized[..], Bounded(4));
|
||||||
assert!(deserialized.is_ok());
|
assert!(deserialized.is_ok());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -247,8 +247,8 @@ fn too_big_deserialize() {
|
||||||
fn char_serialization() {
|
fn char_serialization() {
|
||||||
let chars = "Aa\0☺♪";
|
let chars = "Aa\0☺♪";
|
||||||
for c in chars.chars() {
|
for c in chars.chars() {
|
||||||
let encoded = serialize(&c, Bounded(4)).expect("serializing char failed");
|
let encoded = serialize_little(&c, Bounded(4)).expect("serializing char failed");
|
||||||
let decoded: char = deserialize(&encoded).expect("deserializing failed");
|
let decoded: char = deserialize_little(&encoded).expect("deserializing failed");
|
||||||
assert_eq!(decoded, c);
|
assert_eq!(decoded, c);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -256,47 +256,47 @@ fn char_serialization() {
|
||||||
#[test]
|
#[test]
|
||||||
fn too_big_char_deserialize() {
|
fn too_big_char_deserialize() {
|
||||||
let serialized = vec![0x41];
|
let serialized = vec![0x41];
|
||||||
let deserialized: Result<char> = deserialize_from(&mut &serialized[..], Bounded(1));
|
let deserialized: Result<char> = deserialize_from_little::<_, _>(&mut &serialized[..], Bounded(1));
|
||||||
assert!(deserialized.is_ok());
|
assert!(deserialized.is_ok());
|
||||||
assert_eq!(deserialized.unwrap(), 'A');
|
assert_eq!(deserialized.unwrap(), 'A');
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn too_big_serialize() {
|
fn too_big_serialize() {
|
||||||
assert!(serialize(&0u32, Bounded(3)).is_err());
|
assert!(serialize_little(&0u32, Bounded(3)).is_err());
|
||||||
assert!(serialize(&0u32, Bounded(4)).is_ok());
|
assert!(serialize_little(&0u32, Bounded(4)).is_ok());
|
||||||
|
|
||||||
assert!(serialize(&"abcde", Bounded(8 + 4)).is_err());
|
assert!(serialize_little(&"abcde", Bounded(8 + 4)).is_err());
|
||||||
assert!(serialize(&"abcde", Bounded(8 + 5)).is_ok());
|
assert!(serialize_little(&"abcde", Bounded(8 + 5)).is_ok());
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_proxy_encoded_size() {
|
fn test_proxy_encoded_size() {
|
||||||
assert!(proxy_encoded_size(&0u8) == 1);
|
assert!(serialized_size(&0u8) == 1);
|
||||||
assert!(proxy_encoded_size(&0u16) == 2);
|
assert!(serialized_size(&0u16) == 2);
|
||||||
assert!(proxy_encoded_size(&0u32) == 4);
|
assert!(serialized_size(&0u32) == 4);
|
||||||
assert!(proxy_encoded_size(&0u64) == 8);
|
assert!(serialized_size(&0u64) == 8);
|
||||||
|
|
||||||
// length isize stored as u64
|
// length isize stored as u64
|
||||||
assert!(proxy_encoded_size(&"") == 8);
|
assert!(serialized_size(&"") == 8);
|
||||||
assert!(proxy_encoded_size(&"a") == 8 + 1);
|
assert!(serialized_size(&"a") == 8 + 1);
|
||||||
|
|
||||||
assert!(proxy_encoded_size(&vec![0u32, 1u32, 2u32]) == 8 + 3 * (4))
|
assert!(serialized_size(&vec![0u32, 1u32, 2u32]) == 8 + 3 * (4))
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_serialized_size() {
|
fn test_serialized_size() {
|
||||||
assert!(proxy_encoded_size(&0u8) == 1);
|
assert!(serialized_size(&0u8) == 1);
|
||||||
assert!(proxy_encoded_size(&0u16) == 2);
|
assert!(serialized_size(&0u16) == 2);
|
||||||
assert!(proxy_encoded_size(&0u32) == 4);
|
assert!(serialized_size(&0u32) == 4);
|
||||||
assert!(proxy_encoded_size(&0u64) == 8);
|
assert!(serialized_size(&0u64) == 8);
|
||||||
|
|
||||||
// length isize stored as u64
|
// length isize stored as u64
|
||||||
assert!(proxy_encoded_size(&"") == 8);
|
assert!(serialized_size(&"") == 8);
|
||||||
assert!(proxy_encoded_size(&"a") == 8 + 1);
|
assert!(serialized_size(&"a") == 8 + 1);
|
||||||
|
|
||||||
assert!(proxy_encoded_size(&vec![0u32, 1u32, 2u32]) == 8 + 3 * (4))
|
assert!(serialized_size(&vec![0u32, 1u32, 2u32]) == 8 + 3 * (4))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
|
|
@ -319,8 +319,8 @@ fn test_refbox_serialize() {
|
||||||
|
|
||||||
// Test 1
|
// Test 1
|
||||||
{
|
{
|
||||||
let serialized = serialize(&Message::M1(RefBox::new(&large_object)), Infinite).unwrap();
|
let serialized = serialize_little(&Message::M1(RefBox::new(&large_object)), Infinite).unwrap();
|
||||||
let deserialized: Message<'static> = deserialize_from(&mut &serialized[..], Infinite).unwrap();
|
let deserialized: Message<'static> = deserialize_from_little(&mut &serialized[..], Infinite).unwrap();
|
||||||
|
|
||||||
match deserialized {
|
match deserialized {
|
||||||
Message::M1(b) => assert!(b.take().deref() == &large_object),
|
Message::M1(b) => assert!(b.take().deref() == &large_object),
|
||||||
|
|
@ -330,8 +330,8 @@ fn test_refbox_serialize() {
|
||||||
|
|
||||||
// Test 2
|
// Test 2
|
||||||
{
|
{
|
||||||
let serialized = serialize(&Message::M2(RefBox::new(&large_map)), Infinite).unwrap();
|
let serialized = serialize_little(&Message::M2(RefBox::new(&large_map)), Infinite).unwrap();
|
||||||
let deserialized: Message<'static> = deserialize_from(&mut &serialized[..], Infinite).unwrap();
|
let deserialized: Message<'static> = deserialize_from_little(&mut &serialized[..], Infinite).unwrap();
|
||||||
|
|
||||||
match deserialized {
|
match deserialized {
|
||||||
Message::M2(b) => assert!(b.take().deref() == &large_map),
|
Message::M2(b) => assert!(b.take().deref() == &large_map),
|
||||||
|
|
@ -343,8 +343,8 @@ fn test_refbox_serialize() {
|
||||||
#[test]
|
#[test]
|
||||||
fn test_strbox_serialize() {
|
fn test_strbox_serialize() {
|
||||||
let strx: &'static str = "hello world";
|
let strx: &'static str = "hello world";
|
||||||
let serialized = serialize(&StrBox::new(strx), Infinite).unwrap();
|
let serialized = serialize_little(&StrBox::new(strx), Infinite).unwrap();
|
||||||
let deserialized: StrBox<'static> = deserialize_from(&mut &serialized[..], Infinite).unwrap();
|
let deserialized: StrBox<'static> = deserialize_from_little(&mut &serialized[..], Infinite).unwrap();
|
||||||
let stringx: String = deserialized.take();
|
let stringx: String = deserialized.take();
|
||||||
assert!(strx == &stringx[..]);
|
assert!(strx == &stringx[..]);
|
||||||
}
|
}
|
||||||
|
|
@ -352,8 +352,8 @@ fn test_strbox_serialize() {
|
||||||
#[test]
|
#[test]
|
||||||
fn test_slicebox_serialize() {
|
fn test_slicebox_serialize() {
|
||||||
let slice = [1u32, 2, 3 ,4, 5];
|
let slice = [1u32, 2, 3 ,4, 5];
|
||||||
let serialized = serialize(&SliceBox::new(&slice), Infinite).unwrap();
|
let serialized = serialize_little(&SliceBox::new(&slice), Infinite).unwrap();
|
||||||
let deserialized: SliceBox<'static, u32> = deserialize_from(&mut &serialized[..], Infinite).unwrap();
|
let deserialized: SliceBox<'static, u32> = deserialize_from_little(&mut &serialized[..], Infinite).unwrap();
|
||||||
{
|
{
|
||||||
let sb: &[u32] = &deserialized;
|
let sb: &[u32] = &deserialized;
|
||||||
assert!(slice == sb);
|
assert!(slice == sb);
|
||||||
|
|
@ -364,7 +364,7 @@ fn test_slicebox_serialize() {
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_multi_strings_serialize() {
|
fn test_multi_strings_serialize() {
|
||||||
assert!(serialize(&("foo", "bar", "baz"), Infinite).is_ok());
|
assert!(serialize_little(&("foo", "bar", "baz"), Infinite).is_ok());
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|
@ -384,8 +384,8 @@ fn test_oom_protection() {
|
||||||
fn path_buf() {
|
fn path_buf() {
|
||||||
use std::path::{Path, PathBuf};
|
use std::path::{Path, PathBuf};
|
||||||
let path = Path::new("foo").to_path_buf();
|
let path = Path::new("foo").to_path_buf();
|
||||||
let serde_encoded = serialize(&path, Infinite).unwrap();
|
let serde_encoded = serialize_little(&path, Infinite).unwrap();
|
||||||
let decoded: PathBuf = deserialize(&serde_encoded).unwrap();
|
let decoded: PathBuf = deserialize_little(&serde_encoded).unwrap();
|
||||||
assert!(path.to_str() == decoded.to_str());
|
assert!(path.to_str() == decoded.to_str());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -394,8 +394,16 @@ fn bytes() {
|
||||||
use serde::bytes::Bytes;
|
use serde::bytes::Bytes;
|
||||||
|
|
||||||
let data = b"abc\0123";
|
let data = b"abc\0123";
|
||||||
let s = serialize(&data, Infinite).unwrap();
|
let s = serialize_little(&data, Infinite).unwrap();
|
||||||
let s2 = serialize(&Bytes::new(data), Infinite).unwrap();
|
let s2 = serialize_little(&Bytes::new(data), Infinite).unwrap();
|
||||||
assert_eq!(s[..], s2[8..]);
|
assert_eq!(s[..], s2[8..]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn endian_difference() {
|
||||||
|
let x = 10u64;
|
||||||
|
let little = serialize_little(&x, Infinite).unwrap();
|
||||||
|
let big = serialize::<_, byteorder::BigEndian>(&x, Infinite).unwrap();
|
||||||
|
assert_ne!(little, big);
|
||||||
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue