diff --git a/ethcore/Cargo.toml b/ethcore/Cargo.toml
index 0ea0023d6..acdcd667a 100644
--- a/ethcore/Cargo.toml
+++ b/ethcore/Cargo.toml
@@ -43,3 +43,4 @@ json-tests = []
test-heavy = []
dev = ["clippy"]
default = []
+benches = []
diff --git a/ethcore/src/evm/benches/mod.rs b/ethcore/src/evm/benches/mod.rs
new file mode 100644
index 000000000..8ef730d88
--- /dev/null
+++ b/ethcore/src/evm/benches/mod.rs
@@ -0,0 +1,126 @@
+// Copyright 2015, 2016 Ethcore (UK) Ltd.
+// This file is part of Parity.
+
+// Parity is free software: you can redistribute it and/or modify
+// it under the terms of the GNU General Public License as published by
+// the Free Software Foundation, either version 3 of the License, or
+// (at your option) any later version.
+
+// Parity is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License
+// along with Parity. If not, see .
+
+//! benchmarking for EVM
+//! should be started with:
+//! ```bash
+//! multirust run nightly cargo bench
+//! ```
+
+extern crate test;
+
+use self::test::{Bencher, black_box};
+
+use common::*;
+use evm::{self, Factory, VMType};
+use evm::tests::FakeExt;
+
+#[bench]
+fn simple_loop_log0_usize(b: &mut Bencher) {
+ simple_loop_log0(U256::from(::std::usize::MAX), b)
+}
+
+#[bench]
+fn simple_loop_log0_u256(b: &mut Bencher) {
+ simple_loop_log0(!U256::zero(), b)
+}
+
+fn simple_loop_log0(gas: U256, b: &mut Bencher) {
+ let mut vm = Factory::new(VMType::Interpreter).create(gas);
+ let mut ext = FakeExt::new();
+
+ let address = Address::from_str("0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6").unwrap();
+ let code = black_box(
+ "62ffffff5b600190036000600fa0600357".from_hex().unwrap()
+ );
+
+ b.iter(|| {
+ let mut params = ActionParams::default();
+ params.address = address.clone();
+ params.gas = gas;
+ params.code = Some(code.clone());
+
+ result(vm.exec(params, &mut ext))
+ });
+}
+
+#[bench]
+fn mem_gas_calculation_same_usize(b: &mut Bencher) {
+ mem_gas_calculation_same(U256::from(::std::usize::MAX), b)
+}
+
+#[bench]
+fn mem_gas_calculation_same_u256(b: &mut Bencher) {
+ mem_gas_calculation_same(!U256::zero(), b)
+}
+
+fn mem_gas_calculation_same(gas: U256, b: &mut Bencher) {
+ let mut vm = Factory::new(VMType::Interpreter).create(gas);
+ let mut ext = FakeExt::new();
+
+ let address = Address::from_str("0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6").unwrap();
+
+ b.iter(|| {
+ let code = black_box(
+ "6110006001556001546000555b610fff805560016000540380600055600c57".from_hex().unwrap()
+ );
+
+ let mut params = ActionParams::default();
+ params.address = address.clone();
+ params.gas = gas;
+ params.code = Some(code.clone());
+
+ result(vm.exec(params, &mut ext))
+ });
+}
+
+#[bench]
+fn mem_gas_calculation_increasing_usize(b: &mut Bencher) {
+ mem_gas_calculation_increasing(U256::from(::std::usize::MAX), b)
+}
+
+#[bench]
+fn mem_gas_calculation_increasing_u256(b: &mut Bencher) {
+ mem_gas_calculation_increasing(!U256::zero(), b)
+}
+
+fn mem_gas_calculation_increasing(gas: U256, b: &mut Bencher) {
+ let mut vm = Factory::new(VMType::Interpreter).create(gas);
+ let mut ext = FakeExt::new();
+
+ let address = Address::from_str("0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6").unwrap();
+
+ b.iter(|| {
+ let code = black_box(
+ "6110006001556001546000555b610fff60005401805560016000540380600055600c57".from_hex().unwrap()
+ );
+
+ let mut params = ActionParams::default();
+ params.address = address.clone();
+ params.gas = gas;
+ params.code = Some(code.clone());
+
+ result(vm.exec(params, &mut ext))
+ });
+}
+
+fn result(r: evm::Result) -> U256 {
+ match r {
+ Ok(evm::GasLeft::Known(v)) => v,
+ Ok(evm::GasLeft::NeedsReturn(v, _)) => v,
+ _ => U256::zero(),
+ }
+}
diff --git a/ethcore/src/evm/evm.rs b/ethcore/src/evm/evm.rs
index 740774f38..43919034e 100644
--- a/ethcore/src/evm/evm.rs
+++ b/ethcore/src/evm/evm.rs
@@ -95,6 +95,61 @@ impl<'a> Finalize for Result> {
}
}
+pub trait CostType: ops::Mul