mirror of
https://github.com/hl-archive-node/nanoreth.git
synced 2025-12-06 10:59:55 +00:00
primitives: add own Bloom type with arbitrary (#746)
* add own Bloom type with arbitrary * use impl_hash_compact instead * add doc to exported macro * remove unused crate and code * fix rlp encode length for Bloom * use RlpDecodableWrapper and RlpEncodableWrapper instead
This commit is contained in:
4
Cargo.lock
generated
4
Cargo.lock
generated
@ -3851,14 +3851,16 @@ dependencies = [
|
|||||||
"bytes",
|
"bytes",
|
||||||
"crc",
|
"crc",
|
||||||
"derive_more",
|
"derive_more",
|
||||||
"ethbloom",
|
|
||||||
"ethers-core",
|
"ethers-core",
|
||||||
|
"fixed-hash",
|
||||||
"hash-db",
|
"hash-db",
|
||||||
"hex",
|
"hex",
|
||||||
"hex-literal",
|
"hex-literal",
|
||||||
|
"impl-serde",
|
||||||
"modular-bitfield",
|
"modular-bitfield",
|
||||||
"parity-scale-codec",
|
"parity-scale-codec",
|
||||||
"plain_hasher",
|
"plain_hasher",
|
||||||
|
"proptest",
|
||||||
"rand 0.8.5",
|
"rand 0.8.5",
|
||||||
"reth-codecs",
|
"reth-codecs",
|
||||||
"reth-rlp",
|
"reth-rlp",
|
||||||
|
|||||||
@ -273,7 +273,6 @@ mod ethereum_types_support {
|
|||||||
fixed_hash_impl!(H256);
|
fixed_hash_impl!(H256);
|
||||||
fixed_hash_impl!(H512);
|
fixed_hash_impl!(H512);
|
||||||
fixed_hash_impl!(H520);
|
fixed_hash_impl!(H520);
|
||||||
fixed_hash_impl!(Bloom);
|
|
||||||
|
|
||||||
macro_rules! fixed_uint_impl {
|
macro_rules! fixed_uint_impl {
|
||||||
($t:ty, $n_bytes:tt) => {
|
($t:ty, $n_bytes:tt) => {
|
||||||
|
|||||||
@ -265,7 +265,6 @@ mod ethereum_types_support {
|
|||||||
fixed_hash_impl!(H256);
|
fixed_hash_impl!(H256);
|
||||||
fixed_hash_impl!(H512);
|
fixed_hash_impl!(H512);
|
||||||
fixed_hash_impl!(H520);
|
fixed_hash_impl!(H520);
|
||||||
fixed_hash_impl!(Bloom);
|
|
||||||
|
|
||||||
macro_rules! fixed_uint_impl {
|
macro_rules! fixed_uint_impl {
|
||||||
($t:ty, $n_bytes:tt) => {
|
($t:ty, $n_bytes:tt) => {
|
||||||
|
|||||||
@ -23,7 +23,11 @@ revm-interpreter = { git = "https://github.com/bluealloy/revm", rev = "3a13c9c8a
|
|||||||
ethers-core = { git = "https://github.com/gakonst/ethers-rs", default-features = false }
|
ethers-core = { git = "https://github.com/gakonst/ethers-rs", default-features = false }
|
||||||
parity-scale-codec = { version = "3.2.1", features = ["derive", "bytes"] }
|
parity-scale-codec = { version = "3.2.1", features = ["derive", "bytes"] }
|
||||||
tiny-keccak = { version = "2.0", features = ["keccak"] }
|
tiny-keccak = { version = "2.0", features = ["keccak"] }
|
||||||
ethbloom = { version = "0.13", features = ["codec"] }
|
|
||||||
|
# Bloom
|
||||||
|
fixed-hash = { version = "0.8", default-features = false, features = [
|
||||||
|
"rustc-hex",
|
||||||
|
] }
|
||||||
|
|
||||||
# crypto
|
# crypto
|
||||||
secp256k1 = { version = "0.24.2", default-features = false, features = [
|
secp256k1 = { version = "0.24.2", default-features = false, features = [
|
||||||
@ -47,6 +51,7 @@ hex-literal = "0.3"
|
|||||||
modular-bitfield = "0.11.2"
|
modular-bitfield = "0.11.2"
|
||||||
derive_more = "0.99"
|
derive_more = "0.99"
|
||||||
url = "2.3"
|
url = "2.3"
|
||||||
|
impl-serde = "0.4.0"
|
||||||
|
|
||||||
# proof related
|
# proof related
|
||||||
triehash = "0.8"
|
triehash = "0.8"
|
||||||
@ -61,8 +66,13 @@ hex-literal = "0.3"
|
|||||||
test-fuzz = "3.0.4"
|
test-fuzz = "3.0.4"
|
||||||
rand = "0.8"
|
rand = "0.8"
|
||||||
revm-interpreter = { git = "https://github.com/bluealloy/revm", rev = "3a13c9c8a0cda728941f1b26db0beb1025744ea9", features = ["with-serde", "arbitrary"] }
|
revm-interpreter = { git = "https://github.com/bluealloy/revm", rev = "3a13c9c8a0cda728941f1b26db0beb1025744ea9", features = ["with-serde", "arbitrary"] }
|
||||||
|
proptest = { version = "1.0" }
|
||||||
|
|
||||||
|
|
||||||
# necessary so we don't hit a "undeclared 'std'":
|
# necessary so we don't hit a "undeclared 'std'":
|
||||||
# https://github.com/paradigmxyz/reth/pull/177#discussion_r1021172198
|
# https://github.com/paradigmxyz/reth/pull/177#discussion_r1021172198
|
||||||
secp256k1 = "0.24.2"
|
secp256k1 = "0.24.2"
|
||||||
|
|
||||||
|
[features]
|
||||||
|
default = []
|
||||||
|
arbitrary = ["dep:arbitrary", "revm-interpreter/arbitrary"]
|
||||||
@ -1,10 +1,46 @@
|
|||||||
//! Bloom related utilities.
|
//! Bloom related utilities.
|
||||||
|
use crate::{keccak256, Log};
|
||||||
|
use bytes::Buf;
|
||||||
|
use derive_more::{AsRef, Deref};
|
||||||
|
use fixed_hash::construct_fixed_hash;
|
||||||
|
use impl_serde::impl_fixed_hash_serde;
|
||||||
|
use reth_codecs::{impl_hash_compact, Compact};
|
||||||
|
use reth_rlp::{RlpDecodableWrapper, RlpEncodableWrapper};
|
||||||
|
|
||||||
use crate::{keccak256, Bloom, Log};
|
#[cfg(test)]
|
||||||
|
use proptest::{
|
||||||
|
arbitrary::{any_with, Arbitrary as PropTestArbitrary, ParamsFor},
|
||||||
|
strategy::{BoxedStrategy, Strategy},
|
||||||
|
};
|
||||||
|
|
||||||
|
#[cfg(any(test, feature = "arbitrary"))]
|
||||||
|
use arbitrary::Arbitrary;
|
||||||
|
|
||||||
/// Length of bloom filter used for Ethereum.
|
/// Length of bloom filter used for Ethereum.
|
||||||
pub const BLOOM_BYTE_LENGTH: usize = 256;
|
pub const BLOOM_BYTE_LENGTH: usize = 256;
|
||||||
|
|
||||||
|
construct_fixed_hash! {
|
||||||
|
/// 2048 bits type.
|
||||||
|
#[cfg_attr(any(test, feature = "arbitrary"), derive(Arbitrary))]
|
||||||
|
#[derive(AsRef, Deref, RlpEncodableWrapper, RlpDecodableWrapper)]
|
||||||
|
pub struct Bloom(BLOOM_BYTE_LENGTH);
|
||||||
|
}
|
||||||
|
|
||||||
|
impl_hash_compact!(Bloom);
|
||||||
|
impl_fixed_hash_serde!(Bloom, BLOOM_BYTE_LENGTH);
|
||||||
|
|
||||||
|
#[cfg(test)]
|
||||||
|
impl PropTestArbitrary for Bloom {
|
||||||
|
type Parameters = ParamsFor<u8>;
|
||||||
|
type Strategy = BoxedStrategy<Bloom>;
|
||||||
|
|
||||||
|
fn arbitrary_with(args: Self::Parameters) -> Self::Strategy {
|
||||||
|
proptest::collection::vec(any_with::<u8>(args), BLOOM_BYTE_LENGTH)
|
||||||
|
.prop_map(move |vec| Bloom::from_slice(&vec))
|
||||||
|
.boxed()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// See Section 4.3.1 "Transaction Receipt" of the Yellow Paper
|
// See Section 4.3.1 "Transaction Receipt" of the Yellow Paper
|
||||||
fn m3_2048(bloom: &mut Bloom, x: &[u8]) {
|
fn m3_2048(bloom: &mut Bloom, x: &[u8]) {
|
||||||
let hash = keccak256(x);
|
let hash = keccak256(x);
|
||||||
@ -69,4 +105,19 @@ mod tests {
|
|||||||
))
|
))
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
#[test]
|
||||||
|
fn arbitrary() {
|
||||||
|
proptest::proptest!(|(bloom: Bloom)| {
|
||||||
|
let mut buf = vec![];
|
||||||
|
bloom.to_compact(&mut buf);
|
||||||
|
|
||||||
|
// Add noise
|
||||||
|
buf.push(1);
|
||||||
|
|
||||||
|
let (decoded, remaining_buf) = Bloom::from_compact(&buf, buf.len());
|
||||||
|
|
||||||
|
assert!(bloom == decoded);
|
||||||
|
assert!(remaining_buf.len() == 1);
|
||||||
|
});
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -33,9 +33,9 @@ pub mod proofs;
|
|||||||
|
|
||||||
pub use account::Account;
|
pub use account::Account;
|
||||||
pub use block::{Block, BlockHashOrNumber, SealedBlock};
|
pub use block::{Block, BlockHashOrNumber, SealedBlock};
|
||||||
|
pub use bloom::Bloom;
|
||||||
pub use chain::Chain;
|
pub use chain::Chain;
|
||||||
pub use constants::{EMPTY_OMMER_ROOT, KECCAK_EMPTY, MAINNET_GENESIS};
|
pub use constants::{EMPTY_OMMER_ROOT, KECCAK_EMPTY, MAINNET_GENESIS};
|
||||||
pub use ethbloom::Bloom;
|
|
||||||
pub use forkid::{ForkFilter, ForkHash, ForkId, ForkTransition, ValidationError};
|
pub use forkid::{ForkFilter, ForkHash, ForkId, ForkTransition, ValidationError};
|
||||||
pub use hardfork::Hardfork;
|
pub use hardfork::Hardfork;
|
||||||
pub use header::{Header, HeadersDirection, SealedHeader};
|
pub use header::{Header, HeadersDirection, SealedHeader};
|
||||||
|
|||||||
@ -1,6 +1,5 @@
|
|||||||
use bytes::{Buf, Bytes};
|
use bytes::{Buf, Bytes};
|
||||||
pub use codecs_derive::*;
|
pub use codecs_derive::*;
|
||||||
use ethers_core::types::Bloom;
|
|
||||||
use revm_interpreter::{B160 as H160, B256 as H256, U256};
|
use revm_interpreter::{B160 as H160, B256 as H256, U256};
|
||||||
|
|
||||||
/// Trait that implements the `Compact` codec.
|
/// Trait that implements the `Compact` codec.
|
||||||
@ -222,6 +221,8 @@ impl Compact for Bytes {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Implements the [`Compact`] trait for fixed size hash types like [`H256`].
|
||||||
|
#[macro_export]
|
||||||
macro_rules! impl_hash_compact {
|
macro_rules! impl_hash_compact {
|
||||||
($($name:tt),+) => {
|
($($name:tt),+) => {
|
||||||
$(
|
$(
|
||||||
@ -257,19 +258,6 @@ macro_rules! impl_hash_compact {
|
|||||||
|
|
||||||
impl_hash_compact!(H256, H160);
|
impl_hash_compact!(H256, H160);
|
||||||
|
|
||||||
impl Compact for Bloom {
|
|
||||||
fn to_compact(self, buf: &mut impl bytes::BufMut) -> usize {
|
|
||||||
buf.put_slice(&self.0);
|
|
||||||
256
|
|
||||||
}
|
|
||||||
|
|
||||||
fn from_compact(mut buf: &[u8], _: usize) -> (Self, &[u8]) {
|
|
||||||
let result = Bloom::from_slice(&buf[..256]);
|
|
||||||
buf.advance(256);
|
|
||||||
(result, buf)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl Compact for bool {
|
impl Compact for bool {
|
||||||
/// `bool` vars go directly to the `StructFlags` and are not written to the buffer.
|
/// `bool` vars go directly to the `StructFlags` and are not written to the buffer.
|
||||||
fn to_compact(self, _: &mut impl bytes::BufMut) -> usize {
|
fn to_compact(self, _: &mut impl bytes::BufMut) -> usize {
|
||||||
@ -303,19 +291,6 @@ mod tests {
|
|||||||
assert_eq!(bytes::Bytes::from_compact(&buf, list.len()), (list, vec![1].as_slice()));
|
assert_eq!(bytes::Bytes::from_compact(&buf, list.len()), (list, vec![1].as_slice()));
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
|
||||||
fn compact_bloom() {
|
|
||||||
let mut buf = vec![];
|
|
||||||
assert_eq!(Bloom::default().to_compact(&mut buf), 256);
|
|
||||||
assert_eq!(buf, vec![0; 256]);
|
|
||||||
|
|
||||||
// Add some noise data.
|
|
||||||
buf.push(1);
|
|
||||||
|
|
||||||
// Bloom shouldn't care about the len passed, since it's not actually compacted.
|
|
||||||
assert_eq!(Bloom::from_compact(&buf, 1000), (Bloom::default(), vec![1u8].as_slice()));
|
|
||||||
}
|
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn compact_address() {
|
fn compact_address() {
|
||||||
let mut buf = vec![];
|
let mut buf = vec![];
|
||||||
|
|||||||
@ -164,8 +164,7 @@ mod test {
|
|||||||
ommer.ommers.push(Header::default());
|
ommer.ommers.push(Header::default());
|
||||||
ommer.ommers.push(Header::default());
|
ommer.ommers.push(Header::default());
|
||||||
assert!(
|
assert!(
|
||||||
ommer.clone() ==
|
ommer.clone() == StoredBlockOmmers::decompress::<Vec<_>>(ommer.compress()).unwrap()
|
||||||
StoredBlockOmmers::decompress::<Vec<_>>(ommer.compress().into()).unwrap()
|
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user