rust-bitcoin-unsafe-fast/src/network/serialize.rs

214 lines
6.3 KiB
Rust
Raw Normal View History

2014-07-18 13:56:17 +00:00
// Rust Bitcoin Library
// Written in 2014 by
// Andrew Poelstra <apoelstra@wpsoftware.net>
//
// To the extent possible under law, the author(s) have dedicated all
// copyright and related and neighboring rights to this software to
// the public domain worldwide. This software is distributed without
// any warranty.
//
// You should have received a copy of the CC0 Public Domain Dedication
// along with this software.
// If not, see <http://creativecommons.org/publicdomain/zero/1.0/>.
//
//! # Network Serialization
//!
//! This module defines the `Serializable` trait which is used for
//! (de)serializing Bitcoin objects for transmission on the network.
//! It also defines (de)serialization routines for many primitives.
//!
use collections::Vec;
use std::io::{self, Cursor, Read, Write};
use serialize::hex::ToHex;
2014-07-18 13:56:17 +00:00
use network::encodable::{ConsensusDecodable, ConsensusEncodable};
2014-07-18 13:56:17 +00:00
use util::hash::Sha256dHash;
/// Objects which are referred to by hash
pub trait BitcoinHash {
/// Produces a Sha256dHash which can be used to refer to the object
fn bitcoin_hash(&self) -> Sha256dHash;
2014-07-18 13:56:17 +00:00
}
impl BitcoinHash for Vec<u8> {
fn bitcoin_hash(&self) -> Sha256dHash {
Sha256dHash::from_data(self.as_slice())
2014-07-18 13:56:17 +00:00
}
}
/// Encode an object into a vector
pub fn serialize<T: ConsensusEncodable<RawEncoder<Cursor<Vec<u8>>>>>(obj: &T) -> io::Result<Vec<u8>> {
let mut encoder = RawEncoder::new(Cursor::new(vec![]));
try!(obj.consensus_encode(&mut encoder));
Ok(encoder.unwrap().unwrap())
2014-07-18 13:56:17 +00:00
}
/// Encode an object into a hex-encoded string
pub fn serialize_hex<T: ConsensusEncodable<RawEncoder<Cursor<Vec<u8>>>>>(obj: &T) -> io::Result<String> {
let serial = try!(serialize(obj));
Ok(serial.as_slice().to_hex())
}
/// Deserialize an object from a vector
pub fn deserialize<T: ConsensusDecodable<RawDecoder<Cursor<Vec<u8>>>>>(data: Vec<u8>) -> io::Result<T> {
let mut decoder = RawDecoder::new(Cursor::new(data));
ConsensusDecodable::consensus_decode(&mut decoder)
}
/// An encoder for raw binary data
pub struct RawEncoder<W> {
writer: W
2014-07-18 13:56:17 +00:00
}
/// An decoder for raw binary data
pub struct RawDecoder<R> {
reader: R
2014-07-18 13:56:17 +00:00
}
impl<W:Write> RawEncoder<W> {
/// Constructor
pub fn new(writer: W) -> RawEncoder<W> {
RawEncoder { writer: writer }
2014-07-18 13:56:17 +00:00
}
/// Returns the underlying Writer
pub fn unwrap(self) -> W {
self.writer
2014-07-18 13:56:17 +00:00
}
}
impl<R:Read> RawDecoder<R> {
/// Constructor
pub fn new(reader: R) -> RawDecoder<R> {
RawDecoder { reader: reader }
2014-07-18 13:56:17 +00:00
}
/// Returns the underlying Reader
pub fn unwrap(self) -> R {
self.reader
2014-07-18 13:56:17 +00:00
}
}
/// A simple Encoder trait
pub trait SimpleEncoder {
type Error;
/// Output a 64-bit uint
fn emit_u64(&mut self, v: u64) -> Result<(), Self::Error>;
/// Output a 32-bit uint
fn emit_u32(&mut self, v: u32) -> Result<(), Self::Error>;
/// Output a 16-bit uint
fn emit_u16(&mut self, v: u16) -> Result<(), Self::Error>;
/// Output a 8-bit uint
fn emit_u8(&mut self, v: u8) -> Result<(), Self::Error>;
2014-07-18 13:56:17 +00:00
/// Output a 64-bit int
fn emit_i64(&mut self, v: i64) -> Result<(), Self::Error>;
/// Output a 32-bit int
fn emit_i32(&mut self, v: i32) -> Result<(), Self::Error>;
/// Output a 16-bit int
fn emit_i16(&mut self, v: i16) -> Result<(), Self::Error>;
/// Output a 8-bit int
fn emit_i8(&mut self, v: i8) -> Result<(), Self::Error>;
2014-07-18 13:56:17 +00:00
/// Output a boolean
fn emit_bool(&mut self, v: bool) -> Result<(), Self::Error>;
2014-07-18 13:56:17 +00:00
}
/// A simple Decoder trait
pub trait SimpleDecoder {
type Error;
/// Read a 64-bit uint
fn read_u64(&mut self) -> Result<u64, Self::Error>;
/// Read a 32-bit uint
fn read_u32(&mut self) -> Result<u32, Self::Error>;
/// Read a 16-bit uint
fn read_u16(&mut self) -> Result<u16, Self::Error>;
/// Read a 8-bit uint
fn read_u8(&mut self) -> Result<u8, Self::Error>;
2014-07-18 13:56:17 +00:00
/// Read a 64-bit int
fn read_i64(&mut self) -> Result<i64, Self::Error>;
/// Read a 32-bit int
fn read_i32(&mut self) -> Result<i32, Self::Error>;
/// Read a 16-bit int
fn read_i16(&mut self) -> Result<i16, Self::Error>;
/// Read a 8-bit int
fn read_i8(&mut self) -> Result<i8, Self::Error>;
2014-07-18 13:56:17 +00:00
/// Read a boolean
fn read_bool(&mut self) -> Result<bool, Self::Error>;
2014-07-18 13:56:17 +00:00
/// Signal a decoding error
fn error(&mut self, err: &str) -> Self::Error;
2014-07-18 13:56:17 +00:00
}
// TODO: trait reform: impl SimpleEncoder for every Encoder, ditto for Decoder
2014-07-18 13:56:17 +00:00
impl<W: Write> SimpleEncoder for RawEncoder<W> {
type Error = io::Error;
#[inline]
2015-03-26 16:52:20 +00:00
fn emit_u64(&mut self, v: u64) -> io::Result<()> { self.writer.write_le_u64(v) }
#[inline]
2015-03-26 16:52:20 +00:00
fn emit_u32(&mut self, v: u32) -> io::Result<()> { self.writer.write_le_u32(v) }
#[inline]
2015-03-26 16:52:20 +00:00
fn emit_u16(&mut self, v: u16) -> io::Result<()> { self.writer.write_le_u16(v) }
#[inline]
2015-03-26 16:52:20 +00:00
fn emit_u8(&mut self, v: u8) -> io::Result<()> { self.writer.write_u8(v) }
2014-07-18 13:56:17 +00:00
#[inline]
2015-03-26 16:52:20 +00:00
fn emit_i64(&mut self, v: i64) -> io::Result<()> { self.writer.write_le_i64(v) }
#[inline]
2015-03-26 16:52:20 +00:00
fn emit_i32(&mut self, v: i32) -> io::Result<()> { self.writer.write_le_i32(v) }
#[inline]
2015-03-26 16:52:20 +00:00
fn emit_i16(&mut self, v: i16) -> io::Result<()> { self.writer.write_le_i16(v) }
#[inline]
2015-03-26 16:52:20 +00:00
fn emit_i8(&mut self, v: i8) -> io::Result<()> { self.writer.write_i8(v) }
2014-07-18 13:56:17 +00:00
#[inline]
2015-03-26 16:52:20 +00:00
fn emit_bool(&mut self, v: bool) -> io::Result<()> { self.writer.write_i8(if v {1} else {0}) }
2014-07-18 13:56:17 +00:00
}
impl<R: Read> SimpleDecoder for RawDecoder<R> {
type Error = io::Error;
#[inline]
2015-03-26 16:52:20 +00:00
fn read_u64(&mut self) -> io::Result<u64> { self.reader.read_le_u64() }
#[inline]
2015-03-26 16:52:20 +00:00
fn read_u32(&mut self) -> io::Result<u32> { self.reader.read_le_u32() }
#[inline]
2015-03-26 16:52:20 +00:00
fn read_u16(&mut self) -> io::Result<u16> { self.reader.read_le_u16() }
#[inline]
2015-03-26 16:52:20 +00:00
fn read_u8(&mut self) -> io::Result<u8> { self.reader.read_u8() }
2014-07-18 13:56:17 +00:00
#[inline]
2015-03-26 16:52:20 +00:00
fn read_i64(&mut self) -> io::Result<i64> { self.reader.read_le_i64() }
#[inline]
2015-03-26 16:52:20 +00:00
fn read_i32(&mut self) -> io::Result<i32> { self.reader.read_le_i32() }
#[inline]
2015-03-26 16:52:20 +00:00
fn read_i16(&mut self) -> io::Result<i16> { self.reader.read_le_i16() }
#[inline]
2015-03-26 16:52:20 +00:00
fn read_i8(&mut self) -> io::Result<i8> { self.reader.read_i8() }
2014-07-18 13:56:17 +00:00
#[inline]
2015-03-26 16:52:20 +00:00
fn read_bool(&mut self) -> io::Result<bool> { self.reader.read_u8().map(|res| res != 0) }
#[inline]
2015-03-26 16:52:20 +00:00
fn error(&mut self, err: &str) -> io::Error {
io::Error {
kind: io::ErrorKind::OtherError,
desc: "parse error",
detail: Some(err.to_string())
}
}
}
// Aren't really any tests here.. the main functions are serialize and
// deserialize, which get the crap tested out of them it every other
// module.
2014-07-18 13:56:17 +00:00