mod fill;
pub use fill::{SystemTx, DEFAULT_SYSTEM_CALLER};
pub mod eip2935;
pub mod eip4788;
pub mod eip4895;
pub mod eip6110;
pub mod eip7002;
pub mod eip7251;
pub const MAX_BLOB_GAS_PER_BLOCK_CANCUN: u64 = 786_432;
pub const MAX_BLOB_GAS_PER_BLOCK_PRAGUE: u64 = 1_179_648;
pub const MAX_BLOB_GAS_PER_BLOCK_OSAKA: u64 = 1_749_648;
use crate::{
helpers::{Ctx, Evm},
EvmExtUnchecked, Tx,
};
use alloy::primitives::{Address, Bytes};
use revm::{
bytecode::Bytecode,
context::{
result::{EVMError, ExecutionResult, ResultAndState},
Block, ContextTr, Transaction,
},
primitives::KECCAK_EMPTY,
Database, DatabaseCommit, InspectEvm, Inspector,
};
fn checked_insert_code<Db, Insp>(
evm: &mut Evm<Db, Insp>,
address: Address,
code: &Bytes,
) -> Result<(), EVMError<Db::Error>>
where
Db: Database + DatabaseCommit,
{
if evm.account(address).map_err(EVMError::Database)?.info.code_hash == KECCAK_EMPTY {
evm.set_bytecode(address, Bytecode::new_raw(code.clone())).map_err(EVMError::Database)?;
}
Ok(())
}
fn cleanup_syscall<Db, Insp>(
evm: &mut Evm<Db, Insp>,
result: &mut ResultAndState,
syscall: &SystemTx,
old_gas_limit: u64,
old_base_fee: u64,
previous_nonce_check: bool,
) where
Db: Database + DatabaseCommit,
{
let coinbase = evm.block().beneficiary();
evm.modify_block(|block| {
block.gas_limit = old_gas_limit;
block.basefee = old_base_fee;
});
evm.ctx.modify_cfg(|cfg| cfg.disable_nonce_check = previous_nonce_check);
let state = &mut result.state;
state.remove(&syscall.caller);
state.remove(&coinbase);
}
pub(crate) fn execute_system_tx<Db, Insp>(
evm: &mut Evm<Db, Insp>,
syscall: &SystemTx,
) -> Result<ExecutionResult, EVMError<Db::Error>>
where
Db: Database + DatabaseCommit,
Insp: Inspector<Ctx<Db>>,
{
syscall.fill_tx(evm);
let limit = evm.tx().gas_limit();
let block = &mut evm.ctx.block;
let old_gas_limit = core::mem::replace(&mut block.gas_limit, limit);
let old_base_fee = core::mem::take(&mut block.basefee);
let previous_nonce_check = std::mem::replace(&mut evm.ctx.cfg.disable_nonce_check, true);
let mut result = evm.inspect_tx(evm.tx().clone())?;
cleanup_syscall(evm, &mut result, syscall, old_gas_limit, old_base_fee, previous_nonce_check);
evm.ctx.db_mut().commit(result.state);
Ok(result.result)
}