Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
64 changes: 63 additions & 1 deletion Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

6 changes: 6 additions & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -99,6 +99,9 @@ members = [
"crates/rpc/rpc-testing-util/",
"crates/rpc/rpc-types-compat/",
"crates/rpc/rpc/",
"crates/scroll/primitives",
"crates/scroll/revm",
"crates/scroll/storage",
"crates/stages/api/",
"crates/stages/stages/",
"crates/stages/types/",
Expand Down Expand Up @@ -400,6 +403,9 @@ reth-rpc-eth-types = { path = "crates/rpc/rpc-eth-types", default-features = fal
reth-rpc-layer = { path = "crates/rpc/rpc-layer" }
reth-rpc-server-types = { path = "crates/rpc/rpc-server-types" }
reth-rpc-types-compat = { path = "crates/rpc/rpc-types-compat" }
reth-scroll-primitives = { path = "crates/scroll/primitives" }
reth-scroll-revm = { path = "crates/scroll/revm" }
reth-scroll-storage = { path = "crates/scroll/storage" }
reth-stages = { path = "crates/stages/stages" }
reth-stages-api = { path = "crates/stages/api" }
reth-stages-types = { path = "crates/stages/types" }
Expand Down
5 changes: 4 additions & 1 deletion crates/primitives-traits/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,9 @@ alloy-genesis.workspace = true
alloy-primitives.workspace = true
alloy-rlp.workspace = true

revm-primitives = { workspace = true, features = ["serde"] }
# revm-primitives scroll re-export
revm-primitives = { package = "reth-scroll-revm", path = "../scroll/revm", features = ["serde"] }
reth-scroll-primitives = { workspace = true, optional = true }

# misc
byteorder = "1"
Expand Down Expand Up @@ -81,3 +83,4 @@ serde-bincode-compat = [
"alloy-consensus/serde-bincode-compat",
"alloy-eips/serde-bincode-compat"
]
scroll = ["reth-scroll-primitives"]
90 changes: 80 additions & 10 deletions crates/primitives-traits/src/account.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,9 @@ use byteorder::{BigEndian, ReadBytesExt};
use bytes::Buf;
use derive_more::Deref;
use reth_codecs::{add_arbitrary_tests, Compact};
use revm_primitives::{AccountInfo, Bytecode as RevmBytecode, BytecodeDecodeError, JumpTable};
use revm_primitives::{
AccountInfo, Bytecode as RevmBytecode, BytecodeDecodeError, JumpTable, ScrollAccountInfo,
};
use serde::{Deserialize, Serialize};

/// Identifier for [`LegacyRaw`](RevmBytecode::LegacyRaw).
Expand Down Expand Up @@ -34,6 +36,12 @@ pub struct Account {
pub balance: U256,
/// Hash of the account's bytecode.
pub bytecode_hash: Option<B256>,
#[cfg(feature = "scroll")]
/// Size of the account's code in bytes.
pub code_size: u64,
#[cfg(feature = "scroll")]
/// Poseidon hash of the account's bytecode.
pub poseidon_code_hash: B256,
}

impl Account {
Expand Down Expand Up @@ -158,6 +166,29 @@ impl From<&GenesisAccount> for Account {
nonce: value.nonce.unwrap_or_default(),
balance: value.balance,
bytecode_hash: value.code.as_ref().map(keccak256),
#[cfg(feature = "scroll")]
code_size: value.code.as_ref().map(|c| c.len()).unwrap_or_default() as u64,
#[cfg(feature = "scroll")]
poseidon_code_hash: value
.code
.as_ref()
.map(|c| reth_scroll_primitives::poseidon(c))
.unwrap_or_default(),
}
}
}

impl From<ScrollAccountInfo> for Account {
fn from(revm_acc: ScrollAccountInfo) -> Self {
let code_hash = revm_acc.code_hash;
Self {
balance: revm_acc.balance,
nonce: revm_acc.nonce,
bytecode_hash: (code_hash != KECCAK_EMPTY).then_some(code_hash),
#[cfg(feature = "scroll")]
code_size: revm_acc.code_size,
#[cfg(feature = "scroll")]
poseidon_code_hash: revm_acc.poseidon_code_hash,
}
}
}
Expand All @@ -169,6 +200,25 @@ impl From<AccountInfo> for Account {
balance: revm_acc.balance,
nonce: revm_acc.nonce,
bytecode_hash: (code_hash != KECCAK_EMPTY).then_some(code_hash),
#[cfg(feature = "scroll")]
code_size: 0,
#[cfg(feature = "scroll")]
poseidon_code_hash: B256::ZERO,
Comment on lines +203 to +206
Copy link
Author

@greged93 greged93 Nov 9, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is added as an intermediate solution in order for the clippy check to pass. Once the whole code base is migrated to use our ScrollAccountInfo, this can be removed.

}
}
}

impl From<Account> for ScrollAccountInfo {
fn from(reth_acc: Account) -> Self {
Self {
balance: reth_acc.balance,
nonce: reth_acc.nonce,
code_hash: reth_acc.bytecode_hash.unwrap_or(KECCAK_EMPTY),
code: None,
#[cfg(feature = "scroll")]
code_size: reth_acc.code_size,
#[cfg(feature = "scroll")]
poseidon_code_hash: reth_acc.poseidon_code_hash,
}
}
}
Expand Down Expand Up @@ -208,7 +258,8 @@ mod tests {

#[test]
fn test_empty_account() {
let mut acc = Account { nonce: 0, balance: U256::ZERO, bytecode_hash: None };
let mut acc =
Account { nonce: 0, balance: U256::ZERO, bytecode_hash: None, ..Default::default() };
// Nonce 0, balance 0, and bytecode hash set to None is considered empty.
assert!(acc.is_empty());

Expand Down Expand Up @@ -260,32 +311,47 @@ mod tests {
#[test]
fn test_account_has_bytecode() {
// Account with no bytecode (None)
let acc_no_bytecode = Account { nonce: 1, balance: U256::from(1000), bytecode_hash: None };
let acc_no_bytecode = Account {
nonce: 1,
balance: U256::from(1000),
bytecode_hash: None,
..Default::default()
};
assert!(!acc_no_bytecode.has_bytecode(), "Account should not have bytecode");

// Account with bytecode hash set to KECCAK_EMPTY (should have bytecode)
let acc_empty_bytecode =
Account { nonce: 1, balance: U256::from(1000), bytecode_hash: Some(KECCAK_EMPTY) };
let acc_empty_bytecode = Account {
nonce: 1,
balance: U256::from(1000),
bytecode_hash: Some(KECCAK_EMPTY),
..Default::default()
};
assert!(acc_empty_bytecode.has_bytecode(), "Account should have bytecode");

// Account with a non-empty bytecode hash
let acc_with_bytecode = Account {
nonce: 1,
balance: U256::from(1000),
bytecode_hash: Some(B256::from_slice(&[0x11u8; 32])),
..Default::default()
};
assert!(acc_with_bytecode.has_bytecode(), "Account should have bytecode");
}

#[test]
fn test_account_get_bytecode_hash() {
// Account with no bytecode (should return KECCAK_EMPTY)
let acc_no_bytecode = Account { nonce: 0, balance: U256::ZERO, bytecode_hash: None };
let acc_no_bytecode =
Account { nonce: 0, balance: U256::ZERO, bytecode_hash: None, ..Default::default() };
assert_eq!(acc_no_bytecode.get_bytecode_hash(), KECCAK_EMPTY, "Should return KECCAK_EMPTY");

// Account with bytecode hash set to KECCAK_EMPTY
let acc_empty_bytecode =
Account { nonce: 1, balance: U256::from(1000), bytecode_hash: Some(KECCAK_EMPTY) };
let acc_empty_bytecode = Account {
nonce: 1,
balance: U256::from(1000),
bytecode_hash: Some(KECCAK_EMPTY),
..Default::default()
};
assert_eq!(
acc_empty_bytecode.get_bytecode_hash(),
KECCAK_EMPTY,
Expand All @@ -294,8 +360,12 @@ mod tests {

// Account with a valid bytecode hash
let bytecode_hash = B256::from_slice(&[0x11u8; 32]);
let acc_with_bytecode =
Account { nonce: 1, balance: U256::from(1000), bytecode_hash: Some(bytecode_hash) };
let acc_with_bytecode = Account {
nonce: 1,
balance: U256::from(1000),
bytecode_hash: Some(bytecode_hash),
..Default::default()
};
assert_eq!(
acc_with_bytecode.get_bytecode_hash(),
bytecode_hash,
Expand Down
19 changes: 19 additions & 0 deletions crates/scroll/primitives/Cargo.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
[package]
name = "reth-scroll-primitives"
version.workspace = true
edition.workspace = true
rust-version.workspace = true
license.workspace = true
homepage.workspace = true
repository.workspace = true
exclude.workspace = true

[lints]
workspace = true

[dependencies]
# revm
revm.workspace = true

# scroll
poseidon-bn254 = { git = "https://github.com/scroll-tech/poseidon-bn254", branch = "master", features = ["bn254"] }
12 changes: 12 additions & 0 deletions crates/scroll/primitives/src/execution_context.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
use revm::primitives::{map::HashMap, B256};

/// A Keccak code hash.
type KeccakHash = B256;
/// A Poseidon code hash.
type PoseidonHash = B256;
/// Size of a contract's code in bytes.
type CodeSize = u64;

/// Scroll post execution context maps a Keccak code hash of a contract's bytecode to its code size
/// and Poseidon code hash.
pub type ScrollPostExecutionContext = HashMap<KeccakHash, (CodeSize, PoseidonHash)>;
7 changes: 7 additions & 0 deletions crates/scroll/primitives/src/lib.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
//! Primitive types for the Scroll extension of `Reth`.

pub use execution_context::ScrollPostExecutionContext;
mod execution_context;

pub use poseidon::{poseidon, POSEIDON_EMPTY};
mod poseidon;
10 changes: 10 additions & 0 deletions crates/scroll/primitives/src/poseidon.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
use revm::primitives::{b256, B256};

/// The Poseidon hash of the empty string `""`.
pub const POSEIDON_EMPTY: B256 =
b256!("2098f5fb9e239eab3ceac3f27b81e481dc3124d55ffed523a839ee8446b64864");

/// Poseidon code hash
pub fn poseidon(code: &[u8]) -> B256 {
poseidon_bn254::hash_code(code).into()
}
28 changes: 28 additions & 0 deletions crates/scroll/revm/Cargo.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
[package]
name = "reth-scroll-revm"
version.workspace = true
edition.workspace = true
rust-version.workspace = true
license.workspace = true
homepage.workspace = true
repository.workspace = true
exclude.workspace = true

[lints]
workspace = true

[dependencies]
# revm
revm.workspace = true

# scroll
reth-scroll-primitives.workspace = true

[features]
default = ["std"]

arbitrary = ["revm/arbitrary"]

serde = ["revm/serde"]

std = ["revm/std"]
9 changes: 9 additions & 0 deletions crates/scroll/revm/src/lib.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
//! Scroll `revm` types redefinitions. Account types are redefined with two additional fields
//! `code_size` and `poseidon_code_hash`, which are used during computation of the state root.

pub mod states;

pub mod primitives;

pub use primitives::ScrollAccountInfo;
pub use revm::primitives::*;
Loading