referrerpolicy=no-referrer-when-downgrade

polkadot_runtime_parachains/
lib.rs

1// Copyright (C) Parity Technologies (UK) Ltd.
2// This file is part of Polkadot.
3
4// Polkadot is free software: you can redistribute it and/or modify
5// it under the terms of the GNU General Public License as published by
6// the Free Software Foundation, either version 3 of the License, or
7// (at your option) any later version.
8
9// Polkadot is distributed in the hope that it will be useful,
10// but WITHOUT ANY WARRANTY; without even the implied warranty of
11// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12// GNU General Public License for more details.
13
14// You should have received a copy of the GNU General Public License
15// along with Polkadot.  If not, see <http://www.gnu.org/licenses/>.
16
17//! Runtime modules for parachains code.
18//!
19//! It is crucial to include all the modules from this crate in the runtime, in
20//! particular the `Initializer` module, as it is responsible for initializing the state
21//! of the other modules.
22
23#![cfg_attr(feature = "runtime-benchmarks", recursion_limit = "256")]
24#![cfg_attr(not(feature = "std"), no_std)]
25
26pub mod configuration;
27pub mod coretime;
28pub mod disputes;
29pub mod dmp;
30pub mod hrmp;
31pub mod inclusion;
32pub mod initializer;
33pub mod metrics;
34pub mod on_demand;
35pub mod origin;
36pub mod paras;
37pub mod paras_inherent;
38pub mod reward_points;
39pub mod runtime_api_impl;
40pub mod scheduler;
41pub mod session_info;
42pub mod shared;
43
44mod util;
45
46#[cfg(any(feature = "runtime-benchmarks", test))]
47mod builder;
48#[cfg(test)]
49mod mock;
50#[cfg(test)]
51mod ump_tests;
52
53extern crate alloc;
54
55pub use origin::{ensure_parachain, Origin};
56pub use paras::{ParaLifecycle, UpgradeStrategy};
57use polkadot_primitives::{HeadData, Id as ParaId, ValidationCode};
58use sp_arithmetic::traits::Saturating;
59use sp_runtime::{traits::Get, DispatchResult, FixedU128};
60
61/// Trait for tracking message delivery fees on a transport protocol.
62pub trait FeeTracker {
63	/// Type used for assigning different fee factors to different destinations
64	type Id: Copy;
65
66	/// Minimal delivery fee factor.
67	const MIN_FEE_FACTOR: FixedU128 = FixedU128::from_u32(1);
68	/// The factor that is used to increase the current message fee factor when the transport
69	/// protocol is experiencing some lags.
70	const EXPONENTIAL_FEE_BASE: FixedU128 = FixedU128::from_rational(105, 100); // 1.05
71	/// The factor that is used to increase the current message fee factor for every sent kilobyte.
72	const MESSAGE_SIZE_FEE_BASE: FixedU128 = FixedU128::from_rational(1, 1000); // 0.001
73
74	/// Returns the current message fee factor.
75	fn get_fee_factor(id: Self::Id) -> FixedU128;
76
77	/// Sets the current message fee factor.
78	fn set_fee_factor(id: Self::Id, val: FixedU128);
79
80	fn do_increase_fee_factor(fee_factor: &mut FixedU128, message_size: u128) {
81		let message_size_factor = FixedU128::from(message_size.saturating_div(1024))
82			.saturating_mul(Self::MESSAGE_SIZE_FEE_BASE);
83		*fee_factor = fee_factor
84			.saturating_mul(Self::EXPONENTIAL_FEE_BASE.saturating_add(message_size_factor));
85	}
86
87	/// Increases the delivery fee factor by a factor based on message size and records the result.
88	fn increase_fee_factor(id: Self::Id, message_size: u128) {
89		let mut fee_factor = Self::get_fee_factor(id);
90		Self::do_increase_fee_factor(&mut fee_factor, message_size);
91		Self::set_fee_factor(id, fee_factor);
92	}
93
94	fn do_decrease_fee_factor(fee_factor: &mut FixedU128) -> bool {
95		const { assert!(Self::EXPONENTIAL_FEE_BASE.into_inner() >= FixedU128::from_u32(1).into_inner()) }
96
97		if *fee_factor == Self::MIN_FEE_FACTOR {
98			return false;
99		}
100
101		// This should never lead to a panic because of the static assert above.
102		*fee_factor = Self::MIN_FEE_FACTOR.max(*fee_factor / Self::EXPONENTIAL_FEE_BASE);
103		true
104	}
105
106	/// Decreases the delivery fee factor by a constant factor and records the result.
107	///
108	/// Does not reduce the fee factor below the initial value, which is currently set as 1.
109	///
110	/// Returns `true` if the fee factor was actually decreased, `false` otherwise.
111	fn decrease_fee_factor(id: Self::Id) -> bool {
112		let mut fee_factor = Self::get_fee_factor(id);
113		let res = Self::do_decrease_fee_factor(&mut fee_factor);
114		Self::set_fee_factor(id, fee_factor);
115		res
116	}
117}
118
119/// Helper struct used for accessing `FeeTracker::MIN_FEE_FACTOR`
120pub struct GetMinFeeFactor<T>(core::marker::PhantomData<T>);
121
122impl<T: FeeTracker> Get<FixedU128> for GetMinFeeFactor<T> {
123	fn get() -> FixedU128 {
124		T::MIN_FEE_FACTOR
125	}
126}
127
128/// Schedule a para to be initialized at the start of the next session with the given genesis data.
129pub fn schedule_para_initialize<T: paras::Config>(
130	id: ParaId,
131	genesis: paras::ParaGenesisArgs,
132) -> Result<(), ()> {
133	paras::Pallet::<T>::schedule_para_initialize(id, genesis).map_err(|_| ())
134}
135
136/// Schedule a para to be cleaned up at the start of the next session.
137pub fn schedule_para_cleanup<T: paras::Config>(id: polkadot_primitives::Id) -> Result<(), ()> {
138	paras::Pallet::<T>::schedule_para_cleanup(id).map_err(|_| ())
139}
140
141/// Schedule a parathread (on-demand parachain) to be upgraded to a lease holding parachain.
142pub fn schedule_parathread_upgrade<T: paras::Config>(id: ParaId) -> Result<(), ()> {
143	paras::Pallet::<T>::schedule_parathread_upgrade(id).map_err(|_| ())
144}
145
146/// Schedule a lease holding parachain to be downgraded to an on-demand parachain.
147pub fn schedule_parachain_downgrade<T: paras::Config>(id: ParaId) -> Result<(), ()> {
148	paras::Pallet::<T>::schedule_parachain_downgrade(id).map_err(|_| ())
149}
150
151/// Schedules a validation code upgrade to a parachain with the given id.
152pub fn schedule_code_upgrade<T: paras::Config>(
153	id: ParaId,
154	new_code: ValidationCode,
155	set_go_ahead: UpgradeStrategy,
156) -> DispatchResult {
157	paras::Pallet::<T>::schedule_code_upgrade_external(id, new_code, set_go_ahead)
158}
159
160/// Sets the current parachain head with the given id.
161pub fn set_current_head<T: paras::Config>(id: ParaId, new_head: HeadData) {
162	paras::Pallet::<T>::set_current_head(id, new_head)
163}
164
165/// Ensure more initialization for `ParaId` when benchmarking. (e.g. open HRMP channels, ...)
166#[cfg(feature = "runtime-benchmarks")]
167pub trait EnsureForParachain {
168	fn ensure(para_id: ParaId);
169}
170
171#[cfg(feature = "runtime-benchmarks")]
172#[impl_trait_for_tuples::impl_for_tuples(30)]
173impl EnsureForParachain for Tuple {
174	fn ensure(para: ParaId) {
175		for_tuples!( #(
176			Tuple::ensure(para);
177		)* );
178	}
179}