Skip to main content

anvil/eth/
api.rs

1use super::{
2    backend::mem::{BlockRequest, DatabaseRef, State},
3    sign::build_impersonated,
4};
5use crate::{
6    ClientFork, LoggingManager, Miner, MiningMode, StorageInfo,
7    eth::{
8        backend::{
9            self,
10            db::SerializableState,
11            mem::{MIN_CREATE_GAS, MIN_TRANSACTION_GAS},
12            notifications::NewBlockNotifications,
13            validate::TransactionValidator,
14        },
15        error::{
16            BlockchainError, FeeHistoryError, InvalidTransactionError, Result, ToRpcResponseResult,
17        },
18        fees::{FeeDetails, FeeHistoryCache, MIN_SUGGESTED_PRIORITY_FEE},
19        macros::node_info,
20        miner::FixedBlockTimeMiner,
21        pool::{
22            Pool,
23            transactions::{
24                PoolTransaction, TransactionOrder, TransactionPriority, TxMarker, to_marker,
25            },
26        },
27        sign::{self, Signer},
28    },
29    filter::{EthFilter, Filters, LogsFilter},
30    mem::transaction_build,
31};
32use alloy_consensus::{
33    Blob, BlockHeader, Transaction, TrieAccount, TxEip4844Variant, transaction::Recovered,
34};
35use alloy_dyn_abi::TypedData;
36use alloy_eips::{
37    eip2718::Encodable2718,
38    eip7910::{EthConfig, EthForkConfig},
39};
40use alloy_evm::overrides::{OverrideBlockHashes, apply_state_overrides};
41use alloy_network::{
42    AnyRpcBlock, AnyRpcTransaction, BlockResponse, Network, NetworkTransactionBuilder,
43    ReceiptResponse, TransactionBuilder, TransactionBuilder4844, TransactionResponse,
44    eip2718::Decodable2718,
45};
46use alloy_primitives::{
47    Address, B64, B256, Bytes, TxHash, TxKind, U64, U256,
48    map::{HashMap, HashSet},
49};
50use alloy_rpc_types::{
51    AccessListResult, BlockId, BlockNumberOrTag as BlockNumber, BlockTransactions,
52    EIP1186AccountProofResponse, FeeHistory, Filter, FilteredParams, Index, Log, Work,
53    anvil::{
54        ForkedNetwork, Forking, Metadata, MineOptions, NodeEnvironment, NodeForkConfig, NodeInfo,
55    },
56    request::TransactionRequest,
57    simulate::{SimulatePayload, SimulatedBlock},
58    state::{AccountOverride, EvmOverrides, StateOverridesBuilder},
59    trace::{
60        filter::TraceFilter,
61        geth::{GethDebugTracingCallOptions, GethDebugTracingOptions, GethTrace, TraceResult},
62        parity::{LocalizedTransactionTrace, TraceResultsWithTransactionHash, TraceType},
63    },
64    txpool::{TxpoolContent, TxpoolInspect, TxpoolInspectSummary, TxpoolStatus},
65};
66use alloy_rpc_types_eth::FillTransaction;
67use alloy_serde::WithOtherFields;
68use alloy_sol_types::{SolCall, SolValue, sol};
69use alloy_transport::TransportErrorKind;
70use anvil_core::{
71    eth::{
72        EthRequest,
73        block::BlockInfo,
74        transaction::{MaybeImpersonatedTransaction, PendingTransaction},
75    },
76    types::{ReorgOptions, TransactionData},
77};
78use anvil_rpc::{error::RpcError, response::ResponseResult};
79use foundry_common::{
80    provider::ProviderBuilder,
81    version::{COMMIT_SHA, SEMVER_VERSION},
82};
83use foundry_evm::decode::RevertDecoder;
84use foundry_primitives::{
85    FoundryNetwork, FoundryReceiptEnvelope, FoundryTransactionRequest, FoundryTxEnvelope,
86    FoundryTxReceipt, FoundryTxType, FoundryTypedTx, PaymentLaneClassification, PaymentLaneReason,
87};
88use futures::{
89    StreamExt, TryFutureExt,
90    channel::{mpsc::Receiver, oneshot},
91};
92use parking_lot::RwLock;
93use revm::{
94    context::{BlockEnv, Cfg},
95    context_interface::{
96        block::BlobExcessGasAndPrice,
97        result::{HaltReason, Output},
98    },
99    database::CacheDB,
100    interpreter::{InstructionResult, SuccessOrHalt, return_ok, return_revert},
101    primitives::eip7702::PER_EMPTY_ACCOUNT_COST,
102};
103use std::{sync::Arc, time::Duration};
104use tempo_chainspec::hardfork::TempoHardfork;
105use tokio::{
106    sync::mpsc::{UnboundedReceiver, unbounded_channel},
107    try_join,
108};
109
110/// The client version: `anvil/v{major}.{minor}.{patch}`
111pub const CLIENT_VERSION: &str = concat!("anvil/v", env!("CARGO_PKG_VERSION"));
112
113/// The entry point for executing eth api RPC call - The Eth RPC interface.
114///
115/// This type is cheap to clone and can be used concurrently
116pub struct EthApi<N: Network> {
117    /// The transaction pool
118    pool: Arc<Pool<N::TxEnvelope>>,
119    /// Holds all blockchain related data
120    /// In-Memory only for now
121    pub backend: Arc<backend::mem::Backend<N>>,
122    /// Whether this node is mining
123    is_mining: bool,
124    /// available signers
125    signers: Arc<Vec<Box<dyn Signer<N>>>>,
126    /// data required for `eth_feeHistory`
127    fee_history_cache: FeeHistoryCache,
128    /// max number of items kept in fee cache
129    fee_history_limit: u64,
130    /// access to the actual miner
131    ///
132    /// This access is required in order to adjust miner settings based on requests received from
133    /// custom RPC endpoints
134    miner: Miner<N::TxEnvelope>,
135    /// allows to enabled/disable logging
136    logger: LoggingManager,
137    /// Tracks all active filters
138    filters: Filters<N>,
139    /// How transactions are ordered in the pool
140    transaction_order: Arc<RwLock<TransactionOrder>>,
141    /// Whether we're listening for RPC calls
142    net_listening: bool,
143    /// The instance ID. Changes on every reset.
144    instance_id: Arc<RwLock<B256>>,
145}
146
147impl<N: Network> Clone for EthApi<N> {
148    fn clone(&self) -> Self {
149        Self {
150            pool: self.pool.clone(),
151            backend: self.backend.clone(),
152            is_mining: self.is_mining,
153            signers: self.signers.clone(),
154            fee_history_cache: self.fee_history_cache.clone(),
155            fee_history_limit: self.fee_history_limit,
156            miner: self.miner.clone(),
157            logger: self.logger.clone(),
158            filters: self.filters.clone(),
159            transaction_order: self.transaction_order.clone(),
160            net_listening: self.net_listening,
161            instance_id: self.instance_id.clone(),
162        }
163    }
164}
165
166// == impl EthApi<N: Network> generic methods ==
167
168impl<N: Network> EthApi<N> {
169    /// Creates a new instance
170    #[expect(clippy::too_many_arguments)]
171    pub fn new(
172        pool: Arc<Pool<N::TxEnvelope>>,
173        backend: Arc<backend::mem::Backend<N>>,
174        signers: Arc<Vec<Box<dyn Signer<N>>>>,
175        fee_history_cache: FeeHistoryCache,
176        fee_history_limit: u64,
177        miner: Miner<N::TxEnvelope>,
178        logger: LoggingManager,
179        filters: Filters<N>,
180        transactions_order: TransactionOrder,
181    ) -> Self {
182        Self {
183            pool,
184            backend,
185            is_mining: true,
186            signers,
187            fee_history_cache,
188            fee_history_limit,
189            miner,
190            logger,
191            filters,
192            net_listening: true,
193            transaction_order: Arc::new(RwLock::new(transactions_order)),
194            instance_id: Arc::new(RwLock::new(B256::random())),
195        }
196    }
197
198    /// Returns the current gas price
199    pub fn gas_price(&self) -> u128 {
200        if self.backend.is_eip1559() {
201            if self.backend.is_min_priority_fee_enforced() {
202                (self.backend.base_fee() as u128).saturating_add(self.lowest_suggestion_tip())
203            } else {
204                self.backend.base_fee() as u128
205            }
206        } else {
207            self.backend.fees().raw_gas_price()
208        }
209    }
210
211    /// Returns the suggested fee cap.
212    ///
213    /// Returns at least [MIN_SUGGESTED_PRIORITY_FEE]
214    fn lowest_suggestion_tip(&self) -> u128 {
215        let block_number = self.backend.best_number();
216        let latest_cached_block = self.fee_history_cache.lock().get(&block_number).cloned();
217
218        match latest_cached_block {
219            Some(block) => block.rewards.iter().copied().min(),
220            None => self.fee_history_cache.lock().values().flat_map(|b| b.rewards.clone()).min(),
221        }
222        .map(|fee| fee.max(MIN_SUGGESTED_PRIORITY_FEE))
223        .unwrap_or(MIN_SUGGESTED_PRIORITY_FEE)
224    }
225
226    /// Returns true if auto mining is enabled, and false.
227    ///
228    /// Handler for ETH RPC call: `anvil_getAutomine`
229    pub fn anvil_get_auto_mine(&self) -> Result<bool> {
230        node_info!("anvil_getAutomine");
231        Ok(self.miner.is_auto_mine())
232    }
233
234    /// Returns the value of mining interval, if set.
235    ///
236    /// Handler for ETH RPC call: `anvil_getIntervalMining`.
237    pub fn anvil_get_interval_mining(&self) -> Result<Option<u64>> {
238        node_info!("anvil_getIntervalMining");
239        Ok(self.miner.get_interval())
240    }
241
242    /// Enables or disables, based on the single boolean argument, the automatic mining of new
243    /// blocks with each new transaction submitted to the network.
244    ///
245    /// Handler for ETH RPC call: `evm_setAutomine`
246    pub async fn anvil_set_auto_mine(&self, enable_automine: bool) -> Result<()> {
247        node_info!("evm_setAutomine");
248        if self.miner.is_auto_mine() {
249            if enable_automine {
250                return Ok(());
251            }
252            self.miner.set_mining_mode(MiningMode::None);
253        } else if enable_automine {
254            let listener = self.pool.add_ready_listener();
255            let mode = MiningMode::instant(1_000, listener);
256            self.miner.set_mining_mode(mode);
257        }
258        Ok(())
259    }
260
261    /// Sets the mining behavior to interval with the given interval (seconds)
262    ///
263    /// Handler for ETH RPC call: `evm_setIntervalMining`
264    pub fn anvil_set_interval_mining(&self, secs: u64) -> Result<()> {
265        node_info!("evm_setIntervalMining");
266        let mining_mode = if secs == 0 {
267            MiningMode::None
268        } else {
269            let block_time = Duration::from_secs(secs);
270
271            // This ensures that memory limits are stricter in interval-mine mode
272            self.backend.update_interval_mine_block_time(block_time);
273
274            MiningMode::FixedBlockTime(FixedBlockTimeMiner::new(block_time))
275        };
276        self.miner.set_mining_mode(mining_mode);
277        Ok(())
278    }
279
280    /// Removes transactions from the pool
281    ///
282    /// Handler for RPC call: `anvil_dropTransaction`
283    pub async fn anvil_drop_transaction(&self, tx_hash: B256) -> Result<Option<B256>> {
284        node_info!("anvil_dropTransaction");
285        Ok(self.pool.drop_transaction(tx_hash).map(|tx| tx.hash()))
286    }
287
288    /// Removes all transactions from the pool
289    ///
290    /// Handler for RPC call: `anvil_dropAllTransactions`
291    pub async fn anvil_drop_all_transactions(&self) -> Result<()> {
292        node_info!("anvil_dropAllTransactions");
293        self.pool.clear();
294        Ok(())
295    }
296
297    pub async fn anvil_set_chain_id(&self, chain_id: u64) -> Result<()> {
298        node_info!("anvil_setChainId");
299        self.backend.set_chain_id(chain_id);
300        Ok(())
301    }
302
303    /// Modifies the balance of an account.
304    ///
305    /// Handler for RPC call: `anvil_setBalance`
306    pub async fn anvil_set_balance(&self, address: Address, balance: U256) -> Result<()> {
307        node_info!("anvil_setBalance");
308        self.backend.set_balance(address, balance).await?;
309        Ok(())
310    }
311
312    /// Sets the code of a contract.
313    ///
314    /// Handler for RPC call: `anvil_setCode`
315    pub async fn anvil_set_code(&self, address: Address, code: Bytes) -> Result<()> {
316        node_info!("anvil_setCode");
317        self.backend.set_code(address, code).await?;
318        Ok(())
319    }
320
321    /// Sets the nonce of an address.
322    ///
323    /// Handler for RPC call: `anvil_setNonce`
324    pub async fn anvil_set_nonce(&self, address: Address, nonce: U256) -> Result<()> {
325        node_info!("anvil_setNonce");
326        self.backend.set_nonce(address, nonce).await?;
327        Ok(())
328    }
329
330    /// Writes a single slot of the account's storage.
331    ///
332    /// Handler for RPC call: `anvil_setStorageAt`
333    pub async fn anvil_set_storage_at(
334        &self,
335        address: Address,
336        slot: U256,
337        val: B256,
338    ) -> Result<bool> {
339        node_info!("anvil_setStorageAt");
340        self.backend.set_storage_at(address, slot, val).await?;
341        Ok(true)
342    }
343
344    /// Enable or disable logging.
345    ///
346    /// Handler for RPC call: `anvil_setLoggingEnabled`
347    pub async fn anvil_set_logging(&self, enable: bool) -> Result<()> {
348        node_info!("anvil_setLoggingEnabled");
349        self.logger.set_enabled(enable);
350        Ok(())
351    }
352
353    /// Set the minimum gas price for the node.
354    ///
355    /// Handler for RPC call: `anvil_setMinGasPrice`
356    pub async fn anvil_set_min_gas_price(&self, gas: U256) -> Result<()> {
357        node_info!("anvil_setMinGasPrice");
358        if self.backend.is_eip1559() {
359            return Err(RpcError::invalid_params(
360                "anvil_setMinGasPrice is not supported when EIP-1559 is active",
361            )
362            .into());
363        }
364        self.backend.set_gas_price(gas.saturating_to());
365        Ok(())
366    }
367
368    /// Sets the base fee of the next block.
369    ///
370    /// Handler for RPC call: `anvil_setNextBlockBaseFeePerGas`
371    pub async fn anvil_set_next_block_base_fee_per_gas(&self, basefee: U256) -> Result<()> {
372        node_info!("anvil_setNextBlockBaseFeePerGas");
373        if !self.backend.is_eip1559() {
374            return Err(RpcError::invalid_params(
375                "anvil_setNextBlockBaseFeePerGas is only supported when EIP-1559 is active",
376            )
377            .into());
378        }
379        self.backend.set_base_fee(basefee.saturating_to());
380        Ok(())
381    }
382
383    /// Sets the coinbase address.
384    ///
385    /// Handler for RPC call: `anvil_setCoinbase`
386    pub async fn anvil_set_coinbase(&self, address: Address) -> Result<()> {
387        node_info!("anvil_setCoinbase");
388        self.backend.set_coinbase(address);
389        Ok(())
390    }
391
392    /// Retrieves the Anvil node configuration params.
393    ///
394    /// Handler for RPC call: `anvil_nodeInfo`
395    pub async fn anvil_node_info(&self) -> Result<NodeInfo> {
396        node_info!("anvil_nodeInfo");
397
398        let evm_env = self.backend.evm_env().read();
399        let fork_config = self.backend.get_fork();
400        let tx_order = self.transaction_order.read();
401        let hard_fork = self.backend.hardfork().name();
402
403        Ok(NodeInfo {
404            current_block_number: self.backend.best_number(),
405            current_block_timestamp: evm_env.block_env.timestamp.saturating_to(),
406            current_block_hash: self.backend.best_hash(),
407            hard_fork,
408            transaction_order: match *tx_order {
409                TransactionOrder::Fifo => "fifo".to_string(),
410                TransactionOrder::Fees => "fees".to_string(),
411            },
412            environment: NodeEnvironment {
413                base_fee: self.backend.base_fee() as u128,
414                chain_id: self.backend.chain_id().to::<u64>(),
415                gas_limit: self.backend.gas_limit(),
416                gas_price: self.gas_price(),
417            },
418            fork_config: fork_config
419                .map(|fork| {
420                    let config = fork.config.read();
421
422                    NodeForkConfig {
423                        fork_url: config.eth_rpc_url().map(|s| s.to_string()),
424                        fork_block_number: Some(config.block_number),
425                        fork_retry_backoff: Some(config.backoff.as_millis()),
426                    }
427                })
428                .unwrap_or_default(),
429            network: self.backend.is_tempo().then(|| "tempo".to_string()),
430        })
431    }
432
433    /// Retrieves metadata about the Anvil instance.
434    ///
435    /// Handler for RPC call: `anvil_metadata`
436    pub async fn anvil_metadata(&self) -> Result<Metadata> {
437        node_info!("anvil_metadata");
438        let fork_config = self.backend.get_fork();
439
440        Ok(Metadata {
441            client_version: CLIENT_VERSION.to_string(),
442            client_semver: Some(SEMVER_VERSION.to_string()),
443            client_commit_sha: Some(COMMIT_SHA.to_string()),
444            chain_id: self.backend.chain_id().to::<u64>(),
445            latest_block_hash: self.backend.best_hash(),
446            latest_block_number: self.backend.best_number(),
447            instance_id: *self.instance_id.read(),
448            forked_network: fork_config.map(|cfg| ForkedNetwork {
449                chain_id: cfg.chain_id(),
450                fork_block_number: cfg.block_number(),
451                fork_block_hash: cfg.block_hash(),
452            }),
453            snapshots: self.backend.list_state_snapshots(),
454        })
455    }
456
457    pub async fn anvil_remove_pool_transactions(&self, address: Address) -> Result<()> {
458        node_info!("anvil_removePoolTransactions");
459        self.pool.remove_transactions_by_address(address);
460        Ok(())
461    }
462
463    /// Snapshot the state of the blockchain at the current block.
464    ///
465    /// Handler for RPC call: `evm_snapshot`
466    pub async fn evm_snapshot(&self) -> Result<U256> {
467        node_info!("evm_snapshot");
468        Ok(self.backend.create_state_snapshot().await)
469    }
470
471    /// Jump forward in time by the given amount of time, in seconds.
472    ///
473    /// Handler for RPC call: `evm_increaseTime`
474    pub async fn evm_increase_time(&self, seconds: U256) -> Result<i64> {
475        node_info!("evm_increaseTime");
476        Ok(self.backend.time().increase_time(seconds.try_into().unwrap_or(u64::MAX)) as i64)
477    }
478
479    /// Similar to `evm_increaseTime` but takes the exact timestamp that you want in the next block
480    ///
481    /// Handler for RPC call: `evm_setNextBlockTimestamp`
482    pub fn evm_set_next_block_timestamp(&self, seconds: u64) -> Result<()> {
483        node_info!("evm_setNextBlockTimestamp");
484        self.backend.time().set_next_block_timestamp(seconds)
485    }
486
487    /// Sets the specific timestamp and returns the number of seconds between the given timestamp
488    /// and the current time.
489    ///
490    /// The `timestamp` is in seconds. The `evm_setTime` JSON-RPC method accepts both seconds and
491    /// milliseconds (values above 1e12 are treated as milliseconds); the RPC handler normalises
492    /// the input to seconds before calling this function.
493    ///
494    /// Handler for RPC call: `evm_setTime`
495    pub fn evm_set_time(&self, timestamp: u64) -> Result<u64> {
496        node_info!("evm_setTime");
497        let now = self.backend.time().current_call_timestamp();
498        self.backend.time().reset(timestamp);
499
500        // number of seconds between the given timestamp and the current time.
501        let offset = timestamp.saturating_sub(now);
502        Ok(offset)
503    }
504
505    /// Set the next block gas limit
506    ///
507    /// Handler for RPC call: `evm_setBlockGasLimit`
508    pub fn evm_set_block_gas_limit(&self, gas_limit: U256) -> Result<bool> {
509        node_info!("evm_setBlockGasLimit");
510        self.backend.set_gas_limit(gas_limit.saturating_to());
511        Ok(true)
512    }
513
514    /// Sets an interval for the block timestamp
515    ///
516    /// Handler for RPC call: `anvil_setBlockTimestampInterval`
517    pub fn evm_set_block_timestamp_interval(&self, seconds: u64) -> Result<()> {
518        node_info!("anvil_setBlockTimestampInterval");
519        self.backend.time().set_block_timestamp_interval(seconds);
520        Ok(())
521    }
522
523    /// Sets an interval for the block timestamp
524    ///
525    /// Handler for RPC call: `anvil_removeBlockTimestampInterval`
526    pub fn evm_remove_block_timestamp_interval(&self) -> Result<bool> {
527        node_info!("anvil_removeBlockTimestampInterval");
528        Ok(self.backend.time().remove_block_timestamp_interval())
529    }
530
531    /// Sets the backend rpc url
532    ///
533    /// Handler for ETH RPC call: `anvil_setRpcUrl`
534    pub async fn anvil_set_rpc_url(&self, url: String) -> Result<()> {
535        node_info!("anvil_setRpcUrl");
536        if let Some(fork) = self.backend.get_fork() {
537            let mut config = fork.config.write();
538            // let interval = config.provider.get_interval();
539            let new_provider = Arc::new(
540                ProviderBuilder::new(&url).max_retry(10).initial_backoff(1000).build().map_err(
541                    |_| {
542                        TransportErrorKind::custom_str(
543                            format!("Failed to parse invalid url {url}").as_str(),
544                        )
545                    },
546                    // TODO: Add interval
547                )?, // .interval(interval),
548            );
549            config.provider = new_provider;
550            trace!(target: "backend", "Updated fork rpc from \"{}\" to \"{}\"", config.eth_rpc_url().unwrap_or("none"), url);
551            config.fork_urls = vec![url.clone()];
552        }
553        // Keep node_config in sync so anvil_reset(None) uses the updated URL
554        self.backend.node_config.write().await.fork_urls = vec![url];
555        Ok(())
556    }
557
558    /// Returns the number of transactions currently pending for inclusion in the next block(s), as
559    /// well as the ones that are being scheduled for future execution only.
560    /// Ref: [Here](https://geth.ethereum.org/docs/rpc/ns-txpool#txpool_status)
561    ///
562    /// Handler for ETH RPC call: `txpool_status`
563    pub async fn txpool_status(&self) -> Result<TxpoolStatus> {
564        node_info!("txpool_status");
565        Ok(self.pool.txpool_status())
566    }
567
568    /// Executes the future on a new blocking task.
569    async fn on_blocking_task<C, F, R>(&self, c: C) -> Result<R>
570    where
571        C: FnOnce(Self) -> F,
572        F: Future<Output = Result<R>> + Send + 'static,
573        R: Send + 'static,
574    {
575        let (tx, rx) = oneshot::channel();
576        let this = self.clone();
577        let f = c(this);
578        tokio::task::spawn_blocking(move || {
579            tokio::runtime::Handle::current().block_on(async move {
580                let res = f.await;
581                let _ = tx.send(res);
582            })
583        });
584        rx.await.map_err(|_| BlockchainError::Internal("blocking task panicked".to_string()))?
585    }
586
587    /// Updates the `TransactionOrder`
588    pub fn set_transaction_order(&self, order: TransactionOrder) {
589        *self.transaction_order.write() = order;
590    }
591
592    /// Returns the chain ID used for transaction
593    pub fn chain_id(&self) -> u64 {
594        self.backend.chain_id().to::<u64>()
595    }
596
597    /// Returns the configured fork, if any.
598    pub fn get_fork(&self) -> Option<ClientFork> {
599        self.backend.get_fork()
600    }
601
602    /// Returns the current instance's ID.
603    pub fn instance_id(&self) -> B256 {
604        *self.instance_id.read()
605    }
606
607    /// Resets the instance ID.
608    pub fn reset_instance_id(&self) {
609        *self.instance_id.write() = B256::random();
610    }
611
612    /// Returns the first signer that can sign for the given address
613    #[expect(clippy::borrowed_box)]
614    pub fn get_signer(&self, address: Address) -> Option<&Box<dyn Signer<N>>> {
615        self.signers.iter().find(|signer| signer.is_signer_for(address))
616    }
617
618    /// Returns a new listeners for ready transactions
619    pub fn new_ready_transactions(&self) -> Receiver<TxHash> {
620        self.pool.add_ready_listener()
621    }
622
623    /// Returns true if forked
624    pub fn is_fork(&self) -> bool {
625        self.backend.is_fork()
626    }
627
628    /// Returns the current state root
629    pub async fn state_root(&self) -> Option<B256> {
630        self.backend.get_db().read().await.maybe_state_root()
631    }
632
633    /// Returns true if the `addr` is currently impersonated
634    pub fn is_impersonated(&self, addr: Address) -> bool {
635        self.backend.cheats().is_impersonated(addr)
636    }
637
638    /// Returns a new accessor for certain storage elements
639    pub fn storage_info(&self) -> StorageInfo<N> {
640        StorageInfo::new(Arc::clone(&self.backend))
641    }
642
643    /// Handler for RPC call: `anvil_getBlobByHash`
644    #[allow(clippy::large_stack_frames)]
645    pub fn anvil_get_blob_by_versioned_hash(
646        &self,
647        hash: B256,
648    ) -> Result<Option<alloy_consensus::Blob>> {
649        node_info!("anvil_getBlobByHash");
650        Ok(self.backend.get_blob_by_versioned_hash(hash)?)
651    }
652
653    /// Handler for RPC call: `anvil_getBlobsByBlockId`
654    pub fn anvil_get_blobs_by_block_id(
655        &self,
656        block_id: impl Into<BlockId>,
657        versioned_hashes: Vec<B256>,
658    ) -> Result<Option<Vec<Blob>>> {
659        node_info!("anvil_getBlobsByBlockId");
660        Ok(self.backend.get_blobs_by_block_id(block_id, versioned_hashes)?)
661    }
662
663    /// Returns the genesis time for the Beacon chain
664    ///
665    /// Handler for Beacon API call: `GET /eth/v1/beacon/genesis`
666    pub fn anvil_get_genesis_time(&self) -> Result<u64> {
667        node_info!("anvil_getGenesisTime");
668        Ok(self.backend.genesis_time())
669    }
670
671    /// Reset the fork to a fresh forked state, and optionally update the fork config.
672    ///
673    /// If `forking` is `None` then this will disable forking entirely.
674    ///
675    /// Handler for RPC call: `anvil_reset`
676    pub async fn anvil_reset(&self, forking: Option<Forking>) -> Result<()> {
677        self.reset_instance_id();
678        node_info!("anvil_reset");
679        if let Some(forking) = forking {
680            // if we're resetting the fork we need to reset the instance id
681            self.backend.reset_fork(forking).await?;
682        } else {
683            // Reset to a fresh in-memory state
684            self.backend.reset_to_in_mem().await?;
685        }
686        // Clear pending transactions since they reference the old chain state.
687        self.pool.clear();
688        Ok(())
689    }
690
691    /// Revert the state of the blockchain to a previous snapshot.
692    /// Takes a single parameter, which is the snapshot id to revert to.
693    ///
694    /// Handler for RPC call: `evm_revert`
695    pub async fn evm_revert(&self, id: U256) -> Result<bool> {
696        node_info!("evm_revert");
697        self.backend.revert_state_snapshot(id).await
698    }
699
700    /// Send transactions impersonating specific account and contract addresses.
701    ///
702    /// Handler for ETH RPC call: `anvil_impersonateAccount`
703    pub async fn anvil_impersonate_account(&self, address: Address) -> Result<()> {
704        node_info!("anvil_impersonateAccount");
705        self.backend.impersonate(address);
706        Ok(())
707    }
708
709    /// Stops impersonating an account if previously set with `anvil_impersonateAccount`.
710    ///
711    /// Handler for ETH RPC call: `anvil_stopImpersonatingAccount`
712    pub async fn anvil_stop_impersonating_account(&self, address: Address) -> Result<()> {
713        node_info!("anvil_stopImpersonatingAccount");
714        self.backend.stop_impersonating(address);
715        Ok(())
716    }
717
718    /// If set to true will make every account impersonated
719    ///
720    /// Handler for ETH RPC call: `anvil_autoImpersonateAccount`
721    pub async fn anvil_auto_impersonate_account(&self, enabled: bool) -> Result<()> {
722        node_info!("anvil_autoImpersonateAccount");
723        self.backend.auto_impersonate_account(enabled);
724        Ok(())
725    }
726
727    /// Registers a new address and signature pair to impersonate.
728    pub async fn anvil_impersonate_signature(
729        &self,
730        signature: Bytes,
731        address: Address,
732    ) -> Result<()> {
733        node_info!("anvil_impersonateSignature");
734        self.backend.impersonate_signature(signature, address).await
735    }
736
737    /// Returns a new block event stream that yields Notifications when a new block was added
738    pub fn new_block_notifications(&self) -> NewBlockNotifications {
739        self.backend.new_block_notifications()
740    }
741
742    /// Returns the current client version.
743    ///
744    /// Handler for ETH RPC call: `web3_clientVersion`
745    pub fn client_version(&self) -> Result<String> {
746        node_info!("web3_clientVersion");
747        Ok(CLIENT_VERSION.to_string())
748    }
749
750    /// Returns Keccak-256 (not the standardized SHA3-256) of the given data.
751    ///
752    /// Handler for ETH RPC call: `web3_sha3`
753    pub fn sha3(&self, bytes: Bytes) -> Result<String> {
754        node_info!("web3_sha3");
755        let hash = alloy_primitives::keccak256(bytes.as_ref());
756        Ok(alloy_primitives::hex::encode_prefixed(&hash[..]))
757    }
758
759    /// Returns protocol version encoded as a string (quotes are necessary).
760    ///
761    /// Handler for ETH RPC call: `eth_protocolVersion`
762    pub fn protocol_version(&self) -> Result<u64> {
763        node_info!("eth_protocolVersion");
764        Ok(1)
765    }
766
767    /// Returns the number of hashes per second that the node is mining with.
768    ///
769    /// Handler for ETH RPC call: `eth_hashrate`
770    pub fn hashrate(&self) -> Result<U256> {
771        node_info!("eth_hashrate");
772        Ok(U256::ZERO)
773    }
774
775    /// Returns the client coinbase address.
776    ///
777    /// Handler for ETH RPC call: `eth_coinbase`
778    pub fn author(&self) -> Result<Address> {
779        node_info!("eth_coinbase");
780        Ok(self.backend.coinbase())
781    }
782
783    /// Returns true if client is actively mining new blocks.
784    ///
785    /// Handler for ETH RPC call: `eth_mining`
786    pub fn is_mining(&self) -> Result<bool> {
787        node_info!("eth_mining");
788        Ok(self.is_mining)
789    }
790
791    /// Returns the chain ID used for transaction signing at the
792    /// current best block. None is returned if not
793    /// available.
794    ///
795    /// Handler for ETH RPC call: `eth_chainId`
796    pub fn eth_chain_id(&self) -> Result<Option<U64>> {
797        node_info!("eth_chainId");
798        Ok(Some(self.backend.chain_id().to::<U64>()))
799    }
800
801    /// Returns the same as `chain_id`
802    ///
803    /// Handler for ETH RPC call: `eth_networkId`
804    pub fn network_id(&self) -> Result<Option<String>> {
805        node_info!("eth_networkId");
806        let chain_id = self.backend.chain_id().to::<u64>();
807        Ok(Some(format!("{chain_id}")))
808    }
809
810    /// Returns true if client is actively listening for network connections.
811    ///
812    /// Handler for ETH RPC call: `net_listening`
813    pub fn net_listening(&self) -> Result<bool> {
814        node_info!("net_listening");
815        Ok(self.net_listening)
816    }
817
818    /// Returns the current gas price
819    fn eth_gas_price(&self) -> Result<U256> {
820        node_info!("eth_gasPrice");
821        Ok(U256::from(self.gas_price()))
822    }
823
824    /// Returns the excess blob gas and current blob gas price
825    pub fn excess_blob_gas_and_price(&self) -> Result<Option<BlobExcessGasAndPrice>> {
826        Ok(self.backend.excess_blob_gas_and_price())
827    }
828
829    /// Returns a fee per gas that is an estimate of how much you can pay as a priority fee, or
830    /// 'tip', to get a transaction included in the current block.
831    ///
832    /// Handler for ETH RPC call: `eth_maxPriorityFeePerGas`
833    pub fn gas_max_priority_fee_per_gas(&self) -> Result<U256> {
834        self.max_priority_fee_per_gas()
835    }
836
837    /// Returns the base fee per blob required to send a EIP-4844 tx.
838    ///
839    /// Handler for ETH RPC call: `eth_blobBaseFee`
840    pub fn blob_base_fee(&self) -> Result<U256> {
841        Ok(U256::from(self.backend.fees().base_fee_per_blob_gas()))
842    }
843
844    /// Returns the block gas limit
845    pub fn gas_limit(&self) -> U256 {
846        U256::from(self.backend.gas_limit())
847    }
848
849    /// Returns the accounts list
850    ///
851    /// Handler for ETH RPC call: `eth_accounts`
852    pub fn accounts(&self) -> Result<Vec<Address>> {
853        node_info!("eth_accounts");
854        let mut unique = HashSet::new();
855        let mut accounts: Vec<Address> = Vec::new();
856        for signer in self.signers.iter() {
857            accounts.extend(signer.accounts().into_iter().filter(|acc| unique.insert(*acc)));
858        }
859        accounts.extend(
860            self.backend
861                .cheats()
862                .impersonated_accounts()
863                .into_iter()
864                .filter(|acc| unique.insert(*acc)),
865        );
866        Ok(accounts.into_iter().collect())
867    }
868
869    /// Returns the number of most recent block.
870    ///
871    /// Handler for ETH RPC call: `eth_blockNumber`
872    pub fn block_number(&self) -> Result<U256> {
873        node_info!("eth_blockNumber");
874        Ok(U256::from(self.backend.best_number()))
875    }
876
877    /// Returns block with given hash.
878    ///
879    /// Handler for ETH RPC call: `eth_getBlockByHash`
880    pub async fn block_by_hash(&self, hash: B256) -> Result<Option<AnyRpcBlock>> {
881        node_info!("eth_getBlockByHash");
882        self.backend.block_by_hash(hash).await
883    }
884
885    /// Returns a _full_ block with given hash.
886    ///
887    /// Handler for ETH RPC call: `eth_getBlockByHash`
888    pub async fn block_by_hash_full(&self, hash: B256) -> Result<Option<AnyRpcBlock>> {
889        node_info!("eth_getBlockByHash");
890        self.backend.block_by_hash_full(hash).await
891    }
892
893    /// Returns the number of transactions in a block with given hash.
894    ///
895    /// Handler for ETH RPC call: `eth_getBlockTransactionCountByHash`
896    pub async fn block_transaction_count_by_hash(&self, hash: B256) -> Result<Option<U256>> {
897        node_info!("eth_getBlockTransactionCountByHash");
898        let block = self.backend.block_by_hash(hash).await?;
899        let txs = block.map(|b| match b.transactions() {
900            BlockTransactions::Full(txs) => U256::from(txs.len()),
901            BlockTransactions::Hashes(txs) => U256::from(txs.len()),
902            BlockTransactions::Uncle => U256::from(0),
903        });
904        Ok(txs)
905    }
906
907    /// Returns the number of uncles in a block with given hash.
908    ///
909    /// Handler for ETH RPC call: `eth_getUncleCountByBlockHash`
910    pub async fn block_uncles_count_by_hash(&self, hash: B256) -> Result<U256> {
911        node_info!("eth_getUncleCountByBlockHash");
912        let block =
913            self.backend.block_by_hash(hash).await?.ok_or(BlockchainError::BlockNotFound)?;
914        Ok(U256::from(block.uncles.len()))
915    }
916
917    /// Returns the number of uncles in a block with given block number.
918    ///
919    /// Handler for ETH RPC call: `eth_getUncleCountByBlockNumber`
920    pub async fn block_uncles_count_by_number(&self, block_number: BlockNumber) -> Result<U256> {
921        node_info!("eth_getUncleCountByBlockNumber");
922        let block = self
923            .backend
924            .block_by_number(block_number)
925            .await?
926            .ok_or(BlockchainError::BlockNotFound)?;
927        Ok(U256::from(block.uncles.len()))
928    }
929
930    /// Signs data via [EIP-712](https://github.com/ethereum/EIPs/blob/master/EIPS/eip-712.md).
931    ///
932    /// Handler for ETH RPC call: `eth_signTypedData`
933    pub async fn sign_typed_data(
934        &self,
935        _address: Address,
936        _data: serde_json::Value,
937    ) -> Result<String> {
938        node_info!("eth_signTypedData");
939        Err(BlockchainError::RpcUnimplemented)
940    }
941
942    /// Signs data via [EIP-712](https://github.com/ethereum/EIPs/blob/master/EIPS/eip-712.md).
943    ///
944    /// Handler for ETH RPC call: `eth_signTypedData_v3`
945    pub async fn sign_typed_data_v3(
946        &self,
947        _address: Address,
948        _data: serde_json::Value,
949    ) -> Result<String> {
950        node_info!("eth_signTypedData_v3");
951        Err(BlockchainError::RpcUnimplemented)
952    }
953
954    /// Signs data via [EIP-712](https://github.com/ethereum/EIPs/blob/master/EIPS/eip-712.md), and includes full support of arrays and recursive data structures.
955    ///
956    /// Handler for ETH RPC call: `eth_signTypedData_v4`
957    pub async fn sign_typed_data_v4(&self, address: Address, data: &TypedData) -> Result<String> {
958        node_info!("eth_signTypedData_v4");
959        let signer = self.get_signer(address).ok_or(BlockchainError::NoSignerAvailable)?;
960        let signature = signer.sign_typed_data(address, data).await?;
961        let signature = alloy_primitives::hex::encode(signature.as_bytes());
962        Ok(format!("0x{signature}"))
963    }
964
965    /// The sign method calculates an Ethereum specific signature
966    ///
967    /// Handler for ETH RPC call: `eth_sign`
968    pub async fn sign(&self, address: Address, content: impl AsRef<[u8]>) -> Result<String> {
969        node_info!("eth_sign");
970        let signer = self.get_signer(address).ok_or(BlockchainError::NoSignerAvailable)?;
971        let signature =
972            alloy_primitives::hex::encode(signer.sign(address, content.as_ref()).await?.as_bytes());
973        Ok(format!("0x{signature}"))
974    }
975
976    /// Returns transaction at given block hash and index.
977    ///
978    /// Handler for ETH RPC call: `eth_getTransactionByBlockHashAndIndex`
979    pub async fn transaction_by_block_hash_and_index(
980        &self,
981        hash: B256,
982        index: Index,
983    ) -> Result<Option<AnyRpcTransaction>> {
984        node_info!("eth_getTransactionByBlockHashAndIndex");
985        self.backend.transaction_by_block_hash_and_index(hash, index).await
986    }
987
988    /// Returns transaction by given block number and index.
989    ///
990    /// Handler for ETH RPC call: `eth_getTransactionByBlockNumberAndIndex`
991    pub async fn transaction_by_block_number_and_index(
992        &self,
993        block: BlockNumber,
994        idx: Index,
995    ) -> Result<Option<AnyRpcTransaction>> {
996        node_info!("eth_getTransactionByBlockNumberAndIndex");
997        self.backend.transaction_by_block_number_and_index(block, idx).await
998    }
999
1000    /// Returns an uncles at given block and index.
1001    ///
1002    /// Handler for ETH RPC call: `eth_getUncleByBlockHashAndIndex`
1003    pub async fn uncle_by_block_hash_and_index(
1004        &self,
1005        block_hash: B256,
1006        idx: Index,
1007    ) -> Result<Option<AnyRpcBlock>> {
1008        node_info!("eth_getUncleByBlockHashAndIndex");
1009        let number =
1010            self.backend.ensure_block_number(Some(BlockId::Hash(block_hash.into()))).await?;
1011        if let Some(fork) = self.get_fork()
1012            && fork.predates_fork_inclusive(number)
1013        {
1014            return Ok(fork.uncle_by_block_hash_and_index(block_hash, idx.into()).await?);
1015        }
1016        // It's impossible to have uncles outside of fork mode
1017        Ok(None)
1018    }
1019
1020    /// Returns an uncles at given block and index.
1021    ///
1022    /// Handler for ETH RPC call: `eth_getUncleByBlockNumberAndIndex`
1023    pub async fn uncle_by_block_number_and_index(
1024        &self,
1025        block_number: BlockNumber,
1026        idx: Index,
1027    ) -> Result<Option<AnyRpcBlock>> {
1028        node_info!("eth_getUncleByBlockNumberAndIndex");
1029        let number = self.backend.ensure_block_number(Some(BlockId::Number(block_number))).await?;
1030        if let Some(fork) = self.get_fork()
1031            && fork.predates_fork_inclusive(number)
1032        {
1033            return Ok(fork.uncle_by_block_number_and_index(number, idx.into()).await?);
1034        }
1035        // It's impossible to have uncles outside of fork mode
1036        Ok(None)
1037    }
1038
1039    /// Returns the hash of the current block, the seedHash, and the boundary condition to be met.
1040    ///
1041    /// Handler for ETH RPC call: `eth_getWork`
1042    pub fn work(&self) -> Result<Work> {
1043        node_info!("eth_getWork");
1044        Err(BlockchainError::RpcUnimplemented)
1045    }
1046
1047    /// Returns the sync status, always be fails.
1048    ///
1049    /// Handler for ETH RPC call: `eth_syncing`
1050    pub fn syncing(&self) -> Result<bool> {
1051        node_info!("eth_syncing");
1052        Ok(false)
1053    }
1054
1055    /// Returns the current configuration of the chain.
1056    /// This is useful for finding out what precompiles and system contracts are available.
1057    ///
1058    /// Note: the activation timestamp is always 0 as the configuration is set at genesis.
1059    /// Note: the `fork_id` is always `0x00000000` as this node does not participate in any forking
1060    /// on the network.
1061    /// Note: the `next` and `last` fields are always `null` as this node does not participate in
1062    /// any forking on the network.
1063    ///
1064    /// Handler for ETH RPC call: `eth_config`
1065    pub fn config(&self) -> Result<EthConfig> {
1066        node_info!("eth_config");
1067        Ok(EthConfig {
1068            current: EthForkConfig {
1069                activation_time: 0,
1070                blob_schedule: self.backend.blob_params(),
1071                chain_id: self.backend.chain_id().to::<u64>(),
1072                fork_id: Bytes::from_static(&[0; 4]),
1073                precompiles: self.backend.precompiles(),
1074                system_contracts: self.backend.system_contracts(),
1075            },
1076            next: None,
1077            last: None,
1078        })
1079    }
1080
1081    /// Used for submitting a proof-of-work solution.
1082    ///
1083    /// Handler for ETH RPC call: `eth_submitWork`
1084    pub fn submit_work(&self, _: B64, _: B256, _: B256) -> Result<bool> {
1085        node_info!("eth_submitWork");
1086        Err(BlockchainError::RpcUnimplemented)
1087    }
1088
1089    /// Used for submitting mining hashrate.
1090    ///
1091    /// Handler for ETH RPC call: `eth_submitHashrate`
1092    pub fn submit_hashrate(&self, _: U256, _: B256) -> Result<bool> {
1093        node_info!("eth_submitHashrate");
1094        Err(BlockchainError::RpcUnimplemented)
1095    }
1096
1097    /// Introduced in EIP-1559 for getting information on the appropriate priority fee to use.
1098    ///
1099    /// Handler for ETH RPC call: `eth_feeHistory`
1100    pub async fn fee_history(
1101        &self,
1102        block_count: U256,
1103        newest_block: BlockNumber,
1104        reward_percentiles: Vec<f64>,
1105    ) -> Result<FeeHistory> {
1106        node_info!("eth_feeHistory");
1107        // max number of blocks in the requested range
1108
1109        let number = self.backend.convert_block_number(Some(newest_block));
1110
1111        // check if the number predates the fork, if in fork mode
1112        if let Some(fork) = self.get_fork() {
1113            // if we're still at the forked block we don't have any history and can't compute it
1114            // efficiently, instead we fetch it from the fork
1115            if fork.predates_fork_inclusive(number) {
1116                return fork
1117                    .fee_history(block_count.to(), BlockNumber::Number(number), &reward_percentiles)
1118                    .await
1119                    .map_err(BlockchainError::AlloyForkProvider);
1120            }
1121        }
1122
1123        const MAX_BLOCK_COUNT: u64 = 1024u64;
1124        let block_count = block_count.saturating_to::<u64>().min(MAX_BLOCK_COUNT);
1125
1126        // highest and lowest block num in the requested range
1127        let highest = number;
1128        let lowest = highest.saturating_sub(block_count.saturating_sub(1));
1129
1130        // only support ranges that are in cache range
1131        if lowest < self.backend.best_number().saturating_sub(self.fee_history_limit) {
1132            return Err(FeeHistoryError::InvalidBlockRange.into());
1133        }
1134
1135        let mut response = FeeHistory {
1136            oldest_block: lowest,
1137            base_fee_per_gas: Vec::new(),
1138            gas_used_ratio: Vec::new(),
1139            reward: Some(Default::default()),
1140            base_fee_per_blob_gas: Default::default(),
1141            blob_gas_used_ratio: Default::default(),
1142        };
1143        let mut rewards = Vec::new();
1144
1145        {
1146            let fee_history = self.fee_history_cache.lock();
1147
1148            // iter over the requested block range
1149            for n in lowest..=highest {
1150                // <https://eips.ethereum.org/EIPS/eip-1559>
1151                if let Some(block) = fee_history.get(&n) {
1152                    response.base_fee_per_gas.push(block.base_fee);
1153                    response.base_fee_per_blob_gas.push(block.base_fee_per_blob_gas.unwrap_or(0));
1154                    response.blob_gas_used_ratio.push(block.blob_gas_used_ratio);
1155                    response.gas_used_ratio.push(block.gas_used_ratio);
1156
1157                    // requested percentiles
1158                    if !reward_percentiles.is_empty() {
1159                        let mut block_rewards = Vec::new();
1160                        let resolution_per_percentile: f64 = 2.0;
1161                        for p in &reward_percentiles {
1162                            let p = p.clamp(0.0, 100.0);
1163                            let index = ((p.round() / 2f64) * 2f64) * resolution_per_percentile;
1164                            let reward = block.rewards.get(index as usize).map_or(0, |r| *r);
1165                            block_rewards.push(reward);
1166                        }
1167                        rewards.push(block_rewards);
1168                    }
1169                }
1170            }
1171        }
1172
1173        response.reward = Some(rewards);
1174
1175        // add the next block's base fee to the response
1176        // The spec states that `base_fee_per_gas` "[..] includes the next block after the
1177        // newest of the returned range, because this value can be derived from the
1178        // newest block"
1179        response.base_fee_per_gas.push(self.backend.fees().base_fee() as u128);
1180
1181        // Same goes for the `base_fee_per_blob_gas`:
1182        // > [..] includes the next block after the newest of the returned range, because this
1183        // > value can be derived from the newest block.
1184        response.base_fee_per_blob_gas.push(self.backend.fees().base_fee_per_blob_gas());
1185
1186        Ok(response)
1187    }
1188
1189    /// Introduced in EIP-1159, a Geth-specific and simplified priority fee oracle.
1190    /// Leverages the already existing fee history cache.
1191    ///
1192    /// Returns a suggestion for a gas tip cap for dynamic fee transactions.
1193    ///
1194    /// Handler for ETH RPC call: `eth_maxPriorityFeePerGas`
1195    pub fn max_priority_fee_per_gas(&self) -> Result<U256> {
1196        node_info!("eth_maxPriorityFeePerGas");
1197        Ok(U256::from(self.lowest_suggestion_tip()))
1198    }
1199
1200    /// Returns code by its hash
1201    ///
1202    /// Handler for RPC call: `debug_codeByHash`
1203    pub async fn debug_code_by_hash(
1204        &self,
1205        hash: B256,
1206        block_id: Option<BlockId>,
1207    ) -> Result<Option<Bytes>> {
1208        node_info!("debug_codeByHash");
1209        self.backend.debug_code_by_hash(hash, block_id).await
1210    }
1211
1212    /// Returns the value associated with a key from the database
1213    /// Only supports bytecode lookups.
1214    ///
1215    /// Handler for RPC call: `debug_dbGet`
1216    pub async fn debug_db_get(&self, key: String) -> Result<Option<Bytes>> {
1217        node_info!("debug_dbGet");
1218        self.backend.debug_db_get(key).await
1219    }
1220
1221    /// Returns traces for the transaction hash via parity's tracing endpoint
1222    ///
1223    /// Handler for RPC call: `trace_transaction`
1224    pub async fn trace_transaction(&self, tx_hash: B256) -> Result<Vec<LocalizedTransactionTrace>> {
1225        node_info!("trace_transaction");
1226        self.backend.trace_transaction(tx_hash).await
1227    }
1228
1229    /// Returns traces for the transaction hash via parity's tracing endpoint
1230    ///
1231    /// Handler for RPC call: `trace_block`
1232    pub async fn trace_block(&self, block: BlockNumber) -> Result<Vec<LocalizedTransactionTrace>> {
1233        node_info!("trace_block");
1234        self.backend.trace_block(block).await
1235    }
1236
1237    /// Returns filtered traces over blocks
1238    ///
1239    /// Handler for RPC call: `trace_filter`
1240    pub async fn trace_filter(
1241        &self,
1242        filter: TraceFilter,
1243    ) -> Result<Vec<LocalizedTransactionTrace>> {
1244        node_info!("trace_filter");
1245        self.backend.trace_filter(filter).await
1246    }
1247
1248    /// Replays all transactions in a block returning the requested traces for each transaction
1249    ///
1250    /// Handler for RPC call: `trace_replayBlockTransactions`
1251    pub async fn trace_replay_block_transactions(
1252        &self,
1253        block: BlockNumber,
1254        trace_types: HashSet<TraceType>,
1255    ) -> Result<Vec<TraceResultsWithTransactionHash>> {
1256        node_info!("trace_replayBlockTransactions");
1257        self.backend.trace_replay_block_transactions(block, trace_types).await
1258    }
1259}
1260
1261impl<N: Network<ReceiptEnvelope = FoundryReceiptEnvelope>> EthApi<N> {
1262    /// Returns the current state
1263    pub async fn serialized_state(
1264        &self,
1265        preserve_historical_states: bool,
1266    ) -> Result<SerializableState> {
1267        self.backend.serialized_state(preserve_historical_states).await
1268    }
1269}
1270
1271// == impl EthApi anvil endpoints ==
1272
1273impl EthApi<FoundryNetwork> {
1274    /// Create a buffer that represents all state on the chain, which can be loaded to separate
1275    /// process by calling `anvil_loadState`
1276    ///
1277    /// Handler for RPC call: `anvil_dumpState`
1278    pub async fn anvil_dump_state(
1279        &self,
1280        preserve_historical_states: Option<bool>,
1281    ) -> Result<Bytes> {
1282        node_info!("anvil_dumpState");
1283        self.backend.dump_state(preserve_historical_states.unwrap_or(false)).await
1284    }
1285
1286    /// Append chain state buffer to current chain. Will overwrite any conflicting addresses or
1287    /// storage.
1288    ///
1289    /// Handler for RPC call: `anvil_loadState`
1290    pub async fn anvil_load_state(&self, buf: Bytes) -> Result<bool> {
1291        node_info!("anvil_loadState");
1292        self.backend.load_state_bytes(buf).await
1293    }
1294
1295    async fn block_request(
1296        &self,
1297        block_number: Option<BlockId>,
1298    ) -> Result<BlockRequest<FoundryTxEnvelope>> {
1299        let block_request = match block_number {
1300            Some(BlockId::Number(BlockNumber::Pending)) => {
1301                let pending_txs = self.pool.ready_transactions().collect();
1302                BlockRequest::Pending(pending_txs)
1303            }
1304            _ => {
1305                let number = self.backend.ensure_block_number(block_number).await?;
1306                BlockRequest::Number(number)
1307            }
1308        };
1309        Ok(block_request)
1310    }
1311
1312    /// Increases the balance of an account.
1313    ///
1314    /// Handler for RPC call: `anvil_addBalance`
1315    pub async fn anvil_add_balance(&self, address: Address, balance: U256) -> Result<()> {
1316        node_info!("anvil_addBalance");
1317        let current_balance = self.backend.get_balance(address, None).await?;
1318        self.backend.set_balance(address, current_balance.saturating_add(balance)).await?;
1319        Ok(())
1320    }
1321
1322    /// Rollback the chain to a specific depth.
1323    ///
1324    /// e.g depth = 3
1325    ///     A  -> B  -> C  -> D  -> E
1326    ///     A  -> B
1327    ///
1328    /// Depth specifies the height to rollback the chain back to. Depth must not exceed the current
1329    /// chain height, i.e. can't rollback past the genesis block.
1330    ///
1331    /// Handler for RPC call: `anvil_rollback`
1332    pub async fn anvil_rollback(&self, depth: Option<u64>) -> Result<()> {
1333        node_info!("anvil_rollback");
1334        let depth = depth.unwrap_or(1);
1335
1336        // Check reorg depth doesn't exceed current chain height
1337        let current_height = self.backend.best_number();
1338        let common_height = current_height.checked_sub(depth).ok_or(BlockchainError::RpcError(
1339            RpcError::invalid_params(format!(
1340                "Rollback depth must not exceed current chain height: current height {current_height}, depth {depth}"
1341            )),
1342        ))?;
1343
1344        // Get the common ancestor block
1345        let common_block =
1346            self.backend.get_block(common_height).ok_or(BlockchainError::BlockNotFound)?;
1347
1348        self.backend.rollback(common_block).await?;
1349        Ok(())
1350    }
1351
1352    /// Estimates the gas usage of the `request` with the state.
1353    ///
1354    /// This will execute the transaction request and find the best gas limit via binary search.
1355    fn do_estimate_gas_with_state(
1356        &self,
1357        mut request: WithOtherFields<TransactionRequest>,
1358        state: &dyn DatabaseRef,
1359        block_env: BlockEnv,
1360    ) -> Result<u128> {
1361        let fees = FeeDetails::new(
1362            request.gas_price,
1363            request.max_fee_per_gas,
1364            request.max_priority_fee_per_gas,
1365            request.max_fee_per_blob_gas,
1366        )?
1367        .or_zero_fees();
1368
1369        // get the highest possible gas limit, either the request's set value or the currently
1370        // configured gas limit
1371        let mut highest_gas_limit = request.gas.map_or(block_env.gas_limit.into(), |g| g as u128);
1372
1373        // Tempo AA transactions pay fees in ERC-20 tokens, not ETH. Only treat requests as
1374        // Tempo AA in Tempo mode, otherwise `feeToken` should not bypass ETH funds checks.
1375        let is_tempo_aa_tx =
1376            self.backend.is_tempo() && request.other.get("feeToken").is_some_and(|v| !v.is_null());
1377
1378        let gas_price = fees.gas_price.unwrap_or_default();
1379        // Check transfer value before any fast path, and cap gas limit by sender balance when the
1380        // request has a non-zero gas price. Only enforce this for explicit senders: calls without
1381        // `from` historically estimate against the default caller and must not be capped by the
1382        // zero address balance.
1383        if !is_tempo_aa_tx && let Some(from) = request.from {
1384            let mut available_funds = self.backend.get_balance_with_state(state, from)?;
1385            if let Some(value) = request.value {
1386                if value > available_funds {
1387                    return Err(InvalidTransactionError::InsufficientFunds.into());
1388                }
1389                // safe: value <= available_funds
1390                available_funds -= value;
1391            }
1392            if gas_price > 0 {
1393                // amount of gas the sender can afford with the `gas_price`
1394                let allowance =
1395                    available_funds.checked_div(U256::from(gas_price)).unwrap_or_default();
1396                highest_gas_limit = std::cmp::min(highest_gas_limit, allowance.saturating_to());
1397            }
1398        }
1399
1400        // If the request is a simple native token transfer we can optimize
1401        // We assume it's a transfer if we have no input data.
1402        // Skip this optimization for Tempo mode since native ETH transfers are not allowed
1403        // and Tempo AA transactions have higher intrinsic gas costs (~46k).
1404        if !self.backend.is_tempo() {
1405            let to = request.to.as_ref().and_then(TxKind::to);
1406
1407            // check certain fields to see if the request could be a simple transfer
1408            let maybe_transfer = (request.input.input().is_none()
1409                || request.input.input().is_some_and(|data| data.is_empty()))
1410                && request.authorization_list.is_none()
1411                && request.access_list.is_none()
1412                && request.blob_versioned_hashes.is_none();
1413
1414            if maybe_transfer
1415                && highest_gas_limit >= MIN_TRANSACTION_GAS
1416                && let Some(to) = to
1417                && let Ok(target_code) = self.backend.get_code_with_state(&state, *to)
1418                && target_code.as_ref().is_empty()
1419            {
1420                return Ok(MIN_TRANSACTION_GAS);
1421            }
1422        }
1423
1424        let mut call_to_estimate = request.clone();
1425        call_to_estimate.gas = Some(highest_gas_limit as u64);
1426
1427        // execute the call without writing to db
1428        let ethres =
1429            self.backend.call_with_state(&state, call_to_estimate, fees.clone(), block_env.clone());
1430
1431        let gas_used = match ethres.try_into()? {
1432            GasEstimationCallResult::Success(gas) => Ok(gas),
1433            GasEstimationCallResult::OutOfGas => {
1434                Err(InvalidTransactionError::BasicOutOfGas(highest_gas_limit).into())
1435            }
1436            GasEstimationCallResult::Revert(output) => {
1437                Err(InvalidTransactionError::Revert(output).into())
1438            }
1439            GasEstimationCallResult::EvmError(err) => {
1440                warn!(target: "node", "estimation failed due to {:?}", err);
1441                Err(BlockchainError::EvmError(err))
1442            }
1443        }?;
1444
1445        // at this point we know the call succeeded but want to find the _best_ (lowest) gas the
1446        // transaction succeeds with. we find this by doing a binary search over the
1447        // possible range NOTE: this is the gas the transaction used, which is less than the
1448        // transaction requires to succeed
1449
1450        // Get the starting lowest gas needed depending on the transaction kind.
1451        let mut lowest_gas_limit = determine_base_gas_by_kind(&request);
1452
1453        // pick a point that's close to the estimated gas
1454        let mut mid_gas_limit =
1455            std::cmp::min(gas_used * 3, (highest_gas_limit + lowest_gas_limit) / 2);
1456
1457        // Binary search for the ideal gas limit
1458        while (highest_gas_limit - lowest_gas_limit) > 1 {
1459            request.gas = Some(mid_gas_limit as u64);
1460            let ethres = self.backend.call_with_state(
1461                &state,
1462                request.clone(),
1463                fees.clone(),
1464                block_env.clone(),
1465            );
1466
1467            match ethres.try_into()? {
1468                GasEstimationCallResult::Success(_) => {
1469                    // If the transaction succeeded, we can set a ceiling for the highest gas limit
1470                    // at the current midpoint, as spending any more gas would
1471                    // make no sense (as the TX would still succeed).
1472                    highest_gas_limit = mid_gas_limit;
1473                }
1474                GasEstimationCallResult::OutOfGas
1475                | GasEstimationCallResult::Revert(_)
1476                | GasEstimationCallResult::EvmError(_) => {
1477                    // If the transaction failed, we can set a floor for the lowest gas limit at the
1478                    // current midpoint, as spending any less gas would make no
1479                    // sense (as the TX would still revert due to lack of gas).
1480                    //
1481                    // We don't care about the reason here, as we known that transaction is correct
1482                    // as it succeeded earlier
1483                    lowest_gas_limit = mid_gas_limit;
1484                }
1485            };
1486            // new midpoint
1487            mid_gas_limit = (highest_gas_limit + lowest_gas_limit) / 2;
1488        }
1489
1490        trace!(target : "node", "Estimated Gas for call {:?}", highest_gas_limit);
1491
1492        Ok(highest_gas_limit)
1493    }
1494
1495    /// Executes the [EthRequest] and returns an RPC [ResponseResult].
1496    #[allow(clippy::large_stack_frames)]
1497    pub async fn execute(&self, request: EthRequest) -> ResponseResult {
1498        trace!(target: "rpc::api", "executing eth request");
1499        let response = match request.clone() {
1500            EthRequest::EthProtocolVersion(()) => self.protocol_version().to_rpc_result(),
1501            EthRequest::Web3ClientVersion(()) => self.client_version().to_rpc_result(),
1502            EthRequest::Web3Sha3(content) => self.sha3(content).to_rpc_result(),
1503            EthRequest::EthGetAccount(addr, block) => {
1504                self.get_account(addr, block).await.to_rpc_result()
1505            }
1506            EthRequest::EthGetAccountInfo(addr, block) => {
1507                self.get_account_info(addr, block).await.to_rpc_result()
1508            }
1509            EthRequest::EthGetBalance(addr, block) => {
1510                self.balance(addr, block).await.to_rpc_result()
1511            }
1512            EthRequest::EthGetTransactionByHash(hash) => {
1513                self.transaction_by_hash(hash).await.to_rpc_result()
1514            }
1515            EthRequest::EthSendTransaction(request) => {
1516                self.send_transaction(*request).await.to_rpc_result()
1517            }
1518            EthRequest::EthSendTransactionSync(request) => {
1519                self.send_transaction_sync(*request).await.to_rpc_result()
1520            }
1521            EthRequest::EthChainId(_) => self.eth_chain_id().to_rpc_result(),
1522            EthRequest::EthNetworkId(_) => self.network_id().to_rpc_result(),
1523            EthRequest::NetListening(_) => self.net_listening().to_rpc_result(),
1524            EthRequest::EthHashrate(()) => self.hashrate().to_rpc_result(),
1525            EthRequest::EthGasPrice(_) => self.eth_gas_price().to_rpc_result(),
1526            EthRequest::EthMaxPriorityFeePerGas(_) => {
1527                self.gas_max_priority_fee_per_gas().to_rpc_result()
1528            }
1529            EthRequest::EthBlobBaseFee(_) => self.blob_base_fee().to_rpc_result(),
1530            EthRequest::EthAccounts(_) => self.accounts().to_rpc_result(),
1531            EthRequest::EthBlockNumber(_) => self.block_number().to_rpc_result(),
1532            EthRequest::EthCoinbase(()) => self.author().to_rpc_result(),
1533            EthRequest::EthGetStorageAt(addr, slot, block) => {
1534                self.storage_at(addr, slot, block).await.to_rpc_result()
1535            }
1536            EthRequest::EthGetStorageValues(requests, block) => {
1537                self.storage_values(requests, block).await.to_rpc_result()
1538            }
1539            EthRequest::EthGetBlockByHash(hash, full) => {
1540                if full {
1541                    self.block_by_hash_full(hash).await.to_rpc_result()
1542                } else {
1543                    self.block_by_hash(hash).await.to_rpc_result()
1544                }
1545            }
1546            EthRequest::EthGetBlockByNumber(num, full) => {
1547                if full {
1548                    self.block_by_number_full(num).await.to_rpc_result()
1549                } else {
1550                    self.block_by_number(num).await.to_rpc_result()
1551                }
1552            }
1553            EthRequest::EthGetTransactionCount(addr, block) => {
1554                self.transaction_count(addr, block).await.to_rpc_result()
1555            }
1556            EthRequest::EthGetTransactionCountByHash(hash) => {
1557                self.block_transaction_count_by_hash(hash).await.to_rpc_result()
1558            }
1559            EthRequest::EthGetTransactionCountByNumber(num) => {
1560                self.block_transaction_count_by_number(num).await.to_rpc_result()
1561            }
1562            EthRequest::EthGetUnclesCountByHash(hash) => {
1563                self.block_uncles_count_by_hash(hash).await.to_rpc_result()
1564            }
1565            EthRequest::EthGetUnclesCountByNumber(num) => {
1566                self.block_uncles_count_by_number(num).await.to_rpc_result()
1567            }
1568            EthRequest::EthGetCodeAt(addr, block) => {
1569                self.get_code(addr, block).await.to_rpc_result()
1570            }
1571            EthRequest::EthGetProof(addr, keys, block) => {
1572                self.get_proof(addr, keys, block).await.to_rpc_result()
1573            }
1574            EthRequest::EthSign(addr, content) => self.sign(addr, content).await.to_rpc_result(),
1575            EthRequest::PersonalSign(content, addr) => {
1576                self.sign(addr, content).await.to_rpc_result()
1577            }
1578            EthRequest::EthSignTransaction(request) => {
1579                self.sign_transaction(*request).await.to_rpc_result()
1580            }
1581            EthRequest::EthSignTypedData(addr, data) => {
1582                self.sign_typed_data(addr, data).await.to_rpc_result()
1583            }
1584            EthRequest::EthSignTypedDataV3(addr, data) => {
1585                self.sign_typed_data_v3(addr, data).await.to_rpc_result()
1586            }
1587            EthRequest::EthSignTypedDataV4(addr, data) => {
1588                self.sign_typed_data_v4(addr, &data).await.to_rpc_result()
1589            }
1590            EthRequest::EthSendRawTransaction(tx) => {
1591                self.send_raw_transaction(tx).await.to_rpc_result()
1592            }
1593            EthRequest::EthSendRawTransactionSync(tx) => {
1594                self.send_raw_transaction_sync(tx).await.to_rpc_result()
1595            }
1596            EthRequest::AnvilClassifyTransaction(tx) => {
1597                self.anvil_classify_transaction(tx).to_rpc_result()
1598            }
1599            EthRequest::EthCall(call, block, state_override, block_overrides) => self
1600                .call(call, block, EvmOverrides::new(state_override, block_overrides))
1601                .await
1602                .to_rpc_result(),
1603            EthRequest::EthSimulateV1(simulation, block) => {
1604                self.simulate_v1(simulation, block).await.to_rpc_result()
1605            }
1606            EthRequest::EthCreateAccessList(call, block) => {
1607                self.create_access_list(call, block).await.to_rpc_result()
1608            }
1609            EthRequest::EthEstimateGas(call, block, state_override, block_overrides) => self
1610                .estimate_gas(call, block, EvmOverrides::new(state_override, block_overrides))
1611                .await
1612                .to_rpc_result(),
1613            EthRequest::EthFillTransaction(request) => {
1614                self.fill_transaction(request).await.to_rpc_result()
1615            }
1616            EthRequest::EthGetRawTransactionByHash(hash) => {
1617                self.raw_transaction(hash).await.to_rpc_result()
1618            }
1619            EthRequest::GetBlobByHash(hash) => {
1620                self.anvil_get_blob_by_versioned_hash(hash).to_rpc_result()
1621            }
1622            EthRequest::GetBlobByTransactionHash(hash) => {
1623                self.anvil_get_blob_by_tx_hash(hash).to_rpc_result()
1624            }
1625            EthRequest::GetGenesisTime(()) => self.anvil_get_genesis_time().to_rpc_result(),
1626            EthRequest::EthGetRawTransactionByBlockHashAndIndex(hash, index) => {
1627                self.raw_transaction_by_block_hash_and_index(hash, index).await.to_rpc_result()
1628            }
1629            EthRequest::EthGetRawTransactionByBlockNumberAndIndex(num, index) => {
1630                self.raw_transaction_by_block_number_and_index(num, index).await.to_rpc_result()
1631            }
1632            EthRequest::EthGetTransactionByBlockHashAndIndex(hash, index) => {
1633                self.transaction_by_block_hash_and_index(hash, index).await.to_rpc_result()
1634            }
1635            EthRequest::EthGetTransactionByBlockNumberAndIndex(num, index) => {
1636                self.transaction_by_block_number_and_index(num, index).await.to_rpc_result()
1637            }
1638            EthRequest::EthGetTransactionReceipt(tx) => {
1639                self.transaction_receipt(tx).await.to_rpc_result()
1640            }
1641            EthRequest::EthGetBlockReceipts(number) => {
1642                self.block_receipts(number).await.to_rpc_result()
1643            }
1644            EthRequest::EthGetUncleByBlockHashAndIndex(hash, index) => {
1645                self.uncle_by_block_hash_and_index(hash, index).await.to_rpc_result()
1646            }
1647            EthRequest::EthGetUncleByBlockNumberAndIndex(num, index) => {
1648                self.uncle_by_block_number_and_index(num, index).await.to_rpc_result()
1649            }
1650            EthRequest::EthGetLogs(filter) => self.logs(filter).await.to_rpc_result(),
1651            EthRequest::EthGetWork(_) => self.work().to_rpc_result(),
1652            EthRequest::EthSyncing(_) => self.syncing().to_rpc_result(),
1653            EthRequest::EthConfig(_) => self.config().to_rpc_result(),
1654            EthRequest::EthSubmitWork(nonce, pow, digest) => {
1655                self.submit_work(nonce, pow, digest).to_rpc_result()
1656            }
1657            EthRequest::EthSubmitHashRate(rate, id) => {
1658                self.submit_hashrate(rate, id).to_rpc_result()
1659            }
1660            EthRequest::EthFeeHistory(count, newest, reward_percentiles) => {
1661                self.fee_history(count, newest, reward_percentiles).await.to_rpc_result()
1662            }
1663            // non eth-standard rpc calls
1664            EthRequest::DebugGetRawTransaction(hash) => {
1665                self.raw_transaction(hash).await.to_rpc_result()
1666            }
1667            // non eth-standard rpc calls
1668            EthRequest::DebugTraceTransaction(tx, opts) => {
1669                self.debug_trace_transaction(tx, opts).await.to_rpc_result()
1670            }
1671            // non eth-standard rpc calls
1672            EthRequest::DebugTraceCall(tx, block, opts) => {
1673                self.debug_trace_call(tx, block, opts).await.to_rpc_result()
1674            }
1675            EthRequest::DebugCodeByHash(hash, block) => {
1676                self.debug_code_by_hash(hash, block).await.to_rpc_result()
1677            }
1678            EthRequest::DebugDbGet(key) => self.debug_db_get(key).await.to_rpc_result(),
1679            EthRequest::DebugTraceBlockByHash(block_hash, opts) => {
1680                self.debug_trace_block_by_hash(block_hash, opts).await.to_rpc_result()
1681            }
1682            EthRequest::DebugTraceBlockByNumber(block_number, opts) => {
1683                self.debug_trace_block_by_number(block_number, opts).await.to_rpc_result()
1684            }
1685            EthRequest::TraceTransaction(tx) => self.trace_transaction(tx).await.to_rpc_result(),
1686            EthRequest::TraceBlock(block) => self.trace_block(block).await.to_rpc_result(),
1687            EthRequest::TraceFilter(filter) => self.trace_filter(filter).await.to_rpc_result(),
1688            EthRequest::TraceReplayBlockTransactions(block, trace_types) => {
1689                self.trace_replay_block_transactions(block, trace_types).await.to_rpc_result()
1690            }
1691            EthRequest::ImpersonateAccount(addr) => {
1692                self.anvil_impersonate_account(addr).await.to_rpc_result()
1693            }
1694            EthRequest::StopImpersonatingAccount(addr) => {
1695                self.anvil_stop_impersonating_account(addr).await.to_rpc_result()
1696            }
1697            EthRequest::AutoImpersonateAccount(enable) => {
1698                self.anvil_auto_impersonate_account(enable).await.to_rpc_result()
1699            }
1700            EthRequest::ImpersonateSignature(signature, address) => {
1701                self.anvil_impersonate_signature(signature, address).await.to_rpc_result()
1702            }
1703            EthRequest::GetAutoMine(()) => self.anvil_get_auto_mine().to_rpc_result(),
1704            EthRequest::Mine(blocks, interval) => {
1705                self.anvil_mine(blocks, interval).await.to_rpc_result()
1706            }
1707            EthRequest::SetAutomine(enabled) => {
1708                self.anvil_set_auto_mine(enabled).await.to_rpc_result()
1709            }
1710            EthRequest::SetIntervalMining(interval) => {
1711                self.anvil_set_interval_mining(interval).to_rpc_result()
1712            }
1713            EthRequest::GetIntervalMining(()) => self.anvil_get_interval_mining().to_rpc_result(),
1714            EthRequest::DropTransaction(tx) => {
1715                self.anvil_drop_transaction(tx).await.to_rpc_result()
1716            }
1717            EthRequest::DropAllTransactions() => {
1718                self.anvil_drop_all_transactions().await.to_rpc_result()
1719            }
1720            EthRequest::Reset(fork) => {
1721                self.anvil_reset(fork.and_then(|p| p.params)).await.to_rpc_result()
1722            }
1723            EthRequest::SetBalance(addr, val) => {
1724                self.anvil_set_balance(addr, val).await.to_rpc_result()
1725            }
1726            EthRequest::AddBalance(addr, val) => {
1727                self.anvil_add_balance(addr, val).await.to_rpc_result()
1728            }
1729            EthRequest::DealERC20(addr, token_addr, val) => {
1730                self.anvil_deal_erc20(addr, token_addr, val).await.to_rpc_result()
1731            }
1732            EthRequest::SetERC20Allowance(owner, spender, token_addr, val) => self
1733                .anvil_set_erc20_allowance(owner, spender, token_addr, val)
1734                .await
1735                .to_rpc_result(),
1736            EthRequest::SetCode(addr, code) => {
1737                self.anvil_set_code(addr, code).await.to_rpc_result()
1738            }
1739            EthRequest::SetNonce(addr, nonce) => {
1740                self.anvil_set_nonce(addr, nonce).await.to_rpc_result()
1741            }
1742            EthRequest::SetStorageAt(addr, slot, val) => {
1743                self.anvil_set_storage_at(addr, slot, val).await.to_rpc_result()
1744            }
1745            EthRequest::SetCoinbase(addr) => self.anvil_set_coinbase(addr).await.to_rpc_result(),
1746            EthRequest::SetChainId(id) => self.anvil_set_chain_id(id).await.to_rpc_result(),
1747            EthRequest::SetLogging(log) => self.anvil_set_logging(log).await.to_rpc_result(),
1748            EthRequest::SetMinGasPrice(gas) => {
1749                self.anvil_set_min_gas_price(gas).await.to_rpc_result()
1750            }
1751            EthRequest::SetNextBlockBaseFeePerGas(gas) => {
1752                self.anvil_set_next_block_base_fee_per_gas(gas).await.to_rpc_result()
1753            }
1754            EthRequest::DumpState(preserve_historical_states) => self
1755                .anvil_dump_state(preserve_historical_states.and_then(|s| s.params))
1756                .await
1757                .to_rpc_result(),
1758            EthRequest::LoadState(buf) => self.anvil_load_state(buf).await.to_rpc_result(),
1759            EthRequest::NodeInfo(_) => self.anvil_node_info().await.to_rpc_result(),
1760            EthRequest::AnvilMetadata(_) => self.anvil_metadata().await.to_rpc_result(),
1761            EthRequest::EvmSnapshot(_) => self.evm_snapshot().await.to_rpc_result(),
1762            EthRequest::EvmRevert(id) => self.evm_revert(id).await.to_rpc_result(),
1763            EthRequest::EvmIncreaseTime(time) => self.evm_increase_time(time).await.to_rpc_result(),
1764            EthRequest::EvmSetNextBlockTimeStamp(time) => {
1765                if time >= U256::from(u64::MAX) {
1766                    return ResponseResult::Error(RpcError::invalid_params(
1767                        "The timestamp is too big",
1768                    ));
1769                }
1770                let time = time.to::<u64>();
1771                self.evm_set_next_block_timestamp(time).to_rpc_result()
1772            }
1773            EthRequest::EvmSetTime(timestamp) => {
1774                if timestamp >= U256::from(u64::MAX) {
1775                    return ResponseResult::Error(RpcError::invalid_params(
1776                        "The timestamp is too big",
1777                    ));
1778                }
1779                // evm_setTime accepts either seconds or milliseconds for Ganache compatibility.
1780                // Timestamps above 1e12 are interpreted as milliseconds and converted to
1781                // seconds; below that threshold they are treated as seconds directly.
1782                let raw = timestamp.to::<u64>();
1783                let time = if raw > 1_000_000_000_000 {
1784                    Duration::from_millis(raw).as_secs()
1785                } else {
1786                    raw
1787                };
1788                self.evm_set_time(time).to_rpc_result()
1789            }
1790            EthRequest::EvmSetBlockGasLimit(gas_limit) => {
1791                self.evm_set_block_gas_limit(gas_limit).to_rpc_result()
1792            }
1793            EthRequest::EvmSetBlockTimeStampInterval(time) => {
1794                self.evm_set_block_timestamp_interval(time).to_rpc_result()
1795            }
1796            EthRequest::EvmRemoveBlockTimeStampInterval(()) => {
1797                self.evm_remove_block_timestamp_interval().to_rpc_result()
1798            }
1799            EthRequest::EvmMine(mine) => {
1800                self.evm_mine(mine.and_then(|p| p.params)).await.to_rpc_result()
1801            }
1802            EthRequest::EvmMineDetailed(mine) => {
1803                self.evm_mine_detailed(mine.and_then(|p| p.params)).await.to_rpc_result()
1804            }
1805            EthRequest::SetRpcUrl(url) => self.anvil_set_rpc_url(url).await.to_rpc_result(),
1806            EthRequest::EthSendUnsignedTransaction(tx) => {
1807                self.eth_send_unsigned_transaction(*tx).await.to_rpc_result()
1808            }
1809            EthRequest::EthNewFilter(filter) => self.new_filter(filter).await.to_rpc_result(),
1810            EthRequest::EthGetFilterChanges(id) => self.get_filter_changes(&id).await,
1811            EthRequest::EthNewBlockFilter(_) => self.new_block_filter().await.to_rpc_result(),
1812            EthRequest::EthNewPendingTransactionFilter(_) => {
1813                self.new_pending_transaction_filter().await.to_rpc_result()
1814            }
1815            EthRequest::EthGetFilterLogs(id) => self.get_filter_logs(&id).await.to_rpc_result(),
1816            EthRequest::EthUninstallFilter(id) => self.uninstall_filter(&id).await.to_rpc_result(),
1817            EthRequest::TxPoolStatus(_) => self.txpool_status().await.to_rpc_result(),
1818            EthRequest::TxPoolInspect(_) => self.txpool_inspect().await.to_rpc_result(),
1819            EthRequest::TxPoolContent(_) => self.txpool_content().await.to_rpc_result(),
1820            EthRequest::ErigonGetHeaderByNumber(num) => {
1821                self.erigon_get_header_by_number(num).await.to_rpc_result()
1822            }
1823            EthRequest::OtsGetApiLevel(_) => self.ots_get_api_level().await.to_rpc_result(),
1824            EthRequest::OtsGetInternalOperations(hash) => {
1825                self.ots_get_internal_operations(hash).await.to_rpc_result()
1826            }
1827            EthRequest::OtsHasCode(addr, num) => self.ots_has_code(addr, num).await.to_rpc_result(),
1828            EthRequest::OtsTraceTransaction(hash) => {
1829                self.ots_trace_transaction(hash).await.to_rpc_result()
1830            }
1831            EthRequest::OtsGetTransactionError(hash) => {
1832                self.ots_get_transaction_error(hash).await.to_rpc_result()
1833            }
1834            EthRequest::OtsGetBlockDetails(num) => {
1835                self.ots_get_block_details(num).await.to_rpc_result()
1836            }
1837            EthRequest::OtsGetBlockDetailsByHash(hash) => {
1838                self.ots_get_block_details_by_hash(hash).await.to_rpc_result()
1839            }
1840            EthRequest::OtsGetBlockTransactions(num, page, page_size) => {
1841                self.ots_get_block_transactions(num, page, page_size).await.to_rpc_result()
1842            }
1843            EthRequest::OtsSearchTransactionsBefore(address, num, page_size) => {
1844                self.ots_search_transactions_before(address, num, page_size).await.to_rpc_result()
1845            }
1846            EthRequest::OtsSearchTransactionsAfter(address, num, page_size) => {
1847                self.ots_search_transactions_after(address, num, page_size).await.to_rpc_result()
1848            }
1849            EthRequest::OtsGetTransactionBySenderAndNonce(address, nonce) => {
1850                self.ots_get_transaction_by_sender_and_nonce(address, nonce).await.to_rpc_result()
1851            }
1852            EthRequest::EthGetTransactionBySenderAndNonce(sender, nonce) => {
1853                self.transaction_by_sender_and_nonce(sender, nonce).await.to_rpc_result()
1854            }
1855            EthRequest::OtsGetContractCreator(address) => {
1856                self.ots_get_contract_creator(address).await.to_rpc_result()
1857            }
1858            EthRequest::RemovePoolTransactions(address) => {
1859                self.anvil_remove_pool_transactions(address).await.to_rpc_result()
1860            }
1861            EthRequest::Reorg(reorg_options) => {
1862                self.anvil_reorg(reorg_options).await.to_rpc_result()
1863            }
1864            EthRequest::Rollback(depth) => self.anvil_rollback(depth).await.to_rpc_result(),
1865            EthRequest::SetFeeToken(user, token) => {
1866                self.anvil_set_fee_token(user, token).await.to_rpc_result()
1867            }
1868            EthRequest::SetValidatorFeeToken(validator, token) => {
1869                self.anvil_set_validator_fee_token(validator, token).await.to_rpc_result()
1870            }
1871            EthRequest::SetFeeAmmLiquidity(user_token, validator_token, amount) => self
1872                .anvil_set_fee_amm_liquidity(user_token, validator_token, amount)
1873                .await
1874                .to_rpc_result(),
1875        };
1876
1877        if let ResponseResult::Error(err) = &response {
1878            node_info!("\nRPC request failed:");
1879            node_info!("    Request: {:?}", request);
1880            node_info!("    Error: {}\n", err);
1881        }
1882
1883        response
1884    }
1885
1886    fn sign_request(&self, from: &Address, typed_tx: FoundryTypedTx) -> Result<FoundryTxEnvelope> {
1887        match typed_tx {
1888            #[cfg(feature = "optimism")]
1889            FoundryTypedTx::Deposit(_) => return Ok(build_impersonated(typed_tx)),
1890            _ => {
1891                for signer in self.signers.iter() {
1892                    if signer.accounts().contains(from) {
1893                        return signer.sign_transaction_from(from, typed_tx);
1894                    }
1895                }
1896            }
1897        }
1898        Err(BlockchainError::NoSignerAvailable)
1899    }
1900
1901    async fn inner_raw_transaction(&self, hash: B256) -> Result<Option<Bytes>> {
1902        match self.pool.get_transaction(hash) {
1903            Some(tx) => Ok(Some(tx.transaction.encoded_2718().into())),
1904            None => match self.backend.transaction_by_hash(hash).await? {
1905                Some(tx) => Ok(Some(tx.as_ref().encoded_2718().into())),
1906                None => Ok(None),
1907            },
1908        }
1909    }
1910
1911    /// Returns balance of the given account.
1912    ///
1913    /// Handler for ETH RPC call: `eth_getBalance`
1914    pub async fn balance(&self, address: Address, block_number: Option<BlockId>) -> Result<U256> {
1915        node_info!("eth_getBalance");
1916        let block_request = self.block_request(block_number).await?;
1917
1918        // check if the number predates the fork, if in fork mode
1919        if let BlockRequest::Number(number) = block_request
1920            && let Some(fork) = self.get_fork()
1921            && fork.predates_fork(number)
1922        {
1923            return Ok(fork.get_balance(address, number).await?);
1924        }
1925
1926        self.backend.get_balance(address, Some(block_request)).await
1927    }
1928
1929    /// Returns the ethereum account.
1930    ///
1931    /// Handler for ETH RPC call: `eth_getAccount`
1932    pub async fn get_account(
1933        &self,
1934        address: Address,
1935        block_number: Option<BlockId>,
1936    ) -> Result<TrieAccount> {
1937        node_info!("eth_getAccount");
1938        let block_request = self.block_request(block_number).await?;
1939
1940        // check if the number predates the fork, if in fork mode
1941        if let BlockRequest::Number(number) = block_request
1942            && let Some(fork) = self.get_fork()
1943            && fork.predates_fork(number)
1944        {
1945            return Ok(fork.get_account(address, number).await?);
1946        }
1947
1948        self.backend.get_account_at_block(address, Some(block_request)).await
1949    }
1950
1951    /// Returns the account information including balance, nonce, code and storage
1952    ///
1953    /// Note: This isn't support by all providers
1954    pub async fn get_account_info(
1955        &self,
1956        address: Address,
1957        block_number: Option<BlockId>,
1958    ) -> Result<alloy_rpc_types::eth::AccountInfo> {
1959        node_info!("eth_getAccountInfo");
1960
1961        if let Some(fork) = self.get_fork() {
1962            let block_request = self.block_request(block_number).await?;
1963            // check if the number predates the fork, if in fork mode
1964            if let BlockRequest::Number(number) = block_request {
1965                trace!(target: "node", "get_account_info: fork block {}, requested block {number}", fork.block_number());
1966                return if fork.predates_fork(number) {
1967                    // if this predates the fork we need to fetch balance, nonce, code individually
1968                    // because the provider might not support this endpoint
1969                    let balance = fork.get_balance(address, number).map_err(BlockchainError::from);
1970                    let code = fork.get_code(address, number).map_err(BlockchainError::from);
1971                    let nonce = self.get_transaction_count(address, Some(number.into()));
1972                    let (balance, code, nonce) = try_join!(balance, code, nonce)?;
1973
1974                    Ok(alloy_rpc_types::eth::AccountInfo { balance, nonce, code })
1975                } else {
1976                    // Anvil node is at the same block or higher than the fork block,
1977                    // return account info from backend to reflect current state.
1978                    let account_info = self.backend.get_account(address).await?;
1979                    let code = self.backend.get_code(address, Some(block_request)).await?;
1980                    Ok(alloy_rpc_types::eth::AccountInfo {
1981                        balance: account_info.balance,
1982                        nonce: account_info.nonce,
1983                        code,
1984                    })
1985                };
1986            }
1987        }
1988
1989        let account = self.get_account(address, block_number);
1990        let code = self.get_code(address, block_number);
1991        let (account, code) = try_join!(account, code)?;
1992        Ok(alloy_rpc_types::eth::AccountInfo {
1993            balance: account.balance,
1994            nonce: account.nonce,
1995            code,
1996        })
1997    }
1998    /// Returns content of the storage at given address.
1999    ///
2000    /// Handler for ETH RPC call: `eth_getStorageAt`
2001    pub async fn storage_at(
2002        &self,
2003        address: Address,
2004        index: U256,
2005        block_number: Option<BlockId>,
2006    ) -> Result<B256> {
2007        node_info!("eth_getStorageAt");
2008        let block_request = self.block_request(block_number).await?;
2009
2010        // check if the number predates the fork, if in fork mode
2011        if let BlockRequest::Number(number) = block_request
2012            && let Some(fork) = self.get_fork()
2013            && fork.predates_fork(number)
2014        {
2015            return Ok(B256::from(
2016                fork.storage_at(address, index, Some(BlockNumber::Number(number))).await?,
2017            ));
2018        }
2019
2020        self.backend.storage_at(address, index, Some(block_request)).await
2021    }
2022
2023    /// Returns storage values for multiple accounts and slots in a single call.
2024    ///
2025    /// Handler for ETH RPC call: `eth_getStorageValues`
2026    pub async fn storage_values(
2027        &self,
2028        requests: HashMap<Address, Vec<B256>>,
2029        block_number: Option<BlockId>,
2030    ) -> Result<HashMap<Address, Vec<B256>>> {
2031        node_info!("eth_getStorageValues");
2032
2033        let total_slots: usize = requests.values().map(|s| s.len()).sum();
2034        if total_slots > 1024 {
2035            return Err(BlockchainError::RpcError(RpcError::invalid_params(format!(
2036                "total slot count {total_slots} exceeds limit 1024"
2037            ))));
2038        }
2039
2040        let block_request = self.block_request(block_number).await?;
2041
2042        // check if the number predates the fork, if in fork mode
2043        if let BlockRequest::Number(number) = block_request
2044            && let Some(fork) = self.get_fork()
2045            && fork.predates_fork(number)
2046        {
2047            let mut result: HashMap<Address, Vec<B256>> = HashMap::default();
2048            for (address, slots) in requests {
2049                let mut values = Vec::with_capacity(slots.len());
2050                for slot in &slots {
2051                    let val = fork
2052                        .storage_at(address, (*slot).into(), Some(BlockNumber::Number(number)))
2053                        .await?;
2054                    values.push(B256::from(val));
2055                }
2056                result.insert(address, values);
2057            }
2058            return Ok(result);
2059        }
2060
2061        self.backend.storage_values(requests, Some(block_request)).await
2062    }
2063
2064    /// Returns block with given number.
2065    ///
2066    /// Handler for ETH RPC call: `eth_getBlockByNumber`
2067    pub async fn block_by_number(&self, number: BlockNumber) -> Result<Option<AnyRpcBlock>> {
2068        node_info!("eth_getBlockByNumber");
2069        if number == BlockNumber::Pending {
2070            return Ok(Some(self.pending_block().await));
2071        }
2072
2073        self.backend.block_by_number(number).await
2074    }
2075
2076    /// Returns a _full_ block with given number
2077    ///
2078    /// Handler for ETH RPC call: `eth_getBlockByNumber`
2079    pub async fn block_by_number_full(&self, number: BlockNumber) -> Result<Option<AnyRpcBlock>> {
2080        node_info!("eth_getBlockByNumber");
2081        if number == BlockNumber::Pending {
2082            return Ok(self.pending_block_full().await);
2083        }
2084        self.backend.block_by_number_full(number).await
2085    }
2086
2087    /// Returns the number of transactions sent from given address at given time (block number).
2088    ///
2089    /// Also checks the pending transactions if `block_number` is
2090    /// `BlockId::Number(BlockNumber::Pending)`
2091    ///
2092    /// Handler for ETH RPC call: `eth_getTransactionCount`
2093    pub async fn transaction_count(
2094        &self,
2095        address: Address,
2096        block_number: Option<BlockId>,
2097    ) -> Result<U256> {
2098        node_info!("eth_getTransactionCount");
2099        self.get_transaction_count(address, block_number).await.map(U256::from)
2100    }
2101
2102    /// Returns the number of transactions in a block with given block number.
2103    ///
2104    /// Handler for ETH RPC call: `eth_getBlockTransactionCountByNumber`
2105    pub async fn block_transaction_count_by_number(
2106        &self,
2107        block_number: BlockNumber,
2108    ) -> Result<Option<U256>> {
2109        node_info!("eth_getBlockTransactionCountByNumber");
2110        let block_request = self.block_request(Some(block_number.into())).await?;
2111        if let BlockRequest::Pending(txs) = block_request {
2112            let block = self.backend.pending_block(txs).await;
2113            return Ok(Some(U256::from(block.block.body.transactions.len())));
2114        }
2115        let block = self.backend.block_by_number(block_number).await?;
2116        let txs = block.map(|b| match b.transactions() {
2117            BlockTransactions::Full(txs) => U256::from(txs.len()),
2118            BlockTransactions::Hashes(txs) => U256::from(txs.len()),
2119            BlockTransactions::Uncle => U256::from(0),
2120        });
2121        Ok(txs)
2122    }
2123
2124    /// Returns the code at given address at given time (block number).
2125    ///
2126    /// Handler for ETH RPC call: `eth_getCode`
2127    pub async fn get_code(&self, address: Address, block_number: Option<BlockId>) -> Result<Bytes> {
2128        node_info!("eth_getCode");
2129        let block_request = self.block_request(block_number).await?;
2130        // check if the number predates the fork, if in fork mode
2131        if let BlockRequest::Number(number) = block_request
2132            && let Some(fork) = self.get_fork()
2133            && fork.predates_fork(number)
2134        {
2135            return Ok(fork.get_code(address, number).await?);
2136        }
2137        self.backend.get_code(address, Some(block_request)).await
2138    }
2139
2140    /// Returns the account and storage values of the specified account including the Merkle-proof.
2141    /// This call can be used to verify that the data you are pulling from is not tampered with.
2142    ///
2143    /// Handler for ETH RPC call: `eth_getProof`
2144    pub async fn get_proof(
2145        &self,
2146        address: Address,
2147        keys: Vec<B256>,
2148        block_number: Option<BlockId>,
2149    ) -> Result<EIP1186AccountProofResponse> {
2150        node_info!("eth_getProof");
2151        let block_request = self.block_request(block_number).await?;
2152
2153        // If we're in forking mode, or still on the forked block (no blocks mined yet) then we can
2154        // delegate the call.
2155        if let BlockRequest::Number(number) = block_request
2156            && let Some(fork) = self.get_fork()
2157            && fork.predates_fork_inclusive(number)
2158        {
2159            return Ok(fork.get_proof(address, keys, Some(number.into())).await?);
2160        }
2161
2162        let proof = self.backend.prove_account_at(address, keys, Some(block_request)).await?;
2163        Ok(proof)
2164    }
2165
2166    /// Signs a transaction
2167    ///
2168    /// Handler for ETH RPC call: `eth_signTransaction`
2169    pub async fn sign_transaction(
2170        &self,
2171        request: WithOtherFields<TransactionRequest>,
2172    ) -> Result<String> {
2173        node_info!("eth_signTransaction");
2174
2175        let from = request.from.map(Ok).unwrap_or_else(|| {
2176            self.accounts()?.first().copied().ok_or(BlockchainError::NoSignerAvailable)
2177        })?;
2178
2179        let (nonce, _) = self.request_nonce(&request, from).await?;
2180
2181        let request = self.build_tx_request(request, nonce).await?;
2182
2183        let signed_transaction = self.sign_request(&from, request)?.encoded_2718();
2184        Ok(alloy_primitives::hex::encode_prefixed(signed_transaction))
2185    }
2186
2187    /// Sends a transaction
2188    ///
2189    /// Handler for ETH RPC call: `eth_sendTransaction`
2190    pub async fn send_transaction(
2191        &self,
2192        request: WithOtherFields<TransactionRequest>,
2193    ) -> Result<TxHash> {
2194        node_info!("eth_sendTransaction");
2195
2196        let from = request.from.map(Ok).unwrap_or_else(|| {
2197            self.accounts()?.first().copied().ok_or(BlockchainError::NoSignerAvailable)
2198        })?;
2199        let (nonce, on_chain_nonce) = self.request_nonce(&request, from).await?;
2200
2201        let typed_tx = self.build_tx_request(request, nonce).await?;
2202
2203        // if the sender is currently impersonated we need to "bypass" signing
2204        let pending_transaction = if self.is_impersonated(from) {
2205            let transaction = sign::build_impersonated(typed_tx);
2206            self.ensure_typed_transaction_supported(&transaction)?;
2207            trace!(target : "node", ?from, "eth_sendTransaction: impersonating");
2208            PendingTransaction::with_impersonated(transaction, from)
2209        } else {
2210            let transaction = self.sign_request(&from, typed_tx)?;
2211            self.ensure_typed_transaction_supported(&transaction)?;
2212            PendingTransaction::new(transaction)?
2213        };
2214        // pre-validate
2215        self.backend.validate_pool_transaction(&pending_transaction).await?;
2216
2217        let (requires, provides) = if let Some((requires, provides)) =
2218            tempo_parallel_nonce_markers(&pending_transaction)
2219        {
2220            (requires, provides)
2221        } else {
2222            (required_marker(nonce, on_chain_nonce, from), vec![to_marker(nonce, from)])
2223        };
2224
2225        self.add_pending_transaction(pending_transaction, requires, provides)
2226    }
2227
2228    /// Waits for a transaction to be included in a block and returns its receipt (no timeout).
2229    async fn await_transaction_inclusion(&self, hash: TxHash) -> Result<FoundryTxReceipt> {
2230        let mut stream = self.new_block_notifications();
2231        // Check if the transaction is already included before listening for new blocks.
2232        if let Some(receipt) = self.backend.transaction_receipt(hash).await? {
2233            return Ok(receipt);
2234        }
2235        while let Some(notification) = stream.next().await {
2236            if let Some(block) = self.backend.get_block_by_hash(notification.hash)
2237                && block.body.transactions.iter().any(|tx| tx.hash() == hash)
2238                && let Some(receipt) = self.backend.transaction_receipt(hash).await?
2239            {
2240                return Ok(receipt);
2241            }
2242        }
2243
2244        Err(BlockchainError::Message("Failed to await transaction inclusion".to_string()))
2245    }
2246
2247    /// Waits for a transaction to be included in a block and returns its receipt, with timeout.
2248    async fn check_transaction_inclusion(&self, hash: TxHash) -> Result<FoundryTxReceipt> {
2249        const TIMEOUT_DURATION: Duration = Duration::from_secs(30);
2250        tokio::time::timeout(TIMEOUT_DURATION, self.await_transaction_inclusion(hash))
2251            .await
2252            .unwrap_or_else(|_elapsed| {
2253                Err(BlockchainError::TransactionConfirmationTimeout {
2254                    hash,
2255                    duration: TIMEOUT_DURATION,
2256                })
2257            })
2258    }
2259
2260    /// Sends a transaction and waits for receipt
2261    ///
2262    /// Handler for ETH RPC call: `eth_sendTransactionSync`
2263    pub async fn send_transaction_sync(
2264        &self,
2265        request: WithOtherFields<TransactionRequest>,
2266    ) -> Result<FoundryTxReceipt> {
2267        node_info!("eth_sendTransactionSync");
2268        let hash = self.send_transaction(request).await?;
2269
2270        let receipt = self.check_transaction_inclusion(hash).await?;
2271
2272        Ok(receipt)
2273    }
2274
2275    /// Sends signed transaction, returning its hash.
2276    ///
2277    /// Handler for ETH RPC call: `eth_sendRawTransaction`
2278    pub async fn send_raw_transaction(&self, tx: Bytes) -> Result<TxHash> {
2279        node_info!("eth_sendRawTransaction");
2280        let mut data = tx.as_ref();
2281        if data.is_empty() {
2282            return Err(BlockchainError::EmptyRawTransactionData);
2283        }
2284
2285        let transaction = FoundryTxEnvelope::decode_2718(&mut data)
2286            .map_err(|_| BlockchainError::FailedToDecodeSignedTransaction)?;
2287
2288        self.ensure_typed_transaction_supported(&transaction)?;
2289
2290        if self.backend.is_tempo() && TempoHardfork::from(self.backend.hardfork()).is_t5() {
2291            let classification = transaction.classify_t5_payment_lane();
2292            trace!(target: "node", tx = ?transaction.hash(), ?classification, "classified transaction lane");
2293        }
2294
2295        let pending_transaction = PendingTransaction::new(transaction)?;
2296
2297        // pre-validate
2298        self.backend.validate_pool_transaction(&pending_transaction).await?;
2299
2300        let from = *pending_transaction.sender();
2301        let priority = self.transaction_priority(&pending_transaction.transaction);
2302
2303        // Tempo txs use a 2D nonce system — no sequential ordering by account nonce.
2304        let (requires, provides) = if let Some((requires, provides)) =
2305            tempo_parallel_nonce_markers(&pending_transaction)
2306        {
2307            (requires, provides)
2308        } else {
2309            let on_chain_nonce = self.backend.current_nonce(from).await?;
2310            let nonce = pending_transaction.transaction.nonce();
2311            (required_marker(nonce, on_chain_nonce, from), vec![to_marker(nonce, from)])
2312        };
2313
2314        let pool_transaction =
2315            PoolTransaction { requires, provides, pending_transaction, priority };
2316
2317        let tx = self.pool.add_transaction(pool_transaction)?;
2318        trace!(target: "node", "Added transaction: [{:?}] sender={:?}", tx.hash(), from);
2319        Ok(*tx.hash())
2320    }
2321
2322    /// Classifies a raw transaction with the active Anvil Tempo/T5 payment-lane classifier.
2323    pub fn anvil_classify_transaction(&self, tx: Bytes) -> Result<PaymentLaneClassification> {
2324        node_info!("anvil_classifyTransaction");
2325        let mut data = tx.as_ref();
2326        if data.is_empty() {
2327            return Err(BlockchainError::EmptyRawTransactionData);
2328        }
2329
2330        let transaction = FoundryTxEnvelope::decode_2718(&mut data)
2331            .map_err(|_| BlockchainError::FailedToDecodeSignedTransaction)?;
2332
2333        Ok(self.classify_transaction_envelope(&transaction))
2334    }
2335
2336    fn classify_transaction_envelope(
2337        &self,
2338        transaction: &FoundryTxEnvelope,
2339    ) -> PaymentLaneClassification {
2340        if !self.backend.is_tempo() {
2341            return PaymentLaneClassification::general(PaymentLaneReason::NotTempo);
2342        }
2343
2344        if !TempoHardfork::from(self.backend.hardfork()).is_t5() {
2345            return PaymentLaneClassification::general(PaymentLaneReason::T5NotActive);
2346        }
2347
2348        transaction.classify_t5_payment_lane()
2349    }
2350
2351    /// Sends signed transaction, returning its receipt.
2352    ///
2353    /// Handler for ETH RPC call: `eth_sendRawTransactionSync`
2354    pub async fn send_raw_transaction_sync(&self, tx: Bytes) -> Result<FoundryTxReceipt> {
2355        node_info!("eth_sendRawTransactionSync");
2356
2357        let hash = self.send_raw_transaction(tx).await?;
2358        let receipt = self.check_transaction_inclusion(hash).await?;
2359
2360        Ok(receipt)
2361    }
2362
2363    /// Call contract, returning the output data.
2364    ///
2365    /// Handler for ETH RPC call: `eth_call`
2366    pub async fn call(
2367        &self,
2368        request: WithOtherFields<TransactionRequest>,
2369        block_number: Option<BlockId>,
2370        overrides: EvmOverrides,
2371    ) -> Result<Bytes> {
2372        node_info!("eth_call");
2373        let block_request = self.block_request(block_number).await?;
2374        // check if the number predates the fork, if in fork mode
2375        if let BlockRequest::Number(number) = block_request
2376            && let Some(fork) = self.get_fork()
2377            && fork.predates_fork(number)
2378        {
2379            if overrides.has_state() || overrides.has_block() {
2380                return Err(BlockchainError::EvmOverrideError(
2381                    "not available on past forked blocks".to_string(),
2382                ));
2383            }
2384            return Ok(fork.call(&request, Some(number.into())).await?);
2385        }
2386
2387        let fees = FeeDetails::new(
2388            request.gas_price,
2389            request.max_fee_per_gas,
2390            request.max_priority_fee_per_gas,
2391            request.max_fee_per_blob_gas,
2392        )?
2393        .or_zero_fees();
2394        // this can be blocking for a bit, especially in forking mode
2395        // <https://github.com/foundry-rs/foundry/issues/6036>
2396        self.on_blocking_task(|this| async move {
2397            let (exit, out, gas, _) =
2398                this.backend.call(request, fees, Some(block_request), overrides).await?;
2399            trace!(target : "node", "Call status {:?}, gas {}", exit, gas);
2400
2401            ensure_return_ok(exit, &out)
2402        })
2403        .await
2404    }
2405
2406    pub async fn simulate_v1(
2407        &self,
2408        request: SimulatePayload,
2409        block_number: Option<BlockId>,
2410    ) -> Result<Vec<SimulatedBlock<AnyRpcBlock>>> {
2411        node_info!("eth_simulateV1");
2412        let block_request = self.block_request(block_number).await?;
2413        // check if the number predates the fork, if in fork mode
2414        if let BlockRequest::Number(number) = block_request
2415            && let Some(fork) = self.get_fork()
2416            && fork.predates_fork(number)
2417        {
2418            return Ok(fork.simulate_v1(&request, Some(number.into())).await?);
2419        }
2420
2421        // this can be blocking for a bit, especially in forking mode
2422        // <https://github.com/foundry-rs/foundry/issues/6036>
2423        self.on_blocking_task(|this| async move {
2424            let simulated_blocks = this.backend.simulate(request, Some(block_request)).await?;
2425            trace!(target : "node", "Simulate status {:?}", simulated_blocks);
2426
2427            Ok(simulated_blocks)
2428        })
2429        .await
2430    }
2431
2432    /// This method creates an EIP2930 type accessList based on a given Transaction. The accessList
2433    /// contains all storage slots and addresses read and written by the transaction, except for the
2434    /// sender account and the precompiles.
2435    ///
2436    /// It returns list of addresses and storage keys used by the transaction, plus the gas
2437    /// consumed when the access list is added. That is, it gives you the list of addresses and
2438    /// storage keys that will be used by that transaction, plus the gas consumed if the access
2439    /// list is included. Like eth_estimateGas, this is an estimation; the list could change
2440    /// when the transaction is actually mined. Adding an accessList to your transaction does
2441    /// not necessary result in lower gas usage compared to a transaction without an access
2442    /// list.
2443    ///
2444    /// Handler for ETH RPC call: `eth_createAccessList`
2445    pub async fn create_access_list(
2446        &self,
2447        mut request: WithOtherFields<TransactionRequest>,
2448        block_number: Option<BlockId>,
2449    ) -> Result<AccessListResult> {
2450        node_info!("eth_createAccessList");
2451        let block_request = self.block_request(block_number).await?;
2452        // check if the number predates the fork, if in fork mode
2453        if let BlockRequest::Number(number) = block_request
2454            && let Some(fork) = self.get_fork()
2455            && fork.predates_fork(number)
2456        {
2457            return Ok(fork.create_access_list(&request, Some(number.into())).await?);
2458        }
2459
2460        self.backend
2461            .with_database_at(Some(block_request), |state, block_env| {
2462                let (_, _, _, access_list) = self.backend.build_access_list_with_state(
2463                    &state,
2464                    request.clone(),
2465                    FeeDetails::zero(),
2466                    block_env.clone(),
2467                )?;
2468
2469                // Re-execute with the access list applied to get the post-AL gas usage.
2470                // EVM failures (including reverts) are surfaced in the result's `error`
2471                // field per the execution-apis `eth_createAccessList` spec, so callers
2472                // can still inspect the traced slots when execution fails.
2473                request.access_list = Some(access_list.clone());
2474                let (exit, _, gas_used, _) =
2475                    self.backend.call_with_state(&state, request, FeeDetails::zero(), block_env)?;
2476
2477                Ok(AccessListResult {
2478                    access_list,
2479                    gas_used: U256::from(gas_used),
2480                    error: execution_error(exit),
2481                })
2482            })
2483            .await?
2484    }
2485
2486    /// Estimate gas needed for execution of given contract.
2487    /// If no block parameter is given, it will use the pending block by default
2488    ///
2489    /// Handler for ETH RPC call: `eth_estimateGas`
2490    pub async fn estimate_gas(
2491        &self,
2492        request: WithOtherFields<TransactionRequest>,
2493        block_number: Option<BlockId>,
2494        overrides: EvmOverrides,
2495    ) -> Result<U256> {
2496        node_info!("eth_estimateGas");
2497        self.do_estimate_gas(
2498            request,
2499            block_number.or_else(|| Some(BlockNumber::Pending.into())),
2500            overrides,
2501        )
2502        .await
2503        .map(U256::from)
2504    }
2505
2506    /// Fills a transaction request with default values for missing fields.
2507    ///
2508    /// This method populates missing transaction fields like nonce, gas limit,
2509    /// chain ID, and fee parameters with appropriate defaults.
2510    ///
2511    /// Handler for ETH RPC call: `eth_fillTransaction`
2512    pub async fn fill_transaction(
2513        &self,
2514        mut request: WithOtherFields<TransactionRequest>,
2515    ) -> Result<FillTransaction<AnyRpcTransaction>> {
2516        node_info!("eth_fillTransaction");
2517
2518        let from = match request.as_ref().from() {
2519            Some(from) => from,
2520            None => self.accounts()?.first().copied().ok_or(BlockchainError::NoSignerAvailable)?,
2521        };
2522
2523        let nonce = if let Some(nonce) = request.as_ref().nonce() {
2524            nonce
2525        } else {
2526            self.request_nonce(&request, from).await?.0
2527        };
2528
2529        // Prefill gas limit with estimated gas and bubble up estimation errors directly.
2530        if request.as_ref().gas_limit().is_none() {
2531            let estimated_gas =
2532                self.estimate_gas(request.clone(), None, EvmOverrides::default()).await?;
2533            request.as_mut().set_gas_limit(estimated_gas.to());
2534        }
2535
2536        let typed_tx = self.build_tx_request(request, nonce).await?;
2537        let tx = build_impersonated(typed_tx);
2538
2539        let raw = tx.encoded_2718().into();
2540
2541        let mut tx =
2542            transaction_build(None, MaybeImpersonatedTransaction::new(tx), None, None, None);
2543
2544        // Set the correct `from` address (overrides the recovered zero address from dummy
2545        // signature)
2546        tx.0.inner.inner = Recovered::new_unchecked(tx.0.inner.inner.into_inner(), from);
2547
2548        Ok(FillTransaction { raw, tx })
2549    }
2550
2551    /// Handler for RPC call: `anvil_getBlobsByTransactionHash`
2552    pub fn anvil_get_blob_by_tx_hash(&self, hash: B256) -> Result<Option<Vec<Blob>>> {
2553        node_info!("anvil_getBlobsByTransactionHash");
2554        Ok(self.backend.get_blob_by_tx_hash(hash)?)
2555    }
2556
2557    /// Get transaction by its hash.
2558    ///
2559    /// This will check the storage for a matching transaction, if no transaction exists in storage
2560    /// this will also scan the mempool for a matching pending transaction
2561    ///
2562    /// Handler for ETH RPC call: `eth_getTransactionByHash`
2563    pub async fn transaction_by_hash(&self, hash: B256) -> Result<Option<AnyRpcTransaction>> {
2564        node_info!("eth_getTransactionByHash");
2565        let mut tx = self.pool.get_transaction(hash).map(|pending| {
2566            let from = *pending.sender();
2567            let tx = transaction_build(
2568                Some(*pending.hash()),
2569                pending.transaction,
2570                None,
2571                None,
2572                Some(self.backend.base_fee()),
2573            );
2574
2575            let WithOtherFields { inner: mut tx, other } = tx.0;
2576            // we set the from field here explicitly to the set sender of the pending transaction,
2577            // in case the transaction is impersonated.
2578            tx.inner = Recovered::new_unchecked(tx.inner.into_inner(), from);
2579
2580            AnyRpcTransaction(WithOtherFields { inner: tx, other })
2581        });
2582        if tx.is_none() {
2583            tx = self.backend.transaction_by_hash(hash).await?
2584        }
2585
2586        Ok(tx)
2587    }
2588
2589    /// Returns the transaction by sender and nonce.
2590    ///
2591    /// This will check the mempool for pending transactions first, then perform a binary search
2592    /// over mined blocks to find the transaction.
2593    ///
2594    /// Handler for ETH RPC call: `eth_getTransactionBySenderAndNonce`
2595    pub async fn transaction_by_sender_and_nonce(
2596        &self,
2597        sender: Address,
2598        nonce: U256,
2599    ) -> Result<Option<AnyRpcTransaction>> {
2600        node_info!("eth_getTransactionBySenderAndNonce");
2601
2602        // check pending txs first
2603        for pending_tx in self.pool.ready_transactions().chain(self.pool.pending_transactions()) {
2604            if U256::from(pending_tx.pending_transaction.nonce()) == nonce
2605                && *pending_tx.pending_transaction.sender() == sender
2606            {
2607                let tx = transaction_build(
2608                    Some(*pending_tx.pending_transaction.hash()),
2609                    pending_tx.pending_transaction.transaction.clone(),
2610                    None,
2611                    None,
2612                    Some(self.backend.base_fee()),
2613                );
2614
2615                let WithOtherFields { inner: mut tx, other } = tx.0;
2616                // we set the from field here explicitly to the set sender of the pending
2617                // transaction, in case the transaction is impersonated.
2618                let from = *pending_tx.pending_transaction.sender();
2619                tx.inner = Recovered::new_unchecked(tx.inner.into_inner(), from);
2620
2621                return Ok(Some(AnyRpcTransaction(WithOtherFields { inner: tx, other })));
2622            }
2623        }
2624
2625        let highest_nonce = self.transaction_count(sender, None).await?.saturating_to::<u64>();
2626        let target_nonce = nonce.saturating_to::<u64>();
2627
2628        // if the nonce is higher or equal to the highest nonce, the transaction doesn't exist
2629        if target_nonce >= highest_nonce {
2630            return Ok(None);
2631        }
2632
2633        // no mined blocks yet
2634        let latest_block = self.backend.best_number();
2635        if latest_block == 0 {
2636            return Ok(None);
2637        }
2638
2639        // binary search for the block containing the transaction
2640        let mut low = 1u64;
2641        let mut high = latest_block;
2642
2643        while low <= high {
2644            let mid = low + (high - low) / 2;
2645            let mid_nonce =
2646                self.transaction_count(sender, Some(mid.into())).await?.saturating_to::<u64>();
2647
2648            if mid_nonce > target_nonce {
2649                high = mid - 1;
2650            } else {
2651                low = mid + 1;
2652            }
2653        }
2654
2655        // search in the target block
2656        let target_block = low;
2657        if target_block <= latest_block
2658            && let Some(txs) =
2659                self.backend.mined_transactions_by_block_number(target_block.into()).await
2660        {
2661            for tx in txs {
2662                if tx.from() == sender && tx.nonce() == target_nonce {
2663                    return Ok(Some(tx));
2664                }
2665            }
2666        }
2667
2668        Ok(None)
2669    }
2670
2671    /// Returns transaction receipt by transaction hash.
2672    ///
2673    /// Handler for ETH RPC call: `eth_getTransactionReceipt`
2674    pub async fn transaction_receipt(&self, hash: B256) -> Result<Option<FoundryTxReceipt>> {
2675        node_info!("eth_getTransactionReceipt");
2676        self.backend.transaction_receipt(hash).await
2677    }
2678
2679    /// Returns block receipts by block number.
2680    ///
2681    /// Handler for ETH RPC call: `eth_getBlockReceipts`
2682    pub async fn block_receipts(&self, number: BlockId) -> Result<Option<Vec<FoundryTxReceipt>>> {
2683        node_info!("eth_getBlockReceipts");
2684        self.backend.block_receipts(number).await
2685    }
2686
2687    /// Returns logs matching given filter object.
2688    ///
2689    /// Handler for ETH RPC call: `eth_getLogs`
2690    pub async fn logs(&self, filter: Filter) -> Result<Vec<Log>> {
2691        node_info!("eth_getLogs");
2692        self.backend.logs(filter).await
2693    }
2694
2695    /// Creates a filter object, based on filter options, to notify when the state changes (logs).
2696    ///
2697    /// Handler for ETH RPC call: `eth_newFilter`
2698    pub async fn new_filter(&self, filter: Filter) -> Result<String> {
2699        node_info!("eth_newFilter");
2700        // all logs that are already available that match the filter if the filter's block range is
2701        // in the past
2702        let historic = if filter.block_option.get_from_block().is_some() {
2703            self.backend.logs(filter.clone()).await?
2704        } else {
2705            vec![]
2706        };
2707        let filter = EthFilter::Logs(Box::new(LogsFilter {
2708            blocks: self.new_block_notifications(),
2709            storage: self.storage_info(),
2710            filter: FilteredParams::new(Some(filter)),
2711            historic: Some(historic),
2712        }));
2713        Ok(self.filters.add_filter(filter).await)
2714    }
2715
2716    /// Creates a filter in the node, to notify when a new block arrives.
2717    ///
2718    /// Handler for ETH RPC call: `eth_newBlockFilter`
2719    pub async fn new_block_filter(&self) -> Result<String> {
2720        node_info!("eth_newBlockFilter");
2721        let filter = EthFilter::Blocks(self.new_block_notifications());
2722        Ok(self.filters.add_filter(filter).await)
2723    }
2724
2725    /// Creates a filter in the node, to notify when new pending transactions arrive.
2726    ///
2727    /// Handler for ETH RPC call: `eth_newPendingTransactionFilter`
2728    pub async fn new_pending_transaction_filter(&self) -> Result<String> {
2729        node_info!("eth_newPendingTransactionFilter");
2730        let filter = EthFilter::PendingTransactions(self.new_ready_transactions());
2731        Ok(self.filters.add_filter(filter).await)
2732    }
2733
2734    /// Polling method for a filter, which returns an array of logs which occurred since last poll.
2735    ///
2736    /// Handler for ETH RPC call: `eth_getFilterChanges`
2737    pub async fn get_filter_changes(&self, id: &str) -> ResponseResult {
2738        node_info!("eth_getFilterChanges");
2739        self.filters.get_filter_changes(id).await
2740    }
2741
2742    /// Returns an array of all logs matching filter with given id.
2743    ///
2744    /// Handler for ETH RPC call: `eth_getFilterLogs`
2745    pub async fn get_filter_logs(&self, id: &str) -> Result<Vec<Log>> {
2746        node_info!("eth_getFilterLogs");
2747        if let Some(filter) = self.filters.get_log_filter(id).await {
2748            self.backend.logs(filter).await
2749        } else {
2750            Err(BlockchainError::FilterNotFound)
2751        }
2752    }
2753
2754    /// Handler for ETH RPC call: `eth_uninstallFilter`
2755    pub async fn uninstall_filter(&self, id: &str) -> Result<bool> {
2756        node_info!("eth_uninstallFilter");
2757        Ok(self.filters.uninstall_filter(id).await.is_some())
2758    }
2759
2760    /// Returns EIP-2718 encoded raw transaction
2761    ///
2762    /// Handler for RPC call: `debug_getRawTransaction`
2763    pub async fn raw_transaction(&self, hash: B256) -> Result<Option<Bytes>> {
2764        node_info!("debug_getRawTransaction");
2765        self.inner_raw_transaction(hash).await
2766    }
2767
2768    /// Returns EIP-2718 encoded raw transaction by block hash and index
2769    ///
2770    /// Handler for RPC call: `eth_getRawTransactionByBlockHashAndIndex`
2771    pub async fn raw_transaction_by_block_hash_and_index(
2772        &self,
2773        block_hash: B256,
2774        index: Index,
2775    ) -> Result<Option<Bytes>> {
2776        node_info!("eth_getRawTransactionByBlockHashAndIndex");
2777        match self.backend.transaction_by_block_hash_and_index(block_hash, index).await? {
2778            Some(tx) => self.inner_raw_transaction(tx.tx_hash()).await,
2779            None => Ok(None),
2780        }
2781    }
2782
2783    /// Returns EIP-2718 encoded raw transaction by block number and index
2784    ///
2785    /// Handler for RPC call: `eth_getRawTransactionByBlockNumberAndIndex`
2786    pub async fn raw_transaction_by_block_number_and_index(
2787        &self,
2788        block_number: BlockNumber,
2789        index: Index,
2790    ) -> Result<Option<Bytes>> {
2791        node_info!("eth_getRawTransactionByBlockNumberAndIndex");
2792        match self.backend.transaction_by_block_number_and_index(block_number, index).await? {
2793            Some(tx) => self.inner_raw_transaction(tx.tx_hash()).await,
2794            None => Ok(None),
2795        }
2796    }
2797
2798    /// Returns traces for the transaction hash for geth's tracing endpoint
2799    ///
2800    /// Handler for RPC call: `debug_traceTransaction`
2801    pub async fn debug_trace_transaction(
2802        &self,
2803        tx_hash: B256,
2804        opts: GethDebugTracingOptions,
2805    ) -> Result<GethTrace> {
2806        node_info!("debug_traceTransaction");
2807        self.backend.debug_trace_transaction(tx_hash, opts).await
2808    }
2809
2810    /// Returns traces for all transactions in a block by hash.
2811    ///
2812    /// Handler for RPC call: `debug_traceBlockByHash`
2813    pub async fn debug_trace_block_by_hash(
2814        &self,
2815        block_hash: B256,
2816        opts: GethDebugTracingOptions,
2817    ) -> Result<Vec<TraceResult>> {
2818        node_info!("debug_traceBlockByHash");
2819        self.backend.debug_trace_block_by_hash(block_hash, opts).await
2820    }
2821
2822    /// Returns traces for all transactions in a block by number.
2823    ///
2824    /// Handler for RPC call: `debug_traceBlockByNumber`
2825    pub async fn debug_trace_block_by_number(
2826        &self,
2827        block_number: BlockNumber,
2828        opts: GethDebugTracingOptions,
2829    ) -> Result<Vec<TraceResult>> {
2830        node_info!("debug_traceBlockByNumber");
2831        self.backend.debug_trace_block_by_number(block_number, opts).await
2832    }
2833
2834    /// Returns traces for the transaction for geth's tracing endpoint
2835    ///
2836    /// Handler for RPC call: `debug_traceCall`
2837    pub async fn debug_trace_call(
2838        &self,
2839        request: WithOtherFields<TransactionRequest>,
2840        block_number: Option<BlockId>,
2841        opts: GethDebugTracingCallOptions,
2842    ) -> Result<GethTrace> {
2843        node_info!("debug_traceCall");
2844        let block_request = self.block_request(block_number).await?;
2845        let fees = FeeDetails::new(
2846            request.gas_price,
2847            request.max_fee_per_gas,
2848            request.max_priority_fee_per_gas,
2849            request.max_fee_per_blob_gas,
2850        )?
2851        .or_zero_fees();
2852
2853        let result: std::result::Result<GethTrace, BlockchainError> =
2854            self.backend.call_with_tracing(request, fees, Some(block_request), opts).await;
2855        result
2856    }
2857}
2858
2859// == impl EthApi anvil endpoints ==
2860
2861impl EthApi<FoundryNetwork> {
2862    /// Mines a series of blocks.
2863    ///
2864    /// Handler for ETH RPC call: `anvil_mine`
2865    pub async fn anvil_mine(&self, num_blocks: Option<U256>, interval: Option<U256>) -> Result<()> {
2866        node_info!("anvil_mine");
2867        let interval = interval.map(|i| i.saturating_to::<u64>());
2868        let blocks = num_blocks.unwrap_or(U256::from(1));
2869        if blocks.is_zero() {
2870            return Ok(());
2871        }
2872
2873        self.on_blocking_task(|this| async move {
2874            // mine all the blocks
2875            for _ in 0..blocks.saturating_to::<u64>() {
2876                // If we have an interval, jump forwards in time to the "next" timestamp
2877                if let Some(interval) = interval {
2878                    this.backend.time().increase_time(interval);
2879                }
2880                this.mine_one().await;
2881            }
2882            Ok(())
2883        })
2884        .await?;
2885
2886        Ok(())
2887    }
2888
2889    /// Helper function to find the storage slot for an ERC20 function call by testing slots
2890    /// from an access list until one produces the expected result.
2891    ///
2892    /// Rather than trying to reverse-engineer the storage layout, this function uses a
2893    /// "trial and error" approach: try overriding each slot that the function accesses,
2894    /// and see which one actually affects the function's return value.
2895    ///
2896    /// ## Parameters
2897    /// - `token_address`: The ERC20 token contract address
2898    /// - `calldata`: The encoded function call (e.g., `balanceOf(user)` or `allowance(owner,
2899    ///   spender)`)
2900    /// - `expected_value`: The value we want to set (balance or allowance amount)
2901    ///
2902    /// ## Returns
2903    /// The storage slot (B256) that contains the target ERC20 data, or an error if no slot is
2904    /// found.
2905    async fn find_erc20_storage_slot(
2906        &self,
2907        token_address: Address,
2908        calldata: Bytes,
2909        expected_value: U256,
2910    ) -> Result<B256> {
2911        let tx = TransactionRequest::default().with_to(token_address).with_input(calldata.clone());
2912
2913        // first collect all the slots that are used by the function call
2914        let access_list_result =
2915            self.create_access_list(WithOtherFields::new(tx.clone()), None).await?;
2916        let access_list = access_list_result.access_list;
2917
2918        // iterate over all the accessed slots and try to find the one that contains the
2919        // target value by overriding the slot and checking the function call result
2920        for item in access_list.0 {
2921            if item.address != token_address {
2922                continue;
2923            };
2924            for slot in &item.storage_keys {
2925                let account_override = AccountOverride::default().with_state_diff(std::iter::once(
2926                    (*slot, B256::from(expected_value.to_be_bytes())),
2927                ));
2928
2929                let state_override = StateOverridesBuilder::default()
2930                    .append(token_address, account_override)
2931                    .build();
2932
2933                let evm_override = EvmOverrides::state(Some(state_override));
2934
2935                let Ok(result) =
2936                    self.call(WithOtherFields::new(tx.clone()), None, evm_override).await
2937                else {
2938                    // overriding this slot failed
2939                    continue;
2940                };
2941
2942                let Ok(result_value) = U256::abi_decode(&result) else {
2943                    // response returned something other than a U256
2944                    continue;
2945                };
2946
2947                if result_value == expected_value {
2948                    return Ok(*slot);
2949                }
2950            }
2951        }
2952
2953        Err(BlockchainError::Message("Unable to find storage slot".to_string()))
2954    }
2955
2956    /// Deals ERC20 tokens to a address
2957    ///
2958    /// Handler for RPC call: `anvil_dealERC20`
2959    pub async fn anvil_deal_erc20(
2960        &self,
2961        address: Address,
2962        token_address: Address,
2963        balance: U256,
2964    ) -> Result<()> {
2965        node_info!("anvil_dealERC20");
2966
2967        sol! {
2968            #[sol(rpc)]
2969            contract IERC20 {
2970                function balanceOf(address target) external view returns (uint256);
2971            }
2972        }
2973
2974        let calldata = IERC20::balanceOfCall { target: address }.abi_encode().into();
2975
2976        // Find the storage slot that contains the balance
2977        let slot =
2978            self.find_erc20_storage_slot(token_address, calldata, balance).await.map_err(|_| {
2979                BlockchainError::Message("Unable to set ERC20 balance, no slot found".to_string())
2980            })?;
2981
2982        // Set the storage slot to the desired balance
2983        self.anvil_set_storage_at(
2984            token_address,
2985            U256::from_be_bytes(slot.0),
2986            B256::from(balance.to_be_bytes()),
2987        )
2988        .await?;
2989
2990        Ok(())
2991    }
2992
2993    /// Sets the ERC20 allowance for a spender
2994    ///
2995    /// Handler for RPC call: `anvil_set_erc20_allowance`
2996    pub async fn anvil_set_erc20_allowance(
2997        &self,
2998        owner: Address,
2999        spender: Address,
3000        token_address: Address,
3001        amount: U256,
3002    ) -> Result<()> {
3003        node_info!("anvil_setERC20Allowance");
3004
3005        sol! {
3006            #[sol(rpc)]
3007            contract IERC20 {
3008                function allowance(address owner, address spender) external view returns (uint256);
3009            }
3010        }
3011
3012        let calldata = IERC20::allowanceCall { owner, spender }.abi_encode().into();
3013
3014        // Find the storage slot that contains the allowance
3015        let slot =
3016            self.find_erc20_storage_slot(token_address, calldata, amount).await.map_err(|_| {
3017                BlockchainError::Message("Unable to set ERC20 allowance, no slot found".to_string())
3018            })?;
3019
3020        // Set the storage slot to the desired allowance
3021        self.anvil_set_storage_at(
3022            token_address,
3023            U256::from_be_bytes(slot.0),
3024            B256::from(amount.to_be_bytes()),
3025        )
3026        .await?;
3027
3028        Ok(())
3029    }
3030
3031    /// Reorg the chain to a specific depth and mine new blocks back to the canonical height.
3032    ///
3033    /// e.g depth = 3
3034    ///     A  -> B  -> C  -> D  -> E
3035    ///     A  -> B  -> C' -> D' -> E'
3036    ///
3037    /// Depth specifies the height to reorg the chain back to. Depth must not exceed the current
3038    /// chain height, i.e. can't reorg past the genesis block.
3039    ///
3040    /// Optionally supply a list of transaction and block pairs that will populate the reorged
3041    /// blocks. The maximum block number of the pairs must not exceed the specified depth.
3042    ///
3043    /// Handler for RPC call: `anvil_reorg`
3044    pub async fn anvil_reorg(&self, options: ReorgOptions) -> Result<()> {
3045        node_info!("anvil_reorg");
3046        let depth = options.depth;
3047        let tx_block_pairs = options.tx_block_pairs;
3048
3049        // Check reorg depth doesn't exceed current chain height
3050        let current_height = self.backend.best_number();
3051        let common_height = current_height.checked_sub(depth).ok_or(BlockchainError::RpcError(
3052            RpcError::invalid_params(format!(
3053                "Reorg depth must not exceed current chain height: current height {current_height}, depth {depth}"
3054            )),
3055        ))?;
3056
3057        // Get the common ancestor block
3058        let common_block =
3059            self.backend.get_block(common_height).ok_or(BlockchainError::BlockNotFound)?;
3060
3061        // Convert the transaction requests to pool transactions if they exist, otherwise use empty
3062        // hashmap
3063        let block_pool_txs = if tx_block_pairs.is_empty() {
3064            HashMap::default()
3065        } else {
3066            let mut pairs = tx_block_pairs;
3067
3068            // Check the maximum block supplied number will not exceed the reorged chain height
3069            if let Some((_, num)) = pairs.iter().find(|(_, num)| *num >= depth) {
3070                return Err(BlockchainError::RpcError(RpcError::invalid_params(format!(
3071                    "Block number for reorg tx will exceed the reorged chain height. Block number {num} must not exceed (depth-1) {}",
3072                    depth - 1
3073                ))));
3074            }
3075
3076            // Sort by block number to make it easier to manage new nonces
3077            pairs.sort_by_key(|a| a.1);
3078
3079            // Manage nonces for each signer
3080            // address -> cumulative nonce
3081            let mut nonces: HashMap<Address, u64> = HashMap::default();
3082
3083            let mut txs: HashMap<u64, Vec<Arc<PoolTransaction<FoundryTxEnvelope>>>> =
3084                HashMap::default();
3085            for pair in pairs {
3086                let (tx_data, block_index) = pair;
3087
3088                let pending = match tx_data {
3089                    TransactionData::Raw(bytes) => {
3090                        let mut data = bytes.as_ref();
3091                        let decoded = FoundryTxEnvelope::decode_2718(&mut data)
3092                            .map_err(|_| BlockchainError::FailedToDecodeSignedTransaction)?;
3093                        PendingTransaction::new(decoded)?
3094                    }
3095
3096                    TransactionData::JSON(request) => {
3097                        let from = request.from.map(Ok).unwrap_or_else(|| {
3098                            self.accounts()?
3099                                .first()
3100                                .copied()
3101                                .ok_or(BlockchainError::NoSignerAvailable)
3102                        })?;
3103
3104                        // Get the nonce at the common block
3105                        let curr_nonce = nonces.entry(from).or_insert(
3106                            self.get_transaction_count(
3107                                from,
3108                                Some(common_block.header.number().into()),
3109                            )
3110                            .await?,
3111                        );
3112
3113                        // Build typed transaction request
3114                        let typed_tx = self.build_tx_request(request.into(), *curr_nonce).await?;
3115
3116                        // Increment nonce
3117                        *curr_nonce += 1;
3118
3119                        // Handle signer and convert to pending transaction
3120                        if self.is_impersonated(from) {
3121                            let transaction = sign::build_impersonated(typed_tx);
3122                            self.ensure_typed_transaction_supported(&transaction)?;
3123                            PendingTransaction::with_impersonated(transaction, from)
3124                        } else {
3125                            let transaction = self.sign_request(&from, typed_tx)?;
3126                            self.ensure_typed_transaction_supported(&transaction)?;
3127                            PendingTransaction::new(transaction)?
3128                        }
3129                    }
3130                };
3131
3132                let pooled = PoolTransaction::new(pending);
3133                txs.entry(block_index).or_default().push(Arc::new(pooled));
3134            }
3135
3136            txs
3137        };
3138
3139        self.backend.reorg(depth, block_pool_txs, common_block).await?;
3140        Ok(())
3141    }
3142
3143    /// Mine blocks, instantly.
3144    ///
3145    /// Handler for RPC call: `evm_mine`
3146    ///
3147    /// This will mine the blocks regardless of the configured mining mode.
3148    /// **Note**: ganache returns `0x0` here as placeholder for additional meta-data in the future.
3149    pub async fn evm_mine(&self, opts: Option<MineOptions>) -> Result<String> {
3150        node_info!("evm_mine");
3151
3152        self.do_evm_mine(opts).await?;
3153
3154        Ok("0x0".to_string())
3155    }
3156
3157    /// Mine blocks, instantly and return the mined blocks.
3158    ///
3159    /// Handler for RPC call: `evm_mine_detailed`
3160    ///
3161    /// This will mine the blocks regardless of the configured mining mode.
3162    ///
3163    /// **Note**: This behaves exactly as [Self::evm_mine] but returns different output, for
3164    /// compatibility reasons, this is a separate call since `evm_mine` is not an anvil original.
3165    /// and `ganache` may change the `0x0` placeholder.
3166    pub async fn evm_mine_detailed(&self, opts: Option<MineOptions>) -> Result<Vec<AnyRpcBlock>> {
3167        node_info!("evm_mine_detailed");
3168
3169        let mined_blocks = self.do_evm_mine(opts).await?;
3170
3171        let mut blocks = Vec::with_capacity(mined_blocks as usize);
3172
3173        let latest = self.backend.best_number();
3174        for offset in (0..mined_blocks).rev() {
3175            let block_num = latest - offset;
3176            if let Some(mut block) =
3177                self.backend.block_by_number_full(BlockNumber::Number(block_num)).await?
3178            {
3179                let block_txs = match block.transactions_mut() {
3180                    BlockTransactions::Full(txs) => txs,
3181                    BlockTransactions::Hashes(_) | BlockTransactions::Uncle => unreachable!(),
3182                };
3183                for tx in block_txs.iter_mut() {
3184                    if let Some(receipt) = self.backend.mined_transaction_receipt(tx.tx_hash())
3185                        && let Some(output) = receipt.out
3186                    {
3187                        // insert revert reason if failure
3188                        if !receipt.inner.as_ref().status()
3189                            && let Some(reason) = RevertDecoder::new().maybe_decode(&output, None)
3190                        {
3191                            tx.other.insert(
3192                                "revertReason".to_string(),
3193                                serde_json::to_value(reason).expect("Infallible"),
3194                            );
3195                        }
3196                        tx.other.insert(
3197                            "output".to_string(),
3198                            serde_json::to_value(output).expect("Infallible"),
3199                        );
3200                    }
3201                }
3202                block.transactions = BlockTransactions::Full(block_txs.clone());
3203                blocks.push(block);
3204            }
3205        }
3206
3207        Ok(blocks)
3208    }
3209
3210    /// Execute a transaction regardless of signature status
3211    ///
3212    /// Handler for ETH RPC call: `eth_sendUnsignedTransaction`
3213    pub async fn eth_send_unsigned_transaction(
3214        &self,
3215        request: WithOtherFields<TransactionRequest>,
3216    ) -> Result<TxHash> {
3217        node_info!("eth_sendUnsignedTransaction");
3218        // either use the impersonated account of the request's `from` field
3219        let from = request.from.ok_or(BlockchainError::NoSignerAvailable)?;
3220
3221        let (nonce, on_chain_nonce) = self.request_nonce(&request, from).await?;
3222
3223        let typed_tx = self.build_tx_request(request, nonce).await?;
3224
3225        let transaction = sign::build_impersonated(typed_tx);
3226
3227        self.ensure_typed_transaction_supported(&transaction)?;
3228
3229        let pending_transaction = PendingTransaction::with_impersonated(transaction, from);
3230
3231        // pre-validate
3232        self.backend.validate_pool_transaction(&pending_transaction).await?;
3233
3234        let (requires, provides) = if let Some((requires, provides)) =
3235            tempo_parallel_nonce_markers(&pending_transaction)
3236        {
3237            (requires, provides)
3238        } else {
3239            (required_marker(nonce, on_chain_nonce, from), vec![to_marker(nonce, from)])
3240        };
3241
3242        self.add_pending_transaction(pending_transaction, requires, provides)
3243    }
3244
3245    /// Returns a summary of all the transactions currently pending for inclusion in the next
3246    /// block(s), as well as the ones that are being scheduled for future execution only.
3247    ///
3248    /// See [here](https://geth.ethereum.org/docs/rpc/ns-txpool#txpool_inspect) for more details
3249    ///
3250    /// Handler for ETH RPC call: `txpool_inspect`
3251    pub async fn txpool_inspect(&self) -> Result<TxpoolInspect> {
3252        node_info!("txpool_inspect");
3253        let mut inspect = TxpoolInspect::default();
3254
3255        fn convert(tx: Arc<PoolTransaction<FoundryTxEnvelope>>) -> TxpoolInspectSummary {
3256            let tx = &tx.pending_transaction.transaction;
3257            let to = tx.to();
3258            let gas_price = tx.max_fee_per_gas();
3259            let value = tx.value();
3260            let gas = tx.gas_limit();
3261            TxpoolInspectSummary { to, value, gas, gas_price }
3262        }
3263
3264        // Note: naming differs geth vs anvil:
3265        //
3266        // _Pending transactions_ are transactions that are ready to be processed and included in
3267        // the block. _Queued transactions_ are transactions where the transaction nonce is
3268        // not in sequence. The transaction nonce is an incrementing number for each transaction
3269        // with the same From address.
3270        for pending in self.pool.ready_transactions() {
3271            let entry = inspect.pending.entry(*pending.pending_transaction.sender()).or_default();
3272            let key = txpool_transaction_key(&pending.pending_transaction);
3273            entry.insert(key, convert(pending));
3274        }
3275        for queued in self.pool.pending_transactions() {
3276            let entry = inspect.queued.entry(*queued.pending_transaction.sender()).or_default();
3277            let key = txpool_transaction_key(&queued.pending_transaction);
3278            entry.insert(key, convert(queued));
3279        }
3280        Ok(inspect)
3281    }
3282
3283    /// Returns the details of all transactions currently pending for inclusion in the next
3284    /// block(s), as well as the ones that are being scheduled for future execution only.
3285    ///
3286    /// See [here](https://geth.ethereum.org/docs/rpc/ns-txpool#txpool_content) for more details
3287    ///
3288    /// Handler for ETH RPC call: `txpool_inspect`
3289    pub async fn txpool_content(&self) -> Result<TxpoolContent<AnyRpcTransaction>> {
3290        node_info!("txpool_content");
3291        let mut content = TxpoolContent::<AnyRpcTransaction>::default();
3292        fn convert(tx: Arc<PoolTransaction<FoundryTxEnvelope>>) -> Result<AnyRpcTransaction> {
3293            let from = *tx.pending_transaction.sender();
3294            let tx = transaction_build(
3295                Some(tx.hash()),
3296                tx.pending_transaction.transaction.clone(),
3297                None,
3298                None,
3299                None,
3300            );
3301
3302            let WithOtherFields { inner: mut tx, other } = tx.0;
3303
3304            // we set the from field here explicitly to the set sender of the pending transaction,
3305            // in case the transaction is impersonated.
3306            tx.inner = Recovered::new_unchecked(tx.inner.into_inner(), from);
3307
3308            let tx = AnyRpcTransaction(WithOtherFields { inner: tx, other });
3309
3310            Ok(tx)
3311        }
3312
3313        for pending in self.pool.ready_transactions() {
3314            let entry = content.pending.entry(*pending.pending_transaction.sender()).or_default();
3315            let key = txpool_transaction_key(&pending.pending_transaction);
3316            entry.insert(key, convert(pending)?);
3317        }
3318        for queued in self.pool.pending_transactions() {
3319            let entry = content.queued.entry(*queued.pending_transaction.sender()).or_default();
3320            let key = txpool_transaction_key(&queued.pending_transaction);
3321            entry.insert(key, convert(queued)?);
3322        }
3323
3324        Ok(content)
3325    }
3326}
3327
3328impl EthApi<FoundryNetwork> {
3329    /// Executes the `evm_mine` and returns the number of blocks mined
3330    async fn do_evm_mine(&self, opts: Option<MineOptions>) -> Result<u64> {
3331        let mut blocks_to_mine = 1u64;
3332
3333        if let Some(opts) = opts {
3334            let timestamp = match opts {
3335                MineOptions::Timestamp(timestamp) => timestamp,
3336                MineOptions::Options { timestamp, blocks } => {
3337                    if let Some(blocks) = blocks {
3338                        blocks_to_mine = blocks;
3339                    }
3340                    timestamp
3341                }
3342            };
3343            if let Some(timestamp) = timestamp {
3344                // timestamp was explicitly provided to be the next timestamp
3345                self.evm_set_next_block_timestamp(timestamp)?;
3346            }
3347        }
3348
3349        // this can be blocking for a bit, especially in forking mode
3350        // <https://github.com/foundry-rs/foundry/issues/6036>
3351        self.on_blocking_task(|this| async move {
3352            // mine all the blocks
3353            for _ in 0..blocks_to_mine {
3354                this.mine_one().await;
3355            }
3356            Ok(())
3357        })
3358        .await?;
3359
3360        Ok(blocks_to_mine)
3361    }
3362
3363    async fn do_estimate_gas(
3364        &self,
3365        request: WithOtherFields<TransactionRequest>,
3366        block_number: Option<BlockId>,
3367        overrides: EvmOverrides,
3368    ) -> Result<u128> {
3369        let block_request = self.block_request(block_number).await?;
3370        // check if the number predates the fork, if in fork mode
3371        if let BlockRequest::Number(number) = block_request
3372            && let Some(fork) = self.get_fork()
3373            && fork.predates_fork(number)
3374        {
3375            if overrides.has_state() || overrides.has_block() {
3376                return Err(BlockchainError::EvmOverrideError(
3377                    "not available on past forked blocks".to_string(),
3378                ));
3379            }
3380            return Ok(fork.estimate_gas(&request, Some(number.into())).await?);
3381        }
3382
3383        // this can be blocking for a bit, especially in forking mode
3384        // <https://github.com/foundry-rs/foundry/issues/6036>
3385        self.on_blocking_task(|this| async move {
3386            this.backend
3387                .with_database_at(Some(block_request), |state, mut block| {
3388                    let mut cache_db = CacheDB::new(state);
3389                    if let Some(state_overrides) = overrides.state {
3390                        apply_state_overrides(
3391                            state_overrides.into_iter().collect(),
3392                            &mut cache_db,
3393                        )?;
3394                    }
3395                    if let Some(block_overrides) = overrides.block {
3396                        cache_db.apply_block_overrides(*block_overrides, &mut block);
3397                    }
3398                    this.do_estimate_gas_with_state(request, &cache_db, block)
3399                })
3400                .await?
3401        })
3402        .await
3403    }
3404
3405    /// Returns the priority of the transaction based on the current `TransactionOrder`
3406    fn transaction_priority(&self, tx: &FoundryTxEnvelope) -> TransactionPriority {
3407        self.transaction_order.read().priority(tx)
3408    }
3409
3410    /// Returns a listener for pending transactions, yielding full transactions
3411    pub fn full_pending_transactions(&self) -> UnboundedReceiver<AnyRpcTransaction> {
3412        let (tx, rx) = unbounded_channel();
3413        let mut hashes = self.new_ready_transactions();
3414
3415        let this = self.clone();
3416
3417        tokio::spawn(async move {
3418            while let Some(hash) = hashes.next().await {
3419                if let Ok(Some(txn)) = this.transaction_by_hash(hash).await
3420                    && tx.send(txn).is_err()
3421                {
3422                    break;
3423                }
3424            }
3425        });
3426
3427        rx
3428    }
3429
3430    /// Mines exactly one block
3431    pub async fn mine_one(&self) {
3432        let transactions = self.pool.ready_transactions().collect::<Vec<_>>();
3433        let outcome = self.backend.mine_block(transactions).await;
3434
3435        trace!(target: "node", blocknumber = ?outcome.block_number, "mined block");
3436        self.pool.on_mined_block(outcome);
3437    }
3438
3439    /// Returns the pending block with tx hashes
3440    async fn pending_block(&self) -> AnyRpcBlock {
3441        let transactions = self.pool.ready_transactions().collect::<Vec<_>>();
3442        let info = self.backend.pending_block(transactions).await;
3443        self.backend.convert_block(info.block)
3444    }
3445
3446    /// Returns the full pending block with `Transaction` objects
3447    async fn pending_block_full(&self) -> Option<AnyRpcBlock> {
3448        let transactions = self.pool.ready_transactions().collect::<Vec<_>>();
3449        let BlockInfo { block, transactions, receipts: _ } =
3450            self.backend.pending_block(transactions).await;
3451
3452        let mut partial_block = self.backend.convert_block(block.clone());
3453
3454        let mut block_transactions = Vec::with_capacity(block.body.transactions.len());
3455        let base_fee = self.backend.base_fee();
3456
3457        for info in transactions {
3458            let tx = block.body.transactions.get(info.transaction_index as usize)?.clone();
3459
3460            let tx = transaction_build(
3461                Some(info.transaction_hash),
3462                tx,
3463                Some(&block),
3464                Some(info),
3465                Some(base_fee),
3466            );
3467            block_transactions.push(tx);
3468        }
3469
3470        partial_block.transactions = BlockTransactions::from(block_transactions);
3471
3472        Some(partial_block)
3473    }
3474
3475    /// Prepares transaction request by filling missing fields using Anvil's API, then attempts
3476    /// to build a [`FoundryTypedTx`].
3477    async fn build_tx_request(
3478        &self,
3479        request: WithOtherFields<TransactionRequest>,
3480        nonce: u64,
3481    ) -> Result<FoundryTypedTx> {
3482        let mut request = Into::<FoundryTransactionRequest>::into(request);
3483        let from = request.from().or(self.accounts()?.first().copied());
3484        if let Some(from) = from {
3485            request.set_from(from);
3486        }
3487
3488        // Fill common fields for all tx types
3489        request.chain_id().is_none().then(|| request.set_chain_id(self.chain_id()));
3490        request.nonce().is_none().then(|| request.set_nonce(nonce));
3491        request.kind().is_none().then(|| request.set_kind(TxKind::default()));
3492        if request.gas_limit().is_none() {
3493            let fallback_gas_limit = {
3494                let evm_env = self.backend.evm_env().read();
3495                let block_gas_limit = evm_env.block_env.gas_limit;
3496                if evm_env.cfg_env.tx_gas_limit_cap.is_none() {
3497                    block_gas_limit.min(evm_env.cfg_env().tx_gas_limit_cap())
3498                } else {
3499                    block_gas_limit
3500                }
3501            };
3502            let estimated_gas = self
3503                .do_estimate_gas(request.as_ref().clone().into(), None, EvmOverrides::default())
3504                .await
3505                .map(|v| v as u64)
3506                .unwrap_or_else(|_| {
3507                    if is_simple_transfer_request(request.as_ref()) {
3508                        MIN_TRANSACTION_GAS as u64
3509                    } else {
3510                        fallback_gas_limit
3511                    }
3512                });
3513            request.set_gas_limit(estimated_gas);
3514        }
3515
3516        // Fill missing tx type specific fields
3517        if let Err((tx_type, _)) = request.missing_keys() {
3518            if matches!(tx_type, FoundryTxType::Legacy | FoundryTxType::Eip2930) {
3519                request.gas_price().is_none().then(|| request.set_gas_price(self.gas_price()));
3520            }
3521            if tx_type == FoundryTxType::Eip2930 {
3522                request
3523                    .access_list()
3524                    .is_none()
3525                    .then(|| request.set_access_list(Default::default()));
3526            }
3527            if matches!(
3528                tx_type,
3529                FoundryTxType::Eip1559
3530                    | FoundryTxType::Eip4844
3531                    | FoundryTxType::Eip7702
3532                    | FoundryTxType::Tempo
3533            ) {
3534                request
3535                    .max_fee_per_gas()
3536                    .is_none()
3537                    .then(|| request.set_max_fee_per_gas(self.gas_price()));
3538                request
3539                    .max_priority_fee_per_gas()
3540                    .is_none()
3541                    .then(|| request.set_max_priority_fee_per_gas(MIN_SUGGESTED_PRIORITY_FEE));
3542            }
3543            if tx_type == FoundryTxType::Eip4844 {
3544                request.as_ref().max_fee_per_blob_gas().is_none().then(|| {
3545                    request.as_mut().set_max_fee_per_blob_gas(
3546                        self.backend.fees().get_next_block_blob_base_fee_per_gas(),
3547                    )
3548                });
3549            }
3550        }
3551
3552        match request
3553            .build_unsigned()
3554            .map_err(|e| BlockchainError::InvalidTransactionRequest(e.to_string()))?
3555        {
3556            FoundryTypedTx::Eip4844(TxEip4844Variant::TxEip4844(_))
3557                if !self.backend.skip_blob_validation(from) =>
3558            {
3559                // If blob validation is not skipped, reject TxEip4844 variant without sidecar.
3560                Err(BlockchainError::FailedToDecodeTransaction)
3561            }
3562            res => Ok(res),
3563        }
3564    }
3565
3566    /// Returns the nonce of the `address` depending on the `block_number`
3567    async fn get_transaction_count(
3568        &self,
3569        address: Address,
3570        block_number: Option<BlockId>,
3571    ) -> Result<u64> {
3572        let block_request = self.block_request(block_number).await?;
3573
3574        if let BlockRequest::Number(number) = block_request
3575            && let Some(fork) = self.get_fork()
3576            && fork.predates_fork(number)
3577        {
3578            return Ok(fork.get_nonce(address, number).await?);
3579        }
3580
3581        self.backend.get_nonce(address, block_request).await
3582    }
3583
3584    /// Returns the nonce for this request
3585    ///
3586    /// This returns a tuple of `(request nonce, highest nonce)`
3587    /// If the nonce field of the `request` is `None` then the tuple will be `(highest nonce,
3588    /// highest nonce)`.
3589    ///
3590    /// This will also check the tx pool for pending transactions from the sender.
3591    async fn request_nonce(
3592        &self,
3593        request: &TransactionRequest,
3594        from: Address,
3595    ) -> Result<(u64, u64)> {
3596        let highest_nonce =
3597            self.get_transaction_count(from, Some(BlockId::Number(BlockNumber::Pending))).await?;
3598        let nonce = request.nonce.unwrap_or(highest_nonce);
3599
3600        Ok((nonce, highest_nonce))
3601    }
3602
3603    /// Adds the given transaction to the pool
3604    fn add_pending_transaction(
3605        &self,
3606        pending_transaction: PendingTransaction<FoundryTxEnvelope>,
3607        requires: Vec<TxMarker>,
3608        provides: Vec<TxMarker>,
3609    ) -> Result<TxHash> {
3610        debug_assert!(requires != provides);
3611        let from = *pending_transaction.sender();
3612        let priority = self.transaction_priority(&pending_transaction.transaction);
3613        let pool_transaction =
3614            PoolTransaction { requires, provides, pending_transaction, priority };
3615        let tx = self.pool.add_transaction(pool_transaction)?;
3616        trace!(target: "node", "Added transaction: [{:?}] sender={:?}", tx.hash(), from);
3617        Ok(*tx.hash())
3618    }
3619
3620    /// additional validation against hardfork
3621    fn ensure_typed_transaction_supported(&self, tx: &FoundryTxEnvelope) -> Result<()> {
3622        match &tx {
3623            FoundryTxEnvelope::Eip2930(_) => self.backend.ensure_eip2930_active(),
3624            FoundryTxEnvelope::Eip1559(_) => self.backend.ensure_eip1559_active(),
3625            FoundryTxEnvelope::Eip4844(_) => self.backend.ensure_eip4844_active(),
3626            FoundryTxEnvelope::Eip7702(_) => self.backend.ensure_eip7702_active(),
3627            #[cfg(feature = "optimism")]
3628            FoundryTxEnvelope::Deposit(_) => self.backend.ensure_op_deposits_active(),
3629            #[cfg(feature = "optimism")]
3630            FoundryTxEnvelope::PostExec(_) => Err(BlockchainError::InvalidTransactionRequest(
3631                "not implemented for post-exec tx".to_string(),
3632            )),
3633            FoundryTxEnvelope::Legacy(_) => Ok(()),
3634            FoundryTxEnvelope::Tempo(_) => self.backend.ensure_tempo_active(),
3635        }
3636    }
3637
3638    /// Sets the fee token for a user address.
3639    ///
3640    /// Handler for RPC call: `anvil_setFeeToken`
3641    ///
3642    /// Only supported when running in Tempo mode (`--tempo`).
3643    pub async fn anvil_set_fee_token(&self, user: Address, token: Address) -> Result<()> {
3644        node_info!("anvil_setFeeToken");
3645        if !self.backend.is_tempo() {
3646            return Err(BlockchainError::RpcUnimplemented);
3647        }
3648        self.backend.set_fee_token(user, token).await?;
3649        Ok(())
3650    }
3651
3652    /// Sets the fee token for a validator address.
3653    ///
3654    /// Handler for RPC call: `anvil_setValidatorFeeToken`
3655    ///
3656    /// Only supported when running in Tempo mode (`--tempo`).
3657    pub async fn anvil_set_validator_fee_token(
3658        &self,
3659        validator: Address,
3660        token: Address,
3661    ) -> Result<()> {
3662        node_info!("anvil_setValidatorFeeToken");
3663        if !self.backend.is_tempo() {
3664            return Err(BlockchainError::RpcUnimplemented);
3665        }
3666        self.backend.set_validator_fee_token(validator, token).await?;
3667        Ok(())
3668    }
3669
3670    /// Mints FeeAMM liquidity for a token pair.
3671    ///
3672    /// Handler for RPC call: `anvil_setFeeAmmLiquidity`
3673    ///
3674    /// Only supported when running in Tempo mode (`--tempo`).
3675    pub async fn anvil_set_fee_amm_liquidity(
3676        &self,
3677        user_token: Address,
3678        validator_token: Address,
3679        amount: U256,
3680    ) -> Result<()> {
3681        node_info!("anvil_setFeeAmmLiquidity");
3682        if !self.backend.is_tempo() {
3683            return Err(BlockchainError::RpcUnimplemented);
3684        }
3685        self.backend.set_fee_amm_liquidity(user_token, validator_token, amount).await?;
3686        Ok(())
3687    }
3688}
3689
3690fn is_simple_transfer_request(request: &TransactionRequest) -> bool {
3691    request.to.as_ref().and_then(TxKind::to).is_some()
3692        && (request.input.input().is_none()
3693            || request.input.input().is_some_and(|data| data.is_empty()))
3694        && request.authorization_list.is_none()
3695        && request.access_list.is_none()
3696        && request.blob_versioned_hashes.is_none()
3697}
3698
3699fn required_marker(provided_nonce: u64, on_chain_nonce: u64, from: Address) -> Vec<TxMarker> {
3700    if provided_nonce == on_chain_nonce {
3701        return Vec::new();
3702    }
3703    let prev_nonce = provided_nonce.saturating_sub(1);
3704    if on_chain_nonce <= prev_nonce { vec![to_marker(prev_nonce, from)] } else { Vec::new() }
3705}
3706
3707fn tempo_parallel_nonce_markers(
3708    pending_transaction: &PendingTransaction<FoundryTxEnvelope>,
3709) -> Option<(Vec<TxMarker>, Vec<TxMarker>)> {
3710    // Tempo txs with non-zero nonce_key use a 2D nonce system and should not
3711    // be sequenced by account nonce markers.
3712    pending_transaction
3713        .transaction
3714        .as_ref()
3715        .has_nonzero_tempo_nonce_key()
3716        .then(|| (vec![], vec![pending_transaction.hash().to_vec()]))
3717}
3718
3719fn txpool_transaction_key(pending_transaction: &PendingTransaction<FoundryTxEnvelope>) -> String {
3720    match pending_transaction.transaction.as_ref() {
3721        FoundryTxEnvelope::Tempo(tx) if !tx.tx().nonce_key.is_zero() => {
3722            let tx = tx.tx();
3723            format!("{}:{}", tx.nonce_key, tx.nonce)
3724        }
3725        _ => pending_transaction.nonce().to_string(),
3726    }
3727}
3728
3729fn convert_transact_out(out: &Option<Output>) -> Bytes {
3730    match out {
3731        None => Default::default(),
3732        Some(Output::Call(out)) => out.to_vec().into(),
3733        Some(Output::Create(out, _)) => out.to_vec().into(),
3734    }
3735}
3736
3737/// Returns an error if the `exit` code is _not_ ok
3738fn ensure_return_ok(exit: InstructionResult, out: &Option<Output>) -> Result<Bytes> {
3739    let out = convert_transact_out(out);
3740    match exit {
3741        return_ok!() => Ok(out),
3742        return_revert!() => Err(InvalidTransactionError::Revert(Some(out)).into()),
3743        reason => Err(BlockchainError::EvmError(reason)),
3744    }
3745}
3746
3747/// Maps an EVM exit code to the optional `error` string reported in
3748/// `eth_createAccessList` results.
3749fn execution_error(exit: InstructionResult) -> Option<String> {
3750    match SuccessOrHalt::<HaltReason>::from(exit) {
3751        SuccessOrHalt::Success(_) => None,
3752        SuccessOrHalt::Revert => Some("execution reverted".to_string()),
3753        SuccessOrHalt::Halt(reason) => Some(reason.to_string()),
3754        SuccessOrHalt::FatalExternalError => Some("fatal external error".to_string()),
3755        SuccessOrHalt::Internal(_) => Some("internal EVM error".to_string()),
3756    }
3757}
3758
3759/// Determines the minimum gas needed for a transaction depending on the transaction kind.
3760fn determine_base_gas_by_kind(request: &WithOtherFields<TransactionRequest>) -> u128 {
3761    match request.kind() {
3762        Some(TxKind::Call(_)) => {
3763            MIN_TRANSACTION_GAS
3764                + request.inner().authorization_list.as_ref().map_or(0, |auths_list| {
3765                    auths_list.len() as u128 * PER_EMPTY_ACCOUNT_COST as u128
3766                })
3767        }
3768        Some(TxKind::Create) => MIN_CREATE_GAS,
3769        // Tighten the gas limit upwards if we don't know the tx kind to avoid deployments failing.
3770        None => MIN_CREATE_GAS,
3771    }
3772}
3773
3774/// Keeps result of a call to revm EVM used for gas estimation
3775enum GasEstimationCallResult {
3776    Success(u128),
3777    OutOfGas,
3778    Revert(Option<Bytes>),
3779    EvmError(InstructionResult),
3780}
3781
3782/// Converts the result of a call to revm EVM into a [`GasEstimationCallResult`].
3783///
3784/// Expected to stay up to date with: <https://github.com/bluealloy/revm/blob/main/crates/interpreter/src/instruction_result.rs>
3785impl TryFrom<Result<(InstructionResult, Option<Output>, u128, State)>> for GasEstimationCallResult {
3786    type Error = BlockchainError;
3787
3788    fn try_from(res: Result<(InstructionResult, Option<Output>, u128, State)>) -> Result<Self> {
3789        match res {
3790            // Exceptional case: init used too much gas, treated as out of gas error
3791            Err(BlockchainError::InvalidTransaction(InvalidTransactionError::GasTooHigh(_))) => {
3792                Ok(Self::OutOfGas)
3793            }
3794            // Tempo intrinsic gas errors come through as Message variants
3795            Err(BlockchainError::Message(ref msg))
3796                if msg.contains("insufficient gas for intrinsic cost") =>
3797            {
3798                Ok(Self::OutOfGas)
3799            }
3800            Err(err) => Err(err),
3801            Ok((exit, output, gas, _)) => match exit {
3802                return_ok!() => Ok(Self::Success(gas)),
3803
3804                // Revert opcodes:
3805                InstructionResult::Revert => {
3806                    Ok(Self::Revert(Some(output.map(|o| o.into_data()).unwrap_or_default())))
3807                }
3808                InstructionResult::CallTooDeep
3809                | InstructionResult::OutOfFunds
3810                | InstructionResult::CreateInitCodeStartingEF00
3811                | InstructionResult::InvalidEOFInitCode
3812                | InstructionResult::InvalidExtDelegateCallTarget => Ok(Self::EvmError(exit)),
3813
3814                // Out of gas errors:
3815                InstructionResult::OutOfGas
3816                | InstructionResult::MemoryOOG
3817                | InstructionResult::MemoryLimitOOG
3818                | InstructionResult::PrecompileOOG
3819                | InstructionResult::InvalidOperandOOG
3820                | InstructionResult::ReentrancySentryOOG => Ok(Self::OutOfGas),
3821
3822                // Other errors:
3823                InstructionResult::OpcodeNotFound
3824                | InstructionResult::CallNotAllowedInsideStatic
3825                | InstructionResult::StateChangeDuringStaticCall
3826                | InstructionResult::InvalidFEOpcode
3827                | InstructionResult::InvalidJump
3828                | InstructionResult::NotActivated
3829                | InstructionResult::StackUnderflow
3830                | InstructionResult::StackOverflow
3831                | InstructionResult::OutOfOffset
3832                | InstructionResult::CreateCollision
3833                | InstructionResult::OverflowPayment
3834                | InstructionResult::PrecompileError
3835                | InstructionResult::NonceOverflow
3836                | InstructionResult::CreateContractSizeLimit
3837                | InstructionResult::CreateContractStartingWithEF
3838                | InstructionResult::CreateInitCodeSizeLimit
3839                | InstructionResult::InvalidImmediateEncoding
3840                | InstructionResult::FatalExternalError => Ok(Self::EvmError(exit)),
3841            },
3842        }
3843    }
3844}