foundry_evm/executors/
builder.rs1use crate::{executors::Executor, inspectors::InspectorStackBuilder};
2use foundry_evm_core::{
3 backend::Backend,
4 evm::{BlockEnvFor, EvmEnvFor, FoundryEvmNetwork, SpecFor, TxEnvFor},
5};
6use revm::context::{Block, Transaction};
7
8#[derive(Debug, Clone)]
16#[must_use = "builders do nothing unless you call `build` on them"]
17pub struct ExecutorBuilder<FEN: FoundryEvmNetwork> {
18 stack: InspectorStackBuilder<BlockEnvFor<FEN>>,
20 gas_limit: Option<u64>,
22 spec: Option<SpecFor<FEN>>,
24 legacy_assertions: bool,
25}
26
27impl<FEN: FoundryEvmNetwork> Default for ExecutorBuilder<FEN> {
28 #[inline]
29 fn default() -> Self {
30 Self {
31 stack: InspectorStackBuilder::new(),
32 gas_limit: None,
33 spec: None,
34 legacy_assertions: false,
35 }
36 }
37}
38
39impl<FEN: FoundryEvmNetwork> ExecutorBuilder<FEN> {
40 #[inline]
42 pub fn inspectors(
43 mut self,
44 f: impl FnOnce(
45 InspectorStackBuilder<BlockEnvFor<FEN>>,
46 ) -> InspectorStackBuilder<BlockEnvFor<FEN>>,
47 ) -> Self {
48 self.stack = f(self.stack);
49 self
50 }
51
52 #[inline]
54 pub fn spec_id(mut self, spec: SpecFor<FEN>) -> Self {
55 self.spec = Some(spec);
56 self
57 }
58
59 #[inline]
61 pub fn spec_id_opt(self, spec: Option<SpecFor<FEN>>) -> Self {
62 if let Some(spec) = spec { self.spec_id(spec) } else { self }
63 }
64
65 #[inline]
67 pub fn gas_limit(mut self, gas_limit: u64) -> Self {
68 self.gas_limit = Some(gas_limit);
69 self
70 }
71
72 #[inline]
74 pub fn legacy_assertions(mut self, legacy_assertions: bool) -> Self {
75 self.legacy_assertions = legacy_assertions;
76 self
77 }
78
79 #[inline]
81 pub fn build(
82 self,
83 mut evm_env: EvmEnvFor<FEN>,
84 tx_env: TxEnvFor<FEN>,
85 db: Backend<FEN>,
86 ) -> Executor<FEN> {
87 let Self { mut stack, gas_limit, spec, legacy_assertions, .. } = self;
88 if stack.block.is_none() {
89 stack.block = Some(evm_env.block_env.clone());
90 }
91 if stack.gas_price.is_none() {
92 stack.gas_price = Some(tx_env.gas_price());
93 }
94 let gas_limit = gas_limit.unwrap_or(evm_env.block_env.gas_limit());
95 if let Some(spec) = spec {
96 evm_env.cfg_env.set_spec_and_mainnet_gas_params(spec);
97 }
98 Executor::new(db, evm_env, tx_env, stack.build(), gas_limit, legacy_assertions)
99 }
100}