From 8de5d1573a7dbc6a71b33bda38eaa41e25b57a7e Mon Sep 17 00:00:00 2001 From: koushiro Date: Thu, 29 Aug 2019 16:08:46 +0800 Subject: [PATCH 1/8] Add no_std support for rlp Signed-off-by: koushiro --- .travis.yml | 1 + rlp/Cargo.toml | 8 ++++- rlp/src/error.rs | 4 ++- rlp/src/impls.rs | 12 +++++--- rlp/src/lib.rs | 17 +++++++---- rlp/src/rlpin.rs | 75 +++++++++++++++++----------------------------- rlp/src/stream.rs | 32 +++++++++++--------- rlp/src/traits.rs | 7 ++++- rlp/tests/tests.rs | 21 +++++++++++-- 9 files changed, 102 insertions(+), 75 deletions(-) diff --git a/.travis.yml b/.travis.yml index 9d5a42748..d192a4682 100644 --- a/.travis.yml +++ b/.travis.yml @@ -31,6 +31,7 @@ script: cd fixed-hash/ && cargo test --no-default-features --features="rustc-hex,byteorder" && cd ..; cd keccak-hash/ && cargo test --no-default-features && cd ..; cd contract-address/ && cargo test --features=external_doc && cd ..; + cd rlp/ && cargo test --no-default-features && cd ..; fi - cd fixed-hash/ && cargo test --all-features && cd .. - cd uint/ && cargo test --features=std,quickcheck --release && cd .. diff --git a/rlp/Cargo.toml b/rlp/Cargo.toml index 8795f84ec..723530340 100644 --- a/rlp/Cargo.toml +++ b/rlp/Cargo.toml @@ -8,8 +8,14 @@ authors = ["Parity Technologies "] edition = "2018" [dependencies] -rustc-hex = {version = "2.0", default-features = false } +rustc-hex = { version = "2.0", default-features = false } [dev-dependencies] hex-literal = "0.2" primitive-types = { path = "../primitive-types", version = "0.5", features = ["impl-rlp"] } + +[features] +default = ["std"] +std = [ + "rustc-hex/std", +] diff --git a/rlp/src/error.rs b/rlp/src/error.rs index 7aef6cfbf..d810130b0 100644 --- a/rlp/src/error.rs +++ b/rlp/src/error.rs @@ -6,7 +6,8 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use std::fmt; +use core::fmt; +#[cfg(feature = "std")] use std::error::Error as StdError; #[derive(Debug, PartialEq, Eq, Clone)] @@ -36,6 +37,7 @@ pub enum DecoderError { Custom(&'static str), } +#[cfg(feature = "std")] impl StdError for DecoderError { fn description(&self) -> &str { "builder error" diff --git a/rlp/src/impls.rs b/rlp/src/impls.rs index c478d3a22..12d6ef1d7 100644 --- a/rlp/src/impls.rs +++ b/rlp/src/impls.rs @@ -6,11 +6,15 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use std::{mem, str}; -use std::iter::{once, empty}; -use crate::traits::{Encodable, Decodable}; +#[cfg(not(feature = "std"))] +use alloc::{borrow::ToOwned, vec::Vec, string::String}; +use core::{mem, str}; +use core::iter::{once, empty}; + +use crate::error::DecoderError; +use crate::rlpin::Rlp; use crate::stream::RlpStream; -use crate::{Rlp, DecoderError}; +use crate::traits::{Encodable, Decodable}; pub fn decode_usize(bytes: &[u8]) -> Result { match bytes.len() { diff --git a/rlp/src/lib.rs b/rlp/src/lib.rs index e85c1a0db..1baa52c2f 100644 --- a/rlp/src/lib.rs +++ b/rlp/src/lib.rs @@ -32,7 +32,10 @@ //! * You want to get view onto rlp-slice. //! * You don't want to decode whole rlp at once. -use std::borrow::Borrow; +#![cfg_attr(not(feature = "std"), no_std)] + +#[cfg(not(feature = "std"))] +extern crate alloc; mod traits; mod error; @@ -40,10 +43,14 @@ mod rlpin; mod stream; mod impls; -pub use crate::error::DecoderError; -pub use crate::traits::{Decodable, Encodable}; -pub use crate::rlpin::{Rlp, RlpIterator, PayloadInfo, Prototype}; -pub use crate::stream::RlpStream; +#[cfg(not(feature = "std"))] +use alloc::vec::Vec; +use core::borrow::Borrow; + +pub use self::error::DecoderError; +pub use self::rlpin::{Rlp, RlpIterator, PayloadInfo, Prototype}; +pub use self::stream::RlpStream; +pub use self::traits::{Decodable, Encodable}; /// The RLP encoded empty data (used to mean "null value"). pub const NULL_RLP: [u8; 1] = [0x80; 1]; diff --git a/rlp/src/rlpin.rs b/rlp/src/rlpin.rs index e4a05c76c..0d8c9ad2a 100644 --- a/rlp/src/rlpin.rs +++ b/rlp/src/rlpin.rs @@ -6,11 +6,16 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use std::cell::Cell; -use std::fmt; +#[cfg(not(feature = "std"))] +use alloc::{string::String, vec::Vec}; +use core::cell::Cell; +use core::fmt; + use rustc_hex::ToHex; + +use crate::error::DecoderError; use crate::impls::decode_usize; -use crate::{Decodable, DecoderError}; +use crate::traits::Decodable; /// rlp offset #[derive(Copy, Clone, Debug)] @@ -21,10 +26,7 @@ struct OffsetCache { impl OffsetCache { fn new(index: usize, offset: usize) -> OffsetCache { - OffsetCache { - index: index, - offset: offset, - } + OffsetCache { index, offset } } } @@ -67,10 +69,7 @@ fn calculate_payload_info(header_bytes: &[u8], len_of_len: usize) -> Result PayloadInfo { - PayloadInfo { - header_len: header_len, - value_len: value_len, - } + PayloadInfo { header_len, value_len } } /// Total size of the RLP. @@ -129,7 +128,7 @@ impl<'a> fmt::Display for Rlp<'a> { impl<'a> Rlp<'a> { pub fn new(bytes: &'a [u8]) -> Rlp<'a> { Rlp { - bytes: bytes, + bytes, offset_cache: Cell::new(None), count_cache: Cell::new(None) } @@ -160,24 +159,26 @@ impl<'a> Rlp<'a> { } pub fn item_count(&self) -> Result { - match self.is_list() { - true => match self.count_cache.get() { + if self.is_list() { + match self.count_cache.get() { Some(c) => Ok(c), None => { let c = self.iter().count(); self.count_cache.set(Some(c)); Ok(c) } - }, - false => Err(DecoderError::RlpExpectedToBeList), + } + } else { + Err(DecoderError::RlpExpectedToBeList) } } pub fn size(&self) -> usize { - match self.is_data() { + if self.is_data() { // TODO: No panic on malformed data, but ideally would Err on no PayloadInfo. - true => BasicDecoder::payload_info(self.bytes).map(|b| b.value_len).unwrap_or(0), - false => 0 + BasicDecoder::payload_info(self.bytes).map(|b| b.value_len).unwrap_or(0) + } else { + 0 } } @@ -211,7 +212,7 @@ impl<'a> Rlp<'a> { } pub fn is_null(&self) -> bool { - self.bytes.len() == 0 + self.bytes.is_empty() } pub fn is_empty(&self) -> bool { @@ -232,9 +233,9 @@ impl<'a> Rlp<'a> { } match self.bytes[0] { - 0...0x80 => true, - 0x81...0xb7 => self.bytes[1] != 0, - b @ 0xb8...0xbf => { + 0..=0x80 => true, + 0x81..=0xb7 => self.bytes[1] != 0, + b @ 0xb8..=0xbf => { let payload_idx = 1 + b as usize - 0xb7; payload_idx < self.bytes.len() && self.bytes[payload_idx] != 0 }, @@ -290,9 +291,10 @@ impl<'a> Rlp<'a> { /// consumes slice prefix of length `len` fn consume(bytes: &'a [u8], len: usize) -> Result<&'a [u8], DecoderError> { - match bytes.len() >= len { - true => Ok(&bytes[len..]), - false => Err(DecoderError::RlpIsTooShort) + if bytes.len() >= len { + Ok(&bytes[len..]) + } else { + Err(DecoderError::RlpIsTooShort) } } } @@ -384,24 +386,3 @@ impl<'a> BasicDecoder<'a> { } } } - -#[cfg(test)] -mod tests { - use crate::{Rlp, DecoderError}; - use hex_literal::hex; - - #[test] - fn test_rlp_display() { - let data = hex!("f84d0589010efbef67941f79b2a056e81f171bcc55a6ff8345e692c0f86e5b48e01b996cadc001622fb5e363b421a0c5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470"); - let rlp = Rlp::new(&data); - assert_eq!(format!("{}", rlp), "[\"0x05\", \"0x010efbef67941f79b2\", \"0x56e81f171bcc55a6ff8345e692c0f86e5b48e01b996cadc001622fb5e363b421\", \"0xc5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470\"]"); - } - - #[test] - fn length_overflow() { - let bs = [0xbf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe5]; - let rlp = Rlp::new(&bs); - let res: Result = rlp.as_val(); - assert_eq!(Err(DecoderError::RlpInvalidLength), res); - } -} diff --git a/rlp/src/stream.rs b/rlp/src/stream.rs index 7a133cd0d..ecc5a109e 100644 --- a/rlp/src/stream.rs +++ b/rlp/src/stream.rs @@ -6,7 +6,10 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use std::borrow::Borrow; +#[cfg(not(feature = "std"))] +use alloc::vec::Vec; +use core::borrow::Borrow; + use crate::traits::Encodable; #[derive(Debug, Copy, Clone)] @@ -19,9 +22,9 @@ struct ListInfo { impl ListInfo { fn new(position: usize, max: Option) -> ListInfo { ListInfo { - position: position, + position, current: 0, - max: max, + max, } } } @@ -132,7 +135,7 @@ impl RlpStream { /// assert_eq!(out, vec![0xc8, 0x83, b'c', b'a', b't', 0x83, b'd', b'o', b'g']); /// } /// ``` - pub fn append_iter<'a, I>(&'a mut self, value: I) -> &'a mut Self + pub fn append_iter(&mut self, value: I) -> &mut Self where I: IntoIterator, { self.finished_list = false; @@ -218,7 +221,7 @@ impl RlpStream { } /// Calculate total RLP size for appended payload. - pub fn estimate_size<'a>(&'a self, add: usize) -> usize { + pub fn estimate_size(&self, add: usize) -> usize { let total_size = self.buffer.len() + add; let mut base_size = total_size; for list in &self.unfinished_lists[..] { @@ -233,7 +236,7 @@ impl RlpStream { } /// Returns current RLP size in bytes for the data pushed into the list. - pub fn len<'a>(&'a self) -> usize { + pub fn len(&self) -> usize { self.estimate_size(0) } @@ -275,7 +278,7 @@ impl RlpStream { /// assert_eq!(out, vec![0xc8, 0x83, b'c', b'a', b't', 0x83, b'd', b'o', b'g']); /// } pub fn is_finished(&self) -> bool { - self.unfinished_lists.len() == 0 + self.unfinished_lists.is_empty() } /// Get raw encoded bytes @@ -288,15 +291,16 @@ impl RlpStream { /// /// panic! if stream is not finished. pub fn out(self) -> Vec { - match self.is_finished() { - true => self.buffer, - false => panic!() + if self.is_finished() { + self.buffer + } else { + panic!() } } /// Try to finish lists - fn note_appended(&mut self, inserted_items: usize) -> () { - if self.unfinished_lists.len() == 0 { + fn note_appended(&mut self, inserted_items: usize) { + if self.unfinished_lists.is_empty() { return; } @@ -365,7 +369,7 @@ impl<'a> BasicEncoder<'a> { fn insert_list_payload(&mut self, len: usize, pos: usize) { // 1 byte was already reserved for payload earlier match len { - 0...55 => { + 0..=55 => { self.buffer[pos - 1] = 0xc0u8 + len as u8; }, _ => { @@ -394,7 +398,7 @@ impl<'a> BasicEncoder<'a> { match len { // just 0 0 => self.buffer.push(0x80u8), - len @ 1 ... 55 => { + len @ 1..=55 => { let first = value.next().expect("iterator length is higher than 1"); if len == 1 && first < 0x80 { // byte is its own encoding if < 0x80 diff --git a/rlp/src/traits.rs b/rlp/src/traits.rs index b5502bb15..13531a1b6 100644 --- a/rlp/src/traits.rs +++ b/rlp/src/traits.rs @@ -7,7 +7,12 @@ // except according to those terms. //! Common RLP traits -use crate::{DecoderError, Rlp, RlpStream}; +#[cfg(not(feature = "std"))] +use alloc::vec::Vec; + +use crate::error::DecoderError; +use crate::rlpin::Rlp; +use crate::stream::RlpStream; /// RLP decodable trait pub trait Decodable: Sized { diff --git a/rlp/tests/tests.rs b/rlp/tests/tests.rs index 9022451af..c9b1436e2 100644 --- a/rlp/tests/tests.rs +++ b/rlp/tests/tests.rs @@ -6,11 +6,28 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use primitive_types::{H160, U256}; use std::{fmt, cmp}; -use rlp::{Encodable, Decodable, Rlp, RlpStream, DecoderError}; + +use primitive_types::{H160, U256}; use hex_literal::hex; +use rlp::{Encodable, Decodable, Rlp, RlpStream, DecoderError}; + +#[test] +fn test_rlp_display() { + let data = hex!("f84d0589010efbef67941f79b2a056e81f171bcc55a6ff8345e692c0f86e5b48e01b996cadc001622fb5e363b421a0c5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470"); + let rlp = Rlp::new(&data); + assert_eq!(format!("{}", rlp), "[\"0x05\", \"0x010efbef67941f79b2\", \"0x56e81f171bcc55a6ff8345e692c0f86e5b48e01b996cadc001622fb5e363b421\", \"0xc5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470\"]"); +} + +#[test] +fn length_overflow() { + let bs = [0xbf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe5]; + let rlp = Rlp::new(&bs); + let res: Result = rlp.as_val(); + assert_eq!(Err(DecoderError::RlpInvalidLength), res); +} + #[test] fn rlp_at() { let data = vec![0xc8, 0x83, b'c', b'a', b't', 0x83, b'd', b'o', b'g']; From b11a6231d072c89463a9dccb2a34676b35299051 Mon Sep 17 00:00:00 2001 From: koushiro Date: Thu, 29 Aug 2019 16:25:33 +0800 Subject: [PATCH 2/8] Remove hex-literal Signed-off-by: koushiro --- rlp/Cargo.toml | 1 - rlp/tests/tests.rs | 14 ++++++++------ 2 files changed, 8 insertions(+), 7 deletions(-) diff --git a/rlp/Cargo.toml b/rlp/Cargo.toml index 723530340..882e4950d 100644 --- a/rlp/Cargo.toml +++ b/rlp/Cargo.toml @@ -11,7 +11,6 @@ edition = "2018" rustc-hex = { version = "2.0", default-features = false } [dev-dependencies] -hex-literal = "0.2" primitive-types = { path = "../primitive-types", version = "0.5", features = ["impl-rlp"] } [features] diff --git a/rlp/tests/tests.rs b/rlp/tests/tests.rs index c9b1436e2..406286b92 100644 --- a/rlp/tests/tests.rs +++ b/rlp/tests/tests.rs @@ -9,13 +9,15 @@ use std::{fmt, cmp}; use primitive_types::{H160, U256}; -use hex_literal::hex; - use rlp::{Encodable, Decodable, Rlp, RlpStream, DecoderError}; +fn hex(s: &str) -> Vec { + rustc_hex::FromHex::from_hex(s).unwrap() +} + #[test] fn test_rlp_display() { - let data = hex!("f84d0589010efbef67941f79b2a056e81f171bcc55a6ff8345e692c0f86e5b48e01b996cadc001622fb5e363b421a0c5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470"); + let data = hex("f84d0589010efbef67941f79b2a056e81f171bcc55a6ff8345e692c0f86e5b48e01b996cadc001622fb5e363b421a0c5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470"); let rlp = Rlp::new(&data); assert_eq!(format!("{}", rlp), "[\"0x05\", \"0x010efbef67941f79b2\", \"0x56e81f171bcc55a6ff8345e692c0f86e5b48e01b996cadc001622fb5e363b421\", \"0xc5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470\"]"); } @@ -180,7 +182,7 @@ fn encode_str() { #[test] fn encode_address() { let tests = vec![ - ETestPair(H160::from(hex!("ef2d6d194084c2de36e0dabfce45d046b37d1106")), + ETestPair(H160::from_slice(&hex("ef2d6d194084c2de36e0dabfce45d046b37d1106")), vec![0x94, 0xef, 0x2d, 0x6d, 0x19, 0x40, 0x84, 0xc2, 0xde, 0x36, 0xe0, 0xda, 0xbf, 0xce, 0x45, 0xd0, 0x46, 0xb3, 0x7d, 0x11, 0x06]) @@ -324,7 +326,7 @@ fn decode_untrusted_str() { #[test] fn decode_untrusted_address() { let tests = vec![ - DTestPair(H160::from(hex!("ef2d6d194084c2de36e0dabfce45d046b37d1106")), + DTestPair(H160::from_slice(&hex("ef2d6d194084c2de36e0dabfce45d046b37d1106")), vec![0x94, 0xef, 0x2d, 0x6d, 0x19, 0x40, 0x84, 0xc2, 0xde, 0x36, 0xe0, 0xda, 0xbf, 0xce, 0x45, 0xd0, 0x46, 0xb3, 0x7d, 0x11, 0x06]) @@ -497,7 +499,7 @@ fn test_inner_length_capping_for_short_lists() { // https://github.com/paritytech/parity-ethereum/pull/9663 #[test] fn test_list_at() { - let raw = hex!("f83e82022bd79020010db83c4d001500000000abcdef12820cfa8215a8d79020010db885a308d313198a2e037073488208ae82823a8443b9a355c5010203040531b9019afde696e582a78fa8d95ea13ce3297d4afb8ba6433e4154caa5ac6431af1b80ba76023fa4090c408f6b4bc3701562c031041d4702971d102c9ab7fa5eed4cd6bab8f7af956f7d565ee1917084a95398b6a21eac920fe3dd1345ec0a7ef39367ee69ddf092cbfe5b93e5e568ebc491983c09c76d922dc3"); + let raw = hex("f83e82022bd79020010db83c4d001500000000abcdef12820cfa8215a8d79020010db885a308d313198a2e037073488208ae82823a8443b9a355c5010203040531b9019afde696e582a78fa8d95ea13ce3297d4afb8ba6433e4154caa5ac6431af1b80ba76023fa4090c408f6b4bc3701562c031041d4702971d102c9ab7fa5eed4cd6bab8f7af956f7d565ee1917084a95398b6a21eac920fe3dd1345ec0a7ef39367ee69ddf092cbfe5b93e5e568ebc491983c09c76d922dc3"); let rlp = Rlp::new(&raw); let _rlp1 = rlp.at(1).unwrap(); From 569171b253bf504079abbce0e79d44455e9eadbd Mon Sep 17 00:00:00 2001 From: koushiro Date: Tue, 3 Sep 2019 16:20:58 +0800 Subject: [PATCH 3/8] Replace libtest with criterion Signed-off-by: koushiro --- .travis.yml | 9 ++-- rlp/Cargo.toml | 10 ++-- rlp/benches/rlp.rs | 132 +++++++++++++++++---------------------------- rlp/src/stream.rs | 10 ++-- 4 files changed, 65 insertions(+), 96 deletions(-) diff --git a/.travis.yml b/.travis.yml index d192a4682..351eeff0c 100644 --- a/.travis.yml +++ b/.travis.yml @@ -28,14 +28,13 @@ script: - cargo test --all --exclude uint --exclude fixed-hash - if [ "$TRAVIS_RUST_VERSION" == "nightly" ]; then cd parity-bytes/ && cargo build --no-default-features && cd ..; - cd fixed-hash/ && cargo test --no-default-features --features="rustc-hex,byteorder" && cd ..; - cd keccak-hash/ && cargo test --no-default-features && cd ..; cd contract-address/ && cargo test --features=external_doc && cd ..; - cd rlp/ && cargo test --no-default-features && cd ..; fi - - cd fixed-hash/ && cargo test --all-features && cd .. - - cd uint/ && cargo test --features=std,quickcheck --release && cd .. + - cd fixed-hash/ && cargo test --all-features && cargo test --no-default-features --features="byteorder,rustc-hex" && cd .. + - cd uint/ && cargo test --all-features && cargo test --no-default-features && cd .. + - cd keccak-hash/ && cargo test --no-default-features && cd .. - cd plain_hasher/ && cargo test --no-default-features && cd .. - cd parity-util-mem/ && cargo test --features=estimate-heapsize && cd .. - cd parity-util-mem/ && cargo test --features=jemalloc-global && cd .. - cd parity-util-mem/ && cargo test --features=mimalloc-global && cd .. + - cd rlp/ && cargo test --no-default-features && cargo test --benches && cd .. diff --git a/rlp/Cargo.toml b/rlp/Cargo.toml index 882e4950d..e73cb0c0b 100644 --- a/rlp/Cargo.toml +++ b/rlp/Cargo.toml @@ -11,10 +11,14 @@ edition = "2018" rustc-hex = { version = "2.0", default-features = false } [dev-dependencies] +criterion = "0.3" primitive-types = { path = "../primitive-types", version = "0.5", features = ["impl-rlp"] } [features] default = ["std"] -std = [ - "rustc-hex/std", -] +std = ["rustc-hex/std"] + +[[bench]] +name = "rlp" +path = "benches/rlp.rs" +harness = false diff --git a/rlp/benches/rlp.rs b/rlp/benches/rlp.rs index 606f20a4d..d46719e7e 100644 --- a/rlp/benches/rlp.rs +++ b/rlp/benches/rlp.rs @@ -7,111 +7,77 @@ // except according to those terms. //! benchmarking for rlp -//! should be started with: -//! ```bash -//! multirust run nightly cargo bench -//! ``` -#![feature(test)] +use criterion::{criterion_group, criterion_main, Criterion}; -// TODO: get rid of this one fine day: https://doc.rust-lang.org/nightly/edition-guide/rust-2018/module-system/path-clarity.html#an-exception -extern crate test; - -use primitive_types::U256; -use rlp::{RlpStream, Rlp}; -use test::Bencher; - -#[bench] -fn bench_stream_u64_value(b: &mut Bencher) { - b.iter(|| { - // u64 - let mut stream = RlpStream::new(); +fn bench_encode(c: &mut Criterion) { + c.bench_function("encode_u64", |b| b.iter(|| { + let mut stream = rlp::RlpStream::new(); stream.append(&0x1023456789abcdefu64); let _ = stream.out(); - }); -} - -#[bench] -fn bench_decode_u64_value(b: &mut Bencher) { - b.iter(|| { - // u64 - let data = vec![0x88, 0x10, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef]; - let rlp = Rlp::new(&data); - let _: u64 = rlp.as_val().unwrap(); - }); -} - -#[bench] -fn bench_stream_u256_value(b: &mut Bencher) { - b.iter(|| { - // u256 - let mut stream = RlpStream::new(); - let uint: U256 = "8090a0b0c0d0e0f00910203040506077000000000000000100000000000012f0".into(); + })); + c.bench_function("encode_u256", |b| b.iter(|| { + let mut stream = rlp::RlpStream::new(); + let uint: primitive_types::U256 = "8090a0b0c0d0e0f00910203040506077000000000000000100000000000012f0".into(); stream.append(&uint); let _ = stream.out(); - }); -} - -#[bench] -fn bench_decode_u256_value(b: &mut Bencher) { - b.iter(|| { - // u256 - let data = vec![0xa0, 0x80, 0x90, 0xa0, 0xb0, 0xc0, 0xd0, 0xe0, 0xf0, 0x09, 0x10, 0x20, - 0x30, 0x40, 0x50, 0x60, 0x77, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, - 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x12, 0xf0]; - let rlp = Rlp::new(&data); - let _ : U256 = rlp.as_val().unwrap(); - }); -} - -#[bench] -fn bench_stream_nested_empty_lists(b: &mut Bencher) { - b.iter(|| { + })); + c.bench_function("encode_nested_empty_lists", |b| b.iter(|| { // [ [], [[]], [ [], [[]] ] ] - let mut stream = RlpStream::new_list(3); + let mut stream = rlp::RlpStream::new_list(3); stream.begin_list(0); stream.begin_list(1).begin_list(0); stream.begin_list(2).begin_list(0).begin_list(1).begin_list(0); let _ = stream.out(); - }); + })); + c.bench_function("encode_1000_empty_lists", |b| b.iter(|| { + let mut stream = rlp::RlpStream::new_list(1000); + for _ in 0..1000 { + stream.begin_list(0); + } + let _ = stream.out(); + })); } -#[bench] -fn bench_decode_nested_empty_lists(b: &mut Bencher) { - b.iter(|| { +fn bench_decode(c: &mut Criterion) { + c.bench_function("decode_u64", |b| b.iter(|| { + let data = vec![0x88, 0x10, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef]; + let rlp = rlp::Rlp::new(&data); + let _: u64 = rlp.as_val().unwrap(); + })); + c.bench_function("decode_u256", |b| b.iter(|| { + let data = vec![ + 0xa0, 0x80, 0x90, 0xa0, 0xb0, 0xc0, 0xd0, 0xe0, 0xf0, 0x09, 0x10, 0x20, + 0x30, 0x40, 0x50, 0x60, 0x77, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x12, 0xf0 + ]; + let rlp = rlp::Rlp::new(&data); + let _ : primitive_types::U256 = rlp.as_val().unwrap(); + })); + c.bench_function("decode_nested_empty_lists", |b| b.iter(|| { // [ [], [[]], [ [], [[]] ] ] let data = vec![0xc7, 0xc0, 0xc1, 0xc0, 0xc3, 0xc0, 0xc1, 0xc0]; - let rlp = Rlp::new(&data); + let rlp = rlp::Rlp::new(&data); let _v0: Vec = rlp.at(0).unwrap().as_list().unwrap(); let _v1: Vec = rlp.at(1).unwrap().at(0).unwrap().as_list().unwrap(); let nested_rlp = rlp.at(2).unwrap(); let _v2a: Vec = nested_rlp.at(0).unwrap().as_list().unwrap(); let _v2b: Vec = nested_rlp.at(1).unwrap().at(0).unwrap().as_list().unwrap(); - }); -} - -#[bench] -fn bench_stream_1000_empty_lists(b: &mut Bencher) { - b.iter(|| { - let mut stream = RlpStream::new_list(1000); + })); + c.bench_function("decode_1000_empty_lists", |b| { + let mut stream = rlp::RlpStream::new_list(1000); for _ in 0..1000 { - stream.begin_list(0); + stream.append(&primitive_types::U256::from(1)); } - let _ = stream.out(); + let data= stream.out(); + b.iter(|| { + let rlp = rlp::Rlp::new(&data); + for i in 0..1000 { + let _: primitive_types::U256 = rlp.val_at(i).unwrap(); + } + }); }); } -#[bench] -fn bench_decode_1000_values(b: &mut Bencher) { - let mut stream = RlpStream::new_list(1000); - for _ in 0..1000 { - stream.append(&U256::from(1)); - } - let data= stream.out(); - b.iter(|| { - let rlp = Rlp::new(&data); - for i in 0..1000 { - let _: U256 = rlp.val_at(i).unwrap(); - } - }); -} +criterion_group!(benches, bench_encode, bench_decode); +criterion_main!(benches); diff --git a/rlp/src/stream.rs b/rlp/src/stream.rs index ecc5a109e..4cf22d4f1 100644 --- a/rlp/src/stream.rs +++ b/rlp/src/stream.rs @@ -89,7 +89,7 @@ impl RlpStream { } /// Appends raw (pre-serialised) RLP data. Use with caution. Chainable. - pub fn append_raw<'a>(&'a mut self, bytes: &[u8], item_count: usize) -> &'a mut Self { + pub fn append_raw(&mut self, bytes: &[u8], item_count: usize) -> &mut Self { // push raw items self.buffer.extend_from_slice(bytes); @@ -113,7 +113,7 @@ impl RlpStream { /// assert_eq!(out, vec![0xc8, 0x83, b'c', b'a', b't', 0x83, b'd', b'o', b'g']); /// } /// ``` - pub fn append<'a, E>(&'a mut self, value: &E) -> &'a mut Self where E: Encodable { + pub fn append(&mut self, value: &E) -> &mut Self where E: Encodable { self.finished_list = false; value.rlp_append(self); if !self.finished_list { @@ -147,7 +147,7 @@ impl RlpStream { } /// Appends list of values to the end of stream, chainable. - pub fn append_list<'a, E, K>(&'a mut self, values: &[K]) -> &'a mut Self where E: Encodable, K: Borrow { + pub fn append_list(&mut self, values: &[K]) -> &mut Self where E: Encodable, K: Borrow { self.begin_list(values.len()); for value in values { self.append(value.borrow()); @@ -157,7 +157,7 @@ impl RlpStream { /// Appends value to the end of stream, but do not count it as an appended item. /// It's useful for wrapper types - pub fn append_internal<'a, E>(&'a mut self, value: &E) -> &'a mut Self where E: Encodable { + pub fn append_internal(&mut self, value: &E) -> &mut Self where E: Encodable { value.rlp_append(self); self } @@ -212,7 +212,7 @@ impl RlpStream { } /// Appends raw (pre-serialised) RLP data. Checks for size oveflow. - pub fn append_raw_checked<'a>(&'a mut self, bytes: &[u8], item_count: usize, max_size: usize) -> bool { + pub fn append_raw_checked(&mut self, bytes: &[u8], item_count: usize, max_size: usize) -> bool { if self.estimate_size(bytes.len()) > max_size { return false; } From 78e98daad6bcd79b552943ab8f18698ea79400b9 Mon Sep 17 00:00:00 2001 From: koushiro Date: Wed, 4 Sep 2019 23:36:11 +0800 Subject: [PATCH 4/8] Fix some warnings Signed-off-by: koushiro --- rlp/benches/rlp.rs | 2 +- rlp/src/impls.rs | 8 +++---- rlp/src/stream.rs | 4 ++++ rlp/tests/tests.rs | 54 ++++++++++++++++++++++++---------------------- 4 files changed, 37 insertions(+), 31 deletions(-) diff --git a/rlp/benches/rlp.rs b/rlp/benches/rlp.rs index d46719e7e..5da99d1bf 100644 --- a/rlp/benches/rlp.rs +++ b/rlp/benches/rlp.rs @@ -13,7 +13,7 @@ use criterion::{criterion_group, criterion_main, Criterion}; fn bench_encode(c: &mut Criterion) { c.bench_function("encode_u64", |b| b.iter(|| { let mut stream = rlp::RlpStream::new(); - stream.append(&0x1023456789abcdefu64); + stream.append(&0x1023_4567_89ab_cdefu64); let _ = stream.out(); })); c.bench_function("encode_u256", |b| b.iter(|| { diff --git a/rlp/src/impls.rs b/rlp/src/impls.rs index 12d6ef1d7..3fbf3cf20 100644 --- a/rlp/src/impls.rs +++ b/rlp/src/impls.rs @@ -23,9 +23,9 @@ pub fn decode_usize(bytes: &[u8]) -> Result { return Err(DecoderError::RlpInvalidIndirection); } let mut res = 0usize; - for i in 0..l { + for (i, byte) in bytes.iter().enumerate().take(l) { let shift = (l - 1 - i) * 8; - res = res + ((bytes[i] as usize) << shift); + res += (*byte as usize) << shift; } Ok(res) } @@ -143,9 +143,9 @@ macro_rules! impl_decodable_for_u { return Err(DecoderError::RlpInvalidIndirection); } let mut res = 0 as $name; - for i in 0..l { + for (i, byte) in bytes.iter().enumerate().take(l) { let shift = (l - 1 - i) * 8; - res = res + ((bytes[i] as $name) << shift); + res += (*byte as $name) << shift; } Ok(res) } diff --git a/rlp/src/stream.rs b/rlp/src/stream.rs index cdfc6f82e..cfddc2d95 100644 --- a/rlp/src/stream.rs +++ b/rlp/src/stream.rs @@ -240,6 +240,10 @@ impl RlpStream { self.estimate_size(0) } + pub fn is_empty(&self) -> bool { + self.len() == 0 + } + /// Clear the output stream so far. /// /// ```rust diff --git a/rlp/tests/tests.rs b/rlp/tests/tests.rs index 3cba554c1..fcc7cd0e1 100644 --- a/rlp/tests/tests.rs +++ b/rlp/tests/tests.rs @@ -6,7 +6,9 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use std::{fmt, cmp}; +#[cfg(not(feature = "std"))] +use alloc::{format, string::String, vec, vec::Vec}; +use core::{fmt, cmp}; use primitive_types::{H160, U256}; use rlp::{Encodable, Decodable, Rlp, RlpStream, DecoderError}; @@ -131,8 +133,8 @@ fn encode_u16() { fn encode_u32() { let tests = vec![ ETestPair(0u32, vec![0x80u8]), - ETestPair(0x10000, vec![0x83, 0x01, 0x00, 0x00]), - ETestPair(0xffffff, vec![0x83, 0xff, 0xff, 0xff]), + ETestPair(0x0001_0000, vec![0x83, 0x01, 0x00, 0x00]), + ETestPair(0x00ff_ffff, vec![0x83, 0xff, 0xff, 0xff]), ]; run_encode_tests(tests); } @@ -141,8 +143,8 @@ fn encode_u32() { fn encode_u64() { let tests = vec![ ETestPair(0u64, vec![0x80u8]), - ETestPair(0x1000000, vec![0x84, 0x01, 0x00, 0x00, 0x00]), - ETestPair(0xFFFFFFFF, vec![0x84, 0xff, 0xff, 0xff, 0xff]), + ETestPair(0x0100_0000, vec![0x84, 0x01, 0x00, 0x00, 0x00]), + ETestPair(0xFFFF_FFFF, vec![0x84, 0xff, 0xff, 0xff, 0xff]), ]; run_encode_tests(tests); } @@ -150,8 +152,8 @@ fn encode_u64() { #[test] fn encode_u256() { let tests = vec![ETestPair(U256::from(0u64), vec![0x80u8]), - ETestPair(U256::from(0x1000000u64), vec![0x84, 0x01, 0x00, 0x00, 0x00]), - ETestPair(U256::from(0xffffffffu64), + ETestPair(U256::from(0x0100_0000u64), vec![0x84, 0x01, 0x00, 0x00, 0x00]), + ETestPair(U256::from(0xffff_ffffu64), vec![0x84, 0xff, 0xff, 0xff, 0xff]), ETestPair(("8090a0b0c0d0e0f00910203040506077000000000000\ 000100000000000012f0").into(), @@ -208,7 +210,7 @@ fn encode_vector_u64() { VETestPair(vec![], vec![0xc0]), VETestPair(vec![15u64], vec![0xc1, 0x0f]), VETestPair(vec![1, 2, 3, 7, 0xff], vec![0xc6, 1, 2, 3, 7, 0x81, 0xff]), - VETestPair(vec![0xffffffff, 1, 2, 3, 7, 0xff], vec![0xcb, 0x84, 0xff, 0xff, 0xff, 0xff, 1, 2, 3, 7, 0x81, 0xff]), + VETestPair(vec![0xffff_ffff, 1, 2, 3, 7, 0xff], vec![0xcb, 0x84, 0xff, 0xff, 0xff, 0xff, 1, 2, 3, 7, 0x81, 0xff]), ]; run_encode_tests_list(tests); } @@ -274,8 +276,8 @@ fn decode_untrusted_u16() { #[test] fn decode_untrusted_u32() { let tests = vec![ - DTestPair(0x10000u32, vec![0x83, 0x01, 0x00, 0x00]), - DTestPair(0xffffffu32, vec![0x83, 0xff, 0xff, 0xff]), + DTestPair(0x0001_0000u32, vec![0x83, 0x01, 0x00, 0x00]), + DTestPair(0x00ff_ffffu32, vec![0x83, 0xff, 0xff, 0xff]), ]; run_decode_tests(tests); } @@ -283,8 +285,8 @@ fn decode_untrusted_u32() { #[test] fn decode_untrusted_u64() { let tests = vec![ - DTestPair(0x1000000u64, vec![0x84, 0x01, 0x00, 0x00, 0x00]), - DTestPair(0xFFFFFFFFu64, vec![0x84, 0xff, 0xff, 0xff, 0xff]), + DTestPair(0x0100_0000u64, vec![0x84, 0x01, 0x00, 0x00, 0x00]), + DTestPair(0xFFFF_FFFFu64, vec![0x84, 0xff, 0xff, 0xff, 0xff]), ]; run_decode_tests(tests); } @@ -292,8 +294,8 @@ fn decode_untrusted_u64() { #[test] fn decode_untrusted_u256() { let tests = vec![DTestPair(U256::from(0u64), vec![0x80u8]), - DTestPair(U256::from(0x1000000u64), vec![0x84, 0x01, 0x00, 0x00, 0x00]), - DTestPair(U256::from(0xffffffffu64), + DTestPair(U256::from(0x0100_0000u64), vec![0x84, 0x01, 0x00, 0x00, 0x00]), + DTestPair(U256::from(0xffff_ffffu64), vec![0x84, 0xff, 0xff, 0xff, 0xff]), DTestPair(("8090a0b0c0d0e0f00910203040506077000000000000\ 000100000000000012f0").into(), @@ -340,7 +342,7 @@ fn decode_untrusted_vector_u64() { VDTestPair(vec![], vec![0xc0]), VDTestPair(vec![15u64], vec![0xc1, 0x0f]), VDTestPair(vec![1, 2, 3, 7, 0xff], vec![0xc6, 1, 2, 3, 7, 0x81, 0xff]), - VDTestPair(vec![0xffffffff, 1, 2, 3, 7, 0xff], vec![0xcb, 0x84, 0xff, 0xff, 0xff, 0xff, 1, 2, 3, 7, 0x81, 0xff]), + VDTestPair(vec![0xffff_ffff, 1, 2, 3, 7, 0xff], vec![0xcb, 0x84, 0xff, 0xff, 0xff, 0xff, 1, 2, 3, 7, 0x81, 0xff]), ]; run_decode_tests_list(tests); } @@ -456,12 +458,12 @@ fn test_rlp_is_int() { #[test] fn test_canonical_string_encoding() { assert_ne!( - Rlp::new(&vec![0xc0 + 4, 0xb7 + 1, 2, b'a', b'b']).val_at::(0), - Rlp::new(&vec![0xc0 + 3, 0x82, b'a', b'b']).val_at::(0) + Rlp::new(&[0xc0 + 4, 0xb7 + 1, 2, b'a', b'b']).val_at::(0), + Rlp::new(&[0xc0 + 3, 0x82, b'a', b'b']).val_at::(0) ); assert_eq!( - Rlp::new(&vec![0xc0 + 4, 0xb7 + 1, 2, b'a', b'b']).val_at::(0), + Rlp::new(&[0xc0 + 4, 0xb7 + 1, 2, b'a', b'b']).val_at::(0), Err(DecoderError::RlpInvalidIndirection) ); } @@ -472,12 +474,12 @@ fn test_canonical_string_encoding() { #[test] fn test_canonical_list_encoding() { assert_ne!( - Rlp::new(&vec![0xc0 + 3, 0x82, b'a', b'b']).val_at::(0), - Rlp::new(&vec![0xf7 + 1, 3, 0x82, b'a', b'b']).val_at::(0) + Rlp::new(&[0xc0 + 3, 0x82, b'a', b'b']).val_at::(0), + Rlp::new(&[0xf7 + 1, 3, 0x82, b'a', b'b']).val_at::(0) ); assert_eq!( - Rlp::new(&vec![0xf7 + 1, 3, 0x82, b'a', b'b']).val_at::(0), + Rlp::new(&[0xf7 + 1, 3, 0x82, b'a', b'b']).val_at::(0), Err(DecoderError::RlpInvalidIndirection) ); } @@ -487,11 +489,11 @@ fn test_canonical_list_encoding() { // https://github.com/paritytech/parity-common/issues/48 #[test] fn test_inner_length_capping_for_short_lists() { - assert_eq!(Rlp::new(&vec![0xc0 + 0, 0x82, b'a', b'b']).val_at::(0), Err(DecoderError::RlpIsTooShort)); - assert_eq!(Rlp::new(&vec![0xc0 + 1, 0x82, b'a', b'b']).val_at::(0), Err(DecoderError::RlpIsTooShort)); - assert_eq!(Rlp::new(&vec![0xc0 + 2, 0x82, b'a', b'b']).val_at::(0), Err(DecoderError::RlpIsTooShort)); - assert_eq!(Rlp::new(&vec![0xc0 + 3, 0x82, b'a', b'b']).val_at::(0), Ok("ab".to_owned())); - assert_eq!(Rlp::new(&vec![0xc0 + 4, 0x82, b'a', b'b']).val_at::(0), Err(DecoderError::RlpIsTooShort)); + assert_eq!(Rlp::new(&[0xc0, 0x82, b'a', b'b']).val_at::(0), Err(DecoderError::RlpIsTooShort)); + assert_eq!(Rlp::new(&[0xc0 + 1, 0x82, b'a', b'b']).val_at::(0), Err(DecoderError::RlpIsTooShort)); + assert_eq!(Rlp::new(&[0xc0 + 2, 0x82, b'a', b'b']).val_at::(0), Err(DecoderError::RlpIsTooShort)); + assert_eq!(Rlp::new(&[0xc0 + 3, 0x82, b'a', b'b']).val_at::(0), Ok("ab".to_owned())); + assert_eq!(Rlp::new(&[0xc0 + 4, 0x82, b'a', b'b']).val_at::(0), Err(DecoderError::RlpIsTooShort)); } // test described in From ef9d72996f486fb3c487fc69f61f14688dd94ade Mon Sep 17 00:00:00 2001 From: koushiro Date: Thu, 5 Sep 2019 14:41:41 +0800 Subject: [PATCH 5/8] Remove std feature from primitive-types rlp feature Signed-off-by: koushiro --- primitive-types/Cargo.toml | 2 +- primitive-types/impls/rlp/Cargo.toml | 4 ++++ primitive-types/impls/rlp/src/lib.rs | 2 ++ rlp/tests/tests.rs | 2 -- 4 files changed, 7 insertions(+), 3 deletions(-) diff --git a/primitive-types/Cargo.toml b/primitive-types/Cargo.toml index cf19f7d27..178826eef 100644 --- a/primitive-types/Cargo.toml +++ b/primitive-types/Cargo.toml @@ -21,4 +21,4 @@ libc = ["fixed-hash/libc"] rustc-hex = ["fixed-hash/rustc-hex"] serde = ["std", "impl-serde"] codec = ["impl-codec"] -rlp = ["std", "impl-rlp"] +rlp = ["impl-rlp"] diff --git a/primitive-types/impls/rlp/Cargo.toml b/primitive-types/impls/rlp/Cargo.toml index 7f0ee2696..68d09419a 100644 --- a/primitive-types/impls/rlp/Cargo.toml +++ b/primitive-types/impls/rlp/Cargo.toml @@ -8,3 +8,7 @@ description = "RLP serialization support for uint and fixed hash." [dependencies] rlp = { version = "0.4", path = "../../../rlp" } + +[features] +default = ["std"] +std = ["rlp/std"] diff --git a/primitive-types/impls/rlp/src/lib.rs b/primitive-types/impls/rlp/src/lib.rs index 56f34328c..dffbfe96b 100644 --- a/primitive-types/impls/rlp/src/lib.rs +++ b/primitive-types/impls/rlp/src/lib.rs @@ -8,6 +8,8 @@ //! RLP serialization support for uint and fixed hash. +#![cfg_attr(not(feature = "std"), no_std)] + #[doc(hidden)] pub extern crate rlp; diff --git a/rlp/tests/tests.rs b/rlp/tests/tests.rs index fcc7cd0e1..ecf6a79c8 100644 --- a/rlp/tests/tests.rs +++ b/rlp/tests/tests.rs @@ -6,8 +6,6 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -#[cfg(not(feature = "std"))] -use alloc::{format, string::String, vec, vec::Vec}; use core::{fmt, cmp}; use primitive_types::{H160, U256}; From 2bd7d7c22105bef149bed23f0cc64983d8f2ae4f Mon Sep 17 00:00:00 2001 From: koushiro Date: Thu, 5 Sep 2019 15:17:22 +0800 Subject: [PATCH 6/8] Improve benchmark Signed-off-by: koushiro --- .travis.yml | 4 ++-- rlp/benches/rlp.rs | 26 +++++++++++++++++++++++--- 2 files changed, 25 insertions(+), 5 deletions(-) diff --git a/.travis.yml b/.travis.yml index f03f91890..9b57d057d 100644 --- a/.travis.yml +++ b/.travis.yml @@ -29,7 +29,7 @@ script: - if [ "$TRAVIS_RUST_VERSION" == "nightly" ]; then cd contract-address/ && cargo test --features=external_doc && cd ..; fi - - cd ethbloom/ && cargo test --no-default-features --features="rustc-hex" && cargo test --benches && cd .. + - cd ethbloom/ && cargo test --no-default-features --features="rustc-hex" && cargo check --benches && cd .. - cd fixed-hash/ && cargo test --all-features && cargo test --no-default-features --features="byteorder,rustc-hex" && cd .. - cd uint/ && cargo test --all-features && cargo test --no-default-features && cd .. - cd keccak-hash/ && cargo test --no-default-features && cd .. @@ -38,4 +38,4 @@ script: - cd parity-util-mem/ && cargo test --features=estimate-heapsize && cd .. - cd parity-util-mem/ && cargo test --features=jemalloc-global && cd .. - cd parity-util-mem/ && cargo test --features=mimalloc-global && cd .. - - cd rlp/ && cargo test --no-default-features && cargo test --benches && cd .. + - cd rlp/ && cargo test --no-default-features && cargo check --benches && cd .. diff --git a/rlp/benches/rlp.rs b/rlp/benches/rlp.rs index 5da99d1bf..e874cb0da 100644 --- a/rlp/benches/rlp.rs +++ b/rlp/benches/rlp.rs @@ -22,6 +22,13 @@ fn bench_encode(c: &mut Criterion) { stream.append(&uint); let _ = stream.out(); })); + c.bench_function("encode_1000_u64", |b| b.iter(|| { + let mut stream = rlp::RlpStream::new_list(1000); + for i in 0..1000u64 { + stream.append(&i); + } + let _ = stream.out(); + })); c.bench_function("encode_nested_empty_lists", |b| b.iter(|| { // [ [], [[]], [ [], [[]] ] ] let mut stream = rlp::RlpStream::new_list(3); @@ -54,6 +61,19 @@ fn bench_decode(c: &mut Criterion) { let rlp = rlp::Rlp::new(&data); let _ : primitive_types::U256 = rlp.as_val().unwrap(); })); + c.bench_function("decode_1000_u64", |b| { + let mut stream = rlp::RlpStream::new_list(1000); + for i in 0..1000u64 { + stream.append(&i); + } + let data= stream.out(); + b.iter(|| { + let rlp = rlp::Rlp::new(&data); + for i in 0..1000 { + let _: u64 = rlp.val_at(i).unwrap(); + } + }); + }); c.bench_function("decode_nested_empty_lists", |b| b.iter(|| { // [ [], [[]], [ [], [[]] ] ] let data = vec![0xc7, 0xc0, 0xc1, 0xc0, 0xc3, 0xc0, 0xc1, 0xc0]; @@ -67,13 +87,13 @@ fn bench_decode(c: &mut Criterion) { c.bench_function("decode_1000_empty_lists", |b| { let mut stream = rlp::RlpStream::new_list(1000); for _ in 0..1000 { - stream.append(&primitive_types::U256::from(1)); + stream.begin_list(0); } - let data= stream.out(); + let data = stream.out(); b.iter(|| { let rlp = rlp::Rlp::new(&data); for i in 0..1000 { - let _: primitive_types::U256 = rlp.val_at(i).unwrap(); + let _: Vec = rlp.at(i).unwrap().as_list().unwrap(); } }); }); From 2a86b5e35df794eef3ed92d8356c04207f9b4779 Mon Sep 17 00:00:00 2001 From: koushiro Date: Thu, 5 Sep 2019 15:26:10 +0800 Subject: [PATCH 7/8] Revert hex-literal Signed-off-by: koushiro --- rlp/Cargo.toml | 1 + rlp/tests/tests.rs | 13 +++++-------- 2 files changed, 6 insertions(+), 8 deletions(-) diff --git a/rlp/Cargo.toml b/rlp/Cargo.toml index e73cb0c0b..0ad6d40ea 100644 --- a/rlp/Cargo.toml +++ b/rlp/Cargo.toml @@ -12,6 +12,7 @@ rustc-hex = { version = "2.0", default-features = false } [dev-dependencies] criterion = "0.3" +hex-literal = "0.2" primitive-types = { path = "../primitive-types", version = "0.5", features = ["impl-rlp"] } [features] diff --git a/rlp/tests/tests.rs b/rlp/tests/tests.rs index ecf6a79c8..ba5a423b7 100644 --- a/rlp/tests/tests.rs +++ b/rlp/tests/tests.rs @@ -8,16 +8,13 @@ use core::{fmt, cmp}; +use hex_literal::hex; use primitive_types::{H160, U256}; use rlp::{Encodable, Decodable, Rlp, RlpStream, DecoderError}; -fn hex(s: &str) -> Vec { - rustc_hex::FromHex::from_hex(s).unwrap() -} - #[test] fn test_rlp_display() { - let data = hex("f84d0589010efbef67941f79b2a056e81f171bcc55a6ff8345e692c0f86e5b48e01b996cadc001622fb5e363b421a0c5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470"); + let data = hex!("f84d0589010efbef67941f79b2a056e81f171bcc55a6ff8345e692c0f86e5b48e01b996cadc001622fb5e363b421a0c5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470"); let rlp = Rlp::new(&data); assert_eq!(format!("{}", rlp), "[\"0x05\", \"0x010efbef67941f79b2\", \"0x56e81f171bcc55a6ff8345e692c0f86e5b48e01b996cadc001622fb5e363b421\", \"0xc5d2460186f7233c927e7db2dcc703c0e500b653ca82273b7bfad8045d85a470\"]"); } @@ -182,7 +179,7 @@ fn encode_str() { #[test] fn encode_address() { let tests = vec![ - ETestPair(H160::from_slice(&hex("ef2d6d194084c2de36e0dabfce45d046b37d1106")), + ETestPair(H160::from(hex!("ef2d6d194084c2de36e0dabfce45d046b37d1106")), vec![0x94, 0xef, 0x2d, 0x6d, 0x19, 0x40, 0x84, 0xc2, 0xde, 0x36, 0xe0, 0xda, 0xbf, 0xce, 0x45, 0xd0, 0x46, 0xb3, 0x7d, 0x11, 0x06]) @@ -326,7 +323,7 @@ fn decode_untrusted_str() { #[test] fn decode_untrusted_address() { let tests = vec![ - DTestPair(H160::from_slice(&hex("ef2d6d194084c2de36e0dabfce45d046b37d1106")), + DTestPair(H160::from(hex!("ef2d6d194084c2de36e0dabfce45d046b37d1106")), vec![0x94, 0xef, 0x2d, 0x6d, 0x19, 0x40, 0x84, 0xc2, 0xde, 0x36, 0xe0, 0xda, 0xbf, 0xce, 0x45, 0xd0, 0x46, 0xb3, 0x7d, 0x11, 0x06]) @@ -556,7 +553,7 @@ fn test_nested_list_roundtrip() { // https://github.com/paritytech/parity-ethereum/pull/9663 #[test] fn test_list_at() { - let raw = hex("f83e82022bd79020010db83c4d001500000000abcdef12820cfa8215a8d79020010db885a308d313198a2e037073488208ae82823a8443b9a355c5010203040531b9019afde696e582a78fa8d95ea13ce3297d4afb8ba6433e4154caa5ac6431af1b80ba76023fa4090c408f6b4bc3701562c031041d4702971d102c9ab7fa5eed4cd6bab8f7af956f7d565ee1917084a95398b6a21eac920fe3dd1345ec0a7ef39367ee69ddf092cbfe5b93e5e568ebc491983c09c76d922dc3"); + let raw = hex!("f83e82022bd79020010db83c4d001500000000abcdef12820cfa8215a8d79020010db885a308d313198a2e037073488208ae82823a8443b9a355c5010203040531b9019afde696e582a78fa8d95ea13ce3297d4afb8ba6433e4154caa5ac6431af1b80ba76023fa4090c408f6b4bc3701562c031041d4702971d102c9ab7fa5eed4cd6bab8f7af956f7d565ee1917084a95398b6a21eac920fe3dd1345ec0a7ef39367ee69ddf092cbfe5b93e5e568ebc491983c09c76d922dc3"); let rlp = Rlp::new(&raw); let _rlp1 = rlp.at(1).unwrap(); From 65ef6856cbab8a052f4cea4eb3735a1f9e9646ee Mon Sep 17 00:00:00 2001 From: koushiro Date: Thu, 5 Sep 2019 16:10:25 +0800 Subject: [PATCH 8/8] Fix impl-rlp Signed-off-by: koushiro --- primitive-types/impls/rlp/Cargo.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/primitive-types/impls/rlp/Cargo.toml b/primitive-types/impls/rlp/Cargo.toml index 68d09419a..f2de4e8ba 100644 --- a/primitive-types/impls/rlp/Cargo.toml +++ b/primitive-types/impls/rlp/Cargo.toml @@ -7,7 +7,7 @@ homepage = "https://github.com/paritytech/parity-common" description = "RLP serialization support for uint and fixed hash." [dependencies] -rlp = { version = "0.4", path = "../../../rlp" } +rlp = { version = "0.4", path = "../../../rlp", default-features = false } [features] default = ["std"]