Embedded-parameterised Writer
This commit is contained in:
parent
8f1a83e548
commit
da08189dd4
|
@ -151,7 +151,7 @@ pub fn compile(config: &CompilerConfig) -> Result<(), std::io::Error> {
|
|||
lines.push(format!(" use {}::support as _support;", &config.support_crate));
|
||||
lines.push(" _support::lazy_static! {".to_owned());
|
||||
for (value, name) in &m.literals {
|
||||
let bs = preserves::value::PackedWriter::encode(&value).unwrap();
|
||||
let bs = preserves::value::PackedWriter::encode_iovalue(&value).unwrap();
|
||||
lines.push(format!(
|
||||
" pub static ref {}: {} = /* {:?} */ _support::decode_lit(&vec!{:?}).unwrap();",
|
||||
name,
|
||||
|
|
|
@ -6,7 +6,7 @@ use preserves::value::Embeddable;
|
|||
use preserves::value::IOResult;
|
||||
use preserves::value::IOValue;
|
||||
use preserves::value::NestedValue;
|
||||
use preserves::value::NoEmbeddedDomainDecode;
|
||||
use preserves::value::NoEmbeddedDomainCodec;
|
||||
use preserves::value::Value;
|
||||
|
||||
use std::convert::From;
|
||||
|
@ -14,7 +14,7 @@ use std::convert::TryFrom;
|
|||
use std::sync::Arc;
|
||||
|
||||
pub fn decode_lit<D: Embeddable, N: NestedValue<D>>(bs: &[u8]) -> IOResult<N> {
|
||||
preserves::value::packed::from_bytes(bs, NoEmbeddedDomainDecode)
|
||||
preserves::value::packed::from_bytes(bs, NoEmbeddedDomainCodec)
|
||||
}
|
||||
|
||||
pub fn decode_embedded<D: Domain>(
|
||||
|
|
|
@ -4,7 +4,7 @@ use serde::de::{Visitor, SeqAccess, MapAccess, EnumAccess, VariantAccess, Deseri
|
|||
use std::borrow::Cow;
|
||||
use std::marker::PhantomData;
|
||||
|
||||
use super::value::{IOValue, IOValueDomainDecode, PackedReader};
|
||||
use super::value::{IOValue, IOValueDomainCodec, PackedReader};
|
||||
use super::value::reader::{Reader, IOBinarySource, BytesBinarySource};
|
||||
|
||||
pub use super::error::Error;
|
||||
|
@ -21,7 +21,7 @@ pub fn from_bytes<'de, T>(bytes: &'de [u8]) ->
|
|||
where
|
||||
T: Deserialize<'de>
|
||||
{
|
||||
from_reader(&mut PackedReader::new(&mut BytesBinarySource::new(bytes), IOValueDomainDecode))
|
||||
from_reader(&mut PackedReader::new(&mut BytesBinarySource::new(bytes), IOValueDomainCodec))
|
||||
}
|
||||
|
||||
pub fn from_read<'de, 'r, IOR: std::io::Read, T>(read: &'r mut IOR) ->
|
||||
|
@ -29,7 +29,7 @@ pub fn from_read<'de, 'r, IOR: std::io::Read, T>(read: &'r mut IOR) ->
|
|||
where
|
||||
T: Deserialize<'de>
|
||||
{
|
||||
from_reader(&mut PackedReader::new(&mut IOBinarySource::new(read), IOValueDomainDecode))
|
||||
from_reader(&mut PackedReader::new(&mut IOBinarySource::new(read), IOValueDomainCodec))
|
||||
}
|
||||
|
||||
pub fn from_reader<'r, 'de, R: Reader<'de, IOValue, IOValue>, T>(read: &'r mut R) ->
|
||||
|
|
|
@ -29,7 +29,7 @@ mod dom {
|
|||
Value::Embedded(Dom::One).wrap(),
|
||||
Value::from(2).wrap()])
|
||||
.wrap();
|
||||
assert_eq!(PackedWriter::encode(&v.copy_via(&mut dom_as_preserves).unwrap()).unwrap(),
|
||||
assert_eq!(PackedWriter::encode_iovalue(&v.copy_via(&mut dom_as_preserves).unwrap()).unwrap(),
|
||||
[0xb5, 0x91, 0xb2, 0x04, 255, 255, 255, 255, 0x92, 0x84]);
|
||||
}
|
||||
|
||||
|
@ -38,7 +38,7 @@ mod dom {
|
|||
Value::Embedded(Dom::Two).wrap(),
|
||||
Value::from(2).wrap()])
|
||||
.wrap();
|
||||
assert_eq!(PackedWriter::encode(&v.copy_via(&mut dom_as_preserves).unwrap()).unwrap(),
|
||||
assert_eq!(PackedWriter::encode_iovalue(&v.copy_via(&mut dom_as_preserves).unwrap()).unwrap(),
|
||||
[0xb5, 0x91, 0xb3, 0x08, 68, 111, 109, 58, 58, 84, 119, 111, 0x92, 0x84]);
|
||||
}
|
||||
}
|
||||
|
@ -465,7 +465,7 @@ mod serde_tests {
|
|||
println!("== y: {:#?}", &y);
|
||||
assert_eq!(v, y);
|
||||
|
||||
let v_bytes_1 = PackedWriter::encode(&w).unwrap();
|
||||
let v_bytes_1 = PackedWriter::encode_iovalue(&w).unwrap();
|
||||
println!("== w bytes = {:?}", v_bytes_1);
|
||||
assert_eq!(expected_bytes, v_bytes_1);
|
||||
|
||||
|
|
|
@ -1,4 +1,5 @@
|
|||
use serde::Serialize;
|
||||
use super::value::IOValueDomainCodec;
|
||||
use super::value::writer::{Writer, CompoundWriter};
|
||||
|
||||
pub use super::error::Error;
|
||||
|
@ -153,7 +154,7 @@ impl<'a, 'w, W: Writer> serde::Serializer for &'a mut Serializer<'w, W> {
|
|||
Result<Self::Ok> where T: Serialize
|
||||
{
|
||||
match super::value::magic::receive_output_value(name, value) {
|
||||
Some(v) => Ok(self.write.write(&v)?),
|
||||
Some(v) => Ok(self.write.write(&mut IOValueDomainCodec, &v)?),
|
||||
None => {
|
||||
// TODO: This is apparently discouraged, and we should apparently just serialize `value`?
|
||||
let mut c = self.write.start_record(Some(1))?;
|
||||
|
|
|
@ -3,6 +3,7 @@ use super::Embeddable;
|
|||
use super::IOResult;
|
||||
use super::IOValue;
|
||||
use super::Reader;
|
||||
use super::Writer;
|
||||
use super::packed::PackedReader;
|
||||
|
||||
pub trait DomainDecode<D: Embeddable> {
|
||||
|
@ -13,21 +14,39 @@ pub trait DomainDecode<D: Embeddable> {
|
|||
) -> IOResult<D>;
|
||||
}
|
||||
|
||||
pub struct IOValueDomainDecode;
|
||||
pub trait DomainEncode<D: Embeddable> {
|
||||
fn encode_embedded<W: Writer>(
|
||||
&mut self,
|
||||
w: &mut W,
|
||||
d: &D,
|
||||
) -> IOResult<()>;
|
||||
}
|
||||
|
||||
impl DomainDecode<IOValue> for IOValueDomainDecode {
|
||||
pub struct IOValueDomainCodec;
|
||||
|
||||
impl DomainDecode<IOValue> for IOValueDomainCodec {
|
||||
fn decode_embedded<'de, 'src, S: BinarySource<'de>>(
|
||||
&mut self,
|
||||
src: &'src mut S,
|
||||
read_annotations: bool,
|
||||
) -> IOResult<IOValue> {
|
||||
PackedReader::new(src, IOValueDomainDecode).demand_next(read_annotations)
|
||||
PackedReader::new(src, IOValueDomainCodec).demand_next(read_annotations)
|
||||
}
|
||||
}
|
||||
|
||||
pub struct NoEmbeddedDomainDecode;
|
||||
impl DomainEncode<IOValue> for IOValueDomainCodec {
|
||||
fn encode_embedded<W: Writer>(
|
||||
&mut self,
|
||||
w: &mut W,
|
||||
d: &IOValue,
|
||||
) -> IOResult<()> {
|
||||
w.write(self, d)
|
||||
}
|
||||
}
|
||||
|
||||
impl<D: Embeddable> DomainDecode<D> for NoEmbeddedDomainDecode {
|
||||
pub struct NoEmbeddedDomainCodec;
|
||||
|
||||
impl<D: Embeddable> DomainDecode<D> for NoEmbeddedDomainCodec {
|
||||
fn decode_embedded<'de, 'src, S: BinarySource<'de>>(
|
||||
&mut self,
|
||||
_src: &'src mut S,
|
||||
|
@ -36,3 +55,13 @@ impl<D: Embeddable> DomainDecode<D> for NoEmbeddedDomainDecode {
|
|||
Err(std::io::Error::new(std::io::ErrorKind::Unsupported, "Embedded values not supported here"))
|
||||
}
|
||||
}
|
||||
|
||||
impl<D: Embeddable> DomainEncode<D> for NoEmbeddedDomainCodec {
|
||||
fn encode_embedded<W: Writer>(
|
||||
&mut self,
|
||||
_w: &mut W,
|
||||
_d: &D,
|
||||
) -> IOResult<()> {
|
||||
Err(std::io::Error::new(std::io::ErrorKind::Unsupported, "Embedded values not supported here"))
|
||||
}
|
||||
}
|
||||
|
|
|
@ -11,8 +11,9 @@ pub mod writer;
|
|||
pub use de::Deserializer;
|
||||
pub use de::from_value;
|
||||
pub use domain::DomainDecode;
|
||||
pub use domain::IOValueDomainDecode;
|
||||
pub use domain::NoEmbeddedDomainDecode;
|
||||
pub use domain::DomainEncode;
|
||||
pub use domain::IOValueDomainCodec;
|
||||
pub use domain::NoEmbeddedDomainCodec;
|
||||
pub use packed::PackedReader;
|
||||
pub use packed::PackedWriter;
|
||||
pub use reader::BinarySource;
|
||||
|
|
|
@ -5,7 +5,7 @@ pub mod writer;
|
|||
pub use reader::PackedReader;
|
||||
pub use writer::PackedWriter;
|
||||
|
||||
use super::{BinarySource, DomainDecode, Embeddable, IOResult, IOValue, IOValueDomainDecode, NestedValue, Reader};
|
||||
use super::{BinarySource, DomainDecode, Embeddable, IOResult, IOValue, IOValueDomainCodec, NestedValue, Reader};
|
||||
|
||||
pub fn from_bytes<D: Embeddable, N: NestedValue<D>, Dec: DomainDecode<D>>(
|
||||
bs: &[u8],
|
||||
|
@ -15,7 +15,7 @@ pub fn from_bytes<D: Embeddable, N: NestedValue<D>, Dec: DomainDecode<D>>(
|
|||
}
|
||||
|
||||
pub fn iovalue_from_bytes(bs: &[u8]) -> IOResult<IOValue> {
|
||||
from_bytes(bs, IOValueDomainDecode)
|
||||
from_bytes(bs, IOValueDomainCodec)
|
||||
}
|
||||
|
||||
pub fn annotated_from_bytes<D: Embeddable, N: NestedValue<D>, Dec: DomainDecode<D>>(
|
||||
|
@ -26,5 +26,5 @@ pub fn annotated_from_bytes<D: Embeddable, N: NestedValue<D>, Dec: DomainDecode<
|
|||
}
|
||||
|
||||
pub fn annotated_iovalue_from_bytes(bs: &[u8]) -> IOResult<IOValue> {
|
||||
annotated_from_bytes(bs, IOValueDomainDecode)
|
||||
annotated_from_bytes(bs, IOValueDomainCodec)
|
||||
}
|
||||
|
|
|
@ -4,9 +4,14 @@ use std::convert::TryInto;
|
|||
use std::mem;
|
||||
use std::ops::{Deref, DerefMut};
|
||||
use super::constants::Tag;
|
||||
use super::super::DomainEncode;
|
||||
use super::super::Embeddable;
|
||||
use super::super::IOValue;
|
||||
use super::super::IOValueDomainCodec;
|
||||
use super::super::IOResult;
|
||||
use super::super::NestedValue;
|
||||
|
||||
use super::super::writer::{Writer, AnnotationWriter, CompoundWriter, Result, varint};
|
||||
use super::super::writer::{Writer, AnnotationWriter, CompoundWriter, varint};
|
||||
|
||||
pub enum Suspendable<T> {
|
||||
Active(T),
|
||||
|
@ -70,12 +75,19 @@ impl<T> DerefMut for Suspendable<T> {
|
|||
pub struct PackedWriter<W: std::io::Write>(Suspendable<W>);
|
||||
|
||||
impl PackedWriter<Vec<u8>> {
|
||||
pub fn encode(v: &IOValue) -> std::io::Result<Vec<u8>> {
|
||||
pub fn encode<D: Embeddable, N: NestedValue<D>, Enc: DomainEncode<D>>(
|
||||
enc: &mut Enc,
|
||||
v: &N,
|
||||
) -> IOResult<Vec<u8>> {
|
||||
let mut buf: Vec<u8> = Vec::new();
|
||||
let w = &mut PackedWriter::new(&mut buf);
|
||||
w.write(v)?;
|
||||
w.write(enc, v)?;
|
||||
Ok(buf)
|
||||
}
|
||||
|
||||
pub fn encode_iovalue(v: &IOValue) -> std::io::Result<Vec<u8>> {
|
||||
Self::encode(&mut IOValueDomainCodec, v)
|
||||
}
|
||||
}
|
||||
|
||||
impl<W: std::io::Write> PackedWriter<W> {
|
||||
|
@ -87,18 +99,18 @@ impl<W: std::io::Write> PackedWriter<W> {
|
|||
self.0.deref_mut()
|
||||
}
|
||||
|
||||
pub fn write_byte(&mut self, b: u8) -> Result<()> {
|
||||
pub fn write_byte(&mut self, b: u8) -> IOResult<()> {
|
||||
self.w().write_all(&[b])
|
||||
}
|
||||
|
||||
pub fn write_medium_integer(&mut self, bs: &[u8]) -> Result<()> {
|
||||
pub fn write_medium_integer(&mut self, bs: &[u8]) -> IOResult<()> {
|
||||
let count: u8 = bs.len().try_into().unwrap();
|
||||
if !(1..=16).contains(&count) { panic!("Invalid medium_integer count: {}", count) }
|
||||
self.write_byte(Tag::MediumInteger(count).into())?;
|
||||
self.w().write_all(bs)
|
||||
}
|
||||
|
||||
pub fn write_atom(&mut self, tag: Tag, bs: &[u8]) -> Result<()> {
|
||||
pub fn write_atom(&mut self, tag: Tag, bs: &[u8]) -> IOResult<()> {
|
||||
self.write_byte(tag.into())?;
|
||||
varint(&mut self.w(), bs.len().try_into().unwrap())?;
|
||||
self.w().write_all(bs)
|
||||
|
@ -140,7 +152,7 @@ impl BinaryOrderWriter {
|
|||
self.0.last_mut().unwrap()
|
||||
}
|
||||
|
||||
fn finish<W: WriteWriter>(mut self, w: &mut W) -> Result<()> {
|
||||
fn finish<W: WriteWriter>(mut self, w: &mut W) -> IOResult<()> {
|
||||
if !self.buffer().is_empty() { panic!("Missing final delimit()"); }
|
||||
self.items_mut().pop();
|
||||
self.items_mut().sort();
|
||||
|
@ -153,51 +165,51 @@ impl BinaryOrderWriter {
|
|||
}
|
||||
|
||||
pub trait WriteWriter: Writer {
|
||||
fn write_raw_bytes(&mut self, v: &[u8]) -> Result<()>;
|
||||
fn write_tag(&mut self, tag: Tag) -> Result<()> {
|
||||
fn write_raw_bytes(&mut self, v: &[u8]) -> IOResult<()>;
|
||||
fn write_tag(&mut self, tag: Tag) -> IOResult<()> {
|
||||
self.write_raw_bytes(&[tag.into()])
|
||||
}
|
||||
}
|
||||
|
||||
impl<W: std::io::Write> WriteWriter for PackedWriter<W> {
|
||||
fn write_raw_bytes(&mut self, v: &[u8]) -> Result<()> {
|
||||
fn write_raw_bytes(&mut self, v: &[u8]) -> IOResult<()> {
|
||||
self.w().write_all(v)
|
||||
}
|
||||
}
|
||||
|
||||
impl WriteWriter for BinaryOrderWriter {
|
||||
fn write_raw_bytes(&mut self, v: &[u8]) -> Result<()> {
|
||||
fn write_raw_bytes(&mut self, v: &[u8]) -> IOResult<()> {
|
||||
use std::io::Write;
|
||||
self.buffer().write_all(v)
|
||||
}
|
||||
}
|
||||
|
||||
impl<T: WriteWriter> AnnotationWriter for T {
|
||||
fn start_annotation(&mut self) -> Result<()> {
|
||||
fn start_annotation(&mut self) -> IOResult<()> {
|
||||
Ok(self.write_tag(Tag::Annotation)?)
|
||||
}
|
||||
|
||||
fn start_value(&mut self) -> Result<()> {
|
||||
fn start_value(&mut self) -> IOResult<()> {
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
impl<W: std::io::Write> CompoundWriter for PackedWriter<W> {
|
||||
fn extend(&mut self) -> Result<()> {
|
||||
fn extend(&mut self) -> IOResult<()> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn delimit(&mut self) -> Result<()> {
|
||||
fn delimit(&mut self) -> IOResult<()> {
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
impl CompoundWriter for BinaryOrderWriter {
|
||||
fn extend(&mut self) -> Result<()> {
|
||||
fn extend(&mut self) -> IOResult<()> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn delimit(&mut self) -> Result<()> {
|
||||
fn delimit(&mut self) -> IOResult<()> {
|
||||
self.items_mut().push(vec![]);
|
||||
Ok(())
|
||||
}
|
||||
|
@ -216,67 +228,67 @@ impl Writer for BinaryOrderWriter {
|
|||
type SetWriter = BinaryOrderWriter;
|
||||
type EmbeddedWriter = PackedWriter<Vec<u8>>;
|
||||
|
||||
binary_order_writer_method!(mut align(natural_chunksize: u64) -> Result<()>);
|
||||
binary_order_writer_method!(mut align(natural_chunksize: u64) -> IOResult<()>);
|
||||
|
||||
fn start_annotations(&mut self) -> Result<Self::AnnWriter> {
|
||||
fn start_annotations(&mut self) -> IOResult<Self::AnnWriter> {
|
||||
Ok(self.pop())
|
||||
}
|
||||
fn end_annotations(&mut self, ann: Self::AnnWriter) -> Result<()> {
|
||||
fn end_annotations(&mut self, ann: Self::AnnWriter) -> IOResult<()> {
|
||||
self.push(ann);
|
||||
Ok(())
|
||||
}
|
||||
|
||||
binary_order_writer_method!(mut write_bool(v: bool) -> Result<()>);
|
||||
binary_order_writer_method!(mut write_bool(v: bool) -> IOResult<()>);
|
||||
|
||||
binary_order_writer_method!(mut write_f32(v: f32) -> Result<()>);
|
||||
binary_order_writer_method!(mut write_f64(v: f64) -> Result<()>);
|
||||
binary_order_writer_method!(mut write_f32(v: f32) -> IOResult<()>);
|
||||
binary_order_writer_method!(mut write_f64(v: f64) -> IOResult<()>);
|
||||
|
||||
binary_order_writer_method!(mut write_i8(v: i8) -> Result<()>);
|
||||
binary_order_writer_method!(mut write_u8(v: u8) -> Result<()>);
|
||||
binary_order_writer_method!(mut write_i16(v: i16) -> Result<()>);
|
||||
binary_order_writer_method!(mut write_u16(v: u16) -> Result<()>);
|
||||
binary_order_writer_method!(mut write_i32(v: i32) -> Result<()>);
|
||||
binary_order_writer_method!(mut write_u32(v: u32) -> Result<()>);
|
||||
binary_order_writer_method!(mut write_i64(v: i64) -> Result<()>);
|
||||
binary_order_writer_method!(mut write_u64(v: u64) -> Result<()>);
|
||||
binary_order_writer_method!(mut write_i128(v: i128) -> Result<()>);
|
||||
binary_order_writer_method!(mut write_u128(v: u128) -> Result<()>);
|
||||
binary_order_writer_method!(mut write_int(v: &BigInt) -> Result<()>);
|
||||
binary_order_writer_method!(mut write_i8(v: i8) -> IOResult<()>);
|
||||
binary_order_writer_method!(mut write_u8(v: u8) -> IOResult<()>);
|
||||
binary_order_writer_method!(mut write_i16(v: i16) -> IOResult<()>);
|
||||
binary_order_writer_method!(mut write_u16(v: u16) -> IOResult<()>);
|
||||
binary_order_writer_method!(mut write_i32(v: i32) -> IOResult<()>);
|
||||
binary_order_writer_method!(mut write_u32(v: u32) -> IOResult<()>);
|
||||
binary_order_writer_method!(mut write_i64(v: i64) -> IOResult<()>);
|
||||
binary_order_writer_method!(mut write_u64(v: u64) -> IOResult<()>);
|
||||
binary_order_writer_method!(mut write_i128(v: i128) -> IOResult<()>);
|
||||
binary_order_writer_method!(mut write_u128(v: u128) -> IOResult<()>);
|
||||
binary_order_writer_method!(mut write_int(v: &BigInt) -> IOResult<()>);
|
||||
|
||||
binary_order_writer_method!(mut write_string(v: &str) -> Result<()>);
|
||||
binary_order_writer_method!(mut write_bytes(v: &[u8]) -> Result<()>);
|
||||
binary_order_writer_method!(mut write_symbol(v: &str) -> Result<()>);
|
||||
binary_order_writer_method!(mut write_string(v: &str) -> IOResult<()>);
|
||||
binary_order_writer_method!(mut write_bytes(v: &[u8]) -> IOResult<()>);
|
||||
binary_order_writer_method!(mut write_symbol(v: &str) -> IOResult<()>);
|
||||
|
||||
fn start_record(&mut self, _field_count: Option<usize>) -> Result<Self::SeqWriter> {
|
||||
fn start_record(&mut self, _field_count: Option<usize>) -> IOResult<Self::SeqWriter> {
|
||||
self.write_tag(Tag::Record)?;
|
||||
Ok(self.pop())
|
||||
}
|
||||
fn start_sequence(&mut self, _item_count: Option<usize>) -> Result<Self::SeqWriter> {
|
||||
fn start_sequence(&mut self, _item_count: Option<usize>) -> IOResult<Self::SeqWriter> {
|
||||
self.write_tag(Tag::Sequence)?;
|
||||
Ok(self.pop())
|
||||
}
|
||||
fn end_seq(&mut self, seq: Self::SeqWriter) -> Result<()> {
|
||||
fn end_seq(&mut self, seq: Self::SeqWriter) -> IOResult<()> {
|
||||
self.push(seq);
|
||||
self.write_tag(Tag::End)
|
||||
}
|
||||
|
||||
fn start_set(&mut self, _item_count: Option<usize>) -> Result<Self::SetWriter> {
|
||||
fn start_set(&mut self, _item_count: Option<usize>) -> IOResult<Self::SetWriter> {
|
||||
self.write_tag(Tag::Set)?;
|
||||
Ok(BinaryOrderWriter::new())
|
||||
}
|
||||
fn start_dictionary(&mut self, _entry_count: Option<usize>) -> Result<Self::SetWriter> {
|
||||
fn start_dictionary(&mut self, _entry_count: Option<usize>) -> IOResult<Self::SetWriter> {
|
||||
self.write_tag(Tag::Dictionary)?;
|
||||
Ok(BinaryOrderWriter::new())
|
||||
}
|
||||
fn end_set(&mut self, set: Self::SetWriter) -> Result<()> {
|
||||
fn end_set(&mut self, set: Self::SetWriter) -> IOResult<()> {
|
||||
set.finish(self)
|
||||
}
|
||||
|
||||
fn start_embedded(&mut self) -> Result<Self::EmbeddedWriter> {
|
||||
fn start_embedded(&mut self) -> IOResult<Self::EmbeddedWriter> {
|
||||
self.write_tag(Tag::Embedded)?;
|
||||
Ok(self.pop())
|
||||
}
|
||||
fn end_embedded(&mut self, ptr: Self::EmbeddedWriter) -> Result<()> {
|
||||
fn end_embedded(&mut self, ptr: Self::EmbeddedWriter) -> IOResult<()> {
|
||||
self.push(ptr);
|
||||
Ok(())
|
||||
}
|
||||
|
@ -296,54 +308,54 @@ impl<W: std::io::Write> Writer for PackedWriter<W>
|
|||
type SetWriter = BinaryOrderWriter;
|
||||
type EmbeddedWriter = Self;
|
||||
|
||||
fn start_annotations(&mut self) -> Result<Self::AnnWriter> {
|
||||
fn start_annotations(&mut self) -> IOResult<Self::AnnWriter> {
|
||||
Ok(self.suspend())
|
||||
}
|
||||
|
||||
fn end_annotations(&mut self, ann: Self::AnnWriter) -> Result<()> {
|
||||
fn end_annotations(&mut self, ann: Self::AnnWriter) -> IOResult<()> {
|
||||
self.resume(ann);
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn align(&mut self, _natural_chunksize: u64) -> Result<()> {
|
||||
fn align(&mut self, _natural_chunksize: u64) -> IOResult<()> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn write_bool(&mut self, v: bool) -> Result<()> {
|
||||
fn write_bool(&mut self, v: bool) -> IOResult<()> {
|
||||
self.write_tag(if v { Tag::True } else { Tag::False })
|
||||
}
|
||||
|
||||
fn write_f32(&mut self, v: f32) -> Result<()> {
|
||||
fn write_f32(&mut self, v: f32) -> IOResult<()> {
|
||||
self.write_tag(Tag::Float)?;
|
||||
self.write_raw_bytes(&u32::to_be_bytes(f32::to_bits(v)))
|
||||
}
|
||||
|
||||
fn write_f64(&mut self, v: f64) -> Result<()> {
|
||||
fn write_f64(&mut self, v: f64) -> IOResult<()> {
|
||||
self.write_tag(Tag::Double)?;
|
||||
self.write_raw_bytes(&u64::to_be_bytes(f64::to_bits(v)))
|
||||
}
|
||||
|
||||
fn write_i8(&mut self, v: i8) -> Result<()> {
|
||||
fn write_i8(&mut self, v: i8) -> IOResult<()> {
|
||||
if v >= -3 && v <= 12 { return self.write_tag(Tag::SmallInteger(v)) }
|
||||
self.write_medium_integer(&[v as u8])
|
||||
}
|
||||
|
||||
fn write_u8(&mut self, v: u8) -> Result<()> {
|
||||
fn write_u8(&mut self, v: u8) -> IOResult<()> {
|
||||
if let Ok(w) = v.try_into() { return self.write_i8(w) }
|
||||
self.write_medium_integer(&[0, v])
|
||||
}
|
||||
|
||||
fn write_i16(&mut self, v: i16) -> Result<()> {
|
||||
fn write_i16(&mut self, v: i16) -> IOResult<()> {
|
||||
if let Ok(w) = v.try_into() { return self.write_i8(w) }
|
||||
self.write_medium_integer(&[(v >> 8) as u8, (v & 255) as u8])
|
||||
}
|
||||
|
||||
fn write_u16(&mut self, v: u16) -> Result<()> {
|
||||
fn write_u16(&mut self, v: u16) -> IOResult<()> {
|
||||
if let Ok(w) = v.try_into() { return self.write_i16(w) }
|
||||
self.write_medium_integer(&[0, (v >> 8) as u8, (v & 255) as u8])
|
||||
}
|
||||
|
||||
fn write_i32(&mut self, v: i32) -> Result<()> {
|
||||
fn write_i32(&mut self, v: i32) -> IOResult<()> {
|
||||
if let Ok(w) = v.try_into() { return self.write_i16(w) }
|
||||
if fits_in_bytes!(v, 3) {
|
||||
return self.write_medium_integer(&[(v >> 16) as u8,
|
||||
|
@ -356,7 +368,7 @@ impl<W: std::io::Write> Writer for PackedWriter<W>
|
|||
(v & 255) as u8])
|
||||
}
|
||||
|
||||
fn write_u32(&mut self, v: u32) -> Result<()> {
|
||||
fn write_u32(&mut self, v: u32) -> IOResult<()> {
|
||||
if let Ok(w) = v.try_into() { return self.write_i32(w) }
|
||||
self.write_medium_integer(&[0,
|
||||
(v >> 24) as u8,
|
||||
|
@ -365,7 +377,7 @@ impl<W: std::io::Write> Writer for PackedWriter<W>
|
|||
(v & 255) as u8])
|
||||
}
|
||||
|
||||
fn write_i64(&mut self, v: i64) -> Result<()> {
|
||||
fn write_i64(&mut self, v: i64) -> IOResult<()> {
|
||||
if let Ok(w) = v.try_into() { return self.write_i32(w) }
|
||||
if fits_in_bytes!(v, 5) {
|
||||
return self.write_medium_integer(&[(v >> 32) as u8,
|
||||
|
@ -401,7 +413,7 @@ impl<W: std::io::Write> Writer for PackedWriter<W>
|
|||
(v & 255) as u8])
|
||||
}
|
||||
|
||||
fn write_u64(&mut self, v: u64) -> Result<()> {
|
||||
fn write_u64(&mut self, v: u64) -> IOResult<()> {
|
||||
if let Ok(w) = v.try_into() { return self.write_i64(w) }
|
||||
self.write_medium_integer(&[0,
|
||||
(v >> 56) as u8,
|
||||
|
@ -414,7 +426,7 @@ impl<W: std::io::Write> Writer for PackedWriter<W>
|
|||
(v & 255) as u8])
|
||||
}
|
||||
|
||||
fn write_i128(&mut self, v: i128) -> Result<()> {
|
||||
fn write_i128(&mut self, v: i128) -> IOResult<()> {
|
||||
if let Ok(w) = v.try_into() { return self.write_i64(w) }
|
||||
let bs: [u8; 16] = v.to_be_bytes();
|
||||
if fits_in_bytes!(v, 9) { return self.write_medium_integer(&bs[7..]); }
|
||||
|
@ -427,7 +439,7 @@ impl<W: std::io::Write> Writer for PackedWriter<W>
|
|||
self.write_medium_integer(&bs)
|
||||
}
|
||||
|
||||
fn write_u128(&mut self, v: u128) -> Result<()> {
|
||||
fn write_u128(&mut self, v: u128) -> IOResult<()> {
|
||||
if let Ok(w) = v.try_into() { return self.write_i128(w) }
|
||||
let bs: [u8; 16] = v.to_be_bytes();
|
||||
self.write_tag(Tag::SignedInteger)?;
|
||||
|
@ -436,7 +448,7 @@ impl<W: std::io::Write> Writer for PackedWriter<W>
|
|||
self.write_raw_bytes(&bs)
|
||||
}
|
||||
|
||||
fn write_int(&mut self, v: &BigInt) -> Result<()> {
|
||||
fn write_int(&mut self, v: &BigInt) -> IOResult<()> {
|
||||
match v.to_i8() {
|
||||
Some(n) => self.write_i8(n),
|
||||
None => {
|
||||
|
@ -448,53 +460,53 @@ impl<W: std::io::Write> Writer for PackedWriter<W>
|
|||
}
|
||||
}
|
||||
|
||||
fn write_string(&mut self, v: &str) -> Result<()> {
|
||||
fn write_string(&mut self, v: &str) -> IOResult<()> {
|
||||
self.write_atom(Tag::String, v.as_bytes())
|
||||
}
|
||||
|
||||
fn write_bytes(&mut self, v: &[u8]) -> Result<()> {
|
||||
fn write_bytes(&mut self, v: &[u8]) -> IOResult<()> {
|
||||
self.write_atom(Tag::ByteString, v)
|
||||
}
|
||||
|
||||
fn write_symbol(&mut self, v: &str) -> Result<()> {
|
||||
fn write_symbol(&mut self, v: &str) -> IOResult<()> {
|
||||
self.write_atom(Tag::Symbol, v.as_bytes())
|
||||
}
|
||||
|
||||
fn start_record(&mut self, _field_count: Option<usize>) -> Result<Self::SeqWriter> {
|
||||
fn start_record(&mut self, _field_count: Option<usize>) -> IOResult<Self::SeqWriter> {
|
||||
self.write_tag(Tag::Record)?;
|
||||
Ok(self.suspend())
|
||||
}
|
||||
|
||||
fn start_sequence(&mut self, _item_count: Option<usize>) -> Result<Self::SeqWriter> {
|
||||
fn start_sequence(&mut self, _item_count: Option<usize>) -> IOResult<Self::SeqWriter> {
|
||||
self.write_tag(Tag::Sequence)?;
|
||||
Ok(self.suspend())
|
||||
}
|
||||
|
||||
fn end_seq(&mut self, seq: Self::SeqWriter) -> Result<()> {
|
||||
fn end_seq(&mut self, seq: Self::SeqWriter) -> IOResult<()> {
|
||||
self.resume(seq);
|
||||
self.write_tag(Tag::End)
|
||||
}
|
||||
|
||||
fn start_set(&mut self, _item_count: Option<usize>) -> Result<Self::SetWriter> {
|
||||
fn start_set(&mut self, _item_count: Option<usize>) -> IOResult<Self::SetWriter> {
|
||||
self.write_tag(Tag::Set)?;
|
||||
Ok(BinaryOrderWriter::new())
|
||||
}
|
||||
|
||||
fn start_dictionary(&mut self, _entry_count: Option<usize>) -> Result<Self::SetWriter> {
|
||||
fn start_dictionary(&mut self, _entry_count: Option<usize>) -> IOResult<Self::SetWriter> {
|
||||
self.write_tag(Tag::Dictionary)?;
|
||||
Ok(BinaryOrderWriter::new())
|
||||
}
|
||||
|
||||
fn end_set(&mut self, set: Self::SetWriter) -> Result<()> {
|
||||
fn end_set(&mut self, set: Self::SetWriter) -> IOResult<()> {
|
||||
set.finish(self)
|
||||
}
|
||||
|
||||
fn start_embedded(&mut self) -> Result<Self::EmbeddedWriter> {
|
||||
fn start_embedded(&mut self) -> IOResult<Self::EmbeddedWriter> {
|
||||
self.write_tag(Tag::Embedded)?;
|
||||
Ok(self.suspend())
|
||||
}
|
||||
|
||||
fn end_embedded(&mut self, ann: Self::EmbeddedWriter) -> Result<()> {
|
||||
fn end_embedded(&mut self, ann: Self::EmbeddedWriter) -> IOResult<()> {
|
||||
self.resume(ann);
|
||||
Ok(())
|
||||
}
|
||||
|
|
|
@ -4,7 +4,7 @@ use std::borrow::Cow;
|
|||
use std::io::Read;
|
||||
use std::marker::PhantomData;
|
||||
|
||||
use super::{DomainDecode, Embeddable, IOResult, IOValue, IOValueDomainDecode, NestedValue};
|
||||
use super::{DomainDecode, Embeddable, IOResult, IOValue, IOValueDomainCodec, NestedValue};
|
||||
|
||||
pub type ReaderResult<T> = std::result::Result<T, error::Error>;
|
||||
|
||||
|
@ -173,9 +173,9 @@ pub trait BinarySource<'de>: Sized {
|
|||
}
|
||||
|
||||
fn packed_iovalues(&mut self) ->
|
||||
super::PackedReader<'de, '_, IOValue, IOValue, IOValueDomainDecode, Self>
|
||||
super::PackedReader<'de, '_, IOValue, IOValue, IOValueDomainCodec, Self>
|
||||
{
|
||||
self.packed(IOValueDomainDecode)
|
||||
self.packed(IOValueDomainCodec)
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -1,18 +1,17 @@
|
|||
use num::bigint::BigInt;
|
||||
use std::io::Error;
|
||||
use super::DomainEncode;
|
||||
use super::IOResult;
|
||||
use super::signed_integer::SignedIntegerRepr;
|
||||
use super::repr::{Value, NestedValue, IOValue, UnwrappedIOValue, Float, Double};
|
||||
|
||||
pub type Result<T> = std::result::Result<T, Error>;
|
||||
use super::repr::{Embeddable, Value, NestedValue, Float, Double};
|
||||
|
||||
pub trait AnnotationWriter: Writer {
|
||||
fn start_annotation(&mut self) -> Result<()>;
|
||||
fn start_value(&mut self) -> Result<()>;
|
||||
fn start_annotation(&mut self) -> IOResult<()>;
|
||||
fn start_value(&mut self) -> IOResult<()>;
|
||||
}
|
||||
|
||||
pub trait CompoundWriter: Writer {
|
||||
fn extend(&mut self) -> Result<()>;
|
||||
fn delimit(&mut self) -> Result<()>;
|
||||
fn extend(&mut self) -> IOResult<()>;
|
||||
fn delimit(&mut self) -> IOResult<()>;
|
||||
}
|
||||
|
||||
pub trait Writer: Sized {
|
||||
|
@ -21,65 +20,73 @@ pub trait Writer: Sized {
|
|||
type SetWriter: CompoundWriter;
|
||||
type EmbeddedWriter: Writer;
|
||||
|
||||
fn align(&mut self, natural_chunksize: u64) -> Result<()>;
|
||||
fn align(&mut self, natural_chunksize: u64) -> IOResult<()>;
|
||||
|
||||
fn start_annotations(&mut self) -> Result<Self::AnnWriter>;
|
||||
fn end_annotations(&mut self, ann: Self::AnnWriter) -> Result<()>;
|
||||
fn start_annotations(&mut self) -> IOResult<Self::AnnWriter>;
|
||||
fn end_annotations(&mut self, ann: Self::AnnWriter) -> IOResult<()>;
|
||||
|
||||
fn write_bool(&mut self, v: bool) -> Result<()>;
|
||||
fn write_bool(&mut self, v: bool) -> IOResult<()>;
|
||||
|
||||
fn write_f32(&mut self, v: f32) -> Result<()>;
|
||||
fn write_f64(&mut self, v: f64) -> Result<()>;
|
||||
fn write_f32(&mut self, v: f32) -> IOResult<()>;
|
||||
fn write_f64(&mut self, v: f64) -> IOResult<()>;
|
||||
|
||||
fn write_i8(&mut self, v: i8) -> Result<()>;
|
||||
fn write_u8(&mut self, v: u8) -> Result<()>;
|
||||
fn write_i16(&mut self, v: i16) -> Result<()>;
|
||||
fn write_u16(&mut self, v: u16) -> Result<()>;
|
||||
fn write_i32(&mut self, v: i32) -> Result<()>;
|
||||
fn write_u32(&mut self, v: u32) -> Result<()>;
|
||||
fn write_i64(&mut self, v: i64) -> Result<()>;
|
||||
fn write_u64(&mut self, v: u64) -> Result<()>;
|
||||
fn write_i128(&mut self, v: i128) -> Result<()>;
|
||||
fn write_u128(&mut self, v: u128) -> Result<()>;
|
||||
fn write_int(&mut self, v: &BigInt) -> Result<()>;
|
||||
fn write_i8(&mut self, v: i8) -> IOResult<()>;
|
||||
fn write_u8(&mut self, v: u8) -> IOResult<()>;
|
||||
fn write_i16(&mut self, v: i16) -> IOResult<()>;
|
||||
fn write_u16(&mut self, v: u16) -> IOResult<()>;
|
||||
fn write_i32(&mut self, v: i32) -> IOResult<()>;
|
||||
fn write_u32(&mut self, v: u32) -> IOResult<()>;
|
||||
fn write_i64(&mut self, v: i64) -> IOResult<()>;
|
||||
fn write_u64(&mut self, v: u64) -> IOResult<()>;
|
||||
fn write_i128(&mut self, v: i128) -> IOResult<()>;
|
||||
fn write_u128(&mut self, v: u128) -> IOResult<()>;
|
||||
fn write_int(&mut self, v: &BigInt) -> IOResult<()>;
|
||||
|
||||
fn write_string(&mut self, v: &str) -> Result<()>;
|
||||
fn write_bytes(&mut self, v: &[u8]) -> Result<()>;
|
||||
fn write_symbol(&mut self, v: &str) -> Result<()>;
|
||||
fn write_string(&mut self, v: &str) -> IOResult<()>;
|
||||
fn write_bytes(&mut self, v: &[u8]) -> IOResult<()>;
|
||||
fn write_symbol(&mut self, v: &str) -> IOResult<()>;
|
||||
|
||||
fn start_record(&mut self, field_count: Option<usize>) -> Result<Self::SeqWriter>;
|
||||
fn start_sequence(&mut self, item_count: Option<usize>) -> Result<Self::SeqWriter>;
|
||||
fn end_seq(&mut self, seq: Self::SeqWriter) -> Result<()>;
|
||||
fn start_record(&mut self, field_count: Option<usize>) -> IOResult<Self::SeqWriter>;
|
||||
fn start_sequence(&mut self, item_count: Option<usize>) -> IOResult<Self::SeqWriter>;
|
||||
fn end_seq(&mut self, seq: Self::SeqWriter) -> IOResult<()>;
|
||||
|
||||
fn start_set(&mut self, item_count: Option<usize>) -> Result<Self::SetWriter>;
|
||||
fn start_dictionary(&mut self, entry_count: Option<usize>) -> Result<Self::SetWriter>;
|
||||
fn end_set(&mut self, set: Self::SetWriter) -> Result<()>;
|
||||
fn start_set(&mut self, item_count: Option<usize>) -> IOResult<Self::SetWriter>;
|
||||
fn start_dictionary(&mut self, entry_count: Option<usize>) -> IOResult<Self::SetWriter>;
|
||||
fn end_set(&mut self, set: Self::SetWriter) -> IOResult<()>;
|
||||
|
||||
fn start_embedded(&mut self) -> Result<Self::EmbeddedWriter>;
|
||||
fn end_embedded(&mut self, ptr: Self::EmbeddedWriter) -> Result<()>;
|
||||
fn start_embedded(&mut self) -> IOResult<Self::EmbeddedWriter>;
|
||||
fn end_embedded(&mut self, ptr: Self::EmbeddedWriter) -> IOResult<()>;
|
||||
|
||||
//---------------------------------------------------------------------------
|
||||
|
||||
fn write(&mut self, v: &IOValue) -> Result<()> {
|
||||
fn write<D: Embeddable, N: NestedValue<D>, Enc: DomainEncode<D>>(
|
||||
&mut self,
|
||||
enc: &mut Enc,
|
||||
v: &N,
|
||||
) -> IOResult<()> {
|
||||
match v.annotations().maybe_slice() {
|
||||
None => {
|
||||
self.write_value(v.value())?;
|
||||
self.write_value(enc, v.value())?;
|
||||
}
|
||||
Some(anns) => {
|
||||
let mut a = self.start_annotations()?;
|
||||
for ann in anns {
|
||||
a.start_annotation()?;
|
||||
a.write(ann)?;
|
||||
a.write(enc, ann)?;
|
||||
}
|
||||
a.start_value()?;
|
||||
a.write_value(v.value())?;
|
||||
a.write_value(enc, v.value())?;
|
||||
self.end_annotations(a)?;
|
||||
}
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn write_value(&mut self, v: &UnwrappedIOValue) -> Result<()> {
|
||||
fn write_value<D: Embeddable, N: NestedValue<D>, Enc: DomainEncode<D>>(
|
||||
&mut self,
|
||||
enc: &mut Enc,
|
||||
v: &Value<N, D>,
|
||||
) -> IOResult<()> {
|
||||
match v {
|
||||
Value::Boolean(b) => self.write_bool(*b),
|
||||
Value::Float(Float(f)) => self.write_f32(*f),
|
||||
|
@ -95,11 +102,11 @@ pub trait Writer: Sized {
|
|||
Value::Record(r) => {
|
||||
let mut c = self.start_record(Some(r.arity()))?;
|
||||
c.extend()?;
|
||||
c.write(r.label())?;
|
||||
c.write(enc, r.label())?;
|
||||
c.delimit()?;
|
||||
for f in r.fields() {
|
||||
c.extend()?;
|
||||
c.write(f)?;
|
||||
c.write(enc, f)?;
|
||||
c.delimit()?;
|
||||
}
|
||||
self.end_seq(c)
|
||||
|
@ -108,7 +115,7 @@ pub trait Writer: Sized {
|
|||
let mut c = self.start_sequence(Some(vs.len()))?;
|
||||
for v in vs {
|
||||
c.extend()?;
|
||||
c.write(v)?;
|
||||
c.write(enc, v)?;
|
||||
c.delimit()?;
|
||||
}
|
||||
self.end_seq(c)
|
||||
|
@ -117,7 +124,7 @@ pub trait Writer: Sized {
|
|||
let mut c = self.start_set(Some(vs.len()))?;
|
||||
for v in vs {
|
||||
c.extend()?;
|
||||
c.write(v)?;
|
||||
c.write(enc, v)?;
|
||||
c.delimit()?;
|
||||
}
|
||||
self.end_set(c)
|
||||
|
@ -126,22 +133,22 @@ pub trait Writer: Sized {
|
|||
let mut c = self.start_dictionary(Some(vs.len()))?;
|
||||
for (k, v) in vs {
|
||||
c.extend()?;
|
||||
c.write(k)?;
|
||||
c.write(v)?;
|
||||
c.write(enc, k)?;
|
||||
c.write(enc, v)?;
|
||||
c.delimit()?;
|
||||
}
|
||||
self.end_set(c)
|
||||
}
|
||||
Value::Embedded(d) => {
|
||||
let mut c = self.start_embedded()?;
|
||||
c.write(&d)?;
|
||||
enc.encode_embedded(&mut c, d)?;
|
||||
self.end_embedded(c)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn varint<W: std::io::Write>(w: &mut W, mut v: u64) -> Result<usize> {
|
||||
pub fn varint<W: std::io::Write>(w: &mut W, mut v: u64) -> IOResult<usize> {
|
||||
let mut byte_count = 0;
|
||||
loop {
|
||||
byte_count += 1;
|
||||
|
|
|
@ -27,21 +27,21 @@ fn decode_all(bytes: &'_ [u8]) -> Result<Vec<IOValue>, std::io::Error> {
|
|||
println!("{:?} ==> {:?}", name, case);
|
||||
match case {
|
||||
TestCase::Test(ref bin, ref val) => {
|
||||
assert_eq!(&decode_all(&PackedWriter::encode(val)?[..])?, &[val.clone()]);
|
||||
assert_eq!(&decode_all(&PackedWriter::encode_iovalue(val)?[..])?, &[val.clone()]);
|
||||
assert_eq!(&decode_all(&bin[..])?, &[val.clone()]);
|
||||
assert_eq!(&PackedWriter::encode(val)?, bin);
|
||||
assert_eq!(&PackedWriter::encode_iovalue(val)?, bin);
|
||||
}
|
||||
TestCase::NondeterministicTest(ref bin, ref val) => {
|
||||
// The test cases in samples.pr are carefully written
|
||||
// so that while strictly "nondeterministic", the
|
||||
// order of keys in encoded dictionaries follows
|
||||
// Preserves canonical order.
|
||||
assert_eq!(&PackedWriter::encode(val)?, bin);
|
||||
assert_eq!(&decode_all(&PackedWriter::encode(val)?[..])?, &[val.clone()]);
|
||||
assert_eq!(&PackedWriter::encode_iovalue(val)?, bin);
|
||||
assert_eq!(&decode_all(&PackedWriter::encode_iovalue(val)?[..])?, &[val.clone()]);
|
||||
assert_eq!(&decode_all(&bin[..])?, &[val.clone()]);
|
||||
}
|
||||
TestCase::DecodeTest(ref bin, ref val) => {
|
||||
assert_eq!(&decode_all(&PackedWriter::encode(val)?[..])?, &[val.clone()]);
|
||||
assert_eq!(&decode_all(&PackedWriter::encode_iovalue(val)?[..])?, &[val.clone()]);
|
||||
assert_eq!(&decode_all(&bin[..])?, &[val.clone()]);
|
||||
}
|
||||
TestCase::ParseError(_) => (),
|
||||
|
|
Loading…
Reference in New Issue