Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Implementation of the new validator disabling strategy #2226

Merged
merged 99 commits into from
Apr 26, 2024
Merged
Show file tree
Hide file tree
Changes from 69 commits
Commits
Show all changes
99 commits
Select commit Hold shift + click to select a range
913232a
Handling of disabled validators in backing subsystem (#1259)
tdimitrov Oct 20, 2023
42607ad
Merge branch 'master' into tsv-disabling
tdimitrov Oct 24, 2023
5a6ad28
Merge branch 'master' into tsv-disabling
ordian Oct 26, 2023
c986fd3
Merge branch 'master' into tsv-disabling
tdimitrov Nov 6, 2023
b16c8b6
Merge branch 'master' into tsv-disabling
tdimitrov Nov 6, 2023
bbb6631
Any offender is disabled for a whole era - wip
tdimitrov Nov 8, 2023
c80ae21
Fix `on_offence` compilation errors
tdimitrov Nov 9, 2023
8f5d2b6
Remove `DisableStrategy`
tdimitrov Nov 9, 2023
c8adffe
Merge branch 'master' into tsv-disabling
tdimitrov Nov 9, 2023
2507584
Merge branch 'tsv-disabling' into tsv-disabling-for-era
tdimitrov Nov 9, 2023
bff0240
Fix a compilation error after merge master: `CandidateValidationMessa…
tdimitrov Nov 9, 2023
e601dee
Merge branch 'tsv-disabling' into tsv-disabling-for-era
tdimitrov Nov 9, 2023
95aa673
Update a comment
tdimitrov Nov 10, 2023
873e072
Update comments
tdimitrov Nov 14, 2023
02814e0
Merge branch 'master' into tsv-disabling
tdimitrov Nov 14, 2023
5afbfe3
Merge branch 'tsv-disabling' into tsv-disabling-for-era
tdimitrov Nov 14, 2023
129a986
Replace `OffendingValidatorsThreshold` with `disabling_threshold`. Do…
tdimitrov Nov 13, 2023
ce1539c
Make tests pass
tdimitrov Nov 13, 2023
aee9fe3
Update tests to cover the new disabling strategy
tdimitrov Nov 15, 2023
d23c530
Storage migration for `OffendingValidators`
tdimitrov Nov 15, 2023
d2c5895
Apply suggestions from code review
tdimitrov Nov 16, 2023
06e79d9
Fix storage migration - use `VersionedMigration`, fix storage alias, …
tdimitrov Nov 16, 2023
9f8c598
Rename `disabling_threshold` -> `disabling_limit`
tdimitrov Nov 16, 2023
61b8c22
Merge branch 'master' into tsv-disabling
tdimitrov Nov 16, 2023
0a39a15
Fix test-staking-e2e
tdimitrov Nov 16, 2023
f4f82ec
Fix a compilation error
tdimitrov Nov 16, 2023
879279b
Fix compilation errors in benchmarks
tdimitrov Nov 16, 2023
3f4adaa
Merge branch 'tsv-disabling' into tsv-disabling-for-era
tdimitrov Nov 21, 2023
5936d69
Extract `DisablingStrategy` as a trait
tdimitrov Nov 24, 2023
f330b61
Merge branch 'master' into tsv-disabling
tdimitrov Nov 29, 2023
5e8b367
Fix compilation errors after merge
tdimitrov Nov 29, 2023
f2d4c48
Filter votes from disabled validators in `BackedCandidates` in proces…
tdimitrov Nov 30, 2023
9cb65f8
Fix a typo
tdimitrov Dec 5, 2023
ed203d8
Do not chill validators on offence
tdimitrov Dec 7, 2023
a954ca5
Merge branch 'master' into tsv-disabling
tdimitrov Dec 7, 2023
a210f37
Merge branch 'tsv-disabling' into tsv-disabling-for-era
tdimitrov Dec 7, 2023
6097a32
Don't disable for offences in previous eras
tdimitrov Dec 13, 2023
3109a29
Code review feedback - rework `enters_emergency_phase_after_forcing_b…
tdimitrov Dec 13, 2023
41ce978
Add `DisablingStrategy` to benchmarking mocks
tdimitrov Dec 14, 2023
28d5055
Fix a comment
tdimitrov Dec 14, 2023
71b6f60
`try_state` check for `DisabledValidators`
tdimitrov Dec 14, 2023
790cf4a
Fix another comment
tdimitrov Dec 14, 2023
6dfd0bc
Apply suggestions from code review
tdimitrov Dec 14, 2023
cd185b6
Fix a comment
tdimitrov Dec 14, 2023
cc09228
debug_assert for `DisabledValidators` being sorted
tdimitrov Dec 14, 2023
2552cb6
Unit tests for `UpToByzantineThresholdDisablingStrategy`
tdimitrov Dec 18, 2023
327b9fd
Remove struct DisablingDecision
tdimitrov Jan 2, 2024
c187d50
pub DisablingDecisionContext
tdimitrov Jan 2, 2024
e1899ce
Extract disabling threshold as a generic parameter of `UpToByzantineT…
tdimitrov Jan 4, 2024
1d283dc
Changelog and prdoc
tdimitrov Jan 4, 2024
1ef6e83
Fetch offender info and active set via staking pallet in `make_disabl…
tdimitrov Jan 5, 2024
55ccffe
UpToByzantineThresholdDisablingStrategy -> UpToThresholdDisablingStra…
tdimitrov Jan 5, 2024
52de0f5
Remove `set_validation_intention_after_chilled` from test-staking-e2e…
tdimitrov Jan 5, 2024
87af293
fmt
tdimitrov Jan 5, 2024
3506229
Merge branch 'master' into tsv-disabling
tdimitrov Jan 5, 2024
93f5189
Fix a compilation error from merge
tdimitrov Jan 5, 2024
2cf308f
Merge branch 'master' into tsv-disabling
tdimitrov Jan 8, 2024
68585e1
Merge branch 'tsv-disabling' into tsv-disabling-for-era
tdimitrov Jan 8, 2024
21e662b
Merge branch 'master' into tsv-disabling
tdimitrov Jan 9, 2024
ceb6941
Apply suggestions from code review
tdimitrov Jan 15, 2024
8d56d2f
Return early in `make_disabling_decision` implementation for `UpToThr…
tdimitrov Jan 15, 2024
db43ae1
Remove stale TODO
tdimitrov Jan 15, 2024
18eae58
`DISABLING_FACTOR` becomes `SLASHING_DISABLING_FACTOR` in test-stakin…
tdimitrov Jan 15, 2024
cec4bbe
Don't divide by 0 in `disable_threshold` from `UpToThresholdDisabling…
tdimitrov Jan 15, 2024
859770a
Ensure only the expected set of validators is disabled in `mass_slash…
tdimitrov Jan 16, 2024
6f0d216
Merge branch 'tsv-disabling' into tsv-disabling-for-era
ordian Jan 16, 2024
48da767
Merge branch 'master' into tsv-disabling
tdimitrov Jan 16, 2024
e94fa2c
Merge branch 'tsv-disabling' into tsv-disabling-for-era
tdimitrov Jan 16, 2024
3511b06
Use `defensive!` in disabling threshold calculation
tdimitrov Jan 16, 2024
9a775a5
`make_disabling_decision` returns an `Option` instead of a `Vec`
tdimitrov Jan 17, 2024
0111e69
Update substrate/frame/staking/CHANGELOG.md
tdimitrov Jan 17, 2024
9786407
Merge branch 'master' into tsv-disabling
tdimitrov Jan 18, 2024
5c3e98e
Merge branch 'tsv-disabling' into tsv-disabling-for-era
tdimitrov Jan 18, 2024
aed68dd
Merge branch 'master' into tsv-disabling-for-era
tdimitrov Jan 29, 2024
755192b
Merge branch 'master' into tsv-disabling-for-era
tdimitrov Feb 2, 2024
00456ae
Merge branch 'master' into tsv-disabling-for-era
tdimitrov Feb 28, 2024
460ffd6
Fix a compilation error after merge
tdimitrov Feb 28, 2024
aaf8ee8
Merge branch 'master' into tsv-disabling-for-era
tdimitrov Feb 28, 2024
3f4e73a
Merge branch 'master' into tsv-disabling-for-era
tdimitrov Mar 1, 2024
80fabc5
Update substrate/frame/staking/src/migrations.rs
tdimitrov Mar 12, 2024
9aa8b70
Remove `disabled_validators` getter from `DisabledValidators`
tdimitrov Mar 12, 2024
4e0c3cf
Fix the migration - clear `OffendingValidators` by using `take` inste…
tdimitrov Mar 12, 2024
b71e0db
Ensure `OffendingValidators` after migrating to V15
tdimitrov Mar 12, 2024
37b7c4a
`make_disabling_decision` -> `decision`
tdimitrov Mar 12, 2024
fdb49a3
`DISABLING_THRESHOLD_FACTOR` -> `DISABLING_LIMIT_FACTOR`
tdimitrov Mar 12, 2024
301f48e
Update prdoc
tdimitrov Mar 12, 2024
e3a8528
Merge branch 'master' into tsv-disabling-for-era
tdimitrov Mar 20, 2024
abe8e99
Merge branch 'master' into tsv-disabling-for-era
tdimitrov Apr 11, 2024
cb11fb9
Fix migration
tdimitrov Apr 11, 2024
64ba884
Fix storage migration of `OffendingValidators` (#4083)
tdimitrov Apr 12, 2024
8a509f5
Code review feedback
tdimitrov Apr 23, 2024
049c545
Merge branch 'master' into tsv-disabling-for-era
tdimitrov Apr 23, 2024
d4e4ab3
".git/.scripts/commands/fmt/fmt.sh"
Apr 23, 2024
f84162c
Fix `virtual_nominators_are_lazily_slashed`
tdimitrov Apr 23, 2024
87112ac
Fix `decision` from `UpToLimitDisablingStrategy` (#4262)
tdimitrov Apr 24, 2024
8db8167
Update substrate/frame/staking/src/slashing.rs
tdimitrov Apr 24, 2024
b76e5e7
Update substrate/frame/staking/src/pallet/impls.rs
tdimitrov Apr 24, 2024
a228aff
Remove misleading comment
tdimitrov Apr 25, 2024
1e90461
Merge branch 'master' into tsv-disabling-for-era
tdimitrov Apr 26, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
31 changes: 31 additions & 0 deletions polkadot/roadmap/implementers-guide/src/runtime/parainherent.md
Original file line number Diff line number Diff line change
Expand Up @@ -60,3 +60,34 @@ processing it, so the processed inherent data is simply dropped.
This also means that the `enter` function keeps data around for no good reason. This seems acceptable though as the size
of a block is rather limited. Nevertheless if we ever wanted to optimize this we can easily implement an inherent
collector that has two implementations, where one clones and stores the data and the other just passes it on.

## Data sanitization
`ParasInherent` with the entry point of `create_inherent` sanitizes the input data, while the `enter` entry point
enforces already sanitized input data. If unsanitized data is provided the module generates an error.

Disputes are included in the block with a priority for a security reasons. It's important to include as many dispute
votes onchain as possible so that disputes conclude faster and the offenders are punished. However if there are too many
disputes to include in a block the dispute set is trimmed so that it respects max block weight.

Dispute data is first deduplicated and sorted by block number (older first) and dispute location (local then remote).
Concluded and ancient (disputes initiated before the post conclusion acceptance period) disputes are filtered out.
Votes with invalid signatures or from unknown validators (not found in the active set for the current session) are also
filtered out.

All dispute statements are included in the order described in the previous paragraph until the available block weight is
exhausted. After the dispute data is included all remaining weight is filled in with candidates and availability
bitfields. Bitfields are included with priority, then candidates containing code updates and finally any backed
candidates. If there is not enough weight for all backed candidates they are trimmed by random selection. Disputes are
processed in three separate functions - `deduplicate_and_sort_dispute_data`, `filter_dispute_data` and
`limit_and_sanitize_disputes`.

Availability bitfields are also sanitized by dropping malformed ones, containing disputed cores or bad signatures. Refer
to `sanitize_bitfields` function for implementation details.

Backed candidates sanitization removes malformed ones, candidates which have got concluded invalid disputes against them
or candidates produced by unassigned cores. Furthermore any backing votes from disabled validators for a candidate are
dropped. This is part of the validator disabling strategy. After filtering the statements from disabled validators a
backed candidate may end up with votes count less than `minimum_backing_votes` (a parameter from `HostConfiguiration`).
In this case the whole candidate is dropped otherwise it will be rejected by `process_candidates` from pallet inclusion.
All checks related to backed candidates are implemented in `sanitize_backed_candidates` and
`filter_backed_statements_from_disabled_validators`.
4 changes: 3 additions & 1 deletion polkadot/runtime/common/src/assigned_slots/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -746,7 +746,9 @@ mod tests {
type AssignCoretime = ();
}

impl parachains_shared::Config for Test {}
impl parachains_shared::Config for Test {
type DisabledValidators = ();
}

parameter_types! {
pub const LeasePeriod: BlockNumber = 3;
Expand Down
4 changes: 3 additions & 1 deletion polkadot/runtime/common/src/integration_tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -197,7 +197,9 @@ impl configuration::Config for Test {
type WeightInfo = configuration::TestWeightInfo;
}

impl shared::Config for Test {}
impl shared::Config for Test {
type DisabledValidators = ();
}

impl origin::Config for Test {}

Expand Down
4 changes: 3 additions & 1 deletion polkadot/runtime/common/src/paras_registrar/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -799,7 +799,9 @@ mod tests {
type MaxFreezes = ConstU32<1>;
}

impl shared::Config for Test {}
impl shared::Config for Test {
type DisabledValidators = ();
}

impl origin::Config for Test {}

Expand Down
11 changes: 1 addition & 10 deletions polkadot/runtime/parachains/src/disputes/slashing.rs
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,7 @@ use sp_runtime::{
KeyTypeId, Perbill,
};
use sp_session::{GetSessionNumber, GetValidatorCount};
use sp_staking::offence::{DisableStrategy, Kind, Offence, OffenceError, ReportOffence};
use sp_staking::offence::{Kind, Offence, OffenceError, ReportOffence};
use sp_std::{
collections::{btree_map::Entry, btree_set::BTreeSet},
prelude::*,
Expand Down Expand Up @@ -134,15 +134,6 @@ where
self.time_slot.clone()
}

fn disable_strategy(&self) -> DisableStrategy {
match self.kind {
SlashingOffenceKind::ForInvalid => DisableStrategy::Always,
// in the future we might change it based on number of disputes initiated:
// <https://github.com/paritytech/polkadot/issues/5946>
SlashingOffenceKind::AgainstValid => DisableStrategy::Never,
}
}

fn slash_fraction(&self, _offenders: u32) -> Perbill {
self.slash_fraction
}
Expand Down
27 changes: 26 additions & 1 deletion polkadot/runtime/parachains/src/mock.rs
Original file line number Diff line number Diff line change
Expand Up @@ -194,7 +194,22 @@ impl crate::configuration::Config for Test {
type WeightInfo = crate::configuration::TestWeightInfo;
}

impl crate::shared::Config for Test {}
pub struct MockDisabledValidators {}
impl frame_support::traits::DisabledValidators for MockDisabledValidators {
/// Returns true if the given validator is disabled.
fn is_disabled(index: u32) -> bool {
disabled_validators().iter().any(|v| *v == index)
}

/// Returns a hardcoded list (`DISABLED_VALIDATORS`) of disabled validators
fn disabled_validators() -> Vec<u32> {
disabled_validators()
}
}

impl crate::shared::Config for Test {
type DisabledValidators = MockDisabledValidators;
}

impl origin::Config for Test {}

Expand Down Expand Up @@ -567,6 +582,8 @@ thread_local! {

pub static AVAILABILITY_REWARDS: RefCell<HashMap<ValidatorIndex, usize>>
= RefCell::new(HashMap::new());

pub static DISABLED_VALIDATORS: RefCell<Vec<u32>> = RefCell::new(vec![]);
}

pub fn backing_rewards() -> HashMap<ValidatorIndex, usize> {
Expand All @@ -577,6 +594,10 @@ pub fn availability_rewards() -> HashMap<ValidatorIndex, usize> {
AVAILABILITY_REWARDS.with(|r| r.borrow().clone())
}

pub fn disabled_validators() -> Vec<u32> {
DISABLED_VALIDATORS.with(|r| r.borrow().clone())
}

parameter_types! {
pub static Processed: Vec<(ParaId, UpwardMessage)> = vec![];
}
Expand Down Expand Up @@ -716,3 +737,7 @@ pub(crate) fn deregister_parachain(id: ParaId) {
pub(crate) fn try_deregister_parachain(id: ParaId) -> crate::DispatchResult {
frame_support::storage::transactional::with_storage_layer(|| Paras::schedule_para_cleanup(id))
}

pub(crate) fn set_disabled_validators(disabled: Vec<u32>) {
DISABLED_VALIDATORS.with(|d| *d.borrow_mut() = disabled)
}
Loading