From a97a4a9bc4dc644a64e5d1ea2e58256ff412a59e Mon Sep 17 00:00:00 2001 From: debris Date: Fri, 15 Jan 2016 00:40:29 +0100 Subject: [PATCH 1/3] state logs tests passing --- src/executive.rs | 24 ++++++++++++++++++++---- 1 file changed, 20 insertions(+), 4 deletions(-) diff --git a/src/executive.rs b/src/executive.rs index a73180518..efe4db1b7 100644 --- a/src/executive.rs +++ b/src/executive.rs @@ -39,6 +39,14 @@ impl Substate { } } + pub fn accrue(&mut self, s: Substate) { + self.suicides.extend(s.suicides.into_iter()); + self.logs.extend(s.logs.into_iter()); + self.refunds_count = self.refunds_count + s.refunds_count; + self.out_of_gas |= s.out_of_gas; + self.contracts_created.extend(s.contracts_created.into_iter()); + } + pub fn out_of_gas(&self) -> bool { self.out_of_gas } } @@ -409,8 +417,12 @@ impl<'a> Ext for Externalities<'a> { let mut ex = Executive::from_parent(self.state, self.info, self.engine, self.depth); ex.state.inc_nonce(&self.params.address); - match ex.create(¶ms, self.substate) { - Ok(gas_left) => (gas_left, Some(address)), + let mut substate = Substate::new(); + match ex.create(¶ms, &mut substate) { + Ok(gas_left) => { + self.substate.accrue(substate); + (gas_left, Some(address)) + }, _ => (U256::zero(), None) } } @@ -460,8 +472,12 @@ impl<'a> Ext for Externalities<'a> { }; let mut ex = Executive::from_parent(self.state, self.info, self.engine, self.depth); - match ex.call(¶ms, self.substate, BytesRef::Fixed(output)) { - Ok(gas_left) => Ok((gas + gas_left, true)), //Some(CallResult::new(gas + gas_left, true)), + let mut substate = Substate::new(); + match ex.call(¶ms, &mut substate, BytesRef::Fixed(output)) { + Ok(gas_left) => { + self.substate.accrue(substate); + Ok((gas + gas_left, true)) + }, _ => Ok((gas, false)) } } From 821b3b3b7556c7c1648118443f095f5f35d32049 Mon Sep 17 00:00:00 2001 From: debris Date: Fri, 15 Jan 2016 00:54:19 +0100 Subject: [PATCH 2/3] better substate reverting --- src/executive.rs | 35 ++++++++++++++++------------------- 1 file changed, 16 insertions(+), 19 deletions(-) diff --git a/src/executive.rs b/src/executive.rs index efe4db1b7..a6cc8d650 100644 --- a/src/executive.rs +++ b/src/executive.rs @@ -212,12 +212,15 @@ impl<'a> Executive<'a> { } else if params.code.len() > 0 { // if destination is a contract, do normal message call + // part of substate that may be reverted + let mut unconfirmed_substate = Substate::new(); + let res = { - let mut ext = Externalities::from_executive(self, params, substate, OutputPolicy::Return(output)); + let mut ext = Externalities::from_executive(self, params, &mut unconfirmed_substate, OutputPolicy::Return(output)); let evm = Factory::create(); evm.exec(¶ms, &mut ext) }; - self.revert_if_needed(&res, substate, backup); + self.revert_if_needed(&res, substate, unconfirmed_substate, backup); res } else { // otherwise, nothing @@ -232,6 +235,9 @@ impl<'a> Executive<'a> { // backup used in case of running out of gas let backup = self.state.clone(); + // part of substate that may be reverted + let mut unconfirmed_substate = Substate::new(); + // at first create new contract self.state.new_contract(¶ms.address); @@ -239,11 +245,11 @@ impl<'a> Executive<'a> { self.state.transfer_balance(¶ms.sender, ¶ms.address, ¶ms.value); let res = { - let mut ext = Externalities::from_executive(self, params, substate, OutputPolicy::InitContract); + let mut ext = Externalities::from_executive(self, params, &mut unconfirmed_substate, OutputPolicy::InitContract); let evm = Factory::create(); evm.exec(¶ms, &mut ext) }; - self.revert_if_needed(&res, substate, backup); + self.revert_if_needed(&res, substate, unconfirmed_substate, backup); res } @@ -300,15 +306,14 @@ impl<'a> Executive<'a> { } } - fn revert_if_needed(&mut self, result: &evm::Result, substate: &mut Substate, backup: State) { + fn revert_if_needed(&mut self, result: &evm::Result, substate: &mut Substate, un_substate: Substate, backup: State) { // TODO: handle other evm::Errors same as OutOfGas once they are implemented match result { &Err(evm::Error::OutOfGas) => { substate.out_of_gas = true; self.state.revert(backup); }, - &Err(evm::Error::Internal) => (), - &Ok(_) => () + &Ok(_) | &Err(evm::Error::Internal) => substate.accrue(un_substate) } } } @@ -417,12 +422,8 @@ impl<'a> Ext for Externalities<'a> { let mut ex = Executive::from_parent(self.state, self.info, self.engine, self.depth); ex.state.inc_nonce(&self.params.address); - let mut substate = Substate::new(); - match ex.create(¶ms, &mut substate) { - Ok(gas_left) => { - self.substate.accrue(substate); - (gas_left, Some(address)) - }, + match ex.create(¶ms, self.substate) { + Ok(gas_left) => (gas_left, Some(address)), _ => (U256::zero(), None) } } @@ -472,12 +473,8 @@ impl<'a> Ext for Externalities<'a> { }; let mut ex = Executive::from_parent(self.state, self.info, self.engine, self.depth); - let mut substate = Substate::new(); - match ex.call(¶ms, &mut substate, BytesRef::Fixed(output)) { - Ok(gas_left) => { - self.substate.accrue(substate); - Ok((gas + gas_left, true)) - }, + match ex.call(¶ms, self.substate, BytesRef::Fixed(output)) { + Ok(gas_left) => Ok((gas + gas_left, true)), _ => Ok((gas, false)) } } From 7f8adadd6be5d8ce5c1814db47a819a55fcb9d90 Mon Sep 17 00:00:00 2001 From: debris Date: Fri, 15 Jan 2016 01:00:32 +0100 Subject: [PATCH 3/3] revert_if_needed -> enact_result --- src/executive.rs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/executive.rs b/src/executive.rs index a6cc8d650..edbad0887 100644 --- a/src/executive.rs +++ b/src/executive.rs @@ -220,7 +220,7 @@ impl<'a> Executive<'a> { let evm = Factory::create(); evm.exec(¶ms, &mut ext) }; - self.revert_if_needed(&res, substate, unconfirmed_substate, backup); + self.enact_result(&res, substate, unconfirmed_substate, backup); res } else { // otherwise, nothing @@ -249,7 +249,7 @@ impl<'a> Executive<'a> { let evm = Factory::create(); evm.exec(¶ms, &mut ext) }; - self.revert_if_needed(&res, substate, unconfirmed_substate, backup); + self.enact_result(&res, substate, unconfirmed_substate, backup); res } @@ -306,7 +306,7 @@ impl<'a> Executive<'a> { } } - fn revert_if_needed(&mut self, result: &evm::Result, substate: &mut Substate, un_substate: Substate, backup: State) { + fn enact_result(&mut self, result: &evm::Result, substate: &mut Substate, un_substate: Substate, backup: State) { // TODO: handle other evm::Errors same as OutOfGas once they are implemented match result { &Err(evm::Error::OutOfGas) => {