mirror of
https://github.com/pezkuwichain/pezkuwi-subxt.git
synced 2026-05-09 23:28:00 +00:00
51c67fe881
* pallet_contracts: Inline benchmark helper that is only used once * Move all max_* Schedule items into a new struct * Limit the number of globals a module can declare * The current limits are too high for wasmi to even execute * Limit the amount of parameters any wasm function is allowed to have * Limit the size the BrTable's immediate value * Add instruction benchmarks * Add new benchmarks to the schedule and make use of it * Add Benchmark Results generated by the bench bot * Add proc macro that implements `Debug` for `Schedule` * Add missing imports necessary for no_std build * Make the WeightDebug macro available for no_std In this case a dummy implementation is derived in order to not blow up the code size akin to the RuntimeDebug macro. * Rework instr_memory_grow benchmark to use only the maximum amount of pages allowed * Add maximum amount of memory when benching (seal_)call/instantiate * cargo run --release --features runtime-benchmarks --manifest-path bin/node/cli/Cargo.toml -- benchmark --chain dev --steps 50 --repeat 20 --extrinsic * --execution=wasm --wasm-execution=compiled --heap-pages=4096 --output ./bin/node/runtime/src/weights --header ./HEADER --pallet pallet_contracts * Added utility benchmark that allows pretty printing of the real schedule * review: Add missing header to the proc-macro lib.rs * review: Clarify why #[allow(dead_code)] attribute is there * review: Fix pwasm-utils line * review: Fixup rand usage * review: Fix typo * review: Imported -> Exported * cargo run --release --features=runtime-benchmarks --manifest-path=bin/node/cli/Cargo.toml -- benchmark --chain=dev --steps=50 --repeat=20 --pallet=pallet_contracts --extrinsic=* --execution=wasm --wasm-execution=compiled --heap-pages=4096 --output=./frame/contracts/src/weights.rs --template=./.maintain/frame-weight-template.hbs * contracts: Adapt to new weight structure * contracts: Fixup runtime WeightInfo * contracts: Remove unneeded fullpath of WeightInfo type * Apply suggestions from code review Co-authored-by: Andrew Jones <ascjones@gmail.com> * Fix typo in schedule.rs Co-authored-by: Andrew Jones <ascjones@gmail.com> * Fix docs in schedule.rs * Apply suggestions from code review Co-authored-by: Nikolay Volf <nikvolf@gmail.com> * Don't publish proc-macro crate until 3.0.0 is ready * Optimize imports for less repetition * Break overlong line Co-authored-by: Parity Benchmarking Bot <admin@parity.io> Co-authored-by: Andrew Jones <ascjones@gmail.com> Co-authored-by: Nikolay Volf <nikvolf@gmail.com>
143 lines
3.9 KiB
Rust
143 lines
3.9 KiB
Rust
// This file is part of Substrate.
|
|
|
|
// Copyright (C) 2020 Parity Technologies (UK) Ltd.
|
|
// SPDX-License-Identifier: Apache-2.0
|
|
|
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
|
// you may not use this file except in compliance with the License.
|
|
// You may obtain a copy of the License at
|
|
//
|
|
// http://www.apache.org/licenses/LICENSE-2.0
|
|
//
|
|
// Unless required by applicable law or agreed to in writing, software
|
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
// See the License for the specific language governing permissions and
|
|
// limitations under the License.
|
|
|
|
//! Proc macros used in the contracts module.
|
|
|
|
#![no_std]
|
|
|
|
extern crate alloc;
|
|
|
|
use proc_macro2::TokenStream;
|
|
use quote::{quote, quote_spanned};
|
|
use syn::spanned::Spanned;
|
|
use syn::{parse_macro_input, Data, DataStruct, DeriveInput, Fields, Ident};
|
|
use alloc::string::ToString;
|
|
|
|
/// This derives `Debug` for a struct where each field must be of some numeric type.
|
|
/// It interprets each field as its represents some weight and formats it as times so that
|
|
/// it is readable by humans.
|
|
#[proc_macro_derive(WeightDebug)]
|
|
pub fn derive_weight_debug(input: proc_macro::TokenStream) -> proc_macro::TokenStream {
|
|
derive_debug(input, format_weight)
|
|
}
|
|
|
|
/// This is basically identical to the std libs Debug derive but without adding any
|
|
/// bounds to existing generics.
|
|
#[proc_macro_derive(ScheduleDebug)]
|
|
pub fn derive_schedule_debug(input: proc_macro::TokenStream) -> proc_macro::TokenStream {
|
|
derive_debug(input, format_default)
|
|
}
|
|
|
|
fn derive_debug(
|
|
input: proc_macro::TokenStream,
|
|
fmt: impl Fn(&Ident) -> TokenStream
|
|
) -> proc_macro::TokenStream {
|
|
let input = parse_macro_input!(input as DeriveInput);
|
|
let name = &input.ident;
|
|
let (impl_generics, ty_generics, where_clause) = input.generics.split_for_impl();
|
|
let data = if let Data::Struct(data) = &input.data {
|
|
data
|
|
} else {
|
|
return quote_spanned! {
|
|
name.span() =>
|
|
compile_error!("WeightDebug is only supported for structs.");
|
|
}.into();
|
|
};
|
|
|
|
#[cfg(feature = "full")]
|
|
let fields = iterate_fields(data, fmt);
|
|
|
|
#[cfg(not(feature = "full"))]
|
|
let fields = {
|
|
drop(fmt);
|
|
drop(data);
|
|
TokenStream::new()
|
|
};
|
|
|
|
let tokens = quote! {
|
|
impl #impl_generics core::fmt::Debug for #name #ty_generics #where_clause {
|
|
fn fmt(&self, formatter: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
|
|
use ::sp_runtime::{FixedPointNumber, FixedU128 as Fixed};
|
|
let mut formatter = formatter.debug_struct(stringify!(#name));
|
|
#fields
|
|
formatter.finish()
|
|
}
|
|
}
|
|
};
|
|
|
|
tokens.into()
|
|
}
|
|
|
|
/// This is only used then the `full` feature is activated.
|
|
#[cfg(feature = "full")]
|
|
fn iterate_fields(data: &DataStruct, fmt: impl Fn(&Ident) -> TokenStream) -> TokenStream {
|
|
match &data.fields {
|
|
Fields::Named(fields) => {
|
|
let recurse = fields.named
|
|
.iter()
|
|
.filter_map(|f| {
|
|
let name = f.ident.as_ref()?;
|
|
if name.to_string().starts_with('_') {
|
|
return None;
|
|
}
|
|
let value = fmt(name);
|
|
let ret = quote_spanned!{ f.span() =>
|
|
formatter.field(stringify!(#name), #value);
|
|
};
|
|
Some(ret)
|
|
});
|
|
quote!{
|
|
#( #recurse )*
|
|
}
|
|
}
|
|
Fields::Unnamed(fields) => quote_spanned!{
|
|
fields.span() =>
|
|
compile_error!("Unnamed fields are not supported")
|
|
},
|
|
Fields::Unit => quote!(),
|
|
}
|
|
}
|
|
|
|
fn format_weight(field: &Ident) -> TokenStream {
|
|
quote_spanned! { field.span() =>
|
|
&if self.#field > 1_000_000_000 {
|
|
format!(
|
|
"{:.1?} ms",
|
|
Fixed::saturating_from_rational(self.#field, 1_000_000_000).to_fraction()
|
|
)
|
|
} else if self.#field > 1_000_000 {
|
|
format!(
|
|
"{:.1?} µs",
|
|
Fixed::saturating_from_rational(self.#field, 1_000_000).to_fraction()
|
|
)
|
|
} else if self.#field > 1_000 {
|
|
format!(
|
|
"{:.1?} ns",
|
|
Fixed::saturating_from_rational(self.#field, 1_000).to_fraction()
|
|
)
|
|
} else {
|
|
format!("{} ps", self.#field)
|
|
}
|
|
}
|
|
}
|
|
|
|
fn format_default(field: &Ident) -> TokenStream {
|
|
quote_spanned! { field.span() =>
|
|
&self.#field
|
|
}
|
|
}
|