Skip to content
This repository was archived by the owner on Mar 13, 2023. It is now read-only.

Commit 88588e1

Browse files
author
bear
authored
Gas to weight = ? (#718)
* Add main framework and make it compile * Add benchmark file * Clean code * Update gas to weight radio * Remove benchmark script * Format work * Use array-bytes
1 parent 615a92f commit 88588e1

File tree

8 files changed

+211
-23
lines changed

8 files changed

+211
-23
lines changed

Cargo.lock

+2
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

bin/node/runtime/pangolin/Cargo.toml

+1
Original file line numberDiff line numberDiff line change
@@ -230,6 +230,7 @@ runtime-benchmarks = [
230230
"frame-support/runtime-benchmarks",
231231
"pallet-collective/runtime-benchmarks",
232232
"pallet-society/runtime-benchmarks",
233+
"darwinia-evm/runtime-benchmarks",
233234
"darwinia-s2s-issuing/runtime-benchmarks",
234235
]
235236

bin/node/runtime/pangolin/src/lib.rs

+1
Original file line numberDiff line numberDiff line change
@@ -871,6 +871,7 @@ impl_runtime_apis! {
871871
let params = (&config, &whitelist);
872872

873873
add_benchmark!(params, batches, frame_system, SystemBench::<Runtime>);
874+
add_benchmark!(params, batches, darwinia_evm, EVM);
874875
add_benchmark!(params, batches, darwinia_s2s_issuing, Substrate2SubstrateIssuing);
875876

876877
if batches.is_empty() { return Err("Benchmark not found for this pallet.".into()) }

bin/node/runtime/pangolin/src/pallets/evm_.rs

+2-14
Original file line numberDiff line numberDiff line change
@@ -17,9 +17,7 @@ use sp_core::{crypto::Public, H160, U256};
1717
use sp_std::marker::PhantomData;
1818
// --- darwinia ---
1919
use crate::*;
20-
use darwinia_evm::{
21-
runner::stack::Runner, ConcatAddressMapping, Config, EnsureAddressTruncated, GasWeightMapping,
22-
};
20+
use darwinia_evm::{runner::stack::Runner, ConcatAddressMapping, Config, EnsureAddressTruncated};
2321
use dp_evm::{Precompile, PrecompileSet};
2422
use dvm_ethereum::{
2523
account_basic::{DvmAccountBasic, KtonRemainBalance, RingRemainBalance},
@@ -72,24 +70,14 @@ where
7270
}
7371
}
7472

75-
pub struct DarwiniaGasWeightMapping;
76-
impl GasWeightMapping for DarwiniaGasWeightMapping {
77-
fn gas_to_weight(gas: u64) -> Weight {
78-
gas * 1_000 as Weight
79-
}
80-
fn weight_to_gas(weight: Weight) -> u64 {
81-
weight / 1_000
82-
}
83-
}
84-
8573
frame_support::parameter_types! {
8674
pub const ChainId: u64 = 43;
8775
pub BlockGasLimit: U256 = u32::max_value().into();
8876
}
8977

9078
impl Config for Runtime {
9179
type FeeCalculator = dvm_dynamic_fee::Pallet<Self>;
92-
type GasWeightMapping = DarwiniaGasWeightMapping;
80+
type GasWeightMapping = ();
9381
type CallOrigin = EnsureAddressTruncated<Self::AccountId>;
9482
type AddressMapping = ConcatAddressMapping<Self::AccountId>;
9583
type FindAuthor = EthereumFindAuthor<Babe>;

frame/evm/Cargo.toml

+14-7
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ version = "2.5.0"
1111

1212
[dependencies]
1313
# crates.io
14+
array-bytes = { version = "1.3.3" }
1415
codec = { package = "parity-scale-codec", version = "2.1.1", default-features = false }
1516
evm = { version = "0.27.0", default-features = false, features = ["with-codec"] }
1617
evm-gasometer = { version = "0.27.0", default-features = false }
@@ -24,13 +25,14 @@ sha3 = { version = "0.9.1", default-features = false }
2425
darwinia-balances = { default-features = false, path = "../balances" }
2526
dp-evm = { default-features = false, path = "../../primitives/evm" }
2627
# paritytech
27-
frame-support = { default-features = false, git = "https://github.com/darwinia-network/substrate", branch = "main" }
28-
frame-system = { default-features = false, git = "https://github.com/darwinia-network/substrate", branch = "main" }
29-
pallet-timestamp = { default-features = false, git = "https://github.com/darwinia-network/substrate", branch = "main" }
30-
sp-core = { default-features = false, git = "https://github.com/darwinia-network/substrate", branch = "main" }
31-
sp-io = { default-features = false, git = "https://github.com/darwinia-network/substrate", branch = "main" }
32-
sp-runtime = { default-features = false, git = "https://github.com/darwinia-network/substrate", branch = "main" }
33-
sp-std = { default-features = false, git = "https://github.com/darwinia-network/substrate", branch = "main" }
28+
frame-benchmarking = { optional = true, default-features = false, git = "https://github.com/darwinia-network/substrate", branch = "main" }
29+
frame-support = { default-features = false, git = "https://github.com/darwinia-network/substrate", branch = "main" }
30+
frame-system = { default-features = false, git = "https://github.com/darwinia-network/substrate", branch = "main" }
31+
pallet-timestamp = { default-features = false, git = "https://github.com/darwinia-network/substrate", branch = "main" }
32+
sp-core = { default-features = false, git = "https://github.com/darwinia-network/substrate", branch = "main" }
33+
sp-io = { default-features = false, git = "https://github.com/darwinia-network/substrate", branch = "main" }
34+
sp-runtime = { default-features = false, git = "https://github.com/darwinia-network/substrate", branch = "main" }
35+
sp-std = { default-features = false, git = "https://github.com/darwinia-network/substrate", branch = "main" }
3436

3537
[dev-dependencies]
3638
darwinia-support = { features = ["easy-testing"], path = "../support" }
@@ -53,6 +55,7 @@ std = [
5355
"darwinia-balances/std",
5456
"dp-evm/std",
5557
# paritytech
58+
"frame-benchmarking/std",
5659
"frame-support/std",
5760
"frame-system/std",
5861
"pallet-timestamp/std",
@@ -61,3 +64,7 @@ std = [
6164
"sp-runtime/std",
6265
"sp-std/std",
6366
]
67+
68+
runtime-benchmarks = [
69+
"frame-benchmarking",
70+
]

frame/evm/src/benchmarking.rs

+106
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,106 @@
1+
// This file is part of Darwinia.
2+
//
3+
// Copyright (C) 2018-2021 Darwinia Network
4+
// SPDX-License-Identifier: GPL-3.0
5+
//
6+
// Darwinia is free software: you can redistribute it and/or modify
7+
// it under the terms of the GNU General Public License as published by
8+
// the Free Software Foundation, either version 3 of the License, or
9+
// (at your option) any later version.
10+
//
11+
// Darwinia is distributed in the hope that it will be useful,
12+
// but WITHOUT ANY WARRANTY; without even the implied warranty of
13+
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14+
// GNU General Public License for more details.
15+
//
16+
// You should have received a copy of the GNU General Public License
17+
// along with Darwinia. If not, see <https://www.gnu.org/licenses/>.
18+
19+
#![cfg(feature = "runtime-benchmarks")]
20+
21+
//! Benchmarking
22+
use crate::{runner::Runner, Config, Pallet};
23+
use frame_benchmarking::benchmarks;
24+
use rlp::RlpStream;
25+
use sha3::{Digest, Keccak256};
26+
use sp_core::{H160, U256};
27+
use sp_std::vec;
28+
29+
benchmarks! {
30+
31+
// This benchmark tests the relationship between gas and weight. It deploys a contract which
32+
// has an infinite loop in a public function. We then call this function with varying amounts
33+
// of gas, expecting it to OOG. The benchmarking framework measures the amount of time (aka
34+
// weight) it takes before OOGing and relates that to the amount of gas provided, leaving us
35+
// with an estimate for gas-to-weight mapping.
36+
runner_execute {
37+
38+
let x in 1..10000000;
39+
40+
// contract bytecode below is for:
41+
//
42+
// pragma solidity >=0.8.0;
43+
//
44+
// contract InfiniteContractVar {
45+
// uint public count;
46+
47+
// constructor() public {
48+
// count = 0;
49+
// }
50+
51+
// function infinite() public {
52+
// while (true) {
53+
// count=count+1;
54+
// }
55+
// }
56+
// }
57+
58+
let contract_bytecode = array_bytes::hex2bytes("0x608060405234801561001057600080fd5b506000808190555061017c806100276000396000f3fe608060405234801561001057600080fd5b50600436106100365760003560e01c806306661abd1461003b5780635bec9e6714610059575b600080fd5b610043610063565b604051610050919061009c565b60405180910390f35b610061610069565b005b60005481565b5b60011561008b57600160005461008091906100b7565b60008190555061006a565b565b6100968161010d565b82525050565b60006020820190506100b1600083018461008d565b92915050565b60006100c28261010d565b91506100cd8361010d565b9250827fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff0382111561010257610101610117565b5b828201905092915050565b6000819050919050565b7f4e487b7100000000000000000000000000000000000000000000000000000000600052601160045260246000fdfea26469706673582212207891ca3e64b75f98d843216c9d58cb2867b04996d7d4d731187616e330987fc764736f6c63430008040033").unwrap();
59+
let caller = H160::default();
60+
61+
let mut nonce: u64 = 0;
62+
let nonce_as_u256: U256 = nonce.into();
63+
64+
let value = U256::default();
65+
let gas_limit_create: u64 = 1_250_000 * 1_000_000_000;
66+
let create_runner_results = T::Runner::create(
67+
caller,
68+
contract_bytecode,
69+
value,
70+
gas_limit_create,
71+
None,
72+
Some(nonce_as_u256),
73+
T::config(),
74+
);
75+
assert_eq!(create_runner_results.is_ok(), true, "create() failed");
76+
77+
// derive the resulting contract address from our create
78+
let mut rlp = RlpStream::new_list(2);
79+
rlp.append(&caller);
80+
rlp.append(&0u8);
81+
let contract_address = H160::from_slice(&Keccak256::digest(&rlp.out())[12..]);
82+
83+
// derive encoded contract call -- in this case, just the function selector
84+
let mut encoded_call = vec![0u8; 4];
85+
encoded_call[0..4].copy_from_slice(&Keccak256::digest(b"infinite()")[0..4]);
86+
87+
let gas_limit_call = x as u64;
88+
89+
}: {
90+
91+
nonce = nonce + 1;
92+
let nonce_as_u256: U256 = nonce.into();
93+
94+
let call_runner_results = T::Runner::call(
95+
caller,
96+
contract_address,
97+
encoded_call,
98+
value,
99+
gas_limit_call,
100+
None,
101+
Some(nonce_as_u256),
102+
T::config(),
103+
);
104+
assert_eq!(call_runner_results.is_ok(), true, "call() failed");
105+
}
106+
}

frame/evm/src/lib.rs

+5-2
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,8 @@
2323

2424
pub mod runner;
2525

26+
#[cfg(feature = "runtime-benchmarks")]
27+
mod benchmarking;
2628
#[cfg(test)]
2729
mod tests;
2830

@@ -446,12 +448,13 @@ pub trait GasWeightMapping {
446448
fn gas_to_weight(gas: u64) -> Weight;
447449
fn weight_to_gas(weight: Weight) -> u64;
448450
}
451+
// The radio of gas to weight comes from benchmark test
449452
impl GasWeightMapping for () {
450453
fn gas_to_weight(gas: u64) -> Weight {
451-
gas as Weight
454+
gas * 16_000 as Weight
452455
}
453456
fn weight_to_gas(weight: Weight) -> u64 {
454-
weight
457+
weight / 16_000
455458
}
456459
}
457460

frame/evm/src/weight.rs

+80
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,80 @@
1+
// This file is part of Substrate.
2+
3+
// Copyright (C) 2020 Parity Technologies (UK) Ltd.
4+
// SPDX-License-Identifier: Apache-2.0
5+
6+
// Licensed under the Apache License, Version 2.0 (the "License");
7+
// you may not use this file except in compliance with the License.
8+
// You may obtain a copy of the License at
9+
//
10+
// http://www.apache.org/licenses/LICENSE-2.0
11+
//
12+
// Unless required by applicable law or agreed to in writing, software
13+
// distributed under the License is distributed on an "AS IS" BASIS,
14+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15+
// See the License for the specific language governing permissions and
16+
// limitations under the License.
17+
18+
//! Autogenerated weights for darwinia_evm
19+
//!
20+
//! THIS FILE WAS AUTO-GENERATED USING THE SUBSTRATE BENCHMARK CLI VERSION 3.0.0
21+
//! DATE: 2021-07-23, STEPS: [5, ], REPEAT: 2, LOW RANGE: [], HIGH RANGE: []
22+
//! EXECUTION: Some(Wasm), WASM-EXECUTION: Compiled, CHAIN: Some("dev"), DB CACHE: 128
23+
24+
// Executed Command:
25+
// ./target/release/drml
26+
// benchmark
27+
// --chain
28+
// dev
29+
// --pallet
30+
// darwinia_evm
31+
// --execution
32+
// wasm
33+
// --wasm-execution
34+
// compiled
35+
// --extrinsic=runner_execute
36+
// --steps
37+
// 5
38+
// --repeat
39+
// 2
40+
// --raw
41+
// --heap-pages=4096
42+
// --output=./frame/evm/src/weight.rs
43+
// --template=./.maintain/frame-weight-template.hbs
44+
45+
46+
#![allow(unused_parens)]
47+
#![allow(unused_imports)]
48+
49+
use frame_support::{traits::Get, weights::{Weight, constants::RocksDbWeight}};
50+
use sp_std::marker::PhantomData;
51+
52+
/// Weight functions needed for darwinia_evm.
53+
pub trait WeightInfo {
54+
fn runner_execute(x: u32, ) -> Weight;
55+
56+
}
57+
58+
/// Weights for darwinia_evm using the Substrate node and recommended hardware.
59+
pub struct SubstrateWeight<T>(PhantomData<T>);
60+
impl<T: frame_system::Config> WeightInfo for SubstrateWeight<T> {
61+
fn runner_execute(x: u32, ) -> Weight {
62+
(0 as Weight)
63+
// Standard Error: 0
64+
.saturating_add((16_000 as Weight).saturating_mul(x as Weight))
65+
.saturating_add(T::DbWeight::get().reads(4 as Weight))
66+
67+
}
68+
69+
}
70+
71+
// For backwards compatibility and tests
72+
impl WeightInfo for () {
73+
fn runner_execute(x: u32, ) -> Weight {
74+
(0 as Weight)
75+
.saturating_add((16_000 as Weight).saturating_mul(x as Weight))
76+
.saturating_add(RocksDbWeight::get().reads(4 as Weight))
77+
78+
}
79+
80+
}

0 commit comments

Comments
 (0)