Skip to content
This repository was archived by the owner on Nov 15, 2023. It is now read-only.
Prev Previous commit
Next Next commit
Extract multiplier update stuff from system
  • Loading branch information
kianenigma committed Oct 14, 2019
commit 9b9971d15cca20a6e018b2573d306a3eefdcff8c
39 changes: 36 additions & 3 deletions core/sr-primitives/src/sr_arithmetic.rs
Original file line number Diff line number Diff line change
Expand Up @@ -543,7 +543,6 @@ implement_per_thing!(

/// An unsigned fixed point number. Can hold any value in the range [-9_223_372_036, 9_223_372_036]
/// with fixed point accuracy of one billion.
#[cfg_attr(feature = "std", derive(Debug))]
#[derive(Encode, Decode, Default, Copy, Clone, PartialEq, Eq, PartialOrd, Ord)]
pub struct Fixed64(i64);

Expand Down Expand Up @@ -668,6 +667,13 @@ impl CheckedAdd for Fixed64 {
}
}

#[cfg(feature = "std")]
impl rstd::fmt::Debug for Fixed64 {
fn fmt(&self, f: &mut rstd::fmt::Formatter<'_>) -> rstd::fmt::Result {
write!(f, "Fixed64({},{})", self.0 / DIV, (self.0 % DIV) / 1000)
}
}

/// Infinite precision unsigned integer for substrate runtime.
pub mod biguint {
use super::Zero;
Expand Down Expand Up @@ -981,8 +987,6 @@ pub mod biguint {
let mut q = Self::with_capacity(m + 1);
let mut r = Self::with_capacity(n);

debug_assert!(other.msb() != 0);

// PROOF: 0 <= normalizer_bits < SHIFT 0 <= normalizer < B. all conversions are
// safe.
let normalizer_bits = other.msb().leading_zeros() as Single;
Expand Down Expand Up @@ -2136,6 +2140,35 @@ mod tests_fixed64 {
assert_eq!(max(), Fixed64::from_natural(9_223_372_037));
}

#[test]
fn fixed_64_growth_decrease_curve() {
let test_set = vec![0u32, 1, 10, 1000, 1_000_000_000];

// negative (1/2)
let mut fm = Fixed64::from_rational(-1, 2);
test_set.clone().into_iter().for_each(|i| {
assert_eq!(fm.saturated_multiply_accumulate(i) as i32, i as i32 - i as i32 / 2);
});

// unit (1) multiplier
fm = Fixed64::from_parts(0);
test_set.clone().into_iter().for_each(|i| {
assert_eq!(fm.saturated_multiply_accumulate(i), i);
});

// i.5 multiplier
fm = Fixed64::from_rational(1, 2);
test_set.clone().into_iter().for_each(|i| {
assert_eq!(fm.saturated_multiply_accumulate(i), i * 3 / 2);
});

// dual multiplier
fm = Fixed64::from_rational(1, 1);
test_set.clone().into_iter().for_each(|i| {
assert_eq!(fm.saturated_multiply_accumulate(i), i * 2);
});
}

macro_rules! saturating_mul_acc_test {
($num_type:tt) => {
assert_eq!(
Expand Down
76 changes: 0 additions & 76 deletions core/sr-primitives/src/weights.rs
Original file line number Diff line number Diff line change
Expand Up @@ -23,9 +23,6 @@
//! Note that the decl_module macro _cannot_ enforce this and will simply fail if an invalid struct
//! (something that does not implement `Weighable`) is passed in.

use crate::{Fixed64, traits::Saturating};
use crate::codec::{Encode, Decode};

pub use crate::transaction_validity::TransactionPriority;
use crate::traits::Bounded;

Expand Down Expand Up @@ -167,76 +164,3 @@ impl Default for SimpleDispatchInfo {
SimpleDispatchInfo::FixedNormal(10_000)
}
}

/// Representation of a weight multiplier. This represents how a fee value can be computed from a
/// weighted transaction.
///
/// This is basically a wrapper for the `Fixed64` type a slightly tailored multiplication to u32
/// in the form of the `apply_to` method.
#[cfg_attr(feature = "std", derive(Debug))]
#[derive(Encode, Decode, Default, Copy, Clone, PartialEq, Eq, PartialOrd, Ord)]
pub struct WeightMultiplier(Fixed64);

impl WeightMultiplier {
/// Apply the inner Fixed64 as a weight multiplier to a weight value.
///
/// This will perform a saturated `weight + weight * self.0`.
pub fn apply_to(&self, weight: Weight) -> Weight {
self.0.saturated_multiply_accumulate(weight)
}

/// build self from raw parts per billion.
#[cfg(feature = "std")]
pub fn from_parts(parts: i64) -> Self {
Self(Fixed64::from_parts(parts))
}

/// build self from a fixed64 value.
pub fn from_fixed(f: Fixed64) -> Self {
Self(f)
}

/// Approximate the fraction `n/d`.
pub fn from_rational(n: i64, d: u64) -> Self {
Self(Fixed64::from_rational(n, d))
}
}

impl Saturating for WeightMultiplier {
fn saturating_add(self, rhs: Self) -> Self {
Self(self.0.saturating_add(rhs.0))
}
fn saturating_mul(self, rhs: Self) -> Self {
Self(self.0.saturating_mul(rhs.0))

}
fn saturating_sub(self, rhs: Self) -> Self {
Self(self.0.saturating_sub(rhs.0))
}
}

#[cfg(test)]
mod tests {
use super::*;

#[test]
fn multiplier_apply_to_works() {
let test_set = vec![0, 1, 10, 1000, 1_000_000_000];

// negative (1/2)
let mut fm = WeightMultiplier::from_rational(-1, 2);
test_set.clone().into_iter().for_each(|i| { assert_eq!(fm.apply_to(i) as i32, i as i32 - i as i32 / 2); });

// unit (1) multiplier
fm = WeightMultiplier::from_parts(0);
test_set.clone().into_iter().for_each(|i| { assert_eq!(fm.apply_to(i), i); });

// i.5 multiplier
fm = WeightMultiplier::from_rational(1, 2);
test_set.clone().into_iter().for_each(|i| { assert_eq!(fm.apply_to(i), i * 3 / 2); });

// dual multiplier
fm = WeightMultiplier::from_rational(1, 1);
test_set.clone().into_iter().for_each(|i| { assert_eq!(fm.apply_to(i), i * 2); });
}
}
1 change: 0 additions & 1 deletion core/test-runtime/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -382,7 +382,6 @@ impl srml_system::Trait for Runtime {
type Lookup = IdentityLookup<Self::AccountId>;
type Header = Header;
type Event = Event;
type WeightMultiplierUpdate = ();
type BlockHashCount = BlockHashCount;
type MaximumBlockWeight = MaximumBlockWeight;
type MaximumBlockLength = MaximumBlockLength;
Expand Down
2 changes: 0 additions & 2 deletions node-template/runtime/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -166,8 +166,6 @@ impl system::Trait for Runtime {
type Header = generic::Header<BlockNumber, BlakeTwo256>;
/// The ubiquitous event type.
type Event = Event;
/// Update weight (to fee) multiplier per-block.
type WeightMultiplierUpdate = ();
/// The ubiquitous origin type.
type Origin = Origin;
/// Maximum number of block number to block hash mappings to keep (oldest pruned first).
Expand Down
1 change: 0 additions & 1 deletion node-template/runtime/src/template.rs
Original file line number Diff line number Diff line change
Expand Up @@ -101,7 +101,6 @@ mod tests {
type AccountId = u64;
type Lookup = IdentityLookup<Self::AccountId>;
type Header = Header;
type WeightMultiplierUpdate = ();
type Event = ();
type BlockHashCount = BlockHashCount;
type MaximumBlockWeight = MaximumBlockWeight;
Expand Down
25 changes: 14 additions & 11 deletions node/executor/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -46,16 +46,16 @@ mod tests {
traits::{CodeExecutor, Externalities}, storage::well_known_keys,
};
use sr_primitives::{
assert_eq_error_rate,
assert_eq_error_rate, Fixed64,
traits::{Header as HeaderT, Hash as HashT, Convert}, ApplyResult,
transaction_validity::InvalidTransaction, weights::{WeightMultiplier, GetDispatchInfo},
transaction_validity::InvalidTransaction, weights::GetDispatchInfo,
};
use contracts::ContractAddressFor;
use substrate_executor::{NativeExecutor, WasmExecutionMethod};
use system::{EventRecord, Phase};
use node_runtime::{
Header, Block, UncheckedExtrinsic, CheckedExtrinsic, Call, Runtime, Balances, BuildStorage,
System, Event, TransferFee, TransactionBaseFee, TransactionByteFee,
System, TransactionPayment, Event, TransferFee, TransactionBaseFee, TransactionByteFee,
constants::currency::*, impls::WeightToFee,
};
use node_primitives::{Balance, Hash, BlockNumber};
Expand Down Expand Up @@ -96,7 +96,7 @@ mod tests {
let weight = default_transfer_call().get_dispatch_info().weight;
// NOTE: this is really hard to apply, since the multiplier of each block needs to be fetched
// before the block, while we compute this after the block.
// weight = <system::Module<Runtime>>::next_weight_multiplier().apply_to(weight);
// weight = TransactionPayment::next_fee_multiplier().apply_to(weight);
let weight_fee = <Runtime as transaction_payment::Trait>::WeightToFee::convert(weight);
length_fee + weight_fee + TransferFee::get()
}
Expand Down Expand Up @@ -890,13 +890,14 @@ mod tests {


#[test]
fn weight_multiplier_increases_and_decreases_on_big_weight() {
fn fee_multiplier_increases_and_decreases_on_big_weight() {
let mut t = new_test_ext(COMPACT_CODE, false);

let mut prev_multiplier = WeightMultiplier::default();
// initial fee multiplier must be zero
let mut prev_multiplier = Fixed64::from_parts(0);

sr_primitives::set_and_run_with_externalities(&mut t, || {
assert_eq!(System::next_weight_multiplier(), prev_multiplier);
assert_eq!(TransactionPayment::next_fee_multiplier(), prev_multiplier);
});

let mut tt = new_test_ext(COMPACT_CODE, false);
Expand Down Expand Up @@ -946,9 +947,9 @@ mod tests {
None,
).0.unwrap();

// weight multiplier is increased for next block.
// fee multiplier is increased for next block.
sr_primitives::set_and_run_with_externalities(&mut t, || {
let fm = System::next_weight_multiplier();
let fm = TransactionPayment::next_fee_multiplier();
println!("After a big block: {:?} -> {:?}", prev_multiplier, fm);
assert!(fm > prev_multiplier);
prev_multiplier = fm;
Expand All @@ -965,7 +966,7 @@ mod tests {

// weight multiplier is increased for next block.
sr_primitives::set_and_run_with_externalities(&mut t, || {
let fm = System::next_weight_multiplier();
let fm = TransactionPayment::next_fee_multiplier();
println!("After a small block: {:?} -> {:?}", prev_multiplier, fm);
assert!(fm < prev_multiplier);
});
Expand All @@ -978,7 +979,7 @@ mod tests {
// weight of transfer call as of now: 1_000_000
// if weight of the cheapest weight would be 10^7, this would be 10^9, which is:
// - 1 MILLICENTS in substrate node.
// - 1 milldot based on current polkadot runtime.
// - 1 milli-dot based on current polkadot runtime.
// (this baed on assigning 0.1 CENT to the cheapest tx with `weight = 100`)
let mut t = TestExternalities::<Blake2Hasher>::new_with_code(COMPACT_CODE, (map![
<balances::FreeBalance<Runtime>>::hashed_key_for(alice()) => {
Expand Down Expand Up @@ -1052,6 +1053,7 @@ mod tests {
fn block_weight_capacity_report() {
// Just report how many transfer calls you could fit into a block. The number should at least
// be a few hundred (250 at the time of writing but can change over time). Runs until panic.
use node_primitives::Index;

// execution ext.
let mut t = new_test_ext(COMPACT_CODE, false);
Expand Down Expand Up @@ -1118,6 +1120,7 @@ mod tests {
// Just report how big a block can get. Executes until panic. Should be ignored unless if
// manually inspected. The number should at least be a few megabytes (5 at the time of
// writing but can change over time).
use node_primitives::Index;

// execution ext.
let mut t = new_test_ext(COMPACT_CODE, false);
Expand Down
8 changes: 4 additions & 4 deletions node/runtime/src/constants.rs
Original file line number Diff line number Diff line change
Expand Up @@ -67,10 +67,10 @@ pub mod time {
pub const DAYS: BlockNumber = HOURS * 24;
}

// CRITICAL NOTE: The system module maintains two constants: a _maximum_ block weight and a
// _ratio_ of it yielding the portion which is accessible to normal transactions (reserving the rest
// for operational ones). `TARGET_BLOCK_FULLNESS` is entirely independent and the system module is
// not aware of if, nor should it care about it. This constant simply denotes on which ratio of the
// CRITICAL NOTE: The system module maintains two constants: a _maximum_ block weight and a _ratio_
// of it yielding the portion which is accessible to normal transactions (reserving the rest for
// operational ones). `TARGET_BLOCK_FULLNESS` is entirely independent and the system module is not
// aware of if, nor should it care about it. This constant simply denotes on which ratio of the
// _maximum_ block weight we tweak the fees. It does NOT care about the type of the dispatch.
//
// For the system to be configured in a sane way, `TARGET_BLOCK_FULLNESS` should always be less than
Expand Down
Loading