Skip to main content

Call

Trait Call 

Source
pub trait Call: LoadState + SpawnBlocking
where Self::RpcConvert: RpcConvert<Evm = Self::Evm>, Self::Error: FromEvmError<Self::Evm> + From<<Self::RpcConvert as RpcConvert>::Error> + From<ProviderError>,
{
Show 16 methods // Provided methods fn call_gas_limit(&self) -> u64 { ... } fn max_simulate_blocks(&self) -> u64 { ... } fn compute_state_root_for_eth_simulate(&self) -> bool { ... } fn evm_memory_limit(&self) -> u64 { ... } fn simulate_call_nonce( &self, _request: &<<Self::RpcConvert as RpcConvert>::Network as RpcTypes>::TransactionRequest, _db: &mut dyn DynDatabase, ) -> Result<Option<u64>, EthApiError> { ... } fn caller_gas_allowance( &self, db: impl Database>, _evm_env: &<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmEnv, tx_env: &Recovered<<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes as EvmTypesHost>::Tx>, ) -> Result<u64, Self::Error> where <impl Database as Database>::Error: Into<EthApiError> { ... } fn transact<DB>( &self, db: DB, evm_env: <<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmEnv, tx_env: Recovered<<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes as EvmTypesHost>::Tx>, ) -> Result<TxResultWithState<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes>, Self::Error> where DB: Database + Debug { ... } fn transact_with_inspector<DB, I>( &self, db: DB, evm_env: <<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmEnv, tx_env: Recovered<<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes as EvmTypesHost>::Tx>, inspector: I, ) -> Result<(I, TxResultWithState<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes>), Self::Error> where DB: Database + Debug, I: Inspector<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes> + 'static { ... } fn transact_call_at( &self, request: <<Self::RpcConvert as RpcConvert>::Network as RpcTypes>::TransactionRequest, at: BlockId, overrides: EvmOverrides, ) -> impl Future<Output = Result<TxResultWithState<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes>, Self::Error>> + Send where Self: LoadPendingBlock { ... } fn spawn_with_state_at_block<F, R>( &self, at: impl Into<BlockId>, f: F, ) -> impl Future<Output = Result<R, Self::Error>> + Send where F: FnOnce(Self, CacheDB<Db<StateProviderDatabase<EvmStateProviderAdapter<Box<dyn StateProvider + Send>>>>>) -> Result<R, Self::Error> + Send + 'static, R: Send + 'static { ... } fn spawn_with_call_at<F, R>( &self, request: <<Self::RpcConvert as RpcConvert>::Network as RpcTypes>::TransactionRequest, at: BlockId, overrides: EvmOverrides, f: F, ) -> impl Future<Output = Result<R, Self::Error>> + Send where Self: LoadPendingBlock, F: FnOnce(&mut CacheDB<Db<StateProviderDatabase<EvmStateProviderAdapter<Box<dyn StateProvider + Send>>>>>, <<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmEnv, Recovered<<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes as EvmTypesHost>::Tx>) -> Result<R, Self::Error> + Send + 'static, R: Send + 'static { ... } fn spawn_replay_transaction<F, R>( &self, hash: FixedBytes<32>, f: F, ) -> impl Future<Output = Result<Option<R>, Self::Error>> + Send where Self: LoadBlock + LoadTransaction, F: FnOnce(TransactionInfo, TxResultWithState<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes>, CacheDB<Db<StateProviderDatabase<EvmStateProviderAdapter<Box<dyn StateProvider + Send>>>>>) -> Result<R, Self::Error> + Send + 'static, R: Send + 'static { ... } fn replay_transactions_until_with_executor<'a, Txs>( &self, executor: &mut <<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::Executor<'_>, transactions: Txs, target_tx_index: usize, ) -> Result<(), Self::Error> where Txs: IntoIterator<Item = Recovered<&'a <Self::Provider as TransactionsProvider>::Transaction>> { ... } fn block_executor<'a>( &'a self, block: &'a RecoveredBlock<<Self::Primitives as NodePrimitives>::Block>, db: &'a mut CacheDB<Db<StateProviderDatabase<EvmStateProviderAdapter<Box<dyn StateProvider + Send>>>>>, evm_env: <<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmEnv, ) -> Result<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::Executor<'a>, Self::Error> { ... } fn create_txn_env( &self, evm_env: &<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmEnv, request: <<Self::RpcConvert as RpcConvert>::Network as RpcTypes>::TransactionRequest, db: impl Database>, ) -> Result<Recovered<<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes as EvmTypesHost>::Tx>, Self::Error> where <impl Database as Database>::Error: Into<EthApiError> { ... } fn prepare_call_env<DB>( &self, evm_env: <<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmEnv, request: <<Self::RpcConvert as RpcConvert>::Network as RpcTypes>::TransactionRequest, db: &mut CacheDB<DB>, overrides: EvmOverrides, ) -> Result<(<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmEnv, Recovered<<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes as EvmTypesHost>::Tx>), Self::Error> where DB: DynDatabase { ... }
}
Expand description

Executes code on state.

Provided Methods§

Source

fn call_gas_limit(&self) -> u64

Returns default gas limit to use for eth_call and tracing RPC methods.

Data access in default trait method implementations.

Source

fn max_simulate_blocks(&self) -> u64

Returns the maximum number of blocks accepted for eth_simulateV1.

Source

fn compute_state_root_for_eth_simulate(&self) -> bool

Returns whether eth_simulateV1 should compute state roots.

Source

fn evm_memory_limit(&self) -> u64

Returns the maximum memory the EVM can allocate per RPC request.

Source

fn simulate_call_nonce( &self, _request: &<<Self::RpcConvert as RpcConvert>::Network as RpcTypes>::TransactionRequest, _db: &mut dyn DynDatabase, ) -> Result<Option<u64>, EthApiError>

Returns the nonce for an eth_simulateV1 call that has none.

db holds the simulation state before the call, including all earlier calls. None falls back to the sender’s account nonce, which suits networks with a single nonce per account.

Source

fn caller_gas_allowance( &self, db: impl Database>, _evm_env: &<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmEnv, tx_env: &Recovered<<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes as EvmTypesHost>::Tx>, ) -> Result<u64, Self::Error>
where <impl Database as Database>::Error: Into<EthApiError>,

Returns the max gas limit that the caller can afford given a transaction environment.

Source

fn transact<DB>( &self, db: DB, evm_env: <<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmEnv, tx_env: Recovered<<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes as EvmTypesHost>::Tx>, ) -> Result<TxResultWithState<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes>, Self::Error>
where DB: Database + Debug,

Executes the TxEnv against the given [Database] without committing state changes.

Source

fn transact_with_inspector<DB, I>( &self, db: DB, evm_env: <<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmEnv, tx_env: Recovered<<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes as EvmTypesHost>::Tx>, inspector: I, ) -> Result<(I, TxResultWithState<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes>), Self::Error>
where DB: Database + Debug, I: Inspector<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes> + 'static,

Executes the reth_evm::EvmEnv against the given [Database] without committing state changes.

Source

fn transact_call_at( &self, request: <<Self::RpcConvert as RpcConvert>::Network as RpcTypes>::TransactionRequest, at: BlockId, overrides: EvmOverrides, ) -> impl Future<Output = Result<TxResultWithState<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes>, Self::Error>> + Send
where Self: LoadPendingBlock,

Executes the call request at the given BlockId.

This spawns a new task that obtains the state for the given BlockId and then transacts the call Self::transact. If the future is dropped before the (blocking) transact call is invoked, then the task is cancelled early, (for example if the request is terminated early client-side).

Source

fn spawn_with_state_at_block<F, R>( &self, at: impl Into<BlockId>, f: F, ) -> impl Future<Output = Result<R, Self::Error>> + Send
where F: FnOnce(Self, CacheDB<Db<StateProviderDatabase<EvmStateProviderAdapter<Box<dyn StateProvider + Send>>>>>) -> Result<R, Self::Error> + Send + 'static, R: Send + 'static,

Executes the closure with the state that corresponds to the given BlockId on a new task

Source

fn spawn_with_call_at<F, R>( &self, request: <<Self::RpcConvert as RpcConvert>::Network as RpcTypes>::TransactionRequest, at: BlockId, overrides: EvmOverrides, f: F, ) -> impl Future<Output = Result<R, Self::Error>> + Send
where Self: LoadPendingBlock, F: FnOnce(&mut CacheDB<Db<StateProviderDatabase<EvmStateProviderAdapter<Box<dyn StateProvider + Send>>>>>, <<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmEnv, Recovered<<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes as EvmTypesHost>::Tx>) -> Result<R, Self::Error> + Send + 'static, R: Send + 'static,

Prepares the state and env for the given RpcTxReq at the given BlockId and executes the closure on a new task returning the result of the closure.

This returns the configured reth_evm::EvmEnv for the given RpcTxReq at the given BlockId and with configured call settings: prepare_call_env.

This is primarily used by eth_call.

§Blocking behaviour

This assumes executing the call is relatively more expensive on IO than CPU because it transacts a single transaction on an empty in memory database. Because eth_calls are usually allowed to consume a lot of gas, this also allows a lot of memory operations so we assume this is not primarily CPU bound and instead spawn the call on a regular tokio task instead, where blocking IO is less problematic.

Source

fn spawn_replay_transaction<F, R>( &self, hash: FixedBytes<32>, f: F, ) -> impl Future<Output = Result<Option<R>, Self::Error>> + Send
where Self: LoadBlock + LoadTransaction, F: FnOnce(TransactionInfo, TxResultWithState<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes>, CacheDB<Db<StateProviderDatabase<EvmStateProviderAdapter<Box<dyn StateProvider + Send>>>>>) -> Result<R, Self::Error> + Send + 'static, R: Send + 'static,

Retrieves the transaction if it exists and executes it.

Before the transaction is executed, the state is positioned right before the transaction, either by attaching the block’s cached BAL or by executing all previous transactions in the block. The transaction is executed through the block executor, see Call::block_executor. The callback f is invoked with the TxResultWithStateFor after the transaction was executed and the database that points to the beginning of the transaction. The database may have the block’s BAL attached and must only be used for reads, because an attached BAL takes read precedence over state committed on top, see attach_bal_before_tx.

Note: Implementers should use a threadpool where blocking is allowed, such as BlockingTaskPool.

Source

fn replay_transactions_until_with_executor<'a, Txs>( &self, executor: &mut <<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::Executor<'_>, transactions: Txs, target_tx_index: usize, ) -> Result<(), Self::Error>
where Txs: IntoIterator<Item = Recovered<&'a <Self::Provider as TransactionsProvider>::Transaction>>,

Replays all transactions before the target transaction index through the given executor.

If the target index is greater than or equal to the iterator length, all transactions are replayed.

Source

fn block_executor<'a>( &'a self, block: &'a RecoveredBlock<<Self::Primitives as NodePrimitives>::Block>, db: &'a mut CacheDB<Db<StateProviderDatabase<EvmStateProviderAdapter<Box<dyn StateProvider + Send>>>>>, evm_env: <<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmEnv, ) -> Result<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::Executor<'a>, Self::Error>

Creates a block executor for block on db with the given EVM environment.

Replaying a block’s own transactions through the executor rather than a bare EVM includes the changes the executor applies on top of each EVM result, so replayed results agree with the block’s receipts and state. The executor does not apply the block’s pre-execution changes: callers apply them to db first or position db with the block’s BAL, see attach_bal_before_tx.

Source

fn create_txn_env( &self, evm_env: &<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmEnv, request: <<Self::RpcConvert as RpcConvert>::Network as RpcTypes>::TransactionRequest, db: impl Database>, ) -> Result<Recovered<<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes as EvmTypesHost>::Tx>, Self::Error>
where <impl Database as Database>::Error: Into<EthApiError>,

All TxEnv fields are derived from the given RpcTxReq, if fields are None, they fall back to the reth_evm::EvmEnv’s settings.

Source

fn prepare_call_env<DB>( &self, evm_env: <<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmEnv, request: <<Self::RpcConvert as RpcConvert>::Network as RpcTypes>::TransactionRequest, db: &mut CacheDB<DB>, overrides: EvmOverrides, ) -> Result<(<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmEnv, Recovered<<<<Self::Evm as ConfigureEvm>::BlockExecutorFactory as BlockExecutorFactory>::EvmTypes as EvmTypesHost>::Tx>), Self::Error>
where DB: DynDatabase,

Prepares the reth_evm::EvmEnv for execution of calls.

Does not commit any changes to the underlying database.

§EVM settings

This modifies certain EVM settings to mirror geth’s SkipAccountChecks when transacting requests, see also: https://github.com/ethereum/go-ethereum/blob/380688c636a654becc8f114438c2a5d93d2db032/core/state_transition.go#L145-L148:

  • disable_eip3607 is set to true
  • disable_base_fee is set to true
  • nonce is set to None

In addition, this changes the block’s gas limit to the configured Self::call_gas_limit.

Dyn Compatibility§

This trait is not dyn compatible.

In older versions of Rust, dyn compatibility was called "object safety".

Implementors§

Source§

impl<N, Rpc> Call for EthApi<N, Rpc>
where EthApiError: FromEvmError<<N as RpcNodeCore>::Evm>, Rpc: RpcConvert<Primitives = <N as RpcNodeCore>::Primitives, Error = EthApiError, Evm = <N as RpcNodeCore>::Evm>, N: RpcNodeCore,