lib.rs 36.2 KB
Newer Older
ddorgan's avatar
ddorgan committed
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
// Copyright 2017-2020 Parity Technologies (UK) Ltd.
// This file is part of Polkadot.

// Polkadot is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.

// Polkadot is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// GNU General Public License for more details.

// You should have received a copy of the GNU General Public License
// along with Polkadot.  If not, see <http://www.gnu.org/licenses/>.

//! The Polkadot runtime. This can be compiled with `#[no_std]`, ready for Wasm.

#![cfg_attr(not(feature = "std"), no_std)]
// `construct_runtime!` does a lot of recursion and requires us to increase the limit to 256.
21
#![recursion_limit = "256"]
ddorgan's avatar
ddorgan committed
22

Albrecht's avatar
Albrecht committed
23
use pallet_transaction_payment::CurrencyAdapter;
ddorgan's avatar
ddorgan committed
24
use sp_std::prelude::*;
Sergey Pepyakin's avatar
Sergey Pepyakin committed
25
use sp_std::collections::btree_map::BTreeMap;
26
use parity_scale_codec::{Encode, Decode};
27
use primitives::v1::{
28
29
	AccountId, AccountIndex, Balance, BlockNumber, CandidateEvent, CommittedCandidateReceipt,
	CoreState, GroupRotationInfo, Hash, Id, Moment, Nonce, OccupiedCoreAssumption,
30
	PersistedValidationData, Signature, ValidationCode, ValidatorId, ValidatorIndex,
31
	InboundDownwardMessage, InboundHrmpMessage, SessionInfo,
ddorgan's avatar
ddorgan committed
32
};
33
use runtime_common::{
34
35
	SlowAdjustingFeeUpdate, CurrencyToVote,
	impls::ToAuthor,
36
	BlockHashCount, BlockWeights, BlockLength, RocksDbWeight, OffchainSolutionWeightLimit,
37
	ParachainSessionKeyPlaceholder, AssignmentSessionKeyPlaceholder,
ddorgan's avatar
ddorgan committed
38
39
40
};
use sp_runtime::{
	create_runtime_str, generic, impl_opaque_keys,
41
	ApplyExtrinsicResult, KeyTypeId, Perbill, curve::PiecewiseLinear,
Gavin Wood's avatar
Gavin Wood committed
42
	transaction_validity::{TransactionValidity, TransactionSource, TransactionPriority},
ddorgan's avatar
ddorgan committed
43
	traits::{
44
		BlakeTwo256, Block as BlockT, OpaqueKeys, ConvertInto, AccountIdLookup,
Gavin Wood's avatar
Gavin Wood committed
45
		Extrinsic as ExtrinsicT, SaturatedConversion, Verify,
ddorgan's avatar
ddorgan committed
46
47
48
49
	},
};
#[cfg(feature = "runtime-benchmarks")]
use sp_runtime::RuntimeString;
50
51
use sp_version::RuntimeVersion;
use pallet_grandpa::{AuthorityId as GrandpaId, fg_primitives};
ddorgan's avatar
ddorgan committed
52
#[cfg(any(feature = "std", test))]
53
use sp_version::NativeVersion;
ddorgan's avatar
ddorgan committed
54
55
use sp_core::OpaqueMetadata;
use sp_staking::SessionIndex;
56
use frame_support::{
57
	parameter_types, construct_runtime, RuntimeDebug,
58
	traits::{KeyOwnerProofSystem, Randomness, Filter, InstanceFilter},
59
	weights::Weight,
60
};
61
use pallet_im_online::sr25519::AuthorityId as ImOnlineId;
ddorgan's avatar
ddorgan committed
62
use authority_discovery_primitives::AuthorityId as AuthorityDiscoveryId;
63
use pallet_transaction_payment::{FeeDetails, RuntimeDispatchInfo};
64
use pallet_session::historical as session_historical;
65
use frame_system::{EnsureRoot};
ddorgan's avatar
ddorgan committed
66
67

#[cfg(feature = "std")]
68
pub use pallet_staking::StakerStatus;
ddorgan's avatar
ddorgan committed
69
70
#[cfg(any(feature = "std", test))]
pub use sp_runtime::BuildStorage;
71
72
pub use pallet_timestamp::Call as TimestampCall;
pub use pallet_balances::Call as BalancesCall;
ddorgan's avatar
ddorgan committed
73
74
75
76
77

/// Constant values used within the runtime.
pub mod constants;
use constants::{time::*, currency::*, fee::*};

78
79
80
// Weights used in the runtime
mod weights;

ddorgan's avatar
ddorgan committed
81
82
83
84
// Make the WASM binary available.
#[cfg(feature = "std")]
include!(concat!(env!("OUT_DIR"), "/wasm_binary.rs"));

85
/// Runtime version (Westend).
ddorgan's avatar
ddorgan committed
86
87
88
89
pub const VERSION: RuntimeVersion = RuntimeVersion {
	spec_name: create_runtime_str!("westend"),
	impl_name: create_runtime_str!("parity-westend"),
	authoring_version: 2,
90
	spec_version: 50,
91
	impl_version: 0,
92
	#[cfg(not(feature = "disable-runtime-api"))]
ddorgan's avatar
ddorgan committed
93
	apis: RUNTIME_API_VERSIONS,
94
	#[cfg(feature = "disable-runtime-api")]
95
	apis: version::create_apis_vec![[]],
96
	transaction_version: 5,
ddorgan's avatar
ddorgan committed
97
98
};

99
100
101
102
103
104
105
/// The BABE epoch configuration at genesis.
pub const BABE_GENESIS_EPOCH_CONFIG: babe_primitives::BabeEpochConfiguration =
	babe_primitives::BabeEpochConfiguration {
		c: PRIMARY_PROBABILITY,
		allowed_slots: babe_primitives::AllowedSlots::PrimaryAndSecondaryVRFSlots
	};

ddorgan's avatar
ddorgan committed
106
107
108
109
110
111
112
113
114
/// Native version.
#[cfg(any(feature = "std", test))]
pub fn native_version() -> NativeVersion {
	NativeVersion {
		runtime_version: VERSION,
		can_author_with: Default::default(),
	}
}

115
/// Accept all transactions.
116
117
pub struct BaseFilter;
impl Filter<Call> for BaseFilter {
118
119
	fn filter(_: &Call) -> bool {
		true
ddorgan's avatar
ddorgan committed
120
121
122
123
124
	}
}

parameter_types! {
	pub const Version: RuntimeVersion = VERSION;
125
	pub const SS58Prefix: u8 = 42;
ddorgan's avatar
ddorgan committed
126
127
}

128
impl frame_system::Config for Runtime {
129
	type BaseCallFilter = BaseFilter;
130
131
	type BlockWeights = BlockWeights;
	type BlockLength = BlockLength;
ddorgan's avatar
ddorgan committed
132
133
134
135
136
137
138
	type Origin = Origin;
	type Call = Call;
	type Index = Nonce;
	type BlockNumber = BlockNumber;
	type Hash = Hash;
	type Hashing = BlakeTwo256;
	type AccountId = AccountId;
139
	type Lookup = AccountIdLookup<AccountId, ()>;
ddorgan's avatar
ddorgan committed
140
141
142
	type Header = generic::Header<BlockNumber, BlakeTwo256>;
	type Event = Event;
	type BlockHashCount = BlockHashCount;
143
	type DbWeight = RocksDbWeight;
ddorgan's avatar
ddorgan committed
144
	type Version = Version;
145
	type PalletInfo = PalletInfo;
146
	type AccountData = pallet_balances::AccountData<Balance>;
ddorgan's avatar
ddorgan committed
147
148
	type OnNewAccount = ();
	type OnKilledAccount = ();
149
	type SystemWeightInfo = weights::frame_system::WeightInfo<Runtime>;
150
	type SS58Prefix = SS58Prefix;
ddorgan's avatar
ddorgan committed
151
152
}

153
parameter_types! {
154
155
	pub MaximumSchedulerWeight: Weight = Perbill::from_percent(80) *
		BlockWeights::get().max_block;
156
157
158
	pub const MaxScheduledPerBlock: u32 = 50;
}

159
impl pallet_scheduler::Config for Runtime {
ddorgan's avatar
ddorgan committed
160
161
	type Event = Event;
	type Origin = Origin;
162
	type PalletsOrigin = OriginCaller;
ddorgan's avatar
ddorgan committed
163
	type Call = Call;
164
	type MaximumWeight = MaximumSchedulerWeight;
165
	type ScheduleOrigin = EnsureRoot<AccountId>;
166
	type MaxScheduledPerBlock = MaxScheduledPerBlock;
167
	type WeightInfo = weights::pallet_scheduler::WeightInfo<Runtime>;
ddorgan's avatar
ddorgan committed
168
169
170
171
172
}

parameter_types! {
	pub const EpochDuration: u64 = EPOCH_DURATION_IN_BLOCKS as u64;
	pub const ExpectedBlockTime: Moment = MILLISECS_PER_BLOCK;
173
174
	pub const ReportLongevity: u64 =
		BondingDuration::get() as u64 * SessionsPerEra::get() as u64 * EpochDuration::get();
ddorgan's avatar
ddorgan committed
175
176
}

177
impl pallet_babe::Config for Runtime {
ddorgan's avatar
ddorgan committed
178
179
180
181
	type EpochDuration = EpochDuration;
	type ExpectedBlockTime = ExpectedBlockTime;

	// session module is the trigger
182
	type EpochChangeTrigger = pallet_babe::ExternalTrigger;
183
184
185
186
187

	type KeyOwnerProofSystem = Historical;

	type KeyOwnerProof = <Self::KeyOwnerProofSystem as KeyOwnerProofSystem<(
		KeyTypeId,
188
		pallet_babe::AuthorityId,
189
190
191
192
	)>>::Proof;

	type KeyOwnerIdentification = <Self::KeyOwnerProofSystem as KeyOwnerProofSystem<(
		KeyTypeId,
193
		pallet_babe::AuthorityId,
194
195
196
	)>>::IdentificationTuple;

	type HandleEquivocation =
197
		pallet_babe::EquivocationHandler<Self::KeyOwnerIdentification, Offences, ReportLongevity>;
198
199

	type WeightInfo = ();
ddorgan's avatar
ddorgan committed
200
201
202
203
204
205
}

parameter_types! {
	pub const IndexDeposit: Balance = 1 * DOLLARS;
}

206
impl pallet_indices::Config for Runtime {
ddorgan's avatar
ddorgan committed
207
208
209
210
	type AccountIndex = AccountIndex;
	type Currency = Balances;
	type Deposit = IndexDeposit;
	type Event = Event;
211
	type WeightInfo = weights::pallet_indices::WeightInfo<Runtime>;
ddorgan's avatar
ddorgan committed
212
213
214
215
}

parameter_types! {
	pub const ExistentialDeposit: Balance = 1 * CENTS;
216
	pub const MaxLocks: u32 = 50;
ddorgan's avatar
ddorgan committed
217
218
}

219
impl pallet_balances::Config for Runtime {
ddorgan's avatar
ddorgan committed
220
221
222
223
224
	type Balance = Balance;
	type DustRemoval = ();
	type Event = Event;
	type ExistentialDeposit = ExistentialDeposit;
	type AccountStore = System;
225
	type MaxLocks = MaxLocks;
226
	type WeightInfo = weights::pallet_balances::WeightInfo<Runtime>;
ddorgan's avatar
ddorgan committed
227
228
229
230
231
232
}

parameter_types! {
	pub const TransactionByteFee: Balance = 10 * MILLICENTS;
}

233
impl pallet_transaction_payment::Config for Runtime {
Albrecht's avatar
Albrecht committed
234
	type OnChargeTransaction = CurrencyAdapter<Balances, ToAuthor<Runtime>>;
ddorgan's avatar
ddorgan committed
235
236
	type TransactionByteFee = TransactionByteFee;
	type WeightToFee = WeightToFee;
237
	type FeeMultiplierUpdate = SlowAdjustingFeeUpdate<Self>;
ddorgan's avatar
ddorgan committed
238
239
240
241
242
}

parameter_types! {
	pub const MinimumPeriod: u64 = SLOT_DURATION / 2;
}
243
impl pallet_timestamp::Config for Runtime {
ddorgan's avatar
ddorgan committed
244
245
246
	type Moment = u64;
	type OnTimestampSet = Babe;
	type MinimumPeriod = MinimumPeriod;
247
	type WeightInfo = weights::pallet_timestamp::WeightInfo<Runtime>;
ddorgan's avatar
ddorgan committed
248
249
250
251
252
253
}

parameter_types! {
	pub const UncleGenerations: u32 = 0;
}

254
impl pallet_authorship::Config for Runtime {
255
	type FindAuthor = pallet_session::FindAccountFromAuthorIndex<Self, Babe>;
ddorgan's avatar
ddorgan committed
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
	type UncleGenerations = UncleGenerations;
	type FilterUncle = ();
	type EventHandler = (Staking, ImOnline);
}

parameter_types! {
	pub const Period: BlockNumber = 10 * MINUTES;
	pub const Offset: BlockNumber = 0;
}

impl_opaque_keys! {
	pub struct SessionKeys {
		pub grandpa: Grandpa,
		pub babe: Babe,
		pub im_online: ImOnline,
271
272
		pub para_validator: ParachainSessionKeyPlaceholder<Runtime>,
		pub para_assignment: AssignmentSessionKeyPlaceholder<Runtime>,
ddorgan's avatar
ddorgan committed
273
274
275
276
277
278
279
280
		pub authority_discovery: AuthorityDiscovery,
	}
}

parameter_types! {
	pub const DisabledValidatorsThreshold: Perbill = Perbill::from_percent(17);
}

281
impl pallet_session::Config for Runtime {
ddorgan's avatar
ddorgan committed
282
283
	type Event = Event;
	type ValidatorId = AccountId;
284
	type ValidatorIdOf = pallet_staking::StashOf<Self>;
ddorgan's avatar
ddorgan committed
285
286
	type ShouldEndSession = Babe;
	type NextSessionRotation = Babe;
287
	type SessionManager = pallet_session::historical::NoteHistoricalRoot<Self, Staking>;
ddorgan's avatar
ddorgan committed
288
289
290
	type SessionHandler = <SessionKeys as OpaqueKeys>::KeyTypeIdProviders;
	type Keys = SessionKeys;
	type DisabledValidatorsThreshold = DisabledValidatorsThreshold;
291
	type WeightInfo = weights::pallet_session::WeightInfo<Runtime>;
ddorgan's avatar
ddorgan committed
292
293
}

294
impl pallet_session::historical::Config for Runtime {
295
296
	type FullIdentification = pallet_staking::Exposure<AccountId, Balance>;
	type FullIdentificationOf = pallet_staking::ExposureOf<Runtime>;
ddorgan's avatar
ddorgan committed
297
298
}

299
300
301
parameter_types! {
	// no signed phase for now, just unsigned.
	pub const SignedPhase: u32 = 0;
302
	pub const UnsignedPhase: u32 = EPOCH_DURATION_IN_BLOCKS / 4;
303

304
	// fallback: run election on-chain.
305
	pub const Fallback: pallet_election_provider_multi_phase::FallbackStrategy =
306
		pallet_election_provider_multi_phase::FallbackStrategy::OnChain;
307

308
	pub SolutionImprovementThreshold: Perbill = Perbill::from_rational(5u32, 10_000);
309
310
311
312
313

	// miner configs
	pub const MinerMaxIterations: u32 = 10;
}

314
315
sp_npos_elections::generate_solution_type!(
	#[compact]
316
317
318
319
320
	pub struct NposCompactSolution16::<
		VoterIndex = u32,
		TargetIndex = u16,
		Accuracy = sp_runtime::PerU16,
	>(16)
321
322
);

323
324
325
326
327
impl pallet_election_provider_multi_phase::Config for Runtime {
	type Event = Event;
	type Currency = Balances;
	type SignedPhase = SignedPhase;
	type UnsignedPhase = UnsignedPhase;
328
	type SolutionImprovementThreshold = SolutionImprovementThreshold;
329
330
	type MinerMaxIterations = MinerMaxIterations;
	type MinerMaxWeight = OffchainSolutionWeightLimit; // For now use the one from staking.
331
	type MinerTxPriority = NposSolutionPriority;
332
333
	type DataProvider = Staking;
	type OnChainAccuracy = Perbill;
334
	type CompactSolution = NposCompactSolution16;
335
336
	type Fallback = Fallback;
	type BenchmarkingConfig = ();
337
	type WeightInfo = weights::pallet_election_provider_multi_phase::WeightInfo<Runtime>;
338
339
}

ddorgan's avatar
ddorgan committed
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
pallet_staking_reward_curve::build! {
	const REWARD_CURVE: PiecewiseLinear<'static> = curve!(
		min_inflation: 0_025_000,
		max_inflation: 0_100_000,
		ideal_stake: 0_500_000,
		falloff: 0_050_000,
		max_piece_count: 40,
		test_precision: 0_005_000,
	);
}

parameter_types! {
	// Six sessions in an era (6 hours).
	pub const SessionsPerEra: SessionIndex = 6;
	// 28 eras for unbonding (7 days).
355
	pub const BondingDuration: pallet_staking::EraIndex = 28;
356
	// 27 eras in which slashes can be cancelled (slightly less than 7 days).
357
	pub const SlashDeferDuration: pallet_staking::EraIndex = 27;
ddorgan's avatar
ddorgan committed
358
359
360
361
	pub const RewardCurve: &'static PiecewiseLinear<'static> = &REWARD_CURVE;
	pub const MaxNominatorRewardedPerValidator: u32 = 64;
}

362
impl pallet_staking::Config for Runtime {
363
	const MAX_NOMINATIONS: u32 = <NposCompactSolution16 as sp_npos_elections::CompactSolution>::LIMIT as u32;
ddorgan's avatar
ddorgan committed
364
365
	type Currency = Balances;
	type UnixTime = Timestamp;
366
	type CurrencyToVote = CurrencyToVote;
ddorgan's avatar
ddorgan committed
367
368
369
370
371
372
373
374
	type RewardRemainder = ();
	type Event = Event;
	type Slash = ();
	type Reward = ();
	type SessionsPerEra = SessionsPerEra;
	type BondingDuration = BondingDuration;
	type SlashDeferDuration = SlashDeferDuration;
	// A majority of the council can cancel the slash.
375
	type SlashCancelOrigin = EnsureRoot<AccountId>;
ddorgan's avatar
ddorgan committed
376
	type SessionInterface = Self;
Kian Paimani's avatar
Kian Paimani committed
377
	type EraPayout = pallet_staking::ConvertCurve<RewardCurve>;
ddorgan's avatar
ddorgan committed
378
379
	type MaxNominatorRewardedPerValidator = MaxNominatorRewardedPerValidator;
	type NextNewSession = Session;
380
	type ElectionProvider = ElectionProviderMultiPhase;
381
	type WeightInfo = weights::pallet_staking::WeightInfo<Runtime>;
ddorgan's avatar
ddorgan committed
382
383
384
385
386
387
388
389
390
391
392
393
394
395
}

parameter_types! {
	pub const LaunchPeriod: BlockNumber = 7 * DAYS;
	pub const VotingPeriod: BlockNumber = 7 * DAYS;
	pub const FastTrackVotingPeriod: BlockNumber = 3 * HOURS;
	pub const MinimumDeposit: Balance = 1 * DOLLARS;
	pub const EnactmentPeriod: BlockNumber = 8 * DAYS;
	pub const CooloffPeriod: BlockNumber = 7 * DAYS;
	// One cent: $10,000 / MB
	pub const PreimageByteDeposit: Balance = 10 * MILLICENTS;
	pub const InstantAllowed: bool = true;
}

396
parameter_types! {
397
	pub OffencesWeightSoftLimit: Weight = Perbill::from_percent(60) * BlockWeights::get().max_block;
398
399
}

400
impl pallet_offences::Config for Runtime {
ddorgan's avatar
ddorgan committed
401
	type Event = Event;
402
	type IdentificationTuple = pallet_session::historical::IdentificationTuple<Self>;
ddorgan's avatar
ddorgan committed
403
	type OnOffenceHandler = Staking;
404
	type WeightSoftLimit = OffencesWeightSoftLimit;
ddorgan's avatar
ddorgan committed
405
406
}

407
impl pallet_authority_discovery::Config for Runtime {}
ddorgan's avatar
ddorgan committed
408
409

parameter_types! {
410
	pub const NposSolutionPriority: TransactionPriority = TransactionPriority::max_value() / 2;
ddorgan's avatar
ddorgan committed
411
412
413
	pub const ImOnlineUnsignedPriority: TransactionPriority = TransactionPriority::max_value();
}

414
impl pallet_im_online::Config for Runtime {
ddorgan's avatar
ddorgan committed
415
416
	type AuthorityId = ImOnlineId;
	type Event = Event;
417
	type ValidatorSet = Historical;
418
	type NextSessionRotation = Babe;
ddorgan's avatar
ddorgan committed
419
	type ReportUnresponsiveness = Offences;
420
	type UnsignedPriority = ImOnlineUnsignedPriority;
421
	type WeightInfo = weights::pallet_im_online::WeightInfo<Runtime>;
ddorgan's avatar
ddorgan committed
422
423
}

424
impl pallet_grandpa::Config for Runtime {
ddorgan's avatar
ddorgan committed
425
	type Event = Event;
426
427
428
429
430
431
432
433
434
435
436
437
	type Call = Call;

	type KeyOwnerProofSystem = Historical;

	type KeyOwnerProof =
		<Self::KeyOwnerProofSystem as KeyOwnerProofSystem<(KeyTypeId, GrandpaId)>>::Proof;

	type KeyOwnerIdentification = <Self::KeyOwnerProofSystem as KeyOwnerProofSystem<(
		KeyTypeId,
		GrandpaId,
	)>>::IdentificationTuple;

438
439
	type HandleEquivocation =
		pallet_grandpa::EquivocationHandler<Self::KeyOwnerIdentification, Offences, ReportLongevity>;
440
441

	type WeightInfo = ();
ddorgan's avatar
ddorgan committed
442
443
}

444
445
/// Submits a transaction with the node's public and signature type. Adheres to the signed extension
/// format of the chain.
446
impl<LocalCall> frame_system::offchain::CreateSignedTransaction<LocalCall> for Runtime where
447
448
	Call: From<LocalCall>,
{
449
	fn create_transaction<C: frame_system::offchain::AppCrypto<Self::Public, Self::Signature>>(
450
451
452
		call: Call,
		public: <Signature as Verify>::Signer,
		account: AccountId,
453
		nonce: <Runtime as frame_system::Config>::Index,
454
	) -> Option<(Call, <UncheckedExtrinsic as ExtrinsicT>::SignaturePayload)> {
455
		use sp_runtime::traits::StaticLookup;
456
		// take the biggest period possible.
457
458
459
460
461
462
463
		let period = BlockHashCount::get()
			.checked_next_power_of_two()
			.map(|c| c / 2)
			.unwrap_or(2) as u64;

		let current_block = System::block_number()
			.saturated_into::<u64>()
464
465
			// The `System::block_number` is initialized with `n+1`,
			// so the actual block number is `n`.
466
467
468
			.saturating_sub(1);
		let tip = 0;
		let extra: SignedExtra = (
469
470
471
472
473
474
475
			frame_system::CheckSpecVersion::<Runtime>::new(),
			frame_system::CheckTxVersion::<Runtime>::new(),
			frame_system::CheckGenesis::<Runtime>::new(),
			frame_system::CheckMortality::<Runtime>::from(generic::Era::mortal(period, current_block)),
			frame_system::CheckNonce::<Runtime>::from(nonce),
			frame_system::CheckWeight::<Runtime>::new(),
			pallet_transaction_payment::ChargeTransactionPayment::<Runtime>::from(tip),
476
477
		);
		let raw_payload = SignedPayload::new(call, extra).map_err(|e| {
478
			log::warn!("Unable to create signed payload: {:?}", e);
479
		}).ok()?;
480
481
482
		let signature = raw_payload.using_encoded(|payload| {
			C::sign(payload, public)
		})?;
483
		let (call, extra, _) = raw_payload.deconstruct();
484
485
		let address = <Runtime as frame_system::Config>::Lookup::unlookup(account);
		Some((call, (address, signature, extra)))
486
	}
ddorgan's avatar
ddorgan committed
487
488
}

489
impl frame_system::offchain::SigningTypes for Runtime {
490
491
492
493
	type Public = <Signature as Verify>::Signer;
	type Signature = Signature;
}

494
impl<C> frame_system::offchain::SendTransactionTypes<C> for Runtime where
495
496
497
498
499
500
	Call: From<C>,
{
	type OverarchingCall = Call;
	type Extrinsic = UncheckedExtrinsic;
}

ddorgan's avatar
ddorgan committed
501
502
503
504
505
506
507
parameter_types! {
	// Minimum 100 bytes/KSM deposited (1 CENT/byte)
	pub const BasicDeposit: Balance = 10 * DOLLARS;       // 258 bytes on-chain
	pub const FieldDeposit: Balance = 250 * CENTS;        // 66 bytes on-chain
	pub const SubAccountDeposit: Balance = 2 * DOLLARS;   // 53 bytes on-chain
	pub const MaxSubAccounts: u32 = 100;
	pub const MaxAdditionalFields: u32 = 100;
508
	pub const MaxRegistrars: u32 = 20;
ddorgan's avatar
ddorgan committed
509
510
}

511
impl pallet_identity::Config for Runtime {
ddorgan's avatar
ddorgan committed
512
513
514
515
516
517
518
519
	type Event = Event;
	type Currency = Balances;
	type Slashed = ();
	type BasicDeposit = BasicDeposit;
	type FieldDeposit = FieldDeposit;
	type SubAccountDeposit = SubAccountDeposit;
	type MaxSubAccounts = MaxSubAccounts;
	type MaxAdditionalFields = MaxAdditionalFields;
520
	type MaxRegistrars = MaxRegistrars;
521
522
	type RegistrarOrigin = frame_system::EnsureRoot<AccountId>;
	type ForceOrigin = frame_system::EnsureRoot<AccountId>;
523
	type WeightInfo = weights::pallet_identity::WeightInfo<Runtime>;
ddorgan's avatar
ddorgan committed
524
525
}

526
impl pallet_utility::Config for Runtime {
527
528
	type Event = Event;
	type Call = Call;
529
	type WeightInfo = weights::pallet_utility::WeightInfo<Runtime>;
530
531
}

ddorgan's avatar
ddorgan committed
532
parameter_types! {
533
534
	// One storage item; key size is 32; value is size 4+4+16+32 bytes = 56 bytes.
	pub const DepositBase: Balance = deposit(1, 88);
ddorgan's avatar
ddorgan committed
535
	// Additional storage item size of 32 bytes.
536
	pub const DepositFactor: Balance = deposit(0, 32);
ddorgan's avatar
ddorgan committed
537
538
539
	pub const MaxSignatories: u16 = 100;
}

540
impl pallet_multisig::Config for Runtime {
ddorgan's avatar
ddorgan committed
541
542
543
	type Event = Event;
	type Call = Call;
	type Currency = Balances;
544
545
	type DepositBase = DepositBase;
	type DepositFactor = DepositFactor;
ddorgan's avatar
ddorgan committed
546
	type MaxSignatories = MaxSignatories;
547
	type WeightInfo = weights::pallet_multisig::WeightInfo<Runtime>;
ddorgan's avatar
ddorgan committed
548
549
550
551
552
553
554
555
556
}

parameter_types! {
	pub const ConfigDepositBase: Balance = 5 * DOLLARS;
	pub const FriendDepositFactor: Balance = 50 * CENTS;
	pub const MaxFriends: u16 = 9;
	pub const RecoveryDeposit: Balance = 5 * DOLLARS;
}

557
impl pallet_recovery::Config for Runtime {
ddorgan's avatar
ddorgan committed
558
559
560
561
562
563
564
565
566
567
568
569
570
	type Event = Event;
	type Call = Call;
	type Currency = Balances;
	type ConfigDepositBase = ConfigDepositBase;
	type FriendDepositFactor = FriendDepositFactor;
	type MaxFriends = MaxFriends;
	type RecoveryDeposit = RecoveryDeposit;
}

parameter_types! {
	pub const MinVestedTransfer: Balance = 100 * DOLLARS;
}

571
impl pallet_vesting::Config for Runtime {
ddorgan's avatar
ddorgan committed
572
573
574
575
	type Event = Event;
	type Currency = Balances;
	type BlockNumberToBalance = ConvertInto;
	type MinVestedTransfer = MinVestedTransfer;
576
	type WeightInfo = weights::pallet_vesting::WeightInfo<Runtime>;
ddorgan's avatar
ddorgan committed
577
578
}

579
impl pallet_sudo::Config for Runtime {
ddorgan's avatar
ddorgan committed
580
581
582
583
	type Event = Event;
	type Call = Call;
}

584
585
586
587
588
589
parameter_types! {
	// One storage item; key size 32, value size 8; .
	pub const ProxyDepositBase: Balance = deposit(1, 8);
	// Additional storage item size of 33 bytes.
	pub const ProxyDepositFactor: Balance = deposit(0, 33);
	pub const MaxProxies: u16 = 32;
590
591
592
	pub const AnnouncementDepositBase: Balance = deposit(1, 8);
	pub const AnnouncementDepositFactor: Balance = deposit(0, 66);
	pub const MaxPending: u16 = 32;
593
594
595
596
597
598
599
600
}

/// The type used to represent the kinds of proxying allowed.
#[derive(Copy, Clone, Eq, PartialEq, Ord, PartialOrd, Encode, Decode, RuntimeDebug)]
pub enum ProxyType {
	Any,
	NonTransfer,
	Staking,
601
	SudoBalances,
Chevdor's avatar
Chevdor committed
602
	IdentityJudgement,
Shawn Tabrizi's avatar
Shawn Tabrizi committed
603
	CancelProxy,
604
605
606
607
608
609
}
impl Default for ProxyType { fn default() -> Self { Self::Any } }
impl InstanceFilter<Call> for ProxyType {
	fn filter(&self, c: &Call) -> bool {
		match self {
			ProxyType::Any => true,
610
611
612
613
			ProxyType::NonTransfer => matches!(c,
				Call::System(..) |
				Call::Babe(..) |
				Call::Timestamp(..) |
614
615
616
				Call::Indices(pallet_indices::Call::claim(..)) |
				Call::Indices(pallet_indices::Call::free(..)) |
				Call::Indices(pallet_indices::Call::freeze(..)) |
617
618
619
620
621
622
623
624
625
626
627
				// Specifically omitting Indices `transfer`, `force_transfer`
				// Specifically omitting the entire Balances pallet
				Call::Authorship(..) |
				Call::Staking(..) |
				Call::Offences(..) |
				Call::Session(..) |
				Call::Grandpa(..) |
				Call::ImOnline(..) |
				Call::AuthorityDiscovery(..) |
				Call::Utility(..) |
				Call::Identity(..) |
628
629
630
631
632
633
				Call::Recovery(pallet_recovery::Call::as_recovered(..)) |
				Call::Recovery(pallet_recovery::Call::vouch_recovery(..)) |
				Call::Recovery(pallet_recovery::Call::claim_recovery(..)) |
				Call::Recovery(pallet_recovery::Call::close_recovery(..)) |
				Call::Recovery(pallet_recovery::Call::remove_recovery(..)) |
				Call::Recovery(pallet_recovery::Call::cancel_recovered(..)) |
634
				// Specifically omitting Recovery `create_recovery`, `initiate_recovery`
635
636
				Call::Vesting(pallet_vesting::Call::vest(..)) |
				Call::Vesting(pallet_vesting::Call::vest_other(..)) |
637
638
639
640
641
				// Specifically omitting Vesting `vested_transfer`, and `force_vested_transfer`
				Call::Scheduler(..) |
				// Specifically omitting Sudo pallet
				Call::Proxy(..) |
				Call::Multisig(..)
642
643
			),
			ProxyType::Staking => matches!(c,
Shawn Tabrizi's avatar
Shawn Tabrizi committed
644
645
646
				Call::Staking(..) |
				Call::Session(..) |
				Call::Utility(..)
647
			),
648
			ProxyType::SudoBalances => match c {
649
				Call::Sudo(pallet_sudo::Call::sudo(ref x)) => matches!(x.as_ref(), &Call::Balances(..)),
Gavin Wood's avatar
Gavin Wood committed
650
				Call::Utility(..) => true,
651
652
				_ => false,
			},
Chevdor's avatar
Chevdor committed
653
			ProxyType::IdentityJudgement => matches!(c,
Shawn Tabrizi's avatar
Shawn Tabrizi committed
654
655
				Call::Identity(pallet_identity::Call::provide_judgement(..)) |
				Call::Utility(..)
Shawn Tabrizi's avatar
Shawn Tabrizi committed
656
657
			),
			ProxyType::CancelProxy => matches!(c,
658
				Call::Proxy(pallet_proxy::Call::reject_announcement(..))
Chevdor's avatar
Chevdor committed
659
			)
660
661
662
663
664
665
666
667
668
		}
	}
	fn is_superset(&self, o: &Self) -> bool {
		match (self, o) {
			(x, y) if x == y => true,
			(ProxyType::Any, _) => true,
			(_, ProxyType::Any) => false,
			(ProxyType::NonTransfer, _) => true,
			_ => false,
669
670
671
672
		}
	}
}

673
impl pallet_proxy::Config for Runtime {
674
675
676
677
678
679
680
	type Event = Event;
	type Call = Call;
	type Currency = Balances;
	type ProxyType = ProxyType;
	type ProxyDepositBase = ProxyDepositBase;
	type ProxyDepositFactor = ProxyDepositFactor;
	type MaxProxies = MaxProxies;
681
	type WeightInfo = weights::pallet_proxy::WeightInfo<Runtime>;
682
683
684
685
	type MaxPending = MaxPending;
	type CallHasher = BlakeTwo256;
	type AnnouncementDepositBase = AnnouncementDepositBase;
	type AnnouncementDepositFactor = AnnouncementDepositFactor;
686
687
}

ddorgan's avatar
ddorgan committed
688
689
690
construct_runtime! {
	pub enum Runtime where
		Block = Block,
691
		NodeBlock = primitives::v1::Block,
ddorgan's avatar
ddorgan committed
692
693
694
		UncheckedExtrinsic = UncheckedExtrinsic
	{
		// Basic stuff; balances is uncallable initially.
695
696
		System: frame_system::{Pallet, Call, Storage, Config, Event<T>} = 0,
		RandomnessCollectiveFlip: pallet_randomness_collective_flip::{Pallet, Storage} = 25,
ddorgan's avatar
ddorgan committed
697
698

		// Must be before session.
699
		Babe: pallet_babe::{Pallet, Call, Storage, Config, ValidateUnsigned} = 1,
ddorgan's avatar
ddorgan committed
700

701
702
703
704
		Timestamp: pallet_timestamp::{Pallet, Call, Storage, Inherent} = 2,
		Indices: pallet_indices::{Pallet, Call, Storage, Config<T>, Event<T>} = 3,
		Balances: pallet_balances::{Pallet, Call, Storage, Config<T>, Event<T>} = 4,
		TransactionPayment: pallet_transaction_payment::{Pallet, Storage} = 26,
ddorgan's avatar
ddorgan committed
705
706

		// Consensus support.
707
		Authorship: pallet_authorship::{Pallet, Call, Storage} = 5,
708
		Staking: pallet_staking::{Pallet, Call, Storage, Config<T>, Event<T>} = 6,
709
710
711
712
713
714
		Offences: pallet_offences::{Pallet, Call, Storage, Event} = 7,
		Historical: session_historical::{Pallet} = 27,
		Session: pallet_session::{Pallet, Call, Storage, Event, Config<T>} = 8,
		Grandpa: pallet_grandpa::{Pallet, Call, Storage, Config, Event, ValidateUnsigned} = 10,
		ImOnline: pallet_im_online::{Pallet, Call, Storage, Event<T>, ValidateUnsigned, Config<T>} = 11,
		AuthorityDiscovery: pallet_authority_discovery::{Pallet, Call, Config} = 12,
ddorgan's avatar
ddorgan committed
715
716

		// Utility module.
717
		Utility: pallet_utility::{Pallet, Call, Event} = 16,
ddorgan's avatar
ddorgan committed
718
719

		// Less simple identity module.
720
		Identity: pallet_identity::{Pallet, Call, Storage, Event<T>} = 17,
ddorgan's avatar
ddorgan committed
721
722

		// Social recovery module.
723
		Recovery: pallet_recovery::{Pallet, Call, Storage, Event<T>} = 18,
ddorgan's avatar
ddorgan committed
724
725

		// Vesting. Usable initially, but removed once all vesting is finished.
726
		Vesting: pallet_vesting::{Pallet, Call, Storage, Event<T>, Config<T>} = 19,
ddorgan's avatar
ddorgan committed
727
728

		// System scheduler.
729
		Scheduler: pallet_scheduler::{Pallet, Call, Storage, Event<T>} = 20,
ddorgan's avatar
ddorgan committed
730
731

		// Sudo.
732
		Sudo: pallet_sudo::{Pallet, Call, Storage, Event<T>, Config<T>} = 21,
733
734

		// Proxy module. Late addition.
735
		Proxy: pallet_proxy::{Pallet, Call, Storage, Event<T>} = 22,
736
737

		// Multisig module. Late addition.
738
		Multisig: pallet_multisig::{Pallet, Call, Storage, Event<T>} = 23,
739
740

		// Election pallet. Only works with staking, but placed here to maintain indices.
741
		ElectionProviderMultiPhase: pallet_election_provider_multi_phase::{Pallet, Call, Storage, Event<T>, ValidateUnsigned} = 24,
ddorgan's avatar
ddorgan committed
742
743
744
	}
}

745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
impl pallet_babe::migrations::BabePalletPrefix for Runtime {
	fn pallet_prefix() -> &'static str {
		"Babe"
	}
}

pub struct BabeEpochConfigMigrations;
impl frame_support::traits::OnRuntimeUpgrade for BabeEpochConfigMigrations {
	fn on_runtime_upgrade() -> frame_support::weights::Weight {
		pallet_babe::migrations::add_epoch_configuration::<Runtime>(
			BABE_GENESIS_EPOCH_CONFIG,
		)
	}
}

ddorgan's avatar
ddorgan committed
760
/// The address format for describing accounts.
761
pub type Address = sp_runtime::MultiAddress<AccountId, ()>;
ddorgan's avatar
ddorgan committed
762
763
764
765
766
767
768
769
770
771
/// Block header type as expected by this runtime.
pub type Header = generic::Header<BlockNumber, BlakeTwo256>;
/// Block type as expected by this runtime.
pub type Block = generic::Block<Header, UncheckedExtrinsic>;
/// A Block signed with a Justification
pub type SignedBlock = generic::SignedBlock<Block>;
/// BlockId type as expected by this runtime.
pub type BlockId = generic::BlockId<Block>;
/// The SignedExtension to the basic transaction logic.
pub type SignedExtra = (
772
773
774
775
776
777
778
	frame_system::CheckSpecVersion<Runtime>,
	frame_system::CheckTxVersion<Runtime>,
	frame_system::CheckGenesis<Runtime>,
	frame_system::CheckMortality<Runtime>,
	frame_system::CheckNonce<Runtime>,
	frame_system::CheckWeight<Runtime>,
	pallet_transaction_payment::ChargeTransactionPayment<Runtime>,
ddorgan's avatar
ddorgan committed
779
780
781
782
783
784
);
/// Unchecked extrinsic type as expected by this runtime.
pub type UncheckedExtrinsic = generic::UncheckedExtrinsic<Address, Call, Signature, SignedExtra>;
/// Extrinsic type that has already been checked.
pub type CheckedExtrinsic = generic::CheckedExtrinsic<AccountId, Nonce, Call>;
/// Executive: handles dispatch to the various modules.
785
786
787
788
789
pub type Executive = frame_executive::Executive<
	Runtime,
	Block,
	frame_system::ChainContext<Runtime>,
	Runtime,
790
	AllPallets,
791
	BabeEpochConfigMigrations
792
>;
793
794
/// The payload being signed in transactions.
pub type SignedPayload = generic::SignedPayload<Call, SignedExtra>;
ddorgan's avatar
ddorgan committed
795

796
#[cfg(not(feature = "disable-runtime-api"))]
ddorgan's avatar
ddorgan committed
797
798
799
800
801
802
803
sp_api::impl_runtime_apis! {
	impl sp_api::Core<Block> for Runtime {
		fn version() -> RuntimeVersion {
			VERSION
		}

		fn execute_block(block: Block) {
804
			Executive::execute_block(block);
ddorgan's avatar
ddorgan committed
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
		}

		fn initialize_block(header: &<Block as BlockT>::Header) {
			Executive::initialize_block(header)
		}
	}

	impl sp_api::Metadata<Block> for Runtime {
		fn metadata() -> OpaqueMetadata {
			Runtime::metadata().into()
		}
	}

	impl block_builder_api::BlockBuilder<Block> for Runtime {
		fn apply_extrinsic(extrinsic: <Block as BlockT>::Extrinsic) -> ApplyExtrinsicResult {
			Executive::apply_extrinsic(extrinsic)
		}

		fn finalize_block() -> <Block as BlockT>::Header {
			Executive::finalize_block()
		}

		fn inherent_extrinsics(data: inherents::InherentData) -> Vec<<Block as BlockT>::Extrinsic> {
			data.create_extrinsics()
		}

		fn check_inherents(
			block: Block,
			data: inherents::InherentData,
		) -> inherents::CheckInherentsResult {
			data.check_extrinsics(&block)
		}

		fn random_seed() -> <Block as BlockT>::Hash {
839
			pallet_babe::RandomnessFromOneEpochAgo::<Runtime>::random_seed().0
ddorgan's avatar
ddorgan committed
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
		}
	}

	impl tx_pool_api::runtime_api::TaggedTransactionQueue<Block> for Runtime {
		fn validate_transaction(
			source: TransactionSource,
			tx: <Block as BlockT>::Extrinsic,
		) -> TransactionValidity {
			Executive::validate_transaction(source, tx)
		}
	}

	impl offchain_primitives::OffchainWorkerApi<Block> for Runtime {
		fn offchain_worker(header: &<Block as BlockT>::Header) {
			Executive::offchain_worker(header)
		}
	}

858
859
860
	impl primitives::v1::ParachainHost<Block, Hash, BlockNumber> for Runtime {
		fn validators() -> Vec<ValidatorId> {
			Vec::new()
ddorgan's avatar
ddorgan committed
861
		}
862
863
864

		fn validator_groups() -> (Vec<Vec<ValidatorIndex>>, GroupRotationInfo<BlockNumber>) {
			(Vec::new(), GroupRotationInfo { session_start_block: 0, group_rotation_frequency: 0, now: 0 })
ddorgan's avatar
ddorgan committed
865
		}
866

867
		fn availability_cores() -> Vec<CoreState<Hash, BlockNumber>> {
868
			Vec::new()
ddorgan's avatar
ddorgan committed
869
		}
870
871
872

		fn persisted_validation_data(_: Id, _: OccupiedCoreAssumption)
			-> Option<PersistedValidationData<BlockNumber>> {
873
			None
ddorgan's avatar
ddorgan committed
874
		}
875

876
877
878
879
		fn historical_validation_code(_: Id, _: BlockNumber) -> Option<ValidationCode> {
			None
		}

880
881
		fn check_validation_outputs(
			_: Id,
882
			_: primitives::v1::CandidateCommitments
883
884
885
886
		) -> bool {
			false
		}

887
888
889
890
		fn session_index_for_child() -> SessionIndex {
			0
		}

891
892
893
894
		fn session_info(_: SessionIndex) -> Option<SessionInfo> {
			None
		}

895
		fn validation_code(_: Id, _: OccupiedCoreAssumption) -> Option<ValidationCode> {
896
			None
ddorgan's avatar
ddorgan committed
897
		}
898
899
900

		fn candidate_pending_availability(_: Id) -> Option<CommittedCandidateReceipt<Hash>> {
			None
ddorgan's avatar
ddorgan committed
901
		}
902
903

		fn candidate_events() -> Vec<CandidateEvent<Hash>> {
904
			Vec::new()
905
		}
906

907
908
		fn dmq_contents(
			_recipient: Id,
Sergey Pepyakin's avatar
Sergey Pepyakin committed
909
		) -> Vec<InboundDownwardMessage<BlockNumber>> {
910
911
			Vec::new()
		}
Sergey Pepyakin's avatar
Sergey Pepyakin committed
912
913
914
915
916
917

		fn inbound_hrmp_channels_contents(
			_recipient: Id
		) -> BTreeMap<Id, Vec<InboundHrmpMessage<BlockNumber>>> {
			BTreeMap::new()
		}
ddorgan's avatar
ddorgan committed
918
919
920
921
922
923
	}

	impl fg_primitives::GrandpaApi<Block> for Runtime {
		fn grandpa_authorities() -> Vec<(GrandpaId, u64)> {
			Grandpa::grandpa_authorities()
		}
924

925
		fn submit_report_equivocation_unsigned_extrinsic(
926
927
928
929
930
931
932
933
			equivocation_proof: fg_primitives::EquivocationProof<
				<Block as BlockT>::Hash,
				sp_runtime::traits::NumberFor<Block>,
			>,
			key_owner_proof: fg_primitives::OpaqueKeyOwnershipProof,
		) -> Option<()> {
			let key_owner_proof = key_owner_proof.decode()?;

934
			Grandpa::submit_unsigned_equivocation_report(
935
936
937
938
939
940
941
942
943
				equivocation_proof,
				key_owner_proof,
			)
		}

		fn generate_key_ownership_proof(
			_set_id: fg_primitives::SetId,
			authority_id: fg_primitives::AuthorityId,
		) -> Option<fg_primitives::OpaqueKeyOwnershipProof> {
944
			use parity_scale_codec::Encode;
945
946
947
948
949

			Historical::prove((fg_primitives::KEY_TYPE, authority_id))
				.map(|p| p.encode())
				.map(fg_primitives::OpaqueKeyOwnershipProof::new)
		}
ddorgan's avatar
ddorgan committed
950
951
952
	}

	impl babe_primitives::BabeApi<Block> for Runtime {
953
		fn configuration() -> babe_primitives::BabeGenesisConfiguration {
ddorgan's avatar
ddorgan committed
954
955
956
957
958
			// The choice of `c` parameter (where `1 - c` represents the
			// probability of a slot being empty), is done in accordance to the
			// slot duration and expected target block time, for safely
			// resisting network delays of maximum two seconds.
			// <https://research.web3.foundation/en/latest/polkadot/BABE/Babe/#6-practical-results>
959
			babe_primitives::BabeGenesisConfiguration {
ddorgan's avatar
ddorgan committed
960
961
				slot_duration: Babe::slot_duration(),
				epoch_length: EpochDuration::get(),
962
				c: BABE_GENESIS_EPOCH_CONFIG.c,
ddorgan's avatar
ddorgan committed
963
964
				genesis_authorities: Babe::authorities(),
				randomness: Babe::randomness(),
965
				allowed_slots: BABE_GENESIS_EPOCH_CONFIG.allowed_slots,
ddorgan's avatar
ddorgan committed
966
967
968
			}
		}

Bastian Köcher's avatar
Bastian Köcher committed
969
		fn current_epoch_start() -> babe_primitives::Slot {
ddorgan's avatar
ddorgan committed
970
971
			Babe::current_epoch_start()
		}
972

973
974
975
976
		fn current_epoch() -> babe_primitives::Epoch {
			Babe::current_epoch()
		}

977
978
979
980
		fn next_epoch() -> babe_primitives::Epoch {
			Babe::next_epoch()
		}

981
		fn generate_key_ownership_proof(
Bastian Köcher's avatar
Bastian Köcher committed
982
			_slot: babe_primitives::Slot,
983
984
			authority_id: babe_primitives::AuthorityId,
		) -> Option<babe_primitives::OpaqueKeyOwnershipProof> {
985
			use parity_scale_codec::Encode;
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000

			Historical::prove((babe_primitives::KEY_TYPE, authority_id))
				.map(|p| p.encode())
				.map(babe_primitives::OpaqueKeyOwnershipProof::new)
		}

		fn submit_report_equivocation_unsigned_extrinsic(
			equivocation_proof: babe_primitives::EquivocationProof<<Block as BlockT>::Header>,
			key_owner_proof: babe_primitives::OpaqueKeyOwnershipProof,
		) -> Option<()> {
			let key_owner_proof = key_owner_proof.decode()?;

			Babe::submit_unsigned_equivocation_report(
				equivocation_proof,
				key_owner_proof,
For faster browsing, not all history is shown. View entire blame