idn_runtime/configs/
mod.rs

1/*
2 * Copyright 2025 by Ideal Labs, LLC
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *     http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#[path = "xcm.rs"]
18pub(crate) mod xcm_config;
19
20mod contracts;
21mod xcm_weights;
22
23// Substrate and Polkadot dependencies
24use bp_idn::{
25	impls,
26	types::{self},
27};
28use cumulus_pallet_parachain_system::RelayNumberMonotonicallyIncreases;
29use cumulus_primitives_core::AggregateMessageOrigin;
30use frame_support::{
31	derive_impl,
32	dispatch::DispatchClass,
33	parameter_types,
34	traits::{
35		tokens::imbalance::ResolveTo, ConstBool, ConstU32, ConstU64, ConstU8, EitherOfDiverse,
36		VariantCountOf,
37	},
38	weights::{ConstantMultiplier, Weight},
39	PalletId,
40};
41use frame_system::{
42	limits::{BlockLength, BlockWeights},
43	EnsureRoot,
44};
45#[cfg(not(feature = "runtime-benchmarks"))]
46use pallet_idn_manager::primitives::AllowSiblingsOnly;
47use pallet_idn_manager::{BalanceOf, SubscriptionOf};
48use pallet_xcm::{EnsureXcm, IsVoiceOfBody};
49use polkadot_runtime_common::{BlockHashCount, SlowAdjustingFeeUpdate};
50use sp_consensus_aura::sr25519::AuthorityId as AuraId;
51use sp_version::RuntimeVersion;
52use xcm::prelude::BodyId;
53
54// Local module imports
55#[cfg(not(feature = "runtime-benchmarks"))]
56use super::PolkadotXcm;
57use super::{
58	weights::{
59		BalancesWeightInfo, BlockExecutionWeight, CollatorSelectionWeightInfo,
60		CumulusParachainSystemWeightInfo, ExtrinsicBaseWeight, IdnManagerWeightInfo,
61		RandomnessBeaconWeightInfo, RocksDbWeight, SessionWeightInfo, SudoWeightInfo,
62		SystemWeightInfo, TimestampWeightInfo, TransactionPaymentWeightInfo,
63	},
64	AccountId, Aura, Balance, Balances, Block, BlockNumber, CollatorSelection, ConsensusHook, Hash,
65	MessageQueue, Nonce, PalletInfo, RandomnessCollectiveFlip, Runtime, RuntimeCall, RuntimeEvent,
66	RuntimeFreezeReason, RuntimeHoldReason, RuntimeOrigin, RuntimeTask, Session, SessionKeys,
67	System, WeightToFee, XcmpQueue, AVERAGE_ON_INITIALIZE_RATIO, EXISTENTIAL_DEPOSIT, HOURS,
68	MAXIMUM_BLOCK_WEIGHT, MICROUNIT, NORMAL_DISPATCH_RATIO, SLOT_DURATION, VERSION,
69};
70use xcm_config::RelayLocation;
71
72parameter_types! {
73	pub const Version: RuntimeVersion = VERSION;
74
75	// This part is copied from Substrate's `bin/node/runtime/src/lib.rs`.
76	//  The `RuntimeBlockLength` and `RuntimeBlockWeights` exist here because the
77	// `DeletionWeightLimit` and `DeletionQueueDepth` depend on those to parameterize
78	// the lazy contract deletion.
79	pub RuntimeBlockLength: BlockLength =
80		BlockLength::max_with_normal_ratio(5 * 1024 * 1024, NORMAL_DISPATCH_RATIO);
81	pub RuntimeBlockWeights: BlockWeights = BlockWeights::builder()
82		.base_block(BlockExecutionWeight::get())
83		.for_class(DispatchClass::all(), |weights| {
84			weights.base_extrinsic = ExtrinsicBaseWeight::get();
85		})
86		.for_class(DispatchClass::Normal, |weights| {
87			weights.max_total = Some(NORMAL_DISPATCH_RATIO * MAXIMUM_BLOCK_WEIGHT);
88		})
89		.for_class(DispatchClass::Operational, |weights| {
90			weights.max_total = Some(MAXIMUM_BLOCK_WEIGHT);
91			// Operational transactions have some extra reserved space, so that they
92			// are included even if block reached `MAXIMUM_BLOCK_WEIGHT`.
93			weights.reserved = Some(
94				MAXIMUM_BLOCK_WEIGHT - NORMAL_DISPATCH_RATIO * MAXIMUM_BLOCK_WEIGHT
95			);
96		})
97		.avg_block_initialization(AVERAGE_ON_INITIALIZE_RATIO)
98		.build_or_panic();
99	pub const SS58Prefix: u16 = 0;
100}
101
102/// The default types are being injected by [`derive_impl`](`frame_support::derive_impl`) from
103/// [`ParaChainDefaultConfig`](`struct@frame_system::config_preludes::ParaChainDefaultConfig`),
104/// but overridden as needed.
105#[derive_impl(frame_system::config_preludes::ParaChainDefaultConfig)]
106impl frame_system::Config for Runtime {
107	/// The data to be stored in an account.
108	type AccountData = pallet_balances::AccountData<Balance>;
109	/// The identifier used to distinguish between accounts.
110	type AccountId = AccountId;
111	/// The block type.
112	type Block = Block;
113	/// Maximum number of block number to block hash mappings to keep (oldest pruned first).
114	type BlockHashCount = BlockHashCount;
115	/// The maximum length of a block (in bytes).
116	type BlockLength = RuntimeBlockLength;
117	/// Block & extrinsics weights: base values and limits.
118	type BlockWeights = RuntimeBlockWeights;
119	/// The weight of database operations that the runtime can invoke.
120	type DbWeight = RocksDbWeight;
121	/// The type for hashing blocks and tries.
122	type Hash = Hash;
123	type MaxConsumers = frame_support::traits::ConstU32<16>;
124	/// The index type for storing how many extrinsics an account has signed.
125	type Nonce = Nonce;
126	/// The action to take on a Runtime Upgrade
127	type OnSetCode = cumulus_pallet_parachain_system::ParachainSetCode<Self>;
128	/// This is used as an identifier of the chain. 42 is the generic substrate prefix.
129	type SS58Prefix = SS58Prefix;
130	type SystemWeightInfo = SystemWeightInfo<Runtime>;
131	/// Runtime version.
132	type Version = Version;
133}
134
135impl pallet_timestamp::Config for Runtime {
136	type MinimumPeriod = ConstU64<0>;
137	/// A timestamp: milliseconds since the unix epoch.
138	type Moment = u64;
139	type OnTimestampSet = Aura;
140	type WeightInfo = TimestampWeightInfo<Runtime>;
141}
142
143impl pallet_authorship::Config for Runtime {
144	type EventHandler = (CollatorSelection,);
145	type FindAuthor = pallet_session::FindAccountFromAuthorIndex<Self, Aura>;
146}
147
148parameter_types! {
149	pub const ExistentialDeposit: Balance = EXISTENTIAL_DEPOSIT;
150}
151
152impl pallet_balances::Config for Runtime {
153	type AccountStore = System;
154	/// The type for recording an account's balance.
155	type Balance = Balance;
156	type DoneSlashHandler = ();
157	type DustRemoval = ResolveTo<types::TreasuryAccount, Balances>;
158	type ExistentialDeposit = ExistentialDeposit;
159	type FreezeIdentifier = RuntimeFreezeReason;
160	type MaxFreezes = VariantCountOf<RuntimeFreezeReason>;
161	type MaxLocks = ConstU32<50>;
162	type MaxReserves = ConstU32<50>;
163	type ReserveIdentifier = [u8; 8];
164	/// The ubiquitous event type.
165	type RuntimeEvent = RuntimeEvent;
166	type RuntimeFreezeReason = RuntimeFreezeReason;
167	type RuntimeHoldReason = RuntimeHoldReason;
168	type WeightInfo = BalancesWeightInfo<Runtime>;
169}
170
171parameter_types! {
172	/// Relay Chain `TransactionByteFee` / 10
173	pub const TransactionByteFee: Balance = 10 * MICROUNIT;
174}
175
176impl pallet_transaction_payment::Config for Runtime {
177	type FeeMultiplierUpdate = SlowAdjustingFeeUpdate<Self>;
178	type LengthToFee = ConstantMultiplier<Balance, TransactionByteFee>;
179	type OnChargeTransaction = pallet_transaction_payment::FungibleAdapter<
180		Balances,
181		ResolveTo<types::TreasuryAccount, Balances>,
182	>;
183	type OperationalFeeMultiplier = ConstU8<5>;
184	type RuntimeEvent = RuntimeEvent;
185	type WeightInfo = TransactionPaymentWeightInfo<Runtime>;
186	type WeightToFee = WeightToFee;
187}
188
189impl pallet_sudo::Config for Runtime {
190	type RuntimeCall = RuntimeCall;
191	type RuntimeEvent = RuntimeEvent;
192	type WeightInfo = SudoWeightInfo<Runtime>;
193}
194
195parameter_types! {
196	pub const ReservedXcmpWeight: Weight = MAXIMUM_BLOCK_WEIGHT.saturating_div(4);
197	pub const ReservedDmpWeight: Weight = MAXIMUM_BLOCK_WEIGHT.saturating_div(4);
198	pub const RelayOrigin: AggregateMessageOrigin = AggregateMessageOrigin::Parent;
199}
200
201impl cumulus_pallet_parachain_system::Config for Runtime {
202	type WeightInfo = CumulusParachainSystemWeightInfo<Runtime>;
203	type RuntimeEvent = RuntimeEvent;
204	type OnSystemEvent = ();
205	type SelfParaId = parachain_info::Pallet<Runtime>;
206	type OutboundXcmpMessageSource = XcmpQueue;
207	type DmpQueue = frame_support::traits::EnqueueWithOrigin<MessageQueue, RelayOrigin>;
208	type ReservedDmpWeight = ReservedDmpWeight;
209	type XcmpMessageHandler = XcmpQueue;
210	type ReservedXcmpWeight = ReservedXcmpWeight;
211	type CheckAssociatedRelayNumber = RelayNumberMonotonicallyIncreases;
212	type ConsensusHook = ConsensusHook;
213	type SelectCore = cumulus_pallet_parachain_system::DefaultCoreSelector<Runtime>;
214}
215
216impl parachain_info::Config for Runtime {}
217
218impl cumulus_pallet_aura_ext::Config for Runtime {}
219
220parameter_types! {
221	pub const Period: u32 = 6 * HOURS;
222	pub const Offset: u32 = 0;
223}
224
225impl pallet_session::Config for Runtime {
226	type DisablingStrategy = ();
227	type Keys = SessionKeys;
228	type NextSessionRotation = pallet_session::PeriodicSessions<Period, Offset>;
229	type RuntimeEvent = RuntimeEvent;
230	// Essentially just Aura, but let's be pedantic.
231	type SessionHandler = <SessionKeys as sp_runtime::traits::OpaqueKeys>::KeyTypeIdProviders;
232	type SessionManager = CollatorSelection;
233	type ShouldEndSession = pallet_session::PeriodicSessions<Period, Offset>;
234	type ValidatorId = <Self as frame_system::Config>::AccountId;
235	// we don't have stash and controller, thus we don't need the convert as well.
236	type ValidatorIdOf = pallet_collator_selection::IdentityCollator;
237	type WeightInfo = SessionWeightInfo<Runtime>;
238}
239
240impl pallet_aura::Config for Runtime {
241	type AllowMultipleBlocksPerSlot = ConstBool<true>;
242	type AuthorityId = AuraId;
243	type DisabledValidators = ();
244	type MaxAuthorities = ConstU32<100_000>;
245	type SlotDuration = ConstU64<SLOT_DURATION>;
246}
247
248parameter_types! {
249	pub const PotId: PalletId = PalletId(*b"PotStake");
250	pub const SessionLength: BlockNumber = 6 * HOURS;
251	// StakingAdmin pluralistic body.
252	pub const StakingAdminBodyId: BodyId = BodyId::Defense;
253}
254
255/// We allow root and the StakingAdmin to execute privileged collator selection operations.
256pub type CollatorSelectionUpdateOrigin = EitherOfDiverse<
257	EnsureRoot<AccountId>,
258	EnsureXcm<IsVoiceOfBody<RelayLocation, StakingAdminBodyId>>,
259>;
260
261impl pallet_collator_selection::Config for Runtime {
262	type Currency = Balances;
263	// should be a multiple of session or things will get inconsistent
264	type KickThreshold = Period;
265	type MaxCandidates = ConstU32<100>;
266	type MaxInvulnerables = ConstU32<20>;
267	type MinEligibleCollators = ConstU32<4>;
268	type PotId = PotId;
269	type RuntimeEvent = RuntimeEvent;
270	type UpdateOrigin = CollatorSelectionUpdateOrigin;
271	type ValidatorId = <Self as frame_system::Config>::AccountId;
272	type ValidatorIdOf = pallet_collator_selection::IdentityCollator;
273	type ValidatorRegistration = Session;
274	type WeightInfo = CollatorSelectionWeightInfo<Runtime>;
275}
276
277/// This function helps to keep benchmarks in line with the test mock
278/// environment. When running benchmarks without this mock, when a request is made
279/// that matches the sibling account id, the id is translated to that of the
280/// sibling's account on the IDN.
281#[cfg(feature = "runtime-benchmarks")]
282mod bench_sibling_conversion {
283	use sp_runtime::AccountId32;
284	use xcm::prelude::{Junction::Parachain, Location};
285	use xcm_executor::traits::ConvertLocation;
286	pub struct MockSiblingConversion;
287	pub const SIBLING_PARA_ID: u32 = 88;
288	pub const SIBLING_PARA_ACCOUNT: AccountId32 = AccountId32::new([88u8; 32]);
289	impl ConvertLocation<AccountId32> for MockSiblingConversion {
290		fn convert_location(location: &Location) -> Option<AccountId32> {
291			match location.unpack() {
292				(1, [Parachain(SIBLING_PARA_ID)]) => Some(SIBLING_PARA_ACCOUNT),
293				_ => None,
294			}
295		}
296	}
297}
298
299#[cfg(feature = "runtime-benchmarks")]
300mod bench_ensure_origin {
301	use crate::RuntimeOrigin;
302	use frame_support::pallet_prelude::EnsureOrigin;
303	use frame_system::ensure_signed;
304	use sp_runtime::AccountId32;
305	use xcm::prelude::{Junction, Location};
306
307	pub const SIBLING_PARA_ACCOUNT: AccountId32 = AccountId32::new([88u8; 32]);
308	pub const SIBLING_PARA_ID: u32 = 88;
309
310	pub struct BenchEnsureOrigin;
311	impl EnsureOrigin<RuntimeOrigin> for BenchEnsureOrigin {
312		type Success = Location;
313
314		fn try_origin(origin: RuntimeOrigin) -> Result<Self::Success, RuntimeOrigin> {
315			let caller: AccountId32 = ensure_signed(origin.clone()).unwrap();
316
317			if caller == SIBLING_PARA_ACCOUNT {
318				return Ok(Location::new(1, Junction::Parachain(SIBLING_PARA_ID)));
319			}
320			Err(origin)
321		}
322		fn try_successful_origin() -> Result<RuntimeOrigin, ()> {
323			Ok(RuntimeOrigin::root())
324		}
325	}
326}
327
328parameter_types! {
329	pub const BaseFee: u64 = 2_900_000u64;
330	pub const MaxXcmFees: u128 = 1_000_000_000_000;
331}
332
333impl pallet_idn_manager::Config for Runtime {
334	type Credits = types::Credits;
335	type Currency = Balances;
336	type DepositCalculator = impls::DepositCalculatorImpl<types::SDMultiplier, BalanceOf<Runtime>>;
337	type DiffBalance = impls::DiffBalanceImpl<BalanceOf<Runtime>>;
338	type FeesManager = impls::FeesManagerImpl<
339		types::TreasuryAccount,
340		SubscriptionOf<Runtime>,
341		Balances,
342		BlockNumber,
343		BlockNumber,
344		BaseFee,
345	>;
346	type LocalOriginToLocation = xcm_config::LocalOriginToLocation;
347	type MaxCallDataLen = types::MaxCallDataLen;
348	type MaxMetadataLen = types::MaxMetadataLen;
349	type MaxSubscriptions = types::MaxSubscriptions;
350	type MaxTerminatableSubs = types::MaxTerminatableSubs;
351	type MaxXcmFees = MaxXcmFees;
352	type Pulse = types::RuntimePulse;
353	type RuntimeEvent = RuntimeEvent;
354	type RuntimeHoldReason = RuntimeHoldReason;
355	type SubscriptionId = types::SubscriptionId;
356	type WeightInfo = IdnManagerWeightInfo<Runtime>;
357	#[cfg(not(feature = "runtime-benchmarks"))]
358	type Xcm = PolkadotXcm;
359	#[cfg(feature = "runtime-benchmarks")]
360	type Xcm = ();
361	#[cfg(not(feature = "runtime-benchmarks"))]
362	type XcmLocationToAccountId = xcm_config::LocationToAccountId;
363	#[cfg(feature = "runtime-benchmarks")]
364	type XcmLocationToAccountId = bench_sibling_conversion::MockSiblingConversion;
365	#[cfg(not(feature = "runtime-benchmarks"))]
366	type XcmOriginFilter = EnsureXcm<AllowSiblingsOnly>;
367	#[cfg(feature = "runtime-benchmarks")]
368	type XcmOriginFilter = bench_ensure_origin::BenchEnsureOrigin;
369}
370
371parameter_types! {
372	pub const MaxSigsPerBlock: u8 = 6;
373}
374
375impl pallet_randomness_beacon::Config for Runtime {
376	type Dispatcher = crate::IdnManager;
377	type FallbackRandomness = RandomnessCollectiveFlip;
378	type MaxSigsPerBlock = MaxSigsPerBlock;
379	type Pulse = types::RuntimePulse;
380	type RuntimeEvent = RuntimeEvent;
381	type SignatureVerifier = sp_idn_crypto::verifier::QuicknetVerifier;
382	type WeightInfo = RandomnessBeaconWeightInfo<Runtime>;
383	type Signature = sp_runtime::MultiSignature;
384	type AccountIdentifier = sp_runtime::MultiSigner;
385	type FindAuthor = pallet_session::FindAccountFromAuthorIndex<Self, Aura>;
386}
387
388impl pallet_insecure_randomness_collective_flip::Config for Runtime {}