lib.rs 38.4 KB
Newer Older
Shawn Tabrizi's avatar
Shawn Tabrizi committed
1
// Copyright 2017-2020 Parity Technologies (UK) Ltd.
Gav's avatar
Gav committed
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
// 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/>.

17
//! The Polkadot runtime. This can be compiled with `#[no_std]`, ready for Wasm.
Gav's avatar
Gav committed
18
19

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

23
use runtime_common::{attestations, claims, parachains, registrar, slots,
24
	impls::{CurrencyToVoteHandler, TargetedFeeAdjustment, ToAuthor},
25
	NegativeImbalance, BlockHashCount, MaximumBlockWeight, AvailableBlockRatio,
26
	MaximumBlockLength, BlockExecutionWeight, ExtrinsicBaseWeight, RocksDbWeight,
Gavin Wood's avatar
Gavin Wood committed
27
	MaximumExtrinsicWeight, TransactionCallFilter,
28
};
Gav Wood's avatar
Gav Wood committed
29

30
use sp_std::prelude::*;
31
use sp_core::u32_trait::{_1, _2, _3, _4, _5};
32
use codec::{Encode, Decode};
33
use primitives::{
34
	AccountId, AccountIndex, Balance, BlockNumber, Hash, Nonce, Signature, Moment,
Gavin Wood's avatar
Gavin Wood committed
35
	parachain::{self, ActiveParas, AbridgedCandidateReceipt, SigningContext},
36
};
37
use sp_runtime::{
38
	create_runtime_str, generic, impl_opaque_keys, ModuleId,
39
	ApplyExtrinsicResult, KeyTypeId, Percent, Permill, Perbill, Perquintill, PerThing,
40
	transaction_validity::{
Gavin Wood's avatar
Gavin Wood committed
41
		TransactionValidity, TransactionSource, TransactionPriority,
42
	},
43
	curve::PiecewiseLinear,
44
	traits::{
Gavin Wood's avatar
Gavin Wood committed
45
46
		BlakeTwo256, Block as BlockT, OpaqueKeys, ConvertInto, IdentityLookup,
		Extrinsic as ExtrinsicT, SaturatedConversion, Verify,
47
	},
Gav Wood's avatar
Gav Wood committed
48
};
49
50
#[cfg(feature = "runtime-benchmarks")]
use sp_runtime::RuntimeString;
Arkadiy Paronyan's avatar
Arkadiy Paronyan committed
51
use version::RuntimeVersion;
52
use grandpa::{AuthorityId as GrandpaId, fg_primitives};
53
54
#[cfg(any(feature = "std", test))]
use version::NativeVersion;
55
56
use sp_core::OpaqueMetadata;
use sp_staking::SessionIndex;
57
use frame_support::{
58
	parameter_types, construct_runtime, debug, RuntimeDebug,
Gavin Wood's avatar
Gavin Wood committed
59
	traits::{KeyOwnerProofSystem, SplitTwoWays, Randomness, LockIdentifier, Filter},
60
	weights::Weight,
Gavin Wood's avatar
Gavin Wood committed
61
};
thiolliere's avatar
thiolliere committed
62
use im_online::sr25519::AuthorityId as ImOnlineId;
Gavin Wood's avatar
Gavin Wood committed
63
use authority_discovery_primitives::AuthorityId as AuthorityDiscoveryId;
Gavin Wood's avatar
Gavin Wood committed
64
use transaction_payment_rpc_runtime_api::RuntimeDispatchInfo;
65
use session::historical as session_historical;
66
use static_assertions::const_assert;
67

Gav Wood's avatar
Gav Wood committed
68
69
#[cfg(feature = "std")]
pub use staking::StakerStatus;
70
#[cfg(any(feature = "std", test))]
71
pub use sp_runtime::BuildStorage;
72
pub use timestamp::Call as TimestampCall;
73
pub use balances::Call as BalancesCall;
74
pub use attestations::{Call as AttestationsCall, MORE_ATTESTATIONS_IDENTIFIER};
75
pub use parachains::Call as ParachainsCall;
76
77
78

/// Constant values used within the runtime.
pub mod constants;
79
use constants::{time::*, currency::*, fee::*};
80
use frame_support::traits::InstanceFilter;
81

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

86
// Polkadot version identifier;
87
/// Runtime version (Polkadot).
Arkadiy Paronyan's avatar
Arkadiy Paronyan committed
88
pub const VERSION: RuntimeVersion = RuntimeVersion {
89
90
	spec_name: create_runtime_str!("polkadot"),
	impl_name: create_runtime_str!("parity-polkadot"),
Gavin Wood's avatar
Gavin Wood committed
91
	authoring_version: 0,
92
	spec_version: 3,
93
94
	impl_version: 0,
	apis: RUNTIME_API_VERSIONS,
Gavin Wood's avatar
Gavin Wood committed
95
	transaction_version: 0,
96
};
Arkadiy Paronyan's avatar
Arkadiy Paronyan committed
97

98
99
100
101
102
103
104
105
106
/// Native version.
#[cfg(any(feature = "std", test))]
pub fn native_version() -> NativeVersion {
	NativeVersion {
		runtime_version: VERSION,
		can_author_with: Default::default(),
	}
}

Gavin Wood's avatar
Gavin Wood committed
107
108
109
pub struct IsCallable;
impl Filter<Call> for IsCallable {
	fn filter(call: &Call) -> bool {
110
		match call {
Gavin Wood's avatar
Gavin Wood committed
111
			Call::Parachains(parachains::Call::set_heads(..)) => true,
Gavin Wood's avatar
Gavin Wood committed
112

Gavin Wood's avatar
Gavin Wood committed
113
114
115
116
117
118
			// Governance stuff
			Call::Democracy(_) | Call::Council(_) | Call::TechnicalCommittee(_) |
			Call::ElectionsPhragmen(_) | Call::TechnicalMembership(_) | Call::Treasury(_) |
			// Parachains stuff
			Call::Parachains(_) | Call::Attestations(_) | Call::Slots(_) | Call::Registrar(_) |
			// Balances and Vesting's transfer (which can be used to transfer)
Gavin Wood's avatar
Gavin Wood committed
119
120
			Call::Balances(_) | Call::Vesting(vesting::Call::vested_transfer(..)) |
			Call::Indices(indices::Call::transfer(..)) =>
Gavin Wood's avatar
Gavin Wood committed
121
122
123
124
125
126
127
128
				false,

			// These modules are all allowed to be called by transactions:
			Call::System(_) | Call::Scheduler(_) | Call::Indices(_) |
			Call::Babe(_) | Call::Timestamp(_) |
			Call::Authorship(_) | Call::Staking(_) | Call::Offences(_) |
			Call::Session(_) | Call::FinalityTracker(_) | Call::Grandpa(_) | Call::ImOnline(_) |
			Call::AuthorityDiscovery(_) |
Gavin Wood's avatar
Gavin Wood committed
129
			Call::Utility(_) | Call::Claims(_) | Call::Vesting(_) | Call::Sudo(_) |
130
			Call::Identity(_) | Call::Proxy(_) =>
Gavin Wood's avatar
Gavin Wood committed
131
				true,
132
133
134
135
		}
	}
}

136
parameter_types! {
137
	pub const Version: RuntimeVersion = VERSION;
138
139
}

140
141
impl system::Trait for Runtime {
	type Origin = Origin;
142
	type Call = Call;
Gav Wood's avatar
Gav Wood committed
143
	type Index = Nonce;
144
145
146
147
	type BlockNumber = BlockNumber;
	type Hash = Hash;
	type Hashing = BlakeTwo256;
	type AccountId = AccountId;
148
	type Lookup = IdentityLookup<AccountId>;
149
	type Header = generic::Header<BlockNumber, BlakeTwo256>;
Gav's avatar
Gav committed
150
	type Event = Event;
151
	type BlockHashCount = BlockHashCount;
152
	type MaximumBlockWeight = MaximumBlockWeight;
153
	type DbWeight = RocksDbWeight;
154
155
	type BlockExecutionWeight = BlockExecutionWeight;
	type ExtrinsicBaseWeight = ExtrinsicBaseWeight;
Tomasz Drwięga's avatar
Tomasz Drwięga committed
156
	type MaximumExtrinsicWeight = MaximumExtrinsicWeight;
157
158
	type MaximumBlockLength = MaximumBlockLength;
	type AvailableBlockRatio = AvailableBlockRatio;
159
	type Version = Version;
160
	type ModuleToIndex = ModuleToIndex;
161
	type AccountData = balances::AccountData<Balance>;
Gavin Wood's avatar
Gavin Wood committed
162
	type OnNewAccount = ();
163
	type OnKilledAccount = ();
164
165
}

Gavin Wood's avatar
Gavin Wood committed
166
167
168
169
170
171
172
impl scheduler::Trait for Runtime {
	type Event = Event;
	type Origin = Origin;
	type Call = Call;
	type MaximumWeight = MaximumBlockWeight;
}

173
parameter_types! {
174
	pub const EpochDuration: u64 = EPOCH_DURATION_IN_BLOCKS as u64;
175
176
177
178
179
180
	pub const ExpectedBlockTime: Moment = MILLISECS_PER_BLOCK;
}

impl babe::Trait for Runtime {
	type EpochDuration = EpochDuration;
	type ExpectedBlockTime = ExpectedBlockTime;
181
182
183

	// session module is the trigger
	type EpochChangeTrigger = babe::ExternalTrigger;
184
185
}

Gavin Wood's avatar
Gavin Wood committed
186
parameter_types! {
Gavin Wood's avatar
Gavin Wood committed
187
	pub const IndexDeposit: Balance = 10 * DOLLARS;
Gavin Wood's avatar
Gavin Wood committed
188
189
}

Gav Wood's avatar
Gav Wood committed
190
191
impl indices::Trait for Runtime {
	type AccountIndex = AccountIndex;
192
193
	type Currency = Balances;
	type Deposit = IndexDeposit;
Gav Wood's avatar
Gav Wood committed
194
195
196
	type Event = Event;
}

Gavin Wood's avatar
Gavin Wood committed
197
parameter_types! {
198
	pub const ExistentialDeposit: Balance = 100 * CENTS;
Gavin Wood's avatar
Gavin Wood committed
199
200
201
202
203
}

/// Splits fees 80/20 between treasury and block author.
pub type DealWithFees = SplitTwoWays<
	Balance,
204
205
206
	NegativeImbalance<Runtime>,
	_4, Treasury,   		// 4 parts (80%) goes to the treasury.
	_1, ToAuthor<Runtime>,   	// 1 part (20%) goes to the block author.
Gavin Wood's avatar
Gavin Wood committed
207
208
>;

209
impl balances::Trait for Runtime {
Gav's avatar
Gav committed
210
	type Balance = Balance;
211
	type DustRemoval = ();
Gavin Wood's avatar
Gavin Wood committed
212
	type Event = Event;
Gavin Wood's avatar
Gavin Wood committed
213
	type ExistentialDeposit = ExistentialDeposit;
214
	type AccountStore = System;
215
216
217
218
}

parameter_types! {
	pub const TransactionByteFee: Balance = 10 * MILLICENTS;
219
	pub const TargetBlockFullness: Perquintill = Perquintill::from_percent(25);
220
221
}

222
223
224
225
226
227
228
// for a sane configuration, this should always be less than `AvailableBlockRatio`.
const_assert!(
	TargetBlockFullness::get().deconstruct() <
	(AvailableBlockRatio::get().deconstruct() as <Perquintill as PerThing>::Inner)
		* (<Perquintill as PerThing>::ACCURACY / <Perbill as PerThing>::ACCURACY as <Perquintill as PerThing>::Inner)
);

229
230
231
impl transaction_payment::Trait for Runtime {
	type Currency = Balances;
	type OnTransactionPayment = DealWithFees;
Gavin Wood's avatar
Gavin Wood committed
232
	type TransactionByteFee = TransactionByteFee;
233
	type WeightToFee = WeightToFee;
234
	type FeeMultiplierUpdate = TargetedFeeAdjustment<TargetBlockFullness, Self>;
Gav's avatar
Gav committed
235
236
}

237
parameter_types! {
238
	pub const MinimumPeriod: u64 = SLOT_DURATION / 2;
239
}
240
impl timestamp::Trait for Runtime {
241
	type Moment = u64;
242
	type OnTimestampSet = Babe;
243
	type MinimumPeriod = MinimumPeriod;
244
245
}

Gavin Wood's avatar
Gavin Wood committed
246
parameter_types! {
247
	pub const UncleGenerations: u32 = 0;
Gavin Wood's avatar
Gavin Wood committed
248
249
250
251
}

// TODO: substrate#2986 implement this properly
impl authorship::Trait for Runtime {
252
	type FindAuthor = session::FindAccountFromAuthorIndex<Self, Babe>;
Gavin Wood's avatar
Gavin Wood committed
253
254
	type UncleGenerations = UncleGenerations;
	type FilterUncle = ();
Gavin Wood's avatar
Gavin Wood committed
255
	type EventHandler = (Staking, ImOnline);
Gavin Wood's avatar
Gavin Wood committed
256
257
}

258
impl_opaque_keys! {
259
	pub struct SessionKeys {
Gavin Wood's avatar
Gavin Wood committed
260
261
262
263
		pub grandpa: Grandpa,
		pub babe: Babe,
		pub im_online: ImOnline,
		pub parachain_validator: Parachains,
Gavin Wood's avatar
Gavin Wood committed
264
		pub authority_discovery: AuthorityDiscovery,
265
	}
266
267
}

thiolliere's avatar
thiolliere committed
268
269
270
271
parameter_types! {
	pub const DisabledValidatorsThreshold: Perbill = Perbill::from_percent(17);
}

272
impl session::Trait for Runtime {
Gav's avatar
Gav committed
273
	type Event = Event;
274
275
	type ValidatorId = AccountId;
	type ValidatorIdOf = staking::StashOf<Self>;
Gavin Wood's avatar
Gavin Wood committed
276
	type ShouldEndSession = Babe;
277
	type NextSessionRotation = Babe;
278
	type SessionManager = session::historical::NoteHistoricalRoot<Self, Staking>;
Gavin Wood's avatar
Gavin Wood committed
279
280
	type SessionHandler = <SessionKeys as OpaqueKeys>::KeyTypeIdProviders;
	type Keys = SessionKeys;
thiolliere's avatar
thiolliere committed
281
	type DisabledValidatorsThreshold = DisabledValidatorsThreshold;
282
283
284
285
}

impl session::historical::Trait for Runtime {
	type FullIdentification = staking::Exposure<AccountId, Balance>;
286
	type FullIdentificationOf = staking::ExposureOf<Runtime>;
287
288
}

289
pallet_staking_reward_curve::build! {
thiolliere's avatar
thiolliere committed
290
291
292
293
294
295
296
297
298
299
	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,
	);
}

300
parameter_types! {
Gavin Wood's avatar
Gavin Wood committed
301
	// Six sessions in an era (24 hours).
302
	pub const SessionsPerEra: SessionIndex = 6;
Gavin Wood's avatar
Gavin Wood committed
303
	// 28 eras for unbonding (28 days).
Gavin Wood's avatar
Gavin Wood committed
304
305
	pub const BondingDuration: staking::EraIndex = 28;
	pub const SlashDeferDuration: staking::EraIndex = 28;
thiolliere's avatar
thiolliere committed
306
	pub const RewardCurve: &'static PiecewiseLinear<'static> = &REWARD_CURVE;
Gavin Wood's avatar
Gavin Wood committed
307
	pub const MaxNominatorRewardedPerValidator: u32 = 64;
308
	// quarter of the last session will be for election.
Gavin Wood's avatar
Gavin Wood committed
309
	pub const ElectionLookahead: BlockNumber = EPOCH_DURATION_IN_BLOCKS / 16;
310
311
	pub const MaxIterations: u32 = 10;
	pub MinSolutionScoreBump: Perbill = Perbill::from_rational_approximation(5u32, 10_000);
312
}
313

314
impl staking::Trait for Runtime {
Gavin Wood's avatar
Gavin Wood committed
315
	type Currency = Balances;
316
	type UnixTime = Timestamp;
317
	type CurrencyToVote = CurrencyToVoteHandler<Self>;
Gavin Wood's avatar
Gavin Wood committed
318
	type RewardRemainder = Treasury;
Gav's avatar
Gav committed
319
	type Event = Event;
320
	type Slash = Treasury;
321
	type Reward = ();
322
323
	type SessionsPerEra = SessionsPerEra;
	type BondingDuration = BondingDuration;
Gavin Wood's avatar
Gavin Wood committed
324
325
	type SlashDeferDuration = SlashDeferDuration;
	// A super-majority of the council can cancel the slash.
Gavin Wood's avatar
Gavin Wood committed
326
	type SlashCancelOrigin = collective::EnsureProportionAtLeast<_3, _4, AccountId, CouncilCollective>;
327
	type SessionInterface = Self;
thiolliere's avatar
thiolliere committed
328
	type RewardCurve = RewardCurve;
Gavin Wood's avatar
Gavin Wood committed
329
	type MaxNominatorRewardedPerValidator = MaxNominatorRewardedPerValidator;
330
331
332
	type NextNewSession = Session;
	type ElectionLookahead = ElectionLookahead;
	type Call = Call;
333
	type UnsignedPriority = StakingUnsignedPriority;
334
	type MaxIterations = MaxIterations;
335
	type MinSolutionScoreBump = MinSolutionScoreBump;
336
337
}

Gavin Wood's avatar
Gavin Wood committed
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
parameter_types! {
	// Minimum 4 CENTS/byte
	pub const BasicDeposit: Balance = deposit(1, 258);
	pub const FieldDeposit: Balance = deposit(0, 66);
	pub const SubAccountDeposit: Balance = deposit(1, 53);
	pub const MaxSubAccounts: u32 = 100;
	pub const MaxAdditionalFields: u32 = 100;
	pub const MaxRegistrars: u32 = 20;
}

impl identity::Trait for Runtime {
	type Event = Event;
	type Currency = Balances;
	type BasicDeposit = BasicDeposit;
	type FieldDeposit = FieldDeposit;
	type SubAccountDeposit = SubAccountDeposit;
	type MaxSubAccounts = MaxSubAccounts;
	type MaxAdditionalFields = MaxAdditionalFields;
	type MaxRegistrars = MaxRegistrars;
	type Slashed = Treasury;
	type ForceOrigin = collective::EnsureProportionMoreThan<_1, _2, AccountId, CouncilCollective>;
	type RegistrarOrigin = collective::EnsureProportionMoreThan<_1, _2, AccountId, CouncilCollective>;
}

362
parameter_types! {
363
364
	pub const LaunchPeriod: BlockNumber = 28 * DAYS;
	pub const VotingPeriod: BlockNumber = 28 * DAYS;
365
	pub const FastTrackVotingPeriod: BlockNumber = 3 * HOURS;
366
	pub const MinimumDeposit: Balance = 100 * DOLLARS;
367
368
	pub const EnactmentPeriod: BlockNumber = 8 * DAYS;
	pub const CooloffPeriod: BlockNumber = 7 * DAYS;
Gavin Wood's avatar
Gavin Wood committed
369
370
	// One cent: $10,000 / MB
	pub const PreimageByteDeposit: Balance = 1 * CENTS;
Gavin Wood's avatar
Gavin Wood committed
371
	pub const InstantAllowed: bool = true;
372
	pub const MaxVotes: u32 = 100;
373
374
}

375
376
377
impl democracy::Trait for Runtime {
	type Proposal = Call;
	type Event = Event;
378
	type Currency = Balances;
379
380
381
382
	type EnactmentPeriod = EnactmentPeriod;
	type LaunchPeriod = LaunchPeriod;
	type VotingPeriod = VotingPeriod;
	type MinimumDeposit = MinimumDeposit;
383
384
	/// A straight majority of the council can decide what their next motion is.
	type ExternalOrigin = collective::EnsureProportionAtLeast<_1, _2, AccountId, CouncilCollective>;
385
386
	/// A 60% super-majority can have the next scheduled referendum be a straight majority-carries vote.
	type ExternalMajorityOrigin = collective::EnsureProportionAtLeast<_3, _5, AccountId, CouncilCollective>;
387
388
389
390
391
392
	/// A unanimous council can have the next scheduled referendum be a straight default-carries
	/// (NTB) vote.
	type ExternalDefaultOrigin = collective::EnsureProportionAtLeast<_1, _1, AccountId, CouncilCollective>;
	/// Two thirds of the technical committee can have an ExternalMajority/ExternalDefault vote
	/// be tabled immediately and with a shorter voting/enactment period.
	type FastTrackOrigin = collective::EnsureProportionAtLeast<_2, _3, AccountId, TechnicalCollective>;
393
394
395
	type InstantOrigin = collective::EnsureProportionAtLeast<_1, _1, AccountId, TechnicalCollective>;
	type InstantAllowed = InstantAllowed;
	type FastTrackVotingPeriod = FastTrackVotingPeriod;
396
397
398
399
400
	// To cancel a proposal which has been passed, 2/3 of the council must agree to it.
	type CancellationOrigin = collective::EnsureProportionAtLeast<_2, _3, AccountId, CouncilCollective>;
	// Any single technical committee member may veto a coming council proposal, however they can
	// only do it once and it lasts only for the cooloff period.
	type VetoOrigin = collective::EnsureMember<AccountId, TechnicalCollective>;
401
	type CooloffPeriod = CooloffPeriod;
Gavin Wood's avatar
Gavin Wood committed
402
	type PreimageByteDeposit = PreimageByteDeposit;
Gavin Wood's avatar
Gavin Wood committed
403
	type OperationalPreimageOrigin = collective::EnsureMember<AccountId, CouncilCollective>;
Gavin Wood's avatar
Gavin Wood committed
404
	type Slash = Treasury;
Gavin Wood's avatar
Gavin Wood committed
405
	type Scheduler = Scheduler;
406
	type MaxVotes = MaxVotes;
407
}
408

409
410
parameter_types! {
	pub const CouncilMotionDuration: BlockNumber = 7 * DAYS;
411
	pub const CouncilMaxProposals: u32 = 100;
412
413
}

414
415
type CouncilCollective = collective::Instance1;
impl collective::Trait<CouncilCollective> for Runtime {
416
417
418
	type Origin = Origin;
	type Proposal = Call;
	type Event = Event;
419
	type MotionDuration = CouncilMotionDuration;
420
	type MaxProposals = CouncilMaxProposals;
421
422
}

Gavin Wood's avatar
Gavin Wood committed
423
parameter_types! {
424
425
	pub const CandidacyBond: Balance = 100 * DOLLARS;
	pub const VotingBond: Balance = 5 * DOLLARS;
426
427
428
	/// Weekly council elections initially, later monthly.
	pub const TermDuration: BlockNumber = 7 * DAYS;
	/// 13 members initially, to be increased to 23 eventually.
429
	pub const DesiredMembers: u32 = 13;
430
	pub const DesiredRunnersUp: u32 = 20;
431
	pub const ElectionsPhragmenModuleId: LockIdentifier = *b"phrelect";
432
}
433
// Make sure that there are no more than MAX_MEMBERS members elected via phragmen.
434
const_assert!(DesiredMembers::get() <= collective::MAX_MEMBERS);
435
436

impl elections_phragmen::Trait for Runtime {
437
	type Event = Event;
Gavin Wood's avatar
Gavin Wood committed
438
	type ModuleId = ElectionsPhragmenModuleId;
439
440
	type Currency = Balances;
	type ChangeMembers = Council;
441
	type InitializeMembers = Council;
442
	type CurrencyToVote = CurrencyToVoteHandler<Self>;
Gavin Wood's avatar
Gavin Wood committed
443
444
	type CandidacyBond = CandidacyBond;
	type VotingBond = VotingBond;
445
446
447
	type LoserCandidate = Treasury;
	type BadReport = Treasury;
	type KickedMember = Treasury;
Gavin Wood's avatar
Gavin Wood committed
448
449
450
	type DesiredMembers = DesiredMembers;
	type DesiredRunnersUp = DesiredRunnersUp;
	type TermDuration = TermDuration;
451
452
}

453
454
parameter_types! {
	pub const TechnicalMotionDuration: BlockNumber = 7 * DAYS;
455
	pub const TechnicalMaxProposals: u32 = 100;
456
457
}

458
459
type TechnicalCollective = collective::Instance2;
impl collective::Trait<TechnicalCollective> for Runtime {
460
461
462
	type Origin = Origin;
	type Proposal = Call;
	type Event = Event;
463
	type MotionDuration = TechnicalMotionDuration;
464
	type MaxProposals = TechnicalMaxProposals;
465
466
}

467
468
469
470
471
472
impl membership::Trait<membership::Instance1> for Runtime {
	type Event = Event;
	type AddOrigin = collective::EnsureProportionMoreThan<_1, _2, AccountId, CouncilCollective>;
	type RemoveOrigin = collective::EnsureProportionMoreThan<_1, _2, AccountId, CouncilCollective>;
	type SwapOrigin = collective::EnsureProportionMoreThan<_1, _2, AccountId, CouncilCollective>;
	type ResetOrigin = collective::EnsureProportionMoreThan<_1, _2, AccountId, CouncilCollective>;
473
	type PrimeOrigin = collective::EnsureProportionMoreThan<_1, _2, AccountId, CouncilCollective>;
474
475
476
477
	type MembershipInitialized = TechnicalCommittee;
	type MembershipChanged = TechnicalCommittee;
}

Gavin Wood's avatar
Gavin Wood committed
478
479
parameter_types! {
	pub const ProposalBond: Permill = Permill::from_percent(5);
480
481
482
	pub const ProposalBondMinimum: Balance = 100 * DOLLARS;
	pub const SpendPeriod: BlockNumber = 24 * DAYS;
	pub const Burn: Permill = Permill::from_percent(1);
483
	pub const TreasuryModuleId: ModuleId = ModuleId(*b"py/trsry");
Gavin Wood's avatar
Gavin Wood committed
484
485
486
487
488

	pub const TipCountdown: BlockNumber = 1 * DAYS;
	pub const TipFindersFee: Percent = Percent::from_percent(20);
	pub const TipReportDepositBase: Balance = 1 * DOLLARS;
	pub const TipReportDepositPerByte: Balance = 1 * CENTS;
Gavin Wood's avatar
Gavin Wood committed
489
490
}

491
impl treasury::Trait for Runtime {
Gavin Wood's avatar
Gavin Wood committed
492
	type ModuleId = TreasuryModuleId;
Gavin Wood's avatar
Gavin Wood committed
493
	type Currency = Balances;
494
	type ApproveOrigin = collective::EnsureProportionAtLeast<_3, _5, AccountId, CouncilCollective>;
495
	type RejectOrigin = collective::EnsureProportionMoreThan<_1, _2, AccountId, CouncilCollective>;
Gavin Wood's avatar
Gavin Wood committed
496
497
498
499
500
	type Tippers = ElectionsPhragmen;
	type TipCountdown = TipCountdown;
	type TipFindersFee = TipFindersFee;
	type TipReportDepositBase = TipReportDepositBase;
	type TipReportDepositPerByte = TipReportDepositPerByte;
501
	type Event = Event;
502
	type ProposalRejection = Treasury;
Gavin Wood's avatar
Gavin Wood committed
503
504
505
506
	type ProposalBond = ProposalBond;
	type ProposalBondMinimum = ProposalBondMinimum;
	type SpendPeriod = SpendPeriod;
	type Burn = Burn;
507
}
508

509
parameter_types! {
510
	pub OffencesWeightSoftLimit: Weight = Perbill::from_percent(60) * MaximumBlockWeight::get();
511
512
}

513
514
515
516
impl offences::Trait for Runtime {
	type Event = Event;
	type IdentificationTuple = session::historical::IdentificationTuple<Self>;
	type OnOffenceHandler = Staking;
517
	type WeightSoftLimit = OffencesWeightSoftLimit;
518
519
}

Gavin Wood's avatar
Gavin Wood committed
520
521
impl authority_discovery::Trait for Runtime {}

522
523
524
525
parameter_types! {
	pub const SessionDuration: BlockNumber = EPOCH_DURATION_IN_BLOCKS as _;
}

526
527
528
529
530
parameter_types! {
	pub const StakingUnsignedPriority: TransactionPriority = TransactionPriority::max_value() / 2;
	pub const ImOnlineUnsignedPriority: TransactionPriority = TransactionPriority::max_value();
}

531
impl im_online::Trait for Runtime {
thiolliere's avatar
thiolliere committed
532
	type AuthorityId = ImOnlineId;
533
	type Event = Event;
534
	type SessionDuration = SessionDuration;
Gavin Wood's avatar
Gavin Wood committed
535
	type ReportUnresponsiveness = Offences;
536
	type UnsignedPriority = ImOnlineUnsignedPriority;
537
538
}

539
540
impl grandpa::Trait for Runtime {
	type Event = Event;
541
542
543
544
545
546
547
548
549
550
	type Call = Call;

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

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

Gavin Wood's avatar
Gavin Wood committed
551
552
	type KeyOwnerProofSystem = Historical;

553
554
555
556
557
558
	type HandleEquivocation = grandpa::EquivocationHandler<
		Self::KeyOwnerIdentification,
		primitives::fisherman::FishermanAppCrypto,
		Runtime,
		Offences,
	>;
559
560
}

Gavin Wood's avatar
Gavin Wood committed
561
parameter_types! {
562
563
	pub WindowSize: BlockNumber = finality_tracker::DEFAULT_WINDOW_SIZE.into();
	pub ReportLatency: BlockNumber = finality_tracker::DEFAULT_REPORT_LATENCY.into();
Gavin Wood's avatar
Gavin Wood committed
564
565
566
}

impl finality_tracker::Trait for Runtime {
567
	type OnFinalizationStalled = ();
Gavin Wood's avatar
Gavin Wood committed
568
569
570
571
	type WindowSize = WindowSize;
	type ReportLatency = ReportLatency;
}

572
573
574
575
parameter_types! {
	pub const AttestationPeriod: BlockNumber = 50;
}

576
577
578
impl attestations::Trait for Runtime {
	type AttestationPeriod = AttestationPeriod;
	type ValidatorIdentities = parachains::ValidatorIdentities<Runtime>;
579
	type RewardAttestation = Staking;
580
581
}

582
583
584
parameter_types! {
	pub const MaxCodeSize: u32 = 10 * 1024 * 1024; // 10 MB
	pub const MaxHeadDataSize: u32 = 20 * 1024; // 20 KB
585
586
587
588

	pub const ValidationUpgradeFrequency: BlockNumber = 7 * DAYS;
	pub const ValidationUpgradeDelay: BlockNumber = 1 * DAYS;
	pub const SlashPeriod: BlockNumber = 28 * DAYS;
589
590
}

591
impl parachains::Trait for Runtime {
592
	type AuthorityId = primitives::fisherman::FishermanAppCrypto;
593
594
	type Origin = Origin;
	type Call = Call;
595
	type ParachainCurrency = Balances;
596
	type BlockNumberConversion = sp_runtime::traits::Identity;
597
	type Randomness = RandomnessCollectiveFlip;
598
599
	type ActiveParachains = Registrar;
	type Registrar = Registrar;
600
601
	type MaxCodeSize = MaxCodeSize;
	type MaxHeadDataSize = MaxHeadDataSize;
602
603
604
605
606

	type ValidationUpgradeFrequency = ValidationUpgradeFrequency;
	type ValidationUpgradeDelay = ValidationUpgradeDelay;
	type SlashPeriod = SlashPeriod;

607
	type Proof = sp_session::MembershipProof;
608
609
610
	type KeyOwnerProofSystem = session::historical::Module<Self>;
	type IdentificationTuple = <Self::KeyOwnerProofSystem as KeyOwnerProofSystem<(KeyTypeId, Vec<u8>)>>::IdentificationTuple;
	type ReportOffence = Offences;
611
	type BlockHashConversion = sp_runtime::traits::Identity;
612
613
}

614
615
/// Submits a transaction with the node's public and signature type. Adheres to the signed extension
/// format of the chain.
616
617
618
619
620
621
622
impl<LocalCall> system::offchain::CreateSignedTransaction<LocalCall> for Runtime where
	Call: From<LocalCall>,
{
	fn create_transaction<C: system::offchain::AppCrypto<Self::Public, Self::Signature>>(
		call: Call,
		public: <Signature as Verify>::Signer,
		account: AccountId,
623
624
		nonce: <Runtime as system::Trait>::Index,
	) -> Option<(Call, <UncheckedExtrinsic as ExtrinsicT>::SignaturePayload)> {
625
		// take the biggest period possible.
626
627
628
629
630
631
632
		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>()
633
634
			// The `System::block_number` is initialized with `n+1`,
			// so the actual block number is `n`.
635
636
637
			.saturating_sub(1);
		let tip = 0;
		let extra: SignedExtra = (
Gavin Wood's avatar
Gavin Wood committed
638
			TransactionCallFilter::<IsCallable, Call>::new(),
639
640
			system::CheckSpecVersion::<Runtime>::new(),
			system::CheckTxVersion::<Runtime>::new(),
641
642
643
644
645
646
647
			system::CheckGenesis::<Runtime>::new(),
			system::CheckEra::<Runtime>::from(generic::Era::mortal(period, current_block)),
			system::CheckNonce::<Runtime>::from(nonce),
			system::CheckWeight::<Runtime>::new(),
			transaction_payment::ChargeTransactionPayment::<Runtime>::from(tip),
			registrar::LimitParathreadCommits::<Runtime>::new(),
			parachains::ValidateDoubleVoteReports::<Runtime>::new(),
648
			grandpa::ValidateEquivocationReport::<Runtime>::new(),
649
			claims::PrevalidateAttests::<Runtime>::new(),
650
651
		);
		let raw_payload = SignedPayload::new(call, extra).map_err(|e| {
652
			debug::warn!("Unable to create signed payload: {:?}", e);
653
		}).ok()?;
654
655
656
		let signature = raw_payload.using_encoded(|payload| {
			C::sign(payload, public)
		})?;
657
658
659
		let (call, extra, _) = raw_payload.deconstruct();
		Some((call, (account, signature, extra)))
	}
660
661
}

662
663
664
665
666
impl system::offchain::SigningTypes for Runtime {
	type Public = <Signature as Verify>::Signer;
	type Signature = Signature;
}

Gavin Wood's avatar
Gavin Wood committed
667
impl<C> system::offchain::SendTransactionTypes<C> for Runtime where Call: From<C> {
668
	type Extrinsic = UncheckedExtrinsic;
Gavin Wood's avatar
Gavin Wood committed
669
	type OverarchingCall = Call;
670
671
}

672
673
674
675
676
677
678
679
680
681
682
683
684
685
parameter_types! {
	pub const ParathreadDeposit: Balance = 500 * DOLLARS;
	pub const QueueSize: usize = 2;
	pub const MaxRetries: u32 = 3;
}

impl registrar::Trait for Runtime {
	type Event = Event;
	type Origin = Origin;
	type Currency = Balances;
	type ParathreadDeposit = ParathreadDeposit;
	type SwapAux = Slots;
	type QueueSize = QueueSize;
	type MaxRetries = MaxRetries;
686
}
687

Gavin Wood's avatar
Gavin Wood committed
688
parameter_types! {
689
	pub const LeasePeriod: BlockNumber = 100_000;
Gavin Wood's avatar
Gavin Wood committed
690
691
692
693
694
	pub const EndingPeriod: BlockNumber = 1000;
}

impl slots::Trait for Runtime {
	type Event = Event;
695
696
	type Currency = Balances;
	type Parachains = Registrar;
Gavin Wood's avatar
Gavin Wood committed
697
	type EndingPeriod = EndingPeriod;
Gavin Wood's avatar
Gavin Wood committed
698
	type LeasePeriod = LeasePeriod;
699
	type Randomness = RandomnessCollectiveFlip;
Gavin Wood's avatar
Gavin Wood committed
700
701
}

Gavin Wood's avatar
Gavin Wood committed
702
parameter_types! {
703
	pub Prefix: &'static [u8] = b"Pay DOTs to the Polkadot account:";
704
705
706
707
}

impl claims::Trait for Runtime {
	type Event = Event;
Gavin Wood's avatar
Gavin Wood committed
708
	type VestingSchedule = Vesting;
709
710
711
	type Prefix = Prefix;
}

712
713
714
715
parameter_types! {
	pub const MinVestedTransfer: Balance = 100 * DOLLARS;
}

Gavin Wood's avatar
Gavin Wood committed
716
717
718
719
impl vesting::Trait for Runtime {
	type Event = Event;
	type Currency = Balances;
	type BlockNumberToBalance = ConvertInto;
720
	type MinVestedTransfer = MinVestedTransfer;
Gavin Wood's avatar
Gavin Wood committed
721
722
}

Gavin Wood's avatar
Gavin Wood committed
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
parameter_types! {
	// One storage item; value is size 4+4+16+32 bytes = 56 bytes.
	pub const MultisigDepositBase: Balance = 30 * CENTS;
	// Additional storage item size of 32 bytes.
	pub const MultisigDepositFactor: Balance = 5 * CENTS;
	pub const MaxSignatories: u16 = 100;
}

impl utility::Trait for Runtime {
	type Event = Event;
	type Call = Call;
	type Currency = Balances;
	type MultisigDepositBase = MultisigDepositBase;
	type MultisigDepositFactor = MultisigDepositFactor;
	type MaxSignatories = MaxSignatories;
	type IsCallable = IsCallable;
}

741
742
impl sudo::Trait for Runtime {
	type Event = Event;
743
	type Call = Call;
744
745
}

746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
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;
}

/// 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,
	Governance,
	Staking,
}
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,
			ProxyType::NonTransfer => !matches!(c,
				Call::Balances(..) | Call::Utility(..)
					| Call::Vesting(vesting::Call::vested_transfer(..))
					| Call::Indices(indices::Call::transfer(..))
			),
			ProxyType::Governance => matches!(c,
				Call::Democracy(..) | Call::Council(..) | Call::TechnicalCommittee(..)
					| Call::ElectionsPhragmen(..) | Call::Treasury(..)
			),
			ProxyType::Staking => matches!(c, Call::Staking(..)),
		}
	}
}

impl proxy::Trait for Runtime {
	type Event = Event;
	type Call = Call;
	type Currency = Balances;
	type IsCallable = IsCallable;
	type ProxyType = ProxyType;
	type ProxyDepositBase = ProxyDepositBase;
	type ProxyDepositFactor = ProxyDepositFactor;
	type MaxProxies = MaxProxies;
}

Gavin Wood's avatar
Gavin Wood committed
792
construct_runtime! {
793
	pub enum Runtime where
794
		Block = Block,
795
		NodeBlock = primitives::Block,
796
		UncheckedExtrinsic = UncheckedExtrinsic
797
	{
798
		// Basic stuff; balances is uncallable initially.
Gavin Wood's avatar
Gavin Wood committed
799
		System: system::{Module, Call, Storage, Config, Event<T>},
Ashley's avatar
Ashley committed
800
		RandomnessCollectiveFlip: randomness_collective_flip::{Module, Storage},
Gavin Wood's avatar
Gavin Wood committed
801
		Scheduler: scheduler::{Module, Call, Storage, Event<T>},
802
803

		// Must be before session.
804
		Babe: babe::{Module, Call, Storage, Config, Inherent(Timestamp)},
805
806

		Timestamp: timestamp::{Module, Call, Storage, Inherent},
807
		Indices: indices::{Module, Call, Storage, Config<T>, Event<T>},
808
		Balances: balances::{Module, Call, Storage, Config<T>, Event<T>},
809
		TransactionPayment: transaction_payment::{Module, Storage},
810
811
812

		// Consensus support.
		Authorship: authorship::{Module, Call, Storage},
Kian Paimani's avatar
Kian Paimani committed
813
		Staking: staking::{Module, Call, Storage, Config<T>, Event<T>, ValidateUnsigned},
814
		Offences: offences::{Module, Call, Storage, Event},
815
		Historical: session_historical::{Module},
816
		Session: session::{Module, Call, Storage, Event, Config<T>},
817
		FinalityTracker: finality_tracker::{Module, Call, Storage, Inherent},
818
		Grandpa: grandpa::{Module, Call, Storage, Config, Event},
thiolliere's avatar
thiolliere committed
819
		ImOnline: im_online::{Module, Call, Storage, Event<T>, ValidateUnsigned, Config<T>},
Gavin Wood's avatar
Gavin Wood committed
820
		AuthorityDiscovery: authority_discovery::{Module, Call, Config},
821

Gavin Wood's avatar
Gavin Wood committed
822
823
		// Governance stuff; uncallable initially. Calls should be uncommented once we're ready to
		// enable governance.
Gavin Wood's avatar
Gavin Wood committed
824
		Democracy: democracy::{Module, Call, Storage, Config, Event<T>},
825
826
		Council: collective::<Instance1>::{Module, Call, Storage, Origin<T>, Event<T>, Config<T>},
		TechnicalCommittee: collective::<Instance2>::{Module, Call, Storage, Origin<T>, Event<T>, Config<T>},
827
		ElectionsPhragmen: elections_phragmen::{Module, Call, Storage, Event<T>, Config<T>},
828
		TechnicalMembership: membership::<Instance1>::{Module, Call, Storage, Event<T>, Config<T>},
Gavin Wood's avatar
Gavin Wood committed
829
		Treasury: treasury::{Module, Call, Storage, Event<T>},
830
831

		// Parachains stuff; slots are disabled (no auctions initially). The rest are safe as they
Gavin Wood's avatar
Gavin Wood committed
832
833
		// have no public dispatchables. Disabled `Call` on all of them, but this should be
		// uncommented once we're ready to start parachains.
834
		Parachains: parachains::{Module, Call, Storage, Config, Inherent, Origin},
835
		Attestations: attestations::{Module, Call, Storage},
Gavin Wood's avatar
Gavin Wood committed
836
		Slots: slots::{Module, Call, Storage, Event<T>},
837
		Registrar: registrar::{Module, Call, Storage, Event, Config<T>},
Gavin Wood's avatar
Gavin Wood committed
838
839
840
841
842

		// Claims. Usable initially.
		Claims: claims::{Module, Call, Storage, Event<T>, Config<T>, ValidateUnsigned},
		// Vesting. Usable initially, but removed once all vesting is finished.
		Vesting: vesting::{Module, Call, Storage, Event<T>, Config<T>},
Gavin Wood's avatar
Gavin Wood committed
843
844
		// Cunning utilities. Usable initially.
		Utility: utility::{Module, Call, Storage, Event<T>},
Gavin Wood's avatar
Gavin Wood committed
845
846

		// Sudo. Last module. Usable initially, but removed once governance enabled.
847
		Sudo: sudo::{Module, Call, Storage, Config<T>, Event<T>},
Gavin Wood's avatar
Gavin Wood committed
848
849
850

		// Identity. Late addition.
		Identity: identity::{Module, Call, Storage, Event<T>},
851
852
853

		// Proxy module. Late addition.
		Proxy: proxy::{Module, Call, Storage, Event}
Gav's avatar
Gav committed
854
	}
Gavin Wood's avatar
Gavin Wood committed
855
}
856
857

/// The address format for describing accounts.
858
pub type Address = AccountId;
859
/// Block header type as expected by this runtime.
860
pub type Header = generic::Header<BlockNumber, BlakeTwo256>;
861
862
863
864
865
866
/// 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>;
867
868
/// The SignedExtension to the basic transaction logic.
pub type SignedExtra = (
Gavin Wood's avatar
Gavin Wood committed
869
	TransactionCallFilter<IsCallable, Call>,
870
871
	system::CheckSpecVersion<Runtime>,
	system::CheckTxVersion<Runtime>,
872
	system::CheckGenesis<Runtime>,
873
874
875
	system::CheckEra<Runtime>,
	system::CheckNonce<Runtime>,
	system::CheckWeight<Runtime>,
876
	transaction_payment::ChargeTransactionPayment<Runtime>,
877
	registrar::LimitParathreadCommits<Runtime>,
André Silva's avatar