From 074c5c301373cec1a0b755e213abf973293a0014 Mon Sep 17 00:00:00 2001 From: Dan Cline <6798349+Rjected@users.noreply.github.com> Date: Tue, 30 Apr 2024 22:06:37 -0400 Subject: [PATCH] feat: introduce external context GAT in ConfigureEvm (#7842) --- crates/ethereum/evm/src/lib.rs | 12 +++++++++++- crates/evm/src/lib.rs | 11 +++++++---- crates/optimism/evm/src/lib.rs | 6 ++++-- crates/revm/src/test_utils.rs | 17 +++++++++++------ examples/custom-evm/src/main.rs | 4 +++- 5 files changed, 36 insertions(+), 14 deletions(-) diff --git a/crates/ethereum/evm/src/lib.rs b/crates/ethereum/evm/src/lib.rs index a320a2b3c..adcfd700d 100644 --- a/crates/ethereum/evm/src/lib.rs +++ b/crates/ethereum/evm/src/lib.rs @@ -14,6 +14,7 @@ use reth_primitives::{ revm_primitives::{AnalysisKind, CfgEnvWithHandlerCfg, TxEnv}, Address, ChainSpec, Head, Header, Transaction, U256, }; +use reth_revm::{Database, EvmBuilder}; pub mod execute; /// Ethereum-related EVM configuration. @@ -55,7 +56,16 @@ impl ConfigureEvmEnv for EthEvmConfig { } } -impl ConfigureEvm for EthEvmConfig {} +impl ConfigureEvm for EthEvmConfig { + type DefaultExternalContext<'a> = (); + + fn evm<'a, DB: Database + 'a>( + &self, + db: DB, + ) -> reth_revm::Evm<'a, Self::DefaultExternalContext<'a>, DB> { + EvmBuilder::default().with_db(db).build() + } +} #[cfg(test)] mod tests { diff --git a/crates/evm/src/lib.rs b/crates/evm/src/lib.rs index 9179abc33..154aac2d7 100644 --- a/crates/evm/src/lib.rs +++ b/crates/evm/src/lib.rs @@ -16,14 +16,15 @@ pub mod execute; /// Trait for configuring the EVM for executing full blocks. pub trait ConfigureEvm: ConfigureEvmEnv { + /// Associated type for the default external context that should be configured for the EVM. + type DefaultExternalContext<'a>; + /// Returns new EVM with the given database /// /// This does not automatically configure the EVM with [ConfigureEvmEnv] methods. It is up to /// the caller to call an appropriate method to fill the transaction and block environment /// before executing any transactions using the provided EVM. - fn evm<'a, DB: Database + 'a>(&self, db: DB) -> Evm<'a, (), DB> { - EvmBuilder::default().with_db(db).build() - } + fn evm<'a, DB: Database + 'a>(&self, db: DB) -> Evm<'a, Self::DefaultExternalContext<'a>, DB>; /// Returns a new EVM with the given database configured with the given environment settings, /// including the spec id. @@ -33,7 +34,7 @@ pub trait ConfigureEvm: ConfigureEvmEnv { &self, db: DB, env: EnvWithHandlerCfg, - ) -> Evm<'a, (), DB> { + ) -> Evm<'a, Self::DefaultExternalContext<'a>, DB> { let mut evm = self.evm(db); evm.modify_spec_id(env.spec_id()); evm.context.evm.env = env.env; @@ -43,6 +44,8 @@ pub trait ConfigureEvm: ConfigureEvmEnv { /// Returns a new EVM with the given database configured with the given environment settings, /// including the spec id. /// + /// This will use the given external inspector as the EVM external context. + /// /// This will preserve any handler modifications fn evm_with_env_and_inspector<'a, DB, I>( &self, diff --git a/crates/optimism/evm/src/lib.rs b/crates/optimism/evm/src/lib.rs index 6a6324302..8ab6fd426 100644 --- a/crates/optimism/evm/src/lib.rs +++ b/crates/optimism/evm/src/lib.rs @@ -61,7 +61,9 @@ impl ConfigureEvmEnv for OptimismEvmConfig { } impl ConfigureEvm for OptimismEvmConfig { - fn evm<'a, DB: Database + 'a>(&self, db: DB) -> Evm<'a, (), DB> { + type DefaultExternalContext<'a> = (); + + fn evm<'a, DB: Database + 'a>(&self, db: DB) -> Evm<'a, Self::DefaultExternalContext<'a>, DB> { EvmBuilder::default().with_db(db).optimism().build() } @@ -83,7 +85,7 @@ impl ConfigureEvm for OptimismEvmConfig { mod tests { use super::*; use reth_primitives::revm_primitives::{BlockEnv, CfgEnv}; - use reth_revm::primitives::SpecId; + use revm_primitives::SpecId; #[test] #[ignore] diff --git a/crates/revm/src/test_utils.rs b/crates/revm/src/test_utils.rs index 193736987..73df4ea4b 100644 --- a/crates/revm/src/test_utils.rs +++ b/crates/revm/src/test_utils.rs @@ -18,11 +18,12 @@ use std::collections::HashMap; #[cfg(feature = "optimism")] use { reth_primitives::revm::env::fill_op_tx_env, - revm::{ - inspector_handle_register, - primitives::{HandlerCfg, SpecId}, - Database, Evm, EvmBuilder, GetInspector, - }, + revm::{inspector_handle_register, GetInspector}, +}; + +use revm::{ + primitives::{HandlerCfg, SpecId}, + Database, Evm, EvmBuilder, }; /// Mock state for testing @@ -158,9 +159,13 @@ impl ConfigureEvmEnv for TestEvmConfig { } impl ConfigureEvm for TestEvmConfig { - #[cfg(feature = "optimism")] + type DefaultExternalContext<'a> = (); + fn evm<'a, DB: Database + 'a>(&self, db: DB) -> Evm<'a, (), DB> { + #[cfg(feature = "optimism")] let handler_cfg = HandlerCfg { spec_id: SpecId::LATEST, is_optimism: true }; + #[cfg(not(feature = "optimism"))] + let handler_cfg = HandlerCfg { spec_id: SpecId::LATEST }; EvmBuilder::default().with_db(db).with_handler_cfg(handler_cfg).build() } diff --git a/examples/custom-evm/src/main.rs b/examples/custom-evm/src/main.rs index e5362c808..31edf4f03 100644 --- a/examples/custom-evm/src/main.rs +++ b/examples/custom-evm/src/main.rs @@ -81,7 +81,9 @@ impl ConfigureEvmEnv for MyEvmConfig { } impl ConfigureEvm for MyEvmConfig { - fn evm<'a, DB: Database + 'a>(&self, db: DB) -> Evm<'a, (), DB> { + type DefaultExternalContext<'a> = (); + + fn evm<'a, DB: Database + 'a>(&self, db: DB) -> Evm<'a, Self::DefaultExternalContext<'a>, DB> { EvmBuilder::default() .with_db(db) // add additional precompiles