Avoid schedule copying in nested call/create (#9190)
* Avoid schedule copying in nested call/create * Fix tests * fix test: wrong Schedule used * Fix private-tx test * Fix jsontests compilation
This commit is contained in:
parent
d4f38d3894
commit
4848c384cd
@ -435,7 +435,9 @@ impl Provider where {
|
|||||||
let (new_address, _) = ethcore_contract_address(engine.create_address_scheme(env_info.number), &sender, &nonce, &transaction.data);
|
let (new_address, _) = ethcore_contract_address(engine.create_address_scheme(env_info.number), &sender, &nonce, &transaction.data);
|
||||||
Some(new_address)
|
Some(new_address)
|
||||||
});
|
});
|
||||||
let result = Executive::new(&mut state, &env_info, engine.machine()).transact_virtual(transaction, options)?;
|
let machine = engine.machine();
|
||||||
|
let schedule = machine.schedule(env_info.number);
|
||||||
|
let result = Executive::new(&mut state, &env_info, &machine, &schedule).transact_virtual(transaction, options)?;
|
||||||
let (encrypted_code, encrypted_storage) = match contract_address {
|
let (encrypted_code, encrypted_storage) = match contract_address {
|
||||||
None => bail!(ErrorKind::ContractDoesNotExist),
|
None => bail!(ErrorKind::ContractDoesNotExist),
|
||||||
Some(address) => {
|
Some(address) => {
|
||||||
|
@ -616,7 +616,9 @@ impl Importer {
|
|||||||
).expect("state known to be available for just-imported block; qed");
|
).expect("state known to be available for just-imported block; qed");
|
||||||
|
|
||||||
let options = TransactOptions::with_no_tracing().dont_check_nonce();
|
let options = TransactOptions::with_no_tracing().dont_check_nonce();
|
||||||
let res = Executive::new(&mut state, &env_info, self.engine.machine())
|
let machine = self.engine.machine();
|
||||||
|
let schedule = machine.schedule(env_info.number);
|
||||||
|
let res = Executive::new(&mut state, &env_info, &machine, &schedule)
|
||||||
.transact(&transaction, options);
|
.transact(&transaction, options);
|
||||||
|
|
||||||
let res = match res {
|
let res = match res {
|
||||||
@ -1232,8 +1234,9 @@ impl Client {
|
|||||||
.dont_check_nonce()
|
.dont_check_nonce()
|
||||||
.save_output_from_contract();
|
.save_output_from_contract();
|
||||||
let original_state = if state_diff { Some(state.clone()) } else { None };
|
let original_state = if state_diff { Some(state.clone()) } else { None };
|
||||||
|
let schedule = machine.schedule(env_info.number);
|
||||||
|
|
||||||
let mut ret = Executive::new(state, env_info, machine).transact_virtual(transaction, options)?;
|
let mut ret = Executive::new(state, env_info, &machine, &schedule).transact_virtual(transaction, options)?;
|
||||||
|
|
||||||
if let Some(original) = original_state {
|
if let Some(original) = original_state {
|
||||||
ret.state_diff = Some(state.diff_from(original).map_err(ExecutionError::from)?);
|
ret.state_diff = Some(state.diff_from(original).map_err(ExecutionError::from)?);
|
||||||
@ -1486,7 +1489,9 @@ impl Call for Client {
|
|||||||
let tx = tx.fake_sign(sender);
|
let tx = tx.fake_sign(sender);
|
||||||
|
|
||||||
let mut clone = state.clone();
|
let mut clone = state.clone();
|
||||||
Ok(Executive::new(&mut clone, &env_info, self.engine.machine())
|
let machine = self.engine.machine();
|
||||||
|
let schedule = machine.schedule(env_info.number);
|
||||||
|
Ok(Executive::new(&mut clone, &env_info, &machine, &schedule)
|
||||||
.transact_virtual(&tx, options())
|
.transact_virtual(&tx, options())
|
||||||
.map(|r| r.exception.is_none())
|
.map(|r| r.exception.is_none())
|
||||||
.unwrap_or(false))
|
.unwrap_or(false))
|
||||||
|
@ -184,7 +184,9 @@ impl<'a> EvmTestClient<'a> {
|
|||||||
};
|
};
|
||||||
let mut substate = state::Substate::new();
|
let mut substate = state::Substate::new();
|
||||||
let mut output = vec![];
|
let mut output = vec![];
|
||||||
let mut executive = executive::Executive::new(&mut self.state, &info, self.spec.engine.machine());
|
let machine = self.spec.engine.machine();
|
||||||
|
let schedule = machine.schedule(info.number);
|
||||||
|
let mut executive = executive::Executive::new(&mut self.state, &info, &machine, &schedule);
|
||||||
executive.call(
|
executive.call(
|
||||||
params,
|
params,
|
||||||
&mut substate,
|
&mut substate,
|
||||||
|
@ -21,11 +21,11 @@ use hash::keccak;
|
|||||||
use ethereum_types::{H256, U256, U512, Address};
|
use ethereum_types::{H256, U256, U512, Address};
|
||||||
use bytes::{Bytes, BytesRef};
|
use bytes::{Bytes, BytesRef};
|
||||||
use state::{Backend as StateBackend, State, Substate, CleanupMode};
|
use state::{Backend as StateBackend, State, Substate, CleanupMode};
|
||||||
use machine::EthereumMachine as Machine;
|
|
||||||
use error::ExecutionError;
|
use error::ExecutionError;
|
||||||
|
use machine::EthereumMachine as Machine;
|
||||||
use evm::{CallType, Finalize, FinalizationResult};
|
use evm::{CallType, Finalize, FinalizationResult};
|
||||||
use vm::{
|
use vm::{
|
||||||
self, Ext, EnvInfo, CreateContractAddress, ReturnData, CleanDustMode, ActionParams,
|
self, EnvInfo, CreateContractAddress, ReturnData, CleanDustMode, ActionParams,
|
||||||
ActionValue, Schedule,
|
ActionValue, Schedule,
|
||||||
};
|
};
|
||||||
use externalities::*;
|
use externalities::*;
|
||||||
@ -167,28 +167,31 @@ pub struct Executive<'a, B: 'a> {
|
|||||||
state: &'a mut State<B>,
|
state: &'a mut State<B>,
|
||||||
info: &'a EnvInfo,
|
info: &'a EnvInfo,
|
||||||
machine: &'a Machine,
|
machine: &'a Machine,
|
||||||
|
schedule: &'a Schedule,
|
||||||
depth: usize,
|
depth: usize,
|
||||||
static_flag: bool,
|
static_flag: bool,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, B: 'a + StateBackend> Executive<'a, B> {
|
impl<'a, B: 'a + StateBackend> Executive<'a, B> {
|
||||||
/// Basic constructor.
|
/// Basic constructor.
|
||||||
pub fn new(state: &'a mut State<B>, info: &'a EnvInfo, machine: &'a Machine) -> Self {
|
pub fn new(state: &'a mut State<B>, info: &'a EnvInfo, machine: &'a Machine, schedule: &'a Schedule) -> Self {
|
||||||
Executive {
|
Executive {
|
||||||
state: state,
|
state: state,
|
||||||
info: info,
|
info: info,
|
||||||
machine: machine,
|
machine: machine,
|
||||||
|
schedule: schedule,
|
||||||
depth: 0,
|
depth: 0,
|
||||||
static_flag: false,
|
static_flag: false,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Populates executive from parent properties. Increments executive depth.
|
/// Populates executive from parent properties. Increments executive depth.
|
||||||
pub fn from_parent(state: &'a mut State<B>, info: &'a EnvInfo, machine: &'a Machine, parent_depth: usize, static_flag: bool) -> Self {
|
pub fn from_parent(state: &'a mut State<B>, info: &'a EnvInfo, machine: &'a Machine, schedule: &'a Schedule, parent_depth: usize, static_flag: bool) -> Self {
|
||||||
Executive {
|
Executive {
|
||||||
state: state,
|
state: state,
|
||||||
info: info,
|
info: info,
|
||||||
machine: machine,
|
machine: machine,
|
||||||
|
schedule: schedule,
|
||||||
depth: parent_depth + 1,
|
depth: parent_depth + 1,
|
||||||
static_flag: static_flag,
|
static_flag: static_flag,
|
||||||
}
|
}
|
||||||
@ -205,7 +208,7 @@ impl<'a, B: 'a + StateBackend> Executive<'a, B> {
|
|||||||
static_call: bool,
|
static_call: bool,
|
||||||
) -> Externalities<'any, T, V, B> where T: Tracer, V: VMTracer {
|
) -> Externalities<'any, T, V, B> where T: Tracer, V: VMTracer {
|
||||||
let is_static = self.static_flag || static_call;
|
let is_static = self.static_flag || static_call;
|
||||||
Externalities::new(self.state, self.info, self.machine, self.depth, origin_info, substate, output, tracer, vm_tracer, is_static)
|
Externalities::new(self.state, self.info, self.machine, self.schedule, self.depth, origin_info, substate, output, tracer, vm_tracer, is_static)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// This function should be used to execute transaction.
|
/// This function should be used to execute transaction.
|
||||||
@ -244,7 +247,7 @@ impl<'a, B: 'a + StateBackend> Executive<'a, B> {
|
|||||||
let sender = t.sender();
|
let sender = t.sender();
|
||||||
let nonce = self.state.nonce(&sender)?;
|
let nonce = self.state.nonce(&sender)?;
|
||||||
|
|
||||||
let schedule = self.machine.schedule(self.info.number);
|
let schedule = self.schedule;
|
||||||
let base_gas_required = U256::from(t.gas_required(&schedule));
|
let base_gas_required = U256::from(t.gas_required(&schedule));
|
||||||
|
|
||||||
if t.gas < base_gas_required {
|
if t.gas < base_gas_required {
|
||||||
@ -336,7 +339,6 @@ impl<'a, B: 'a + StateBackend> Executive<'a, B> {
|
|||||||
|
|
||||||
fn exec_vm<T, V>(
|
fn exec_vm<T, V>(
|
||||||
&mut self,
|
&mut self,
|
||||||
schedule: Schedule,
|
|
||||||
params: ActionParams,
|
params: ActionParams,
|
||||||
unconfirmed_substate: &mut Substate,
|
unconfirmed_substate: &mut Substate,
|
||||||
output_policy: OutputPolicy,
|
output_policy: OutputPolicy,
|
||||||
@ -350,19 +352,22 @@ impl<'a, B: 'a + StateBackend> Executive<'a, B> {
|
|||||||
// Ordinary execution - keep VM in same thread
|
// Ordinary execution - keep VM in same thread
|
||||||
if self.depth != depth_threshold {
|
if self.depth != depth_threshold {
|
||||||
let vm_factory = self.state.vm_factory();
|
let vm_factory = self.state.vm_factory();
|
||||||
|
let wasm = self.schedule.wasm.is_some();
|
||||||
|
trace!(target: "executive", "ext.schedule.have_delegate_call: {}", self.schedule.have_delegate_call);
|
||||||
let mut ext = self.as_externalities(OriginInfo::from(¶ms), unconfirmed_substate, output_policy, tracer, vm_tracer, static_call);
|
let mut ext = self.as_externalities(OriginInfo::from(¶ms), unconfirmed_substate, output_policy, tracer, vm_tracer, static_call);
|
||||||
trace!(target: "executive", "ext.schedule.have_delegate_call: {}", ext.schedule().have_delegate_call);
|
let mut vm = vm_factory.create(¶ms, wasm);
|
||||||
let mut vm = vm_factory.create(¶ms, &schedule);
|
|
||||||
return vm.exec(params, &mut ext).finalize(ext);
|
return vm.exec(params, &mut ext).finalize(ext);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Start in new thread with stack size needed up to max depth
|
// Start in new thread with stack size needed up to max depth
|
||||||
crossbeam::scope(|scope| {
|
crossbeam::scope(|scope| {
|
||||||
let vm_factory = self.state.vm_factory();
|
let vm_factory = self.state.vm_factory();
|
||||||
|
let max_depth = self.schedule.max_depth;
|
||||||
|
let wasm = self.schedule.wasm.is_some();
|
||||||
let mut ext = self.as_externalities(OriginInfo::from(¶ms), unconfirmed_substate, output_policy, tracer, vm_tracer, static_call);
|
let mut ext = self.as_externalities(OriginInfo::from(¶ms), unconfirmed_substate, output_policy, tracer, vm_tracer, static_call);
|
||||||
|
|
||||||
scope.builder().stack_size(::std::cmp::max(schedule.max_depth.saturating_sub(depth_threshold) * STACK_SIZE_PER_DEPTH, local_stack_size)).spawn(move || {
|
scope.builder().stack_size(::std::cmp::max(max_depth.saturating_sub(depth_threshold) * STACK_SIZE_PER_DEPTH, local_stack_size)).spawn(move || {
|
||||||
let mut vm = vm_factory.create(¶ms, &schedule);
|
let mut vm = vm_factory.create(¶ms, wasm);
|
||||||
vm.exec(params, &mut ext).finalize(ext)
|
vm.exec(params, &mut ext).finalize(ext)
|
||||||
}).expect("Sub-thread creation cannot fail; the host might run out of resources; qed")
|
}).expect("Sub-thread creation cannot fail; the host might run out of resources; qed")
|
||||||
}).join()
|
}).join()
|
||||||
@ -392,7 +397,7 @@ impl<'a, B: 'a + StateBackend> Executive<'a, B> {
|
|||||||
// backup used in case of running out of gas
|
// backup used in case of running out of gas
|
||||||
self.state.checkpoint();
|
self.state.checkpoint();
|
||||||
|
|
||||||
let schedule = self.machine.schedule(self.info.number);
|
let schedule = self.schedule;
|
||||||
|
|
||||||
// at first, transfer value to destination
|
// at first, transfer value to destination
|
||||||
if let ActionValue::Transfer(val) = params.value {
|
if let ActionValue::Transfer(val) = params.value {
|
||||||
@ -479,7 +484,7 @@ impl<'a, B: 'a + StateBackend> Executive<'a, B> {
|
|||||||
let mut subvmtracer = vm_tracer.prepare_subtrace(params.code.as_ref().expect("scope is conditional on params.code.is_some(); qed"));
|
let mut subvmtracer = vm_tracer.prepare_subtrace(params.code.as_ref().expect("scope is conditional on params.code.is_some(); qed"));
|
||||||
|
|
||||||
let res = {
|
let res = {
|
||||||
self.exec_vm(schedule, params, &mut unconfirmed_substate, OutputPolicy::Return(output, trace_output.as_mut()), &mut subtracer, &mut subvmtracer)
|
self.exec_vm(params, &mut unconfirmed_substate, OutputPolicy::Return(output, trace_output.as_mut()), &mut subtracer, &mut subvmtracer)
|
||||||
};
|
};
|
||||||
|
|
||||||
vm_tracer.done_subtrace(subvmtracer);
|
vm_tracer.done_subtrace(subvmtracer);
|
||||||
@ -552,7 +557,7 @@ impl<'a, B: 'a + StateBackend> Executive<'a, B> {
|
|||||||
let mut unconfirmed_substate = Substate::new();
|
let mut unconfirmed_substate = Substate::new();
|
||||||
|
|
||||||
// create contract and transfer value to it if necessary
|
// create contract and transfer value to it if necessary
|
||||||
let schedule = self.machine.schedule(self.info.number);
|
let schedule = self.schedule;
|
||||||
let nonce_offset = if schedule.no_empty {1} else {0}.into();
|
let nonce_offset = if schedule.no_empty {1} else {0}.into();
|
||||||
let prev_bal = self.state.balance(¶ms.address)?;
|
let prev_bal = self.state.balance(¶ms.address)?;
|
||||||
if let ActionValue::Transfer(val) = params.value {
|
if let ActionValue::Transfer(val) = params.value {
|
||||||
@ -571,7 +576,6 @@ impl<'a, B: 'a + StateBackend> Executive<'a, B> {
|
|||||||
let mut subvmtracer = vm_tracer.prepare_subtrace(params.code.as_ref().expect("two ways into create (Externalities::create and Executive::transact_with_tracer); both place `Some(...)` `code` in `params`; qed"));
|
let mut subvmtracer = vm_tracer.prepare_subtrace(params.code.as_ref().expect("two ways into create (Externalities::create and Executive::transact_with_tracer); both place `Some(...)` `code` in `params`; qed"));
|
||||||
|
|
||||||
let res = self.exec_vm(
|
let res = self.exec_vm(
|
||||||
schedule,
|
|
||||||
params,
|
params,
|
||||||
&mut unconfirmed_substate,
|
&mut unconfirmed_substate,
|
||||||
OutputPolicy::InitContract(output.as_mut().or(trace_output.as_mut())),
|
OutputPolicy::InitContract(output.as_mut().or(trace_output.as_mut())),
|
||||||
@ -607,7 +611,7 @@ impl<'a, B: 'a + StateBackend> Executive<'a, B> {
|
|||||||
trace: Vec<T>,
|
trace: Vec<T>,
|
||||||
vm_trace: Option<V>
|
vm_trace: Option<V>
|
||||||
) -> Result<Executed<T, V>, ExecutionError> {
|
) -> Result<Executed<T, V>, ExecutionError> {
|
||||||
let schedule = self.machine.schedule(self.info.number);
|
let schedule = self.schedule;
|
||||||
|
|
||||||
// refunds from SSTORE nonzero -> zero
|
// refunds from SSTORE nonzero -> zero
|
||||||
let sstore_refunds = U256::from(schedule.sstore_refund_gas) * substate.sstore_clears_count;
|
let sstore_refunds = U256::from(schedule.sstore_refund_gas) * substate.sstore_clears_count;
|
||||||
@ -756,10 +760,11 @@ mod tests {
|
|||||||
state.add_balance(&sender, &U256::from(0x100u64), CleanupMode::NoEmpty).unwrap();
|
state.add_balance(&sender, &U256::from(0x100u64), CleanupMode::NoEmpty).unwrap();
|
||||||
let info = EnvInfo::default();
|
let info = EnvInfo::default();
|
||||||
let machine = make_frontier_machine(0);
|
let machine = make_frontier_machine(0);
|
||||||
|
let schedule = machine.schedule(info.number);
|
||||||
let mut substate = Substate::new();
|
let mut substate = Substate::new();
|
||||||
|
|
||||||
let FinalizationResult { gas_left, .. } = {
|
let FinalizationResult { gas_left, .. } = {
|
||||||
let mut ex = Executive::new(&mut state, &info, &machine);
|
let mut ex = Executive::new(&mut state, &info, &machine, &schedule);
|
||||||
ex.create(params, &mut substate, &mut None, &mut NoopTracer, &mut NoopVMTracer).unwrap()
|
ex.create(params, &mut substate, &mut None, &mut NoopTracer, &mut NoopVMTracer).unwrap()
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -813,10 +818,11 @@ mod tests {
|
|||||||
state.add_balance(&sender, &U256::from(100), CleanupMode::NoEmpty).unwrap();
|
state.add_balance(&sender, &U256::from(100), CleanupMode::NoEmpty).unwrap();
|
||||||
let info = EnvInfo::default();
|
let info = EnvInfo::default();
|
||||||
let machine = make_frontier_machine(0);
|
let machine = make_frontier_machine(0);
|
||||||
|
let schedule = machine.schedule(info.number);
|
||||||
let mut substate = Substate::new();
|
let mut substate = Substate::new();
|
||||||
|
|
||||||
let FinalizationResult { gas_left, .. } = {
|
let FinalizationResult { gas_left, .. } = {
|
||||||
let mut ex = Executive::new(&mut state, &info, &machine);
|
let mut ex = Executive::new(&mut state, &info, &machine, &schedule);
|
||||||
ex.create(params, &mut substate, &mut None, &mut NoopTracer, &mut NoopVMTracer).unwrap()
|
ex.create(params, &mut substate, &mut None, &mut NoopTracer, &mut NoopVMTracer).unwrap()
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -855,11 +861,12 @@ mod tests {
|
|||||||
state.add_balance(&sender, &U256::from(100), CleanupMode::NoEmpty).unwrap();
|
state.add_balance(&sender, &U256::from(100), CleanupMode::NoEmpty).unwrap();
|
||||||
let info = EnvInfo::default();
|
let info = EnvInfo::default();
|
||||||
let machine = make_byzantium_machine(5);
|
let machine = make_byzantium_machine(5);
|
||||||
|
let schedule = machine.schedule(info.number);
|
||||||
let mut substate = Substate::new();
|
let mut substate = Substate::new();
|
||||||
let mut tracer = ExecutiveTracer::default();
|
let mut tracer = ExecutiveTracer::default();
|
||||||
let mut vm_tracer = ExecutiveVMTracer::toplevel();
|
let mut vm_tracer = ExecutiveVMTracer::toplevel();
|
||||||
|
|
||||||
let mut ex = Executive::new(&mut state, &info, &machine);
|
let mut ex = Executive::new(&mut state, &info, &machine, &schedule);
|
||||||
let output = BytesRef::Fixed(&mut[0u8;0]);
|
let output = BytesRef::Fixed(&mut[0u8;0]);
|
||||||
ex.call(params, &mut substate, output, &mut tracer, &mut vm_tracer).unwrap();
|
ex.call(params, &mut substate, output, &mut tracer, &mut vm_tracer).unwrap();
|
||||||
|
|
||||||
@ -939,12 +946,13 @@ mod tests {
|
|||||||
state.add_balance(&sender, &U256::from(100), CleanupMode::NoEmpty).unwrap();
|
state.add_balance(&sender, &U256::from(100), CleanupMode::NoEmpty).unwrap();
|
||||||
let info = EnvInfo::default();
|
let info = EnvInfo::default();
|
||||||
let machine = make_frontier_machine(5);
|
let machine = make_frontier_machine(5);
|
||||||
|
let schedule = machine.schedule(info.number);
|
||||||
let mut substate = Substate::new();
|
let mut substate = Substate::new();
|
||||||
let mut tracer = ExecutiveTracer::default();
|
let mut tracer = ExecutiveTracer::default();
|
||||||
let mut vm_tracer = ExecutiveVMTracer::toplevel();
|
let mut vm_tracer = ExecutiveVMTracer::toplevel();
|
||||||
|
|
||||||
let FinalizationResult { gas_left, .. } = {
|
let FinalizationResult { gas_left, .. } = {
|
||||||
let mut ex = Executive::new(&mut state, &info, &machine);
|
let mut ex = Executive::new(&mut state, &info, &machine, &schedule);
|
||||||
let output = BytesRef::Fixed(&mut[0u8;0]);
|
let output = BytesRef::Fixed(&mut[0u8;0]);
|
||||||
ex.call(params, &mut substate, output, &mut tracer, &mut vm_tracer).unwrap()
|
ex.call(params, &mut substate, output, &mut tracer, &mut vm_tracer).unwrap()
|
||||||
};
|
};
|
||||||
@ -1055,12 +1063,13 @@ mod tests {
|
|||||||
state.add_balance(&sender, &U256::from(100), CleanupMode::NoEmpty).unwrap();
|
state.add_balance(&sender, &U256::from(100), CleanupMode::NoEmpty).unwrap();
|
||||||
let info = EnvInfo::default();
|
let info = EnvInfo::default();
|
||||||
let machine = ::ethereum::new_byzantium_test_machine();
|
let machine = ::ethereum::new_byzantium_test_machine();
|
||||||
|
let schedule = machine.schedule(info.number);
|
||||||
let mut substate = Substate::new();
|
let mut substate = Substate::new();
|
||||||
let mut tracer = ExecutiveTracer::default();
|
let mut tracer = ExecutiveTracer::default();
|
||||||
let mut vm_tracer = ExecutiveVMTracer::toplevel();
|
let mut vm_tracer = ExecutiveVMTracer::toplevel();
|
||||||
|
|
||||||
let FinalizationResult { gas_left, .. } = {
|
let FinalizationResult { gas_left, .. } = {
|
||||||
let mut ex = Executive::new(&mut state, &info, &machine);
|
let mut ex = Executive::new(&mut state, &info, &machine, &schedule);
|
||||||
let output = BytesRef::Fixed(&mut[0u8;0]);
|
let output = BytesRef::Fixed(&mut[0u8;0]);
|
||||||
ex.call(params, &mut substate, output, &mut tracer, &mut vm_tracer).unwrap()
|
ex.call(params, &mut substate, output, &mut tracer, &mut vm_tracer).unwrap()
|
||||||
};
|
};
|
||||||
@ -1127,12 +1136,13 @@ mod tests {
|
|||||||
state.add_balance(&sender, &U256::from(100), CleanupMode::NoEmpty).unwrap();
|
state.add_balance(&sender, &U256::from(100), CleanupMode::NoEmpty).unwrap();
|
||||||
let info = EnvInfo::default();
|
let info = EnvInfo::default();
|
||||||
let machine = make_frontier_machine(5);
|
let machine = make_frontier_machine(5);
|
||||||
|
let schedule = machine.schedule(info.number);
|
||||||
let mut substate = Substate::new();
|
let mut substate = Substate::new();
|
||||||
let mut tracer = ExecutiveTracer::default();
|
let mut tracer = ExecutiveTracer::default();
|
||||||
let mut vm_tracer = ExecutiveVMTracer::toplevel();
|
let mut vm_tracer = ExecutiveVMTracer::toplevel();
|
||||||
|
|
||||||
let FinalizationResult { gas_left, .. } = {
|
let FinalizationResult { gas_left, .. } = {
|
||||||
let mut ex = Executive::new(&mut state, &info, &machine);
|
let mut ex = Executive::new(&mut state, &info, &machine, &schedule);
|
||||||
ex.create(params.clone(), &mut substate, &mut None, &mut tracer, &mut vm_tracer).unwrap()
|
ex.create(params.clone(), &mut substate, &mut None, &mut tracer, &mut vm_tracer).unwrap()
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -1214,10 +1224,11 @@ mod tests {
|
|||||||
state.add_balance(&sender, &U256::from(100), CleanupMode::NoEmpty).unwrap();
|
state.add_balance(&sender, &U256::from(100), CleanupMode::NoEmpty).unwrap();
|
||||||
let info = EnvInfo::default();
|
let info = EnvInfo::default();
|
||||||
let machine = make_frontier_machine(0);
|
let machine = make_frontier_machine(0);
|
||||||
|
let schedule = machine.schedule(info.number);
|
||||||
let mut substate = Substate::new();
|
let mut substate = Substate::new();
|
||||||
|
|
||||||
let FinalizationResult { gas_left, .. } = {
|
let FinalizationResult { gas_left, .. } = {
|
||||||
let mut ex = Executive::new(&mut state, &info, &machine);
|
let mut ex = Executive::new(&mut state, &info, &machine, &schedule);
|
||||||
ex.create(params, &mut substate, &mut None, &mut NoopTracer, &mut NoopVMTracer).unwrap()
|
ex.create(params, &mut substate, &mut None, &mut NoopTracer, &mut NoopVMTracer).unwrap()
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -1265,10 +1276,11 @@ mod tests {
|
|||||||
state.add_balance(&sender, &U256::from(100), CleanupMode::NoEmpty).unwrap();
|
state.add_balance(&sender, &U256::from(100), CleanupMode::NoEmpty).unwrap();
|
||||||
let info = EnvInfo::default();
|
let info = EnvInfo::default();
|
||||||
let machine = make_frontier_machine(1024);
|
let machine = make_frontier_machine(1024);
|
||||||
|
let schedule = machine.schedule(info.number);
|
||||||
let mut substate = Substate::new();
|
let mut substate = Substate::new();
|
||||||
|
|
||||||
{
|
{
|
||||||
let mut ex = Executive::new(&mut state, &info, &machine);
|
let mut ex = Executive::new(&mut state, &info, &machine, &schedule);
|
||||||
ex.create(params, &mut substate, &mut None, &mut NoopTracer, &mut NoopVMTracer).unwrap();
|
ex.create(params, &mut substate, &mut None, &mut NoopTracer, &mut NoopVMTracer).unwrap();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1325,10 +1337,11 @@ mod tests {
|
|||||||
|
|
||||||
let info = EnvInfo::default();
|
let info = EnvInfo::default();
|
||||||
let machine = make_frontier_machine(0);
|
let machine = make_frontier_machine(0);
|
||||||
|
let schedule = machine.schedule(info.number);
|
||||||
let mut substate = Substate::new();
|
let mut substate = Substate::new();
|
||||||
|
|
||||||
let FinalizationResult { gas_left, .. } = {
|
let FinalizationResult { gas_left, .. } = {
|
||||||
let mut ex = Executive::new(&mut state, &info, &machine);
|
let mut ex = Executive::new(&mut state, &info, &machine, &schedule);
|
||||||
ex.call(params, &mut substate, BytesRef::Fixed(&mut []), &mut NoopTracer, &mut NoopVMTracer).unwrap()
|
ex.call(params, &mut substate, BytesRef::Fixed(&mut []), &mut NoopTracer, &mut NoopVMTracer).unwrap()
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -1369,10 +1382,11 @@ mod tests {
|
|||||||
state.init_code(&address, code).unwrap();
|
state.init_code(&address, code).unwrap();
|
||||||
let info = EnvInfo::default();
|
let info = EnvInfo::default();
|
||||||
let machine = make_frontier_machine(0);
|
let machine = make_frontier_machine(0);
|
||||||
|
let schedule = machine.schedule(info.number);
|
||||||
let mut substate = Substate::new();
|
let mut substate = Substate::new();
|
||||||
|
|
||||||
let FinalizationResult { gas_left, .. } = {
|
let FinalizationResult { gas_left, .. } = {
|
||||||
let mut ex = Executive::new(&mut state, &info, &machine);
|
let mut ex = Executive::new(&mut state, &info, &machine, &schedule);
|
||||||
ex.call(params, &mut substate, BytesRef::Fixed(&mut []), &mut NoopTracer, &mut NoopVMTracer).unwrap()
|
ex.call(params, &mut substate, BytesRef::Fixed(&mut []), &mut NoopTracer, &mut NoopVMTracer).unwrap()
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -1402,9 +1416,10 @@ mod tests {
|
|||||||
let mut info = EnvInfo::default();
|
let mut info = EnvInfo::default();
|
||||||
info.gas_limit = U256::from(100_000);
|
info.gas_limit = U256::from(100_000);
|
||||||
let machine = make_frontier_machine(0);
|
let machine = make_frontier_machine(0);
|
||||||
|
let schedule = machine.schedule(info.number);
|
||||||
|
|
||||||
let executed = {
|
let executed = {
|
||||||
let mut ex = Executive::new(&mut state, &info, &machine);
|
let mut ex = Executive::new(&mut state, &info, &machine, &schedule);
|
||||||
let opts = TransactOptions::with_no_tracing();
|
let opts = TransactOptions::with_no_tracing();
|
||||||
ex.transact(&t, opts).unwrap()
|
ex.transact(&t, opts).unwrap()
|
||||||
};
|
};
|
||||||
@ -1439,9 +1454,10 @@ mod tests {
|
|||||||
let mut info = EnvInfo::default();
|
let mut info = EnvInfo::default();
|
||||||
info.gas_limit = U256::from(100_000);
|
info.gas_limit = U256::from(100_000);
|
||||||
let machine = make_frontier_machine(0);
|
let machine = make_frontier_machine(0);
|
||||||
|
let schedule = machine.schedule(info.number);
|
||||||
|
|
||||||
let res = {
|
let res = {
|
||||||
let mut ex = Executive::new(&mut state, &info, &machine);
|
let mut ex = Executive::new(&mut state, &info, &machine, &schedule);
|
||||||
let opts = TransactOptions::with_no_tracing();
|
let opts = TransactOptions::with_no_tracing();
|
||||||
ex.transact(&t, opts)
|
ex.transact(&t, opts)
|
||||||
};
|
};
|
||||||
@ -1472,9 +1488,10 @@ mod tests {
|
|||||||
info.gas_used = U256::from(20_000);
|
info.gas_used = U256::from(20_000);
|
||||||
info.gas_limit = U256::from(100_000);
|
info.gas_limit = U256::from(100_000);
|
||||||
let machine = make_frontier_machine(0);
|
let machine = make_frontier_machine(0);
|
||||||
|
let schedule = machine.schedule(info.number);
|
||||||
|
|
||||||
let res = {
|
let res = {
|
||||||
let mut ex = Executive::new(&mut state, &info, &machine);
|
let mut ex = Executive::new(&mut state, &info, &machine, &schedule);
|
||||||
let opts = TransactOptions::with_no_tracing();
|
let opts = TransactOptions::with_no_tracing();
|
||||||
ex.transact(&t, opts)
|
ex.transact(&t, opts)
|
||||||
};
|
};
|
||||||
@ -1505,9 +1522,10 @@ mod tests {
|
|||||||
let mut info = EnvInfo::default();
|
let mut info = EnvInfo::default();
|
||||||
info.gas_limit = U256::from(100_000);
|
info.gas_limit = U256::from(100_000);
|
||||||
let machine = make_frontier_machine(0);
|
let machine = make_frontier_machine(0);
|
||||||
|
let schedule = machine.schedule(info.number);
|
||||||
|
|
||||||
let res = {
|
let res = {
|
||||||
let mut ex = Executive::new(&mut state, &info, &machine);
|
let mut ex = Executive::new(&mut state, &info, &machine, &schedule);
|
||||||
let opts = TransactOptions::with_no_tracing();
|
let opts = TransactOptions::with_no_tracing();
|
||||||
ex.transact(&t, opts)
|
ex.transact(&t, opts)
|
||||||
};
|
};
|
||||||
@ -1538,10 +1556,11 @@ mod tests {
|
|||||||
state.add_balance(&sender, &U256::from_str("152d02c7e14af6800000").unwrap(), CleanupMode::NoEmpty).unwrap();
|
state.add_balance(&sender, &U256::from_str("152d02c7e14af6800000").unwrap(), CleanupMode::NoEmpty).unwrap();
|
||||||
let info = EnvInfo::default();
|
let info = EnvInfo::default();
|
||||||
let machine = make_frontier_machine(0);
|
let machine = make_frontier_machine(0);
|
||||||
|
let schedule = machine.schedule(info.number);
|
||||||
let mut substate = Substate::new();
|
let mut substate = Substate::new();
|
||||||
|
|
||||||
let result = {
|
let result = {
|
||||||
let mut ex = Executive::new(&mut state, &info, &machine);
|
let mut ex = Executive::new(&mut state, &info, &machine, &schedule);
|
||||||
ex.create(params, &mut substate, &mut None, &mut NoopTracer, &mut NoopVMTracer)
|
ex.create(params, &mut substate, &mut None, &mut NoopTracer, &mut NoopVMTracer)
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -1571,11 +1590,12 @@ mod tests {
|
|||||||
params.value = ActionValue::Transfer(U256::zero());
|
params.value = ActionValue::Transfer(U256::zero());
|
||||||
let info = EnvInfo::default();
|
let info = EnvInfo::default();
|
||||||
let machine = ::ethereum::new_byzantium_test_machine();
|
let machine = ::ethereum::new_byzantium_test_machine();
|
||||||
|
let schedule = machine.schedule(info.number);
|
||||||
let mut substate = Substate::new();
|
let mut substate = Substate::new();
|
||||||
|
|
||||||
let mut output = [0u8; 14];
|
let mut output = [0u8; 14];
|
||||||
let FinalizationResult { gas_left: result, .. } = {
|
let FinalizationResult { gas_left: result, .. } = {
|
||||||
let mut ex = Executive::new(&mut state, &info, &machine);
|
let mut ex = Executive::new(&mut state, &info, &machine, &schedule);
|
||||||
ex.call(params, &mut substate, BytesRef::Fixed(&mut output), &mut NoopTracer, &mut NoopVMTracer).unwrap()
|
ex.call(params, &mut substate, BytesRef::Fixed(&mut output), &mut NoopTracer, &mut NoopVMTracer).unwrap()
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -1618,7 +1638,8 @@ mod tests {
|
|||||||
|
|
||||||
let mut output = [0u8; 20];
|
let mut output = [0u8; 20];
|
||||||
let FinalizationResult { gas_left: result, .. } = {
|
let FinalizationResult { gas_left: result, .. } = {
|
||||||
let mut ex = Executive::new(&mut state, &info, &machine);
|
let schedule = machine.schedule(info.number);
|
||||||
|
let mut ex = Executive::new(&mut state, &info, &machine, &schedule);
|
||||||
ex.call(params.clone(), &mut Substate::new(), BytesRef::Fixed(&mut output), &mut NoopTracer, &mut NoopVMTracer).unwrap()
|
ex.call(params.clone(), &mut Substate::new(), BytesRef::Fixed(&mut output), &mut NoopTracer, &mut NoopVMTracer).unwrap()
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -1631,7 +1652,8 @@ mod tests {
|
|||||||
|
|
||||||
let mut output = [0u8; 20];
|
let mut output = [0u8; 20];
|
||||||
let FinalizationResult { gas_left: result, .. } = {
|
let FinalizationResult { gas_left: result, .. } = {
|
||||||
let mut ex = Executive::new(&mut state, &info, &machine);
|
let schedule = machine.schedule(info.number);
|
||||||
|
let mut ex = Executive::new(&mut state, &info, &machine, &schedule);
|
||||||
ex.call(params, &mut Substate::new(), BytesRef::Fixed(&mut output), &mut NoopTracer, &mut NoopVMTracer).unwrap()
|
ex.call(params, &mut Substate::new(), BytesRef::Fixed(&mut output), &mut NoopTracer, &mut NoopVMTracer).unwrap()
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -66,11 +66,11 @@ impl OriginInfo {
|
|||||||
pub struct Externalities<'a, T: 'a, V: 'a, B: 'a> {
|
pub struct Externalities<'a, T: 'a, V: 'a, B: 'a> {
|
||||||
state: &'a mut State<B>,
|
state: &'a mut State<B>,
|
||||||
env_info: &'a EnvInfo,
|
env_info: &'a EnvInfo,
|
||||||
machine: &'a Machine,
|
|
||||||
depth: usize,
|
depth: usize,
|
||||||
origin_info: OriginInfo,
|
origin_info: OriginInfo,
|
||||||
substate: &'a mut Substate,
|
substate: &'a mut Substate,
|
||||||
schedule: Schedule,
|
machine: &'a Machine,
|
||||||
|
schedule: &'a Schedule,
|
||||||
output: OutputPolicy<'a, 'a>,
|
output: OutputPolicy<'a, 'a>,
|
||||||
tracer: &'a mut T,
|
tracer: &'a mut T,
|
||||||
vm_tracer: &'a mut V,
|
vm_tracer: &'a mut V,
|
||||||
@ -81,9 +81,11 @@ impl<'a, T: 'a, V: 'a, B: 'a> Externalities<'a, T, V, B>
|
|||||||
where T: Tracer, V: VMTracer, B: StateBackend
|
where T: Tracer, V: VMTracer, B: StateBackend
|
||||||
{
|
{
|
||||||
/// Basic `Externalities` constructor.
|
/// Basic `Externalities` constructor.
|
||||||
pub fn new(state: &'a mut State<B>,
|
pub fn new(
|
||||||
|
state: &'a mut State<B>,
|
||||||
env_info: &'a EnvInfo,
|
env_info: &'a EnvInfo,
|
||||||
machine: &'a Machine,
|
machine: &'a Machine,
|
||||||
|
schedule: &'a Schedule,
|
||||||
depth: usize,
|
depth: usize,
|
||||||
origin_info: OriginInfo,
|
origin_info: OriginInfo,
|
||||||
substate: &'a mut Substate,
|
substate: &'a mut Substate,
|
||||||
@ -95,11 +97,11 @@ impl<'a, T: 'a, V: 'a, B: 'a> Externalities<'a, T, V, B>
|
|||||||
Externalities {
|
Externalities {
|
||||||
state: state,
|
state: state,
|
||||||
env_info: env_info,
|
env_info: env_info,
|
||||||
machine: machine,
|
|
||||||
depth: depth,
|
depth: depth,
|
||||||
origin_info: origin_info,
|
origin_info: origin_info,
|
||||||
substate: substate,
|
substate: substate,
|
||||||
schedule: machine.schedule(env_info.number),
|
machine: machine,
|
||||||
|
schedule: schedule,
|
||||||
output: output,
|
output: output,
|
||||||
tracer: tracer,
|
tracer: tracer,
|
||||||
vm_tracer: vm_tracer,
|
vm_tracer: vm_tracer,
|
||||||
@ -170,7 +172,7 @@ impl<'a, T: 'a, V: 'a, B: 'a> Ext for Externalities<'a, T, V, B>
|
|||||||
};
|
};
|
||||||
|
|
||||||
let mut output = H256::new();
|
let mut output = H256::new();
|
||||||
let mut ex = Executive::new(self.state, self.env_info, self.machine);
|
let mut ex = Executive::new(self.state, self.env_info, self.machine, self.schedule);
|
||||||
let r = ex.call(params, self.substate, BytesRef::Fixed(&mut output), self.tracer, self.vm_tracer);
|
let r = ex.call(params, self.substate, BytesRef::Fixed(&mut output), self.tracer, self.vm_tracer);
|
||||||
trace!("ext: blockhash contract({}) -> {:?}({}) self.env_info.number={}\n", number, r, output, self.env_info.number);
|
trace!("ext: blockhash contract({}) -> {:?}({}) self.env_info.number={}\n", number, r, output, self.env_info.number);
|
||||||
output
|
output
|
||||||
@ -226,7 +228,7 @@ impl<'a, T: 'a, V: 'a, B: 'a> Ext for Externalities<'a, T, V, B>
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
let mut ex = Executive::from_parent(self.state, self.env_info, self.machine, self.depth, self.static_flag);
|
let mut ex = Executive::from_parent(self.state, self.env_info, self.machine, self.schedule, self.depth, self.static_flag);
|
||||||
|
|
||||||
// TODO: handle internal error separately
|
// TODO: handle internal error separately
|
||||||
match ex.create(params, self.substate, &mut None, self.tracer, self.vm_tracer) {
|
match ex.create(params, self.substate, &mut None, self.tracer, self.vm_tracer) {
|
||||||
@ -280,7 +282,7 @@ impl<'a, T: 'a, V: 'a, B: 'a> Ext for Externalities<'a, T, V, B>
|
|||||||
params.value = ActionValue::Transfer(value);
|
params.value = ActionValue::Transfer(value);
|
||||||
}
|
}
|
||||||
|
|
||||||
let mut ex = Executive::from_parent(self.state, self.env_info, self.machine, self.depth, self.static_flag);
|
let mut ex = Executive::from_parent(self.state, self.env_info, self.machine, self.schedule, self.depth, self.static_flag);
|
||||||
|
|
||||||
match ex.call(params, self.substate, BytesRef::Fixed(output), self.tracer, self.vm_tracer) {
|
match ex.call(params, self.substate, BytesRef::Fixed(output), self.tracer, self.vm_tracer) {
|
||||||
Ok(FinalizationResult{ gas_left, return_data, apply_state: true }) => MessageCallResult::Success(gas_left, return_data),
|
Ok(FinalizationResult{ gas_left, return_data, apply_state: true }) => MessageCallResult::Success(gas_left, return_data),
|
||||||
@ -440,6 +442,7 @@ mod tests {
|
|||||||
struct TestSetup {
|
struct TestSetup {
|
||||||
state: State<::state_db::StateDB>,
|
state: State<::state_db::StateDB>,
|
||||||
machine: ::machine::EthereumMachine,
|
machine: ::machine::EthereumMachine,
|
||||||
|
schedule: Schedule,
|
||||||
sub_state: Substate,
|
sub_state: Substate,
|
||||||
env_info: EnvInfo
|
env_info: EnvInfo
|
||||||
}
|
}
|
||||||
@ -452,11 +455,15 @@ mod tests {
|
|||||||
|
|
||||||
impl TestSetup {
|
impl TestSetup {
|
||||||
fn new() -> Self {
|
fn new() -> Self {
|
||||||
|
let machine = ::spec::Spec::new_test_machine();
|
||||||
|
let env_info = get_test_env_info();
|
||||||
|
let schedule = machine.schedule(env_info.number);
|
||||||
TestSetup {
|
TestSetup {
|
||||||
state: get_temp_state(),
|
state: get_temp_state(),
|
||||||
machine: ::spec::Spec::new_test_machine(),
|
schedule: schedule,
|
||||||
|
machine: machine,
|
||||||
sub_state: Substate::new(),
|
sub_state: Substate::new(),
|
||||||
env_info: get_test_env_info()
|
env_info: env_info,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -468,7 +475,7 @@ mod tests {
|
|||||||
let mut tracer = NoopTracer;
|
let mut tracer = NoopTracer;
|
||||||
let mut vm_tracer = NoopVMTracer;
|
let mut vm_tracer = NoopVMTracer;
|
||||||
|
|
||||||
let ext = Externalities::new(state, &setup.env_info, &setup.machine, 0, get_test_origin(), &mut setup.sub_state, OutputPolicy::InitContract(None), &mut tracer, &mut vm_tracer, false);
|
let ext = Externalities::new(state, &setup.env_info, &setup.machine, &setup.schedule, 0, get_test_origin(), &mut setup.sub_state, OutputPolicy::InitContract(None), &mut tracer, &mut vm_tracer, false);
|
||||||
|
|
||||||
assert_eq!(ext.env_info().number, 100);
|
assert_eq!(ext.env_info().number, 100);
|
||||||
}
|
}
|
||||||
@ -480,7 +487,7 @@ mod tests {
|
|||||||
let mut tracer = NoopTracer;
|
let mut tracer = NoopTracer;
|
||||||
let mut vm_tracer = NoopVMTracer;
|
let mut vm_tracer = NoopVMTracer;
|
||||||
|
|
||||||
let mut ext = Externalities::new(state, &setup.env_info, &setup.machine, 0, get_test_origin(), &mut setup.sub_state, OutputPolicy::InitContract(None), &mut tracer, &mut vm_tracer, false);
|
let mut ext = Externalities::new(state, &setup.env_info, &setup.machine, &setup.schedule, 0, get_test_origin(), &mut setup.sub_state, OutputPolicy::InitContract(None), &mut tracer, &mut vm_tracer, false);
|
||||||
|
|
||||||
let hash = ext.blockhash(&"0000000000000000000000000000000000000000000000000000000000120000".parse::<U256>().unwrap());
|
let hash = ext.blockhash(&"0000000000000000000000000000000000000000000000000000000000120000".parse::<U256>().unwrap());
|
||||||
|
|
||||||
@ -504,7 +511,7 @@ mod tests {
|
|||||||
let mut tracer = NoopTracer;
|
let mut tracer = NoopTracer;
|
||||||
let mut vm_tracer = NoopVMTracer;
|
let mut vm_tracer = NoopVMTracer;
|
||||||
|
|
||||||
let mut ext = Externalities::new(state, &setup.env_info, &setup.machine, 0, get_test_origin(), &mut setup.sub_state, OutputPolicy::InitContract(None), &mut tracer, &mut vm_tracer, false);
|
let mut ext = Externalities::new(state, &setup.env_info, &setup.machine, &setup.schedule, 0, get_test_origin(), &mut setup.sub_state, OutputPolicy::InitContract(None), &mut tracer, &mut vm_tracer, false);
|
||||||
|
|
||||||
let hash = ext.blockhash(&"0000000000000000000000000000000000000000000000000000000000120000".parse::<U256>().unwrap());
|
let hash = ext.blockhash(&"0000000000000000000000000000000000000000000000000000000000120000".parse::<U256>().unwrap());
|
||||||
|
|
||||||
@ -519,7 +526,7 @@ mod tests {
|
|||||||
let mut tracer = NoopTracer;
|
let mut tracer = NoopTracer;
|
||||||
let mut vm_tracer = NoopVMTracer;
|
let mut vm_tracer = NoopVMTracer;
|
||||||
|
|
||||||
let mut ext = Externalities::new(state, &setup.env_info, &setup.machine, 0, get_test_origin(), &mut setup.sub_state, OutputPolicy::InitContract(None), &mut tracer, &mut vm_tracer, false);
|
let mut ext = Externalities::new(state, &setup.env_info, &setup.machine, &setup.schedule, 0, get_test_origin(), &mut setup.sub_state, OutputPolicy::InitContract(None), &mut tracer, &mut vm_tracer, false);
|
||||||
|
|
||||||
let mut output = vec![];
|
let mut output = vec![];
|
||||||
|
|
||||||
@ -547,7 +554,7 @@ mod tests {
|
|||||||
let mut vm_tracer = NoopVMTracer;
|
let mut vm_tracer = NoopVMTracer;
|
||||||
|
|
||||||
{
|
{
|
||||||
let mut ext = Externalities::new(state, &setup.env_info, &setup.machine, 0, get_test_origin(), &mut setup.sub_state, OutputPolicy::InitContract(None), &mut tracer, &mut vm_tracer, false);
|
let mut ext = Externalities::new(state, &setup.env_info, &setup.machine, &setup.schedule, 0, get_test_origin(), &mut setup.sub_state, OutputPolicy::InitContract(None), &mut tracer, &mut vm_tracer, false);
|
||||||
ext.log(log_topics, &log_data).unwrap();
|
ext.log(log_topics, &log_data).unwrap();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -564,7 +571,7 @@ mod tests {
|
|||||||
let mut vm_tracer = NoopVMTracer;
|
let mut vm_tracer = NoopVMTracer;
|
||||||
|
|
||||||
{
|
{
|
||||||
let mut ext = Externalities::new(state, &setup.env_info, &setup.machine, 0, get_test_origin(), &mut setup.sub_state, OutputPolicy::InitContract(None), &mut tracer, &mut vm_tracer, false);
|
let mut ext = Externalities::new(state, &setup.env_info, &setup.machine, &setup.schedule, 0, get_test_origin(), &mut setup.sub_state, OutputPolicy::InitContract(None), &mut tracer, &mut vm_tracer, false);
|
||||||
ext.suicide(refund_account).unwrap();
|
ext.suicide(refund_account).unwrap();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -18,7 +18,7 @@ use trie::TrieFactory;
|
|||||||
use ethtrie::RlpCodec;
|
use ethtrie::RlpCodec;
|
||||||
use account_db::Factory as AccountFactory;
|
use account_db::Factory as AccountFactory;
|
||||||
use evm::{Factory as EvmFactory, VMType};
|
use evm::{Factory as EvmFactory, VMType};
|
||||||
use vm::{Vm, ActionParams, Schedule};
|
use vm::{Vm, ActionParams};
|
||||||
use wasm::WasmInterpreter;
|
use wasm::WasmInterpreter;
|
||||||
use keccak_hasher::KeccakHasher;
|
use keccak_hasher::KeccakHasher;
|
||||||
|
|
||||||
@ -31,8 +31,8 @@ pub struct VmFactory {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl VmFactory {
|
impl VmFactory {
|
||||||
pub fn create(&self, params: &ActionParams, schedule: &Schedule) -> Box<Vm> {
|
pub fn create(&self, params: &ActionParams, wasm: bool) -> Box<Vm> {
|
||||||
if schedule.wasm.is_some() && params.code.as_ref().map_or(false, |code| code.len() > 4 && &code[0..4] == WASM_MAGIC_NUMBER) {
|
if wasm && params.code.as_ref().map_or(false, |code| code.len() > 4 && &code[0..4] == WASM_MAGIC_NUMBER) {
|
||||||
Box::new(WasmInterpreter)
|
Box::new(WasmInterpreter)
|
||||||
} else {
|
} else {
|
||||||
self.evm.create(¶ms.gas)
|
self.evm.create(¶ms.gas)
|
||||||
|
@ -86,6 +86,7 @@ impl<'a, T: 'a, V: 'a, B: 'a> TestExt<'a, T, V, B>
|
|||||||
state: &'a mut State<B>,
|
state: &'a mut State<B>,
|
||||||
info: &'a EnvInfo,
|
info: &'a EnvInfo,
|
||||||
machine: &'a Machine,
|
machine: &'a Machine,
|
||||||
|
schedule: &'a Schedule,
|
||||||
depth: usize,
|
depth: usize,
|
||||||
origin_info: OriginInfo,
|
origin_info: OriginInfo,
|
||||||
substate: &'a mut Substate,
|
substate: &'a mut Substate,
|
||||||
@ -97,7 +98,7 @@ impl<'a, T: 'a, V: 'a, B: 'a> TestExt<'a, T, V, B>
|
|||||||
let static_call = false;
|
let static_call = false;
|
||||||
Ok(TestExt {
|
Ok(TestExt {
|
||||||
nonce: state.nonce(&address)?,
|
nonce: state.nonce(&address)?,
|
||||||
ext: Externalities::new(state, info, machine, depth, origin_info, substate, output, tracer, vm_tracer, static_call),
|
ext: Externalities::new(state, info, machine, schedule, depth, origin_info, substate, output, tracer, vm_tracer, static_call),
|
||||||
callcreates: vec![],
|
callcreates: vec![],
|
||||||
sender: address,
|
sender: address,
|
||||||
})
|
})
|
||||||
@ -245,7 +246,7 @@ fn do_json_test_for<H: FnMut(&str, HookType)>(vm_type: &VMType, json_data: &[u8]
|
|||||||
let out_of_gas = vm.out_of_gas();
|
let out_of_gas = vm.out_of_gas();
|
||||||
let mut state = get_temp_state();
|
let mut state = get_temp_state();
|
||||||
state.populate_from(From::from(vm.pre_state.clone()));
|
state.populate_from(From::from(vm.pre_state.clone()));
|
||||||
let info = From::from(vm.env);
|
let info: EnvInfo = From::from(vm.env);
|
||||||
let machine = {
|
let machine = {
|
||||||
let mut machine = ::ethereum::new_frontier_test_machine();
|
let mut machine = ::ethereum::new_frontier_test_machine();
|
||||||
machine.set_schedule_creation_rules(Box::new(move |s, _| s.max_depth = 1));
|
machine.set_schedule_creation_rules(Box::new(move |s, _| s.max_depth = 1));
|
||||||
@ -262,10 +263,12 @@ fn do_json_test_for<H: FnMut(&str, HookType)>(vm_type: &VMType, json_data: &[u8]
|
|||||||
|
|
||||||
// execute
|
// execute
|
||||||
let (res, callcreates) = {
|
let (res, callcreates) = {
|
||||||
|
let schedule = machine.schedule(info.number);
|
||||||
let mut ex = try_fail!(TestExt::new(
|
let mut ex = try_fail!(TestExt::new(
|
||||||
&mut state,
|
&mut state,
|
||||||
&info,
|
&info,
|
||||||
&machine,
|
&machine,
|
||||||
|
&schedule,
|
||||||
0,
|
0,
|
||||||
OriginInfo::from(¶ms),
|
OriginInfo::from(¶ms),
|
||||||
&mut substate,
|
&mut substate,
|
||||||
@ -274,7 +277,7 @@ fn do_json_test_for<H: FnMut(&str, HookType)>(vm_type: &VMType, json_data: &[u8]
|
|||||||
&mut tracer,
|
&mut tracer,
|
||||||
&mut vm_tracer,
|
&mut vm_tracer,
|
||||||
));
|
));
|
||||||
let mut evm = vm_factory.create(¶ms, &machine.schedule(0u64.into()));
|
let mut evm = vm_factory.create(¶ms, schedule.wasm.is_some());
|
||||||
let res = evm.exec(params, &mut ex);
|
let res = evm.exec(params, &mut ex);
|
||||||
// a return in finalize will not alter callcreates
|
// a return in finalize will not alter callcreates
|
||||||
let callcreates = ex.callcreates.clone();
|
let callcreates = ex.callcreates.clone();
|
||||||
|
@ -145,7 +145,8 @@ impl EthereumMachine {
|
|||||||
call_type: CallType::Call,
|
call_type: CallType::Call,
|
||||||
params_type: ParamsType::Separate,
|
params_type: ParamsType::Separate,
|
||||||
};
|
};
|
||||||
let mut ex = Executive::new(&mut state, &env_info, self);
|
let schedule = self.schedule(env_info.number);
|
||||||
|
let mut ex = Executive::new(&mut state, &env_info, self, &schedule);
|
||||||
let mut substate = Substate::new();
|
let mut substate = Substate::new();
|
||||||
let mut output = Vec::new();
|
let mut output = Vec::new();
|
||||||
if let Err(e) = ex.call(params, &mut substate, BytesRef::Flexible(&mut output), &mut NoopTracer, &mut NoopVMTracer) {
|
if let Err(e) = ex.call(params, &mut substate, BytesRef::Flexible(&mut output), &mut NoopTracer, &mut NoopVMTracer) {
|
||||||
|
@ -631,7 +631,9 @@ impl Spec {
|
|||||||
let mut substate = Substate::new();
|
let mut substate = Substate::new();
|
||||||
|
|
||||||
{
|
{
|
||||||
let mut exec = Executive::new(&mut state, &env_info, self.engine.machine());
|
let machine = self.engine.machine();
|
||||||
|
let schedule = machine.schedule(env_info.number);
|
||||||
|
let mut exec = Executive::new(&mut state, &env_info, &machine, &schedule);
|
||||||
if let Err(e) = exec.create(params, &mut substate, &mut None, &mut NoopTracer, &mut NoopVMTracer) {
|
if let Err(e) = exec.create(params, &mut substate, &mut None, &mut NoopTracer, &mut NoopVMTracer) {
|
||||||
warn!(target: "spec", "Genesis constructor execution at {} failed: {}.", address, e);
|
warn!(target: "spec", "Genesis constructor execution at {} failed: {}.", address, e);
|
||||||
}
|
}
|
||||||
|
@ -745,7 +745,8 @@ impl<B: Backend> State<B> {
|
|||||||
fn execute<T, V>(&mut self, env_info: &EnvInfo, machine: &Machine, t: &SignedTransaction, options: TransactOptions<T, V>, virt: bool)
|
fn execute<T, V>(&mut self, env_info: &EnvInfo, machine: &Machine, t: &SignedTransaction, options: TransactOptions<T, V>, virt: bool)
|
||||||
-> Result<Executed<T::Output, V::Output>, ExecutionError> where T: trace::Tracer, V: trace::VMTracer,
|
-> Result<Executed<T::Output, V::Output>, ExecutionError> where T: trace::Tracer, V: trace::VMTracer,
|
||||||
{
|
{
|
||||||
let mut e = Executive::new(self, env_info, machine);
|
let schedule = machine.schedule(env_info.number);
|
||||||
|
let mut e = Executive::new(self, env_info, machine, &schedule);
|
||||||
|
|
||||||
match virt {
|
match virt {
|
||||||
true => e.transact_virtual(t, options),
|
true => e.transact_virtual(t, options),
|
||||||
|
@ -373,8 +373,11 @@ fn transaction_proof() {
|
|||||||
factories.accountdb = ::account_db::Factory::Plain; // raw state values, no mangled keys.
|
factories.accountdb = ::account_db::Factory::Plain; // raw state values, no mangled keys.
|
||||||
let root = *client.best_block_header().state_root();
|
let root = *client.best_block_header().state_root();
|
||||||
|
|
||||||
|
let machine = test_spec.engine.machine();
|
||||||
|
let env_info = client.latest_env_info();
|
||||||
|
let schedule = machine.schedule(env_info.number);
|
||||||
let mut state = State::from_existing(backend, root, 0.into(), factories.clone()).unwrap();
|
let mut state = State::from_existing(backend, root, 0.into(), factories.clone()).unwrap();
|
||||||
Executive::new(&mut state, &client.latest_env_info(), test_spec.engine.machine())
|
Executive::new(&mut state, &env_info, &machine, &schedule)
|
||||||
.transact(&transaction, TransactOptions::with_no_tracing().dont_check_nonce()).unwrap();
|
.transact(&transaction, TransactOptions::with_no_tracing().dont_check_nonce()).unwrap();
|
||||||
|
|
||||||
assert_eq!(state.balance(&Address::default()).unwrap(), 5.into());
|
assert_eq!(state.balance(&Address::default()).unwrap(), 5.into());
|
||||||
|
@ -62,7 +62,8 @@ fn test_blockhash_eip210(factory: Factory) {
|
|||||||
call_type: CallType::Call,
|
call_type: CallType::Call,
|
||||||
params_type: ParamsType::Separate,
|
params_type: ParamsType::Separate,
|
||||||
};
|
};
|
||||||
let mut ex = Executive::new(&mut state, &env_info, &machine);
|
let schedule = machine.schedule(env_info.number);
|
||||||
|
let mut ex = Executive::new(&mut state, &env_info, &machine, &schedule);
|
||||||
let mut substate = Substate::new();
|
let mut substate = Substate::new();
|
||||||
let mut output = [];
|
let mut output = [];
|
||||||
if let Err(e) = ex.call(params, &mut substate, BytesRef::Fixed(&mut output), &mut NoopTracer, &mut NoopVMTracer) {
|
if let Err(e) = ex.call(params, &mut substate, BytesRef::Fixed(&mut output), &mut NoopTracer, &mut NoopVMTracer) {
|
||||||
@ -85,7 +86,8 @@ fn test_blockhash_eip210(factory: Factory) {
|
|||||||
call_type: CallType::Call,
|
call_type: CallType::Call,
|
||||||
params_type: ParamsType::Separate,
|
params_type: ParamsType::Separate,
|
||||||
};
|
};
|
||||||
let mut ex = Executive::new(&mut state, &env_info, &machine);
|
let schedule = machine.schedule(env_info.number);
|
||||||
|
let mut ex = Executive::new(&mut state, &env_info, &machine, &schedule);
|
||||||
let mut substate = Substate::new();
|
let mut substate = Substate::new();
|
||||||
let mut output = H256::new();
|
let mut output = H256::new();
|
||||||
if let Err(e) = ex.call(params, &mut substate, BytesRef::Fixed(&mut output), &mut NoopTracer, &mut NoopVMTracer) {
|
if let Err(e) = ex.call(params, &mut substate, BytesRef::Fixed(&mut output), &mut NoopTracer, &mut NoopVMTracer) {
|
||||||
|
Loading…
Reference in New Issue
Block a user