use std::io;
use std::mem;
use std::str;
use std::char;
use std::vec;
use std::io::{BufReader, BufRead, Read};
use std::str::FromStr;
use std::collections::BTreeMap;
use std::iter::FusedIterator;
use serde::{de, forward_to_deserialize_any};
use serde::de::Visitor;
use num_bigint::{BigInt, Sign};
use num_traits::ToPrimitive;
use byteorder::{ByteOrder, BigEndian, LittleEndian};
use iter_read::{IterRead, IterReadItem};
use super::error::{Error, ErrorCode, Result};
use super::consts::*;
use super::value;
type MemoId = u32;
#[derive(Clone, Debug, PartialEq)]
enum Global {
Set,
Frozenset,
Bytearray,
Encode,
Other,
}
#[derive(Clone, Debug, PartialEq)]
enum Value {
MemoRef(MemoId),
Global(Global),
None,
Bool(bool),
I64(i64),
Int(BigInt),
F64(f64),
Bytes(Vec<u8>),
String(String),
List(Vec<Value>),
Tuple(Vec<Value>),
Set(Vec<Value>),
FrozenSet(Vec<Value>),
Dict(Vec<(Value, Value)>),
}
pub struct Deserializer<R: Read> {
rdr: BufReader<R>,
pos: usize,
value: Option<Value>,
memo: BTreeMap<MemoId, (Value, i32)>,
stack: Vec<Value>,
stacks: Vec<Vec<Value>>,
decode_strings: bool,
}
impl<R: Read> Deserializer<R> {
pub fn new(rdr: R, decode_strings: bool) -> Deserializer<R> {
Deserializer {
rdr: BufReader::new(rdr),
pos: 0,
value: None,
memo: BTreeMap::new(),
stack: Vec::with_capacity(128),
stacks: Vec::with_capacity(16),
decode_strings,
}
}
pub fn deserialize_value(&mut self) -> Result<value::Value> {
let internal_value = self.parse_value()?;
self.convert_value(internal_value)
}
fn get_next_value(&mut self) -> Result<Value> {
match self.value.take() {
Some(v) => Ok(v),
None => self.parse_value(),
}
}
fn parse_value(&mut self) -> Result<Value> {
loop {
match self.read_byte()? {
PROTO => {
self.read_byte()?;
}
FRAME => {
self.read_bytes(8)?;
}
STOP => return self.pop(),
MARK => {
let stack = mem::replace(&mut self.stack, Vec::with_capacity(128));
self.stacks.push(stack);
}
POP => {
if self.stack.is_empty() {
self.pop_mark()?;
} else {
self.pop()?;
}
},
POP_MARK => { self.pop_mark()?; },
DUP => { let top = self.top()?.clone(); self.stack.push(top); },
PUT => {
let bytes = self.read_line()?;
let memo_id = self.parse_ascii(bytes)?;
self.memoize(memo_id)?;
}
BINPUT => {
let memo_id = self.read_byte()?;
self.memoize(memo_id.into())?;
}
LONG_BINPUT => {
let bytes = self.read_bytes(4)?;
let memo_id = LittleEndian::read_u32(&bytes);
self.memoize(memo_id)?;
}
MEMOIZE => {
let memo_id = self.memo.len();
self.memoize(memo_id as MemoId)?;
}
GET => {
let bytes = self.read_line()?;
let memo_id = self.parse_ascii(bytes)?;
self.push_memo_ref(memo_id)?;
}
BINGET => {
let memo_id = self.read_byte()?;
self.push_memo_ref(memo_id.into())?;
}
LONG_BINGET => {
let bytes = self.read_bytes(4)?;
let memo_id = LittleEndian::read_u32(&bytes);
self.push_memo_ref(memo_id)?;
}
NONE => self.stack.push(Value::None),
NEWFALSE => self.stack.push(Value::Bool(false)),
NEWTRUE => self.stack.push(Value::Bool(true)),
INT => {
let line = self.read_line()?;
let val = self.decode_text_int(line)?;
self.stack.push(val);
}
LONG => {
let line = self.read_line()?;
let long = self.decode_text_long(line)?;
self.stack.push(long);
}
FLOAT => {
let line = self.read_line()?;
let f = self.parse_ascii(line)?;
self.stack.push(Value::F64(f));
}
STRING => {
let line = self.read_line()?;
let string = self.decode_escaped_string(&line)?;
self.stack.push(string);
}
UNICODE => {
let line = self.read_line()?;
let string = self.decode_escaped_unicode(&line)?;
self.stack.push(string);
}
BINFLOAT => {
let bytes = self.read_bytes(8)?;
self.stack.push(Value::F64(BigEndian::read_f64(&bytes)));
}
BININT => {
let bytes = self.read_bytes(4)?;
self.stack.push(Value::I64(LittleEndian::read_i32(&bytes).into()));
}
BININT1 => {
let byte = self.read_byte()?;
self.stack.push(Value::I64(byte.into()));
}
BININT2 => {
let bytes = self.read_bytes(2)?;
self.stack.push(Value::I64(LittleEndian::read_u16(&bytes).into()));
}
LONG1 => {
let bytes = self.read_u8_prefixed_bytes()?;
let long = self.decode_binary_long(bytes);
self.stack.push(long);
}
LONG4 => {
let bytes = self.read_i32_prefixed_bytes()?;
let long = self.decode_binary_long(bytes);
self.stack.push(long);
}
SHORT_BINBYTES => {
let string = self.read_u8_prefixed_bytes()?;
self.stack.push(Value::Bytes(string));
}
BINBYTES => {
let string = self.read_u32_prefixed_bytes()?;
self.stack.push(Value::Bytes(string));
}
BINBYTES8 => {
let string = self.read_u64_prefixed_bytes()?;
self.stack.push(Value::Bytes(string));
}
SHORT_BINSTRING => {
let string = self.read_u8_prefixed_bytes()?;
let decoded = self.decode_string(string)?;
self.stack.push(decoded);
}
BINSTRING => {
let string = self.read_i32_prefixed_bytes()?;
let decoded = self.decode_string(string)?;
self.stack.push(decoded);
}
SHORT_BINUNICODE => {
let string = self.read_u8_prefixed_bytes()?;
let decoded = self.decode_unicode(string)?;
self.stack.push(decoded);
}
BINUNICODE => {
let string = self.read_u32_prefixed_bytes()?;
let decoded = self.decode_unicode(string)?;
self.stack.push(decoded);
}
BINUNICODE8 => {
let string = self.read_u64_prefixed_bytes()?;
let decoded = self.decode_unicode(string)?;
self.stack.push(decoded);
}
EMPTY_TUPLE => self.stack.push(Value::Tuple(Vec::new())),
TUPLE1 => {
let item = self.pop()?;
self.stack.push(Value::Tuple(vec![item]));
}
TUPLE2 => {
let item2 = self.pop()?;
let item1 = self.pop()?;
self.stack.push(Value::Tuple(vec![item1, item2]));
}
TUPLE3 => {
let item3 = self.pop()?;
let item2 = self.pop()?;
let item1 = self.pop()?;
self.stack.push(Value::Tuple(vec![item1, item2, item3]));
}
TUPLE => {
let items = self.pop_mark()?;
self.stack.push(Value::Tuple(items));
}
EMPTY_LIST => self.stack.push(Value::List(Vec::new())),
LIST => {
let items = self.pop_mark()?;
self.stack.push(Value::List(items));
}
APPEND => {
let value = self.pop()?;
self.modify_list(|list| list.push(value))?;
}
APPENDS => {
let items = self.pop_mark()?;
self.modify_list(|list| list.extend(items))?;
}
EMPTY_DICT => self.stack.push(Value::Dict(Vec::new())),
DICT => {
let items = self.pop_mark()?;
let mut dict = Vec::with_capacity(items.len() / 2);
Self::extend_dict(&mut dict, items);
self.stack.push(Value::Dict(dict));
}
SETITEM => {
let value = self.pop()?;
let key = self.pop()?;
self.modify_dict(|dict| dict.push((key, value)))?;
}
SETITEMS => {
let items = self.pop_mark()?;
self.modify_dict(|dict| Self::extend_dict(dict, items))?;
}
EMPTY_SET => self.stack.push(Value::Set(Vec::new())),
FROZENSET => {
let items = self.pop_mark()?;
self.stack.push(Value::FrozenSet(items));
}
ADDITEMS => {
let items = self.pop_mark()?;
self.modify_set(|set| set.extend(items))?;
}
GLOBAL => {
let modname = self.read_line()?;
let globname = self.read_line()?;
let value = self.decode_global(modname, globname)?;
self.stack.push(value);
}
STACK_GLOBAL => {
let globname = match self.pop_resolve()? {
Value::String(string) => string.into_bytes(),
other => return Self::stack_error("string", &other, self.pos),
};
let modname = match self.pop_resolve()? {
Value::String(string) => string.into_bytes(),
other => return Self::stack_error("string", &other, self.pos),
};
let value = self.decode_global(modname, globname)?;
self.stack.push(value);
}
REDUCE => {
let argtuple = match self.pop_resolve()? {
Value::Tuple(args) => args,
other => return Self::stack_error("tuple", &other, self.pos),
};
let global = self.pop_resolve()?;
self.reduce_global(global, argtuple)?;
}
INST => {
for _ in 0..2 {
self.read_line()?;
}
self.pop_mark()?;
self.stack.push(Value::Dict(Vec::new()));
}
OBJ => {
self.pop_mark()?;
self.pop()?;
self.stack.push(Value::Dict(Vec::new()));
}
NEWOBJ => {
for _ in 0..2 {
self.pop()?;
}
self.stack.push(Value::Dict(Vec::new()));
}
NEWOBJ_EX => {
for _ in 0..3 {
self.pop()?;
}
self.stack.push(Value::Dict(Vec::new()));
}
BUILD => {
let state = self.pop()?;
self.pop()?;
self.stack.push(state);
}
code => return self.error(ErrorCode::Unsupported(code as char))
}
}
}
fn pop(&mut self) -> Result<Value> {
match self.stack.pop() {
Some(v) => Ok(v),
None => self.error(ErrorCode::StackUnderflow)
}
}
fn pop_resolve(&mut self) -> Result<Value> {
let top = self.stack.pop();
match self.resolve(top) {
Some(v) => Ok(v),
None => self.error(ErrorCode::StackUnderflow)
}
}
fn pop_mark(&mut self) -> Result<Vec<Value>> {
match self.stacks.pop() {
Some(new) => Ok(mem::replace(&mut self.stack, new)),
None => self.error(ErrorCode::StackUnderflow)
}
}
fn top(&mut self) -> Result<&mut Value> {
match self.stack.last_mut() {
Some(&mut Value::MemoRef(n)) =>
self.memo.get_mut(&n)
.map(|&mut (ref mut v, _)| v)
.ok_or_else(|| Error::Syntax(ErrorCode::MissingMemo(n))),
Some(other_value) => Ok(other_value),
None => Err(Error::Eval(ErrorCode::StackUnderflow, self.pos)),
}
}
fn push_memo_ref(&mut self, memo_id: MemoId) -> Result<()> {
self.stack.push(Value::MemoRef(memo_id));
match self.memo.get_mut(&memo_id) {
Some(&mut (_, ref mut count)) => { *count += 1; Ok(()) }
None => Err(Error::Eval(ErrorCode::MissingMemo(memo_id), self.pos)),
}
}
fn memoize(&mut self, memo_id: MemoId) -> Result<()> {
let mut item = self.pop()?;
if let Value::MemoRef(id) = item {
item = match self.memo.get(&id) {
Some(&(ref v, _)) => v.clone(),
None => return Err(Error::Eval(ErrorCode::MissingMemo(id), self.pos)),
};
}
self.memo.insert(memo_id, (item, 1));
self.stack.push(Value::MemoRef(memo_id));
Ok(())
}
fn resolve(&mut self, maybe_memo: Option<Value>) -> Option<Value> {
match maybe_memo {
Some(Value::MemoRef(id)) => {
self.memo.get_mut(&id).map(|&mut (ref val, ref mut count)| {
*count -= 1;
val.clone()
})
},
other => other
}
}
fn resolve_recursive<T, U, F>(&mut self, id: MemoId, u: U, f: F) -> Result<T>
where F: Fn(&mut Self, U, Value) -> Result<T>
{
let (value, mut count) = match self.memo.remove(&id) {
Some(entry) => entry,
None => return Err(Error::Syntax(ErrorCode::Recursive)),
};
count -= 1;
if count <= 0 {
f(self, u, value)
} else {
let result = f(self, u, value.clone());
self.memo.insert(id, (value, count));
result
}
}
pub fn end(&mut self) -> Result<()> {
let mut buf = [0];
match self.rdr.read(&mut buf) {
Err(err) => Err(Error::Io(err)),
Ok(1) => self.error(ErrorCode::TrailingBytes),
_ => Ok(())
}
}
fn read_line(&mut self) -> Result<Vec<u8>> {
let mut buf = Vec::with_capacity(16);
match self.rdr.read_until(b'\n', &mut buf) {
Ok(_) => {
self.pos += buf.len();
buf.pop();
if buf.last() == Some(&b'\r') { buf.pop(); }
Ok(buf)
},
Err(err) => Err(Error::Io(err))
}
}
#[inline]
fn read_byte(&mut self) -> Result<u8> {
let mut buf = [0];
match self.rdr.read(&mut buf) {
Ok(1) => { self.pos += 1; Ok(buf[0]) },
Ok(_) => self.error(ErrorCode::EOFWhileParsing),
Err(err) => Err(Error::Io(err)),
}
}
#[inline]
fn read_bytes(&mut self, n: usize) -> Result<Vec<u8>> {
let mut buf = Vec::new();
match self.rdr.by_ref().take(n as u64).read_to_end(&mut buf) {
Ok(m) if n == m => { self.pos += n; Ok(buf) },
Ok(_) => self.error(ErrorCode::EOFWhileParsing),
Err(err) => Err(Error::Io(err)),
}
}
fn read_i32_prefixed_bytes(&mut self) -> Result<Vec<u8>> {
let lenbytes = self.read_bytes(4)?;
match LittleEndian::read_i32(&lenbytes) {
0 => Ok(vec![]),
l if l < 0 => self.error(ErrorCode::NegativeLength),
l => self.read_bytes(l as usize)
}
}
fn read_u64_prefixed_bytes(&mut self) -> Result<Vec<u8>> {
let lenbytes = self.read_bytes(8)?;
self.read_bytes(LittleEndian::read_u64(&lenbytes) as usize)
}
fn read_u32_prefixed_bytes(&mut self) -> Result<Vec<u8>> {
let lenbytes = self.read_bytes(4)?;
self.read_bytes(LittleEndian::read_u32(&lenbytes) as usize)
}
fn read_u8_prefixed_bytes(&mut self) -> Result<Vec<u8>> {
let lenbyte = self.read_byte()?;
self.read_bytes(lenbyte as usize)
}
fn parse_ascii<T: FromStr>(&self, bytes: Vec<u8>) -> Result<T> {
match str::from_utf8(&bytes).unwrap_or("").parse() {
Ok(v) => Ok(v),
Err(_) => self.error(ErrorCode::InvalidLiteral(bytes)),
}
}
fn decode_text_int(&self, line: Vec<u8>) -> Result<Value> {
Ok(if line == b"00" {
Value::Bool(false)
} else if line == b"01" {
Value::Bool(true)
} else {
let i = self.parse_ascii(line)?;
Value::I64(i)
})
}
fn decode_text_long(&self, mut line: Vec<u8>) -> Result<Value> {
if line.last() == Some(&b'L') { line.pop(); }
match BigInt::parse_bytes(&line, 10) {
Some(i) => Ok(Value::Int(i)),
None => self.error(ErrorCode::InvalidLiteral(line))
}
}
fn decode_escaped_string(&self, slice: &[u8]) -> Result<Value> {
let slice = if (slice.len() >= 2) &&
(slice[0] == slice[slice.len() - 1]) &&
(slice[0] == b'"' || slice[0] == b'\'')
{
&slice[1..slice.len() - 1]
} else {
slice
};
let mut result = Vec::with_capacity(slice.len());
let mut iter = slice.iter();
while let Some(&b) = iter.next() {
match b {
b'\\' => match iter.next() {
Some(&b'\\') => result.push(b'\\'),
Some(&b'a') => result.push(b'\x07'),
Some(&b'b') => result.push(b'\x08'),
Some(&b't') => result.push(b'\x09'),
Some(&b'n') => result.push(b'\x0a'),
Some(&b'v') => result.push(b'\x0b'),
Some(&b'f') => result.push(b'\x0c'),
Some(&b'r') => result.push(b'\x0d'),
Some(&b'x') => {
match iter.next()
.and_then(|&ch1| (ch1 as char).to_digit(16))
.and_then(|v1| iter.next()
.and_then(|&ch2| (ch2 as char).to_digit(16))
.map(|v2| 16*(v1 as u8) + (v2 as u8)))
{
Some(v) => result.push(v),
None => return self.error(ErrorCode::InvalidLiteral(slice.into()))
}
},
_ => return self.error(ErrorCode::InvalidLiteral(slice.into())),
},
_ => result.push(b)
}
}
self.decode_string(result)
}
fn decode_escaped_unicode(&self, s: &[u8]) -> Result<Value> {
let mut result = String::with_capacity(s.len());
let mut iter = s.iter();
while let Some(&b) = iter.next() {
match b {
b'\\' => {
let nescape = match iter.next() {
Some(&b'u') => 4,
Some(&b'U') => 8,
_ => return self.error(ErrorCode::InvalidLiteral(s.into())),
};
let mut accum = 0;
for _i in 0..nescape {
accum *= 16;
match iter.next().and_then(|&ch| (ch as char).to_digit(16)) {
Some(v) => accum += v,
None => return self.error(ErrorCode::InvalidLiteral(s.into()))
}
}
match char::from_u32(accum) {
Some(v) => result.push(v),
None => return self.error(ErrorCode::InvalidLiteral(s.into()))
}
}
_ => result.push(b as char)
}
}
Ok(Value::String(result))
}
fn decode_string(&self, string: Vec<u8>) -> Result<Value> {
if self.decode_strings {
self.decode_unicode(string)
} else {
Ok(Value::Bytes(string))
}
}
fn decode_unicode(&self, string: Vec<u8>) -> Result<Value> {
match String::from_utf8(string) {
Ok(v) => Ok(Value::String(v)),
Err(_) => self.error(ErrorCode::StringNotUTF8)
}
}
fn decode_binary_long(&self, bytes: Vec<u8>) -> Value {
let negative = !bytes.is_empty() && (bytes[bytes.len() - 1] & 0x80 != 0);
let mut val = BigInt::from_bytes_le(Sign::Plus, &bytes);
if negative {
val -= BigInt::from(1) << (bytes.len() * 8);
}
Value::Int(val)
}
fn modify_list<F>(&mut self, f: F) -> Result<()>
where F: FnOnce(&mut Vec<Value>)
{
let pos = self.pos;
let top = self.top()?;
if let Value::List(ref mut list) = *top {
f(list);
Ok(())
} else {
Self::stack_error("list", top, pos)
}
}
fn extend_dict(dict: &mut Vec<(Value, Value)>, items: Vec<Value>) {
let mut key = None;
for value in items {
match key.take() {
None => key = Some(value),
Some(key) => dict.push((key, value))
}
}
}
fn modify_dict<F>(&mut self, f: F) -> Result<()>
where F: FnOnce(&mut Vec<(Value, Value)>)
{
let pos = self.pos;
let top = self.top()?;
if let Value::Dict(ref mut dict) = *top {
f(dict);
Ok(())
} else {
Self::stack_error("dict", top, pos)
}
}
fn modify_set<F>(&mut self, f: F) -> Result<()>
where F: FnOnce(&mut Vec<Value>)
{
let pos = self.pos;
let top = self.top()?;
if let Value::Set(ref mut set) = *top {
f(set);
Ok(())
} else {
Self::stack_error("set", top, pos)
}
}
fn decode_global(&mut self, modname: Vec<u8>, globname: Vec<u8>) -> Result<Value> {
let value = match (&*modname, &*globname) {
(b"_codecs", b"encode") => Value::Global(Global::Encode),
(b"__builtin__", b"set") | (b"builtins", b"set") =>
Value::Global(Global::Set),
(b"__builtin__", b"frozenset") | (b"builtins", b"frozenset") =>
Value::Global(Global::Frozenset),
(b"__builtin__", b"bytearray") | (b"builtins", b"bytearray") =>
Value::Global(Global::Bytearray),
_ => Value::Global(Global::Other),
};
Ok(value)
}
fn reduce_global(&mut self, global: Value, mut argtuple: Vec<Value>) -> Result<()> {
match global {
Value::Global(Global::Set) => {
match self.resolve(argtuple.pop()) {
Some(Value::List(items)) => {
self.stack.push(Value::Set(items));
Ok(())
}
_ => self.error(ErrorCode::InvalidValue("set() arg".into())),
}
}
Value::Global(Global::Frozenset) => {
match self.resolve(argtuple.pop()) {
Some(Value::List(items)) => {
self.stack.push(Value::FrozenSet(items));
Ok(())
}
_ => self.error(ErrorCode::InvalidValue("frozenset() arg".into())),
}
}
Value::Global(Global::Bytearray) => {
argtuple.truncate(1);
match self.resolve(argtuple.pop()) {
Some(Value::Bytes(bytes)) => {
self.stack.push(Value::Bytes(bytes));
Ok(())
}
Some(Value::String(string)) => {
self.stack.push(Value::Bytes(
string.chars().map(|ch| ch as u32 as u8).collect()));
Ok(())
}
_ => self.error(ErrorCode::InvalidValue("bytearray() arg".into())),
}
}
Value::Global(Global::Encode) => {
match self.resolve(argtuple.pop()) {
Some(Value::String(_)) => { }
_ => return self.error(ErrorCode::InvalidValue("encode() arg".into())),
}
match self.resolve(argtuple.pop()) {
Some(Value::String(s)) => {
let bytes = s.chars().map(|ch| ch as u8).collect();
self.stack.push(Value::Bytes(bytes));
Ok(())
}
_ => self.error(ErrorCode::InvalidValue("encode() arg".into())),
}
}
Value::Global(Global::Other) => {
self.stack.push(Value::Global(Global::Other));
Ok(())
}
other => Self::stack_error("global reference", &other, self.pos),
}
}
fn stack_error<T>(what: &'static str, value: &Value, pos: usize) -> Result<T> {
let it = format!("{:?}", value);
Err(Error::Eval(ErrorCode::InvalidStackTop(what, it), pos))
}
fn error<T>(&self, reason: ErrorCode) -> Result<T> {
Err(Error::Eval(reason, self.pos))
}
fn convert_value(&mut self, value: Value) -> Result<value::Value> {
match value {
Value::None => Ok(value::Value::None),
Value::Bool(v) => Ok(value::Value::Bool(v)),
Value::I64(v) => Ok(value::Value::I64(v)),
Value::Int(v) => {
if let Some(i) = v.to_i64() {
Ok(value::Value::I64(i))
} else {
Ok(value::Value::Int(v))
}
},
Value::F64(v) => Ok(value::Value::F64(v)),
Value::Bytes(v) => Ok(value::Value::Bytes(v)),
Value::String(v) => Ok(value::Value::String(v)),
Value::List(v) => {
let new = v.into_iter().map(|v| self.convert_value(v))
.collect::<Result<_>>();
Ok(value::Value::List(new?))
},
Value::Tuple(v) => {
let new = v.into_iter().map(|v| self.convert_value(v))
.collect::<Result<_>>();
Ok(value::Value::Tuple(new?))
},
Value::Set(v) => {
let new = v.into_iter().map(|v| self.convert_value(v)
.and_then(|rv| rv.into_hashable()))
.collect::<Result<_>>();
Ok(value::Value::Set(new?))
},
Value::FrozenSet(v) => {
let new = v.into_iter().map(|v| self.convert_value(v)
.and_then(|rv| rv.into_hashable()))
.collect::<Result<_>>();
Ok(value::Value::FrozenSet(new?))
},
Value::Dict(v) => {
let mut map = BTreeMap::new();
for (key, value) in v {
let real_key = self.convert_value(key).and_then(|rv| rv.into_hashable())?;
let real_value = self.convert_value(value)?;
map.insert(real_key, real_value);
}
Ok(value::Value::Dict(map))
},
Value::MemoRef(memo_id) => {
self.resolve_recursive(memo_id, (), |slf, (), value| slf.convert_value(value))
},
Value::Global(_) => Err(Error::Syntax(ErrorCode::UnresolvedGlobal)),
}
}
}
impl<'de: 'a, 'a, R: Read> de::Deserializer<'de> for &'a mut Deserializer<R> {
type Error = Error;
fn deserialize_any<V: Visitor<'de>>(mut self, visitor: V) -> Result<V::Value> {
let value = self.get_next_value()?;
match value {
Value::None => visitor.visit_unit(),
Value::Bool(v) => visitor.visit_bool(v),
Value::I64(v) => visitor.visit_i64(v),
Value::Int(v) => {
if let Some(i) = v.to_i64() {
visitor.visit_i64(i)
} else {
return Err(Error::Syntax(ErrorCode::InvalidValue("integer too large".into())));
}
},
Value::F64(v) => visitor.visit_f64(v),
Value::Bytes(v) => visitor.visit_byte_buf(v),
Value::String(v) => visitor.visit_string(v),
Value::List(v) => {
let len = v.len();
visitor.visit_seq(SeqAccess {
de: &mut self,
iter: v.into_iter(),
len,
})
},
Value::Tuple(v) => {
visitor.visit_seq(SeqAccess {
len: v.len(),
iter: v.into_iter(),
de: &mut self,
})
}
Value::Set(v) | Value::FrozenSet(v) => {
visitor.visit_seq(SeqAccess {
de: &mut self,
len: v.len(),
iter: v.into_iter(),
})
},
Value::Dict(v) => {
let len = v.len();
visitor.visit_map(MapAccess {
de: &mut self,
iter: v.into_iter(),
value: None,
len,
})
},
Value::MemoRef(memo_id) => {
self.resolve_recursive(memo_id, visitor, |slf, visitor, value| {
slf.value = Some(value);
slf.deserialize_any(visitor)
})
},
Value::Global(_) => Err(Error::Syntax(ErrorCode::UnresolvedGlobal)),
}
}
#[inline]
fn deserialize_option<V: Visitor<'de>>(self, visitor: V) -> Result<V::Value> {
let value = self.get_next_value()?;
match value {
Value::None => visitor.visit_none(),
_ => {
self.value = Some(value);
visitor.visit_some(self)
}
}
}
#[inline]
fn deserialize_newtype_struct<V: Visitor<'de>>(self, _name: &'static str, visitor: V) -> Result<V::Value> {
visitor.visit_newtype_struct(self)
}
#[inline]
fn deserialize_enum<V: Visitor<'de>>(mut self, _name: &'static str, _variants: &'static [&'static str],
visitor: V) -> Result<V::Value> {
visitor.visit_enum(VariantAccess { de: &mut self })
}
forward_to_deserialize_any! {
bool u8 u16 u32 u64 i8 i16 i32 i64 f32 f64 char str string unit seq
bytes byte_buf map tuple_struct struct identifier
tuple ignored_any unit_struct
}
}
struct VariantAccess<'a, R: Read + 'a> {
de: &'a mut Deserializer<R>,
}
impl<'de: 'a, 'a, R: Read + 'a> de::EnumAccess<'de> for VariantAccess<'a, R> {
type Error = Error;
type Variant = Self;
fn variant_seed<V: de::DeserializeSeed<'de>>(self, seed: V) -> Result<(V::Value, Self)> {
let value = self.de.get_next_value()?;
match value {
Value::Tuple(mut v) => {
if v.len() == 2 {
let args = v.pop();
self.de.value = v.pop();
let val = seed.deserialize(&mut *self.de)?;
self.de.value = args;
Ok((val, self))
} else {
self.de.value = v.pop();
let val = seed.deserialize(&mut *self.de)?;
Ok((val, self))
}
}
Value::Dict(mut v) => {
if v.len() != 1 {
Err(Error::Syntax(ErrorCode::Structure("enum variants must \
have one dict entry".into())))
} else {
let (name, args) = v.pop().unwrap();
self.de.value = Some(name);
let val = seed.deserialize(&mut *self.de)?;
self.de.value = Some(args);
Ok((val, self))
}
}
s @ Value::String(_) => {
self.de.value = Some(s);
let val = seed.deserialize(&mut *self.de)?;
Ok((val, self))
}
_ => Err(Error::Syntax(ErrorCode::Structure("enums must be represented as \
dicts or tuples".into())))
}
}
}
impl<'de: 'a, 'a, R: Read + 'a> de::VariantAccess<'de> for VariantAccess<'a, R> {
type Error = Error;
fn unit_variant(self) -> Result<()> {
Ok(())
}
fn newtype_variant_seed<T: de::DeserializeSeed<'de>>(self, seed: T) -> Result<T::Value> {
seed.deserialize(self.de)
}
fn tuple_variant<V: Visitor<'de>>(self, _len: usize, visitor: V) -> Result<V::Value> {
de::Deserializer::deserialize_any(self.de, visitor)
}
fn struct_variant<V: Visitor<'de>>(self, _fields: &'static [&'static str], visitor: V) -> Result<V::Value> {
de::Deserializer::deserialize_any(self.de, visitor)
}
}
struct SeqAccess<'a, R: Read + 'a> {
de: &'a mut Deserializer<R>,
iter: vec::IntoIter<Value>,
len: usize,
}
impl<'de: 'a, 'a, R: Read> de::SeqAccess<'de> for SeqAccess<'a, R> {
type Error = Error;
fn next_element_seed<T: de::DeserializeSeed<'de>>(&mut self, seed: T) -> Result<Option<T::Value>> {
match self.iter.next() {
Some(value) => {
self.len -= 1;
self.de.value = Some(value);
Ok(Some(seed.deserialize(&mut *self.de)?))
}
None => Ok(None),
}
}
fn size_hint(&self) -> Option<usize> {
Some(self.len)
}
}
struct MapAccess<'a, R: Read + 'a> {
de: &'a mut Deserializer<R>,
iter: vec::IntoIter<(Value, Value)>,
value: Option<Value>,
len: usize,
}
impl<'de: 'a, 'a, R: Read> de::MapAccess<'de> for MapAccess<'a, R> {
type Error = Error;
fn next_key_seed<T: de::DeserializeSeed<'de>>(&mut self, seed: T) -> Result<Option<T::Value>> {
match self.iter.next() {
Some((key, value)) => {
self.len -= 1;
self.value = Some(value);
self.de.value = Some(key);
Ok(Some(seed.deserialize(&mut *self.de)?))
}
None => Ok(None),
}
}
fn next_value_seed<T: de::DeserializeSeed<'de>>(&mut self, seed: T) -> Result<T::Value> {
let value = self.value.take().unwrap();
self.de.value = Some(value);
Ok(seed.deserialize(&mut *self.de)?)
}
fn size_hint(&self) -> Option<usize> {
Some(self.len)
}
}
pub fn from_reader<'de, R: io::Read, T: de::Deserialize<'de>>(rdr: R) -> Result<T> {
let mut de = Deserializer::new(rdr, false);
let value = de::Deserialize::deserialize(&mut de)?;
de.end()?;
Ok(value)
}
pub fn from_slice<'de, T: de::Deserialize<'de>>(v: &[u8]) -> Result<T> {
from_reader(io::Cursor::new(v))
}
pub fn from_iter<'de, E: IterReadItem, I: FusedIterator<Item=E>, T: de::Deserialize<'de>>(it: I) -> Result<T> {
from_reader(IterRead::new(it))
}
pub fn value_from_reader<R: io::Read>(rdr: R) -> Result<value::Value> {
let mut de = Deserializer::new(rdr, false);
let value = de.deserialize_value()?;
de.end()?;
Ok(value)
}
pub fn value_from_slice(v: &[u8]) -> Result<value::Value> {
value_from_reader(io::Cursor::new(v))
}
pub fn value_from_iter<E: IterReadItem, I: FusedIterator<Item=E>>(it: I) -> Result<value::Value> {
value_from_reader(IterRead::new(it))
}