diff --git a/CHANGELOG.md b/CHANGELOG.md index 6f42d7dac..5654a91cd 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -47,6 +47,8 @@ and this project adheres to [Semantic Versioning]. - The helper function `evmc_is_abi_compatible()` returns now `bool` instead of `int`. [[#442](https://github.com/ethereum/evmc/pull/442)] +- In the Rust bindings make `ExecutionContext` optional within `execute`. + [[#350](https://github.com/ethereum/evmc/pull/350)] ## [6.3.1] - 2019-08-19 diff --git a/bindings/rust/evmc-declare-tests/src/lib.rs b/bindings/rust/evmc-declare-tests/src/lib.rs index a2ef12e98..8640d4fcf 100644 --- a/bindings/rust/evmc-declare-tests/src/lib.rs +++ b/bindings/rust/evmc-declare-tests/src/lib.rs @@ -22,7 +22,7 @@ impl EvmcVm for FooVM { _revision: evmc_sys::evmc_revision, _code: &[u8], _message: &ExecutionMessage, - _context: &mut ExecutionContext, + _context: Option<&mut ExecutionContext>, ) -> ExecutionResult { ExecutionResult::success(1337, None) } diff --git a/bindings/rust/evmc-declare/src/lib.rs b/bindings/rust/evmc-declare/src/lib.rs index 506a2ce64..9e4bc0198 100644 --- a/bindings/rust/evmc-declare/src/lib.rs +++ b/bindings/rust/evmc-declare/src/lib.rs @@ -22,7 +22,7 @@ //! ExampleVM {} //! } //! -//! fn execute(&self, revision: evmc_vm::ffi::evmc_revision, code: &[u8], message: &evmc_vm::ExecutionMessage, context: &mut evmc_vm::ExecutionContext) -> evmc_vm::ExecutionResult { +//! fn execute(&self, revision: evmc_vm::ffi::evmc_revision, code: &[u8], message: &evmc_vm::ExecutionMessage, context: Option<&mut evmc_vm::ExecutionContext>) -> evmc_vm::ExecutionResult { //! evmc_vm::ExecutionResult::success(1337, None) //! } //! } @@ -346,14 +346,12 @@ fn build_execute_fn(names: &VMNameSet) -> proc_macro2::TokenStream { use evmc_vm::EvmcVm; // TODO: context is optional in case of the "precompiles" capability - if instance.is_null() || host.is_null() || msg.is_null() || (code.is_null() && code_size != 0) { + if instance.is_null() || msg.is_null() || (code.is_null() && code_size != 0) { // These are irrecoverable errors that violate the EVMC spec. std::process::abort(); } assert!(!instance.is_null()); - // TODO: host is optional in case of the "precompiles" capability - assert!(!host.is_null()); assert!(!msg.is_null()); let execution_message: ::evmc_vm::ExecutionMessage = unsafe { @@ -376,13 +374,17 @@ fn build_execute_fn(names: &VMNameSet) -> proc_macro2::TokenStream { }; let result = ::std::panic::catch_unwind(|| { - let mut execution_context = unsafe { - ::evmc_vm::ExecutionContext::new( - host.as_ref().expect("EVMC host is null"), - context, - ) - }; - container.execute(revision, code_ref, &execution_message, &mut execution_context) + if host.is_null() { + container.execute(revision, code_ref, &execution_message, None) + } else { + let mut execution_context = unsafe { + ::evmc_vm::ExecutionContext::new( + host.as_ref().expect("EVMC host is null"), + context, + ) + }; + container.execute(revision, code_ref, &execution_message, Some(&mut execution_context)) + } }); let result = if result.is_err() { diff --git a/bindings/rust/evmc-vm/src/container.rs b/bindings/rust/evmc-vm/src/container.rs index 4155d36be..136cb8765 100644 --- a/bindings/rust/evmc-vm/src/container.rs +++ b/bindings/rust/evmc-vm/src/container.rs @@ -69,7 +69,7 @@ mod tests { _revision: evmc_sys::evmc_revision, _code: &[u8], _message: &ExecutionMessage, - _context: &mut ExecutionContext, + _context: Option<&mut ExecutionContext>, ) -> ExecutionResult { ExecutionResult::failure() } @@ -142,7 +142,7 @@ mod tests { evmc_sys::evmc_revision::EVMC_PETERSBURG, &code, &message, - &mut context, + Some(&mut context) ) .status_code(), ::evmc_sys::evmc_status_code::EVMC_FAILURE @@ -158,7 +158,7 @@ mod tests { evmc_sys::evmc_revision::EVMC_PETERSBURG, &code, &message, - &mut context, + Some(&mut context) ) .status_code(), ::evmc_sys::evmc_status_code::EVMC_FAILURE diff --git a/bindings/rust/evmc-vm/src/lib.rs b/bindings/rust/evmc-vm/src/lib.rs index e14a91d33..6f604e000 100644 --- a/bindings/rust/evmc-vm/src/lib.rs +++ b/bindings/rust/evmc-vm/src/lib.rs @@ -25,7 +25,7 @@ pub trait EvmcVm { revision: ffi::evmc_revision, code: &'a [u8], message: &'a ExecutionMessage, - context: &'a mut ExecutionContext<'a>, + context: Option<&'a mut ExecutionContext<'a>>, ) -> ExecutionResult; } diff --git a/examples/example-rust-vm/src/lib.rs b/examples/example-rust-vm/src/lib.rs index 360460a1f..09464808a 100644 --- a/examples/example-rust-vm/src/lib.rs +++ b/examples/example-rust-vm/src/lib.rs @@ -6,7 +6,7 @@ use evmc_declare::evmc_declare_vm; use evmc_vm::*; -#[evmc_declare_vm("ExampleRustVM", "evm", "6.3.0-dev")] +#[evmc_declare_vm("ExampleRustVM", "evm, precompiles", "6.3.0-dev")] pub struct ExampleRustVM; impl EvmcVm for ExampleRustVM { @@ -19,8 +19,13 @@ impl EvmcVm for ExampleRustVM { _revision: evmc_sys::evmc_revision, _code: &'a [u8], message: &'a ExecutionMessage, - _context: &'a mut ExecutionContext<'a>, + _context: Option<&'a mut ExecutionContext<'a>>, ) -> ExecutionResult { + if _context.is_none() { + return ExecutionResult::failure(); + } + let _context = _context.unwrap(); + if message.kind() != evmc_sys::evmc_call_kind::EVMC_CALL { return ExecutionResult::failure(); }