Allow single opcode stepping for EVM (#9051)

* Feed in ActionParams on VM creation

* Fix ethcore after Vm interface change

* Move informant inside Interpreter struct

* Move do_trace to Interpreter struct

* Move all remaining exec variables to Interpreter struct

* Refactor VM to allow single opcode step

* Fix all EVM tests

* Fix all wasm tests

* Fix wasm runner tests

* Fix a check case where code length is zero

* Fix jsontests compile

* Fix cargo lock

* Use match instead of expect

* Use cheaper check reader.len() == 0 for the initial special case

* Get rid of try_and_done! macro by using Result<(), ReturnType>

* Use Never instead of ()

* Fix parity-bytes path

* Bypass gasometer lifetime problem by borrow only for a instance

* typo: missing {

* Fix ethcore test compile

* Fix evm tests
This commit is contained in:
Wei Tang
2018-08-14 04:06:15 +08:00
committed by GitHub
parent 98dbd1fdc7
commit 9c595aff95
14 changed files with 574 additions and 446 deletions

View File

@@ -21,7 +21,7 @@ use std::sync::Arc;
use std::collections::{HashMap, HashSet};
use rustc_hex::FromHex;
use ethereum_types::{U256, H256, Address};
use vm::{self, ActionParams, ActionValue};
use vm::{self, ActionParams, ActionValue, Ext};
use vm::tests::{FakeExt, FakeCall, FakeCallType, test_finalize};
use factory::Factory;
use vmtype::VMType;
@@ -38,8 +38,8 @@ fn test_add(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_eq!(gas_left, U256::from(79_988));
@@ -58,8 +58,8 @@ fn test_sha3(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_eq!(gas_left, U256::from(79_961));
@@ -78,8 +78,8 @@ fn test_address(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_eq!(gas_left, U256::from(79_995));
@@ -100,8 +100,8 @@ fn test_origin(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_eq!(gas_left, U256::from(79_995));
@@ -122,8 +122,8 @@ fn test_sender(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_eq!(gas_left, U256::from(79_995));
@@ -157,8 +157,8 @@ fn test_extcodecopy(factory: super::Factory) {
ext.codes.insert(sender, Arc::new(sender_code));
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_eq!(gas_left, U256::from(79_935));
@@ -177,8 +177,8 @@ fn test_log_empty(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_eq!(gas_left, U256::from(99_619));
@@ -209,8 +209,8 @@ fn test_log_sender(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_eq!(gas_left, U256::from(98_974));
@@ -234,8 +234,8 @@ fn test_blockhash(factory: super::Factory) {
ext.blockhashes.insert(U256::zero(), blockhash.clone());
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_eq!(gas_left, U256::from(79_974));
@@ -256,8 +256,8 @@ fn test_calldataload(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_eq!(gas_left, U256::from(79_991));
@@ -277,8 +277,8 @@ fn test_author(factory: super::Factory) {
ext.info.author = author;
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_eq!(gas_left, U256::from(79_995));
@@ -297,8 +297,8 @@ fn test_timestamp(factory: super::Factory) {
ext.info.timestamp = timestamp;
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_eq!(gas_left, U256::from(79_995));
@@ -317,8 +317,8 @@ fn test_number(factory: super::Factory) {
ext.info.number = number;
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_eq!(gas_left, U256::from(79_995));
@@ -337,8 +337,8 @@ fn test_difficulty(factory: super::Factory) {
ext.info.difficulty = difficulty;
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_eq!(gas_left, U256::from(79_995));
@@ -357,8 +357,8 @@ fn test_gas_limit(factory: super::Factory) {
ext.info.gas_limit = gas_limit;
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_eq!(gas_left, U256::from(79_995));
@@ -375,8 +375,8 @@ fn test_mul(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_store(&ext, 0, "000000000000000000000000000000000000000000000000734349397b853383");
@@ -393,8 +393,8 @@ fn test_sub(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_store(&ext, 0, "0000000000000000000000000000000000000000000000000000012364ad0302");
@@ -411,8 +411,8 @@ fn test_div(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_store(&ext, 0, "000000000000000000000000000000000000000000000000000000000002e0ac");
@@ -429,8 +429,8 @@ fn test_div_zero(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_store(&ext, 0, "0000000000000000000000000000000000000000000000000000000000000000");
@@ -447,8 +447,8 @@ fn test_mod(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_store(&ext, 0, "0000000000000000000000000000000000000000000000000000000000076b4b");
@@ -466,8 +466,8 @@ fn test_smod(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_store(&ext, 0, "0000000000000000000000000000000000000000000000000000000000076b4b");
@@ -485,8 +485,8 @@ fn test_sdiv(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_store(&ext, 0, "000000000000000000000000000000000000000000000000000000000002e0ac");
@@ -504,8 +504,8 @@ fn test_exp(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_store(&ext, 0, "90fd23767b60204c3d6fc8aec9e70a42a3f127140879c133a20129a597ed0c59");
@@ -524,8 +524,8 @@ fn test_comparison(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_store(&ext, 0, "0000000000000000000000000000000000000000000000000000000000000000");
@@ -545,8 +545,8 @@ fn test_signed_comparison(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_store(&ext, 0, "0000000000000000000000000000000000000000000000000000000000000000");
@@ -566,8 +566,8 @@ fn test_bitops(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_store(&ext, 0, "00000000000000000000000000000000000000000000000000000000000000f0");
@@ -589,8 +589,8 @@ fn test_addmod_mulmod(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_store(&ext, 0, "0000000000000000000000000000000000000000000000000000000000000001");
@@ -610,8 +610,8 @@ fn test_byte(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_store(&ext, 0, "0000000000000000000000000000000000000000000000000000000000000000");
@@ -629,8 +629,8 @@ fn test_signextend(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_store(&ext, 0, "0000000000000000000000000000000000000000000000000000000000000fff");
@@ -649,8 +649,8 @@ fn test_badinstruction_int() {
let mut ext = FakeExt::new();
let err = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap_err()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap_err()
};
match err {
@@ -669,8 +669,8 @@ fn test_pop(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_store(&ext, 0, "00000000000000000000000000000000000000000000000000000000000000f0");
@@ -689,8 +689,8 @@ fn test_extops(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_store(&ext, 0, "0000000000000000000000000000000000000000000000000000000000000004"); // PC / CALLDATASIZE
@@ -712,8 +712,8 @@ fn test_jumps(factory: super::Factory) {
let mut ext = FakeExt::new();
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_eq!(ext.sstore_clears, 1);
@@ -740,8 +740,8 @@ fn test_calls(factory: super::Factory) {
};
let gas_left = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_set_contains(&ext.calls, &FakeCall {
@@ -781,8 +781,8 @@ fn test_create_in_staticcall(factory: super::Factory) {
ext.is_static = true;
let err = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap_err()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap_err()
};
assert_eq!(err, vm::Error::MutableCallInStaticContext);
@@ -1049,8 +1049,8 @@ fn push_two_pop_one_constantinople_test(factory: &super::Factory, opcode: u8, pu
let mut ext = FakeExt::new_constantinople();
let _ = {
let mut vm = factory.create(&params.gas);
test_finalize(vm.exec(params, &mut ext)).unwrap()
let mut vm = factory.create(params, ext.schedule(), ext.depth());
test_finalize(vm.exec(&mut ext)).unwrap()
};
assert_store(&ext, 0, result);