Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions crates/cast/bin/cmd/run.rs
Original file line number Diff line number Diff line change
Expand Up @@ -94,6 +94,10 @@ pub struct RunArgs {
/// Use current project artifacts for trace decoding.
#[arg(long, visible_alias = "la")]
pub with_local_artifacts: bool,

/// Skip transaction preverification (nonce etc.)
#[arg(long, visible_alias = "sp")]
pub skip_preverification: bool,
}

impl RunArgs {
Expand Down Expand Up @@ -181,6 +185,7 @@ impl RunArgs {
odyssey,
create2_deployer,
);
executor.set_skip_preverification(self.skip_preverification);
let mut env =
EnvWithHandlerCfg::new_with_spec_id(Box::new(env.clone()), executor.spec_id());

Expand Down
26 changes: 24 additions & 2 deletions crates/evm/core/src/backend/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -766,15 +766,37 @@ impl Backend {
&mut self,
env: &mut EnvWithHandlerCfg,
inspector: &mut I,
) -> eyre::Result<ResultAndState> {
self.inspect_inner(env, inspector, false)
}

/// Executes the configured test call of the `env` without committing state changes and
/// skipping transaction preverification.
#[instrument(name = "inspect", level = "debug", skip_all)]
pub fn inspect_preverified<I: InspectorExt>(
&mut self,
env: &mut EnvWithHandlerCfg,
inspector: &mut I,
) -> eyre::Result<ResultAndState> {
self.inspect_inner(env, inspector, true)
}

#[instrument(name = "inspect", level = "debug", skip_all)]
pub fn inspect_inner<I: InspectorExt>(
&mut self,
env: &mut EnvWithHandlerCfg,
inspector: &mut I,
skip_preverification: bool,
) -> eyre::Result<ResultAndState> {
self.initialize(env);
let mut evm = crate::utils::new_evm_with_inspector(self, env.clone(), inspector);

let res = evm.transact().wrap_err("EVM error")?;
let res = if skip_preverification { evm.transact_preverified() } else { evm.transact() };
let inner_res = res.wrap_err("EVM error")?;

env.env = evm.context.evm.inner.env;

Ok(res)
Ok(inner_res)
}

/// Returns true if the address is a precompile
Expand Down
21 changes: 19 additions & 2 deletions crates/evm/evm/src/executors/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -90,6 +90,8 @@ pub struct Executor {
gas_limit: u64,
/// Whether `failed()` should be called on the test contract to determine if the test failed.
legacy_assertions: bool,
/// skips transaction preverification
skip_preverification: bool,
}

impl Executor {
Expand Down Expand Up @@ -121,7 +123,7 @@ impl Executor {
},
);

Self { backend, env, inspector, gas_limit, legacy_assertions }
Self { backend, env, inspector, gas_limit, legacy_assertions, skip_preverification: false }
}

fn clone_with_backend(&self, backend: Backend) -> Self {
Expand Down Expand Up @@ -194,6 +196,16 @@ impl Executor {
self.legacy_assertions = legacy_assertions;
}

/// Returns whether preverification of transactions should be skipped
pub fn skip_preverification(&self) -> bool {
self.skip_preverification
}

/// Sets whether preverification of transactions should be skipped
pub fn set_skip_preverification(&mut self, skip_preverification: bool) {
self.skip_preverification = skip_preverification;
}

/// Creates the default CREATE2 Contract Deployer for local tests and scripts.
pub fn deploy_create2_deployer(&mut self) -> eyre::Result<()> {
trace!("deploying local create2 deployer");
Expand Down Expand Up @@ -451,8 +463,13 @@ impl Executor {
#[instrument(name = "transact", level = "debug", skip_all)]
pub fn transact_with_env(&mut self, mut env: EnvWithHandlerCfg) -> eyre::Result<RawCallResult> {
let mut inspector = self.inspector().clone();
let skip_preverification = self.skip_preverification;
let backend = self.backend_mut();
let result = backend.inspect(&mut env, &mut inspector)?;
let result = if skip_preverification {
backend.inspect_preverified(&mut env, &mut inspector)?
} else {
backend.inspect(&mut env, &mut inspector)?
};
let mut result =
convert_executed_result(env, inspector, result, backend.has_state_snapshot_failure())?;
self.commit(&mut result);
Expand Down