Skip to content
This repository has been archived by the owner on Nov 15, 2023. It is now read-only.

Fix offchain election to respect the weight #7215

Merged
25 commits merged into from
Oct 2, 2020
Merged

Conversation

kianenigma
Copy link
Contributor

@kianenigma kianenigma commented Sep 25, 2020

Closes #7170, hopefully partially fix some recent issues in polkadot. How? Using this:

/// Greedily reduce the size of the a solution to fit into the block, wrt weight.
///
/// The weight of the solution is foremost a function of the number of voters (i.e.
/// `compact.len()`). Aside from this, the other components of the weight are invariant. The number
/// of winners shall not be changed (otherwise the solution is invalid) and the `ElectionSize` is
/// merely a representation of the total number of stakers.
///
/// Thus, we reside to stripping away some voters. This means only changing the `compact` struct.
///
/// Note that the solution is already computed, and the winners are elected based on the merit of
/// teh entire stake in the system. Nonetheless, some of the voters will be removed further down the
/// line.
///
/// Indeed, the score must be computed **after** this step. If this step reduces the score too much,
/// then the solution will be discarded.

Full writeup of the situation: https://hackmd.io/sP9KlLUBRpukfhL6GyPa2w

I don't have any tests for this. But I've tested it against both polkadot and kusama. It seems like actually a lot of the nominators that we have are quite insignificant, meaning that they have very small values. Here's a log from my test script that uses this branch. This is in a case where we allow 90% of the block weight to be consumed by this.

2020-09-25T13:56:03Z INFO ] Maximum weight = 1800000000000 // current weight = 1865170206000 // maximum voters = 5880 // current votes = 6094
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 1348 with stake 158333 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 334 with stake 187173 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 4302 with stake 294473 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 2833 with stake 304895 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 4634 with stake 331878 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 718 with stake 1747697 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 3839 with stake 2455855 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 1214 with stake 2781387 from compact to reduce the size
...
...
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 3408 with stake 10000000000 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 3436 with stake 10000000000 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 3463 with stake 10000000000 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 4393 with stake 10000000000 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 4883 with stake 10000000000 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 4927 with stake 10000000000 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 4957 with stake 10000000000 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 5595 with stake 10000000000 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 5660 with stake 10000000000 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 5690 with stake 10000000000 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 5788 with stake 10000000000 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 5802 with stake 10000000000 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 6294 with stake 10000000000 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 6505 with stake 10000000000 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 6593 with stake 10000000000 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 6683 with stake 10000000000 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 404 with stake 10002906719 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 2437 with stake 10003281779 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 2755 with stake 10003281779 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 4755 with stake 10003686141 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 1130 with stake 10006704468 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 44 with stake 10007114498 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 2184 with stake 10007317556 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 5820 with stake 10011380861 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 59 with stake 10011530707 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 4641 with stake 10011542180 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 2751 with stake 10015531287 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 894 with stake 10016889078 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 3094 with stake 10017625922 from compact to reduce the size
[2020-09-25T13:56:05Z DEBUG] removed a voter at index 407 with stake 10017683661 from compact to reduce the size
[2020-09-25T13:56:05Z WARN ] 215 voters had to be removed from compact solution due to size limits.
[2020-09-25T13:56:06Z INFO ] prepared a seq-phragmen solution with 10 balancing iterations and score [26316480084687572, 6176088461156567857, 196338935690240526926418411607984375]
[2020-09-25T13:56:08Z INFO ] 💸 A better solution (with compute ElectionCompute::Unsigned and score [26316480084687572, 6176088461156567857, 196338935690240526926418411607984375]) has been validated and stored on chain.
[2020-09-25T13:56:08Z INFO ] Outcome of submitting this to the chian will be: Ok(PostDispatchInfo { actual_weight: None, pays_fee: Pays::Yes })

As you see, the solution hasn't changed much. The first element which is the most important is actually the same. The second, which is the total amount at stake, is indeed reduced.

This is on Polkadot, and essentially means a nominator cannot be effective with a stake less than 10_017_683_661, 10 new DOTs if I am not mistaking.

Also, I made the transaction Operational so that it can consume more of the weight.

polkadot companion: paritytech/polkadot#1768


TODOs:

  • Fix the fuzzer.
  • Check log amounts, levels and targets.
  • Companion should ensure that UnsignedPriority is high enough so that this transaction is almost always the first one to be put in the block (and effectively preventing anything else from getting into the block. )
  • Run a testnet and make sure that this value of OffchainSolutionWeightLimit is correct. Otherwise this whole PR is moot.

frame/staking/src/lib.rs Outdated Show resolved Hide resolved
@gui1117
Copy link
Contributor

gui1117 commented Sep 25, 2020

This PR mostly touches offchain which is currently in crisis anyway, so I didn't review carefully yet, but the only on-chain change is making the dispatchable submit_solution_unsigned operational AFAICT

kianenigma and others added 4 commits September 28, 2020 09:05
Co-authored-by: Shawn Tabrizi <shawntabrizi@gmail.com>
Co-authored-by: Shawn Tabrizi <shawntabrizi@gmail.com>
@kianenigma kianenigma added the D9-needsaudit 👮 PR contains changes to fund-managing logic that should be properly reviewed and externally audited label Sep 28, 2020
bin/node/runtime/src/lib.rs Outdated Show resolved Hide resolved
bin/node/runtime/src/lib.rs Outdated Show resolved Hide resolved
frame/staking/src/benchmarking.rs Show resolved Hide resolved
frame/staking/src/lib.rs Outdated Show resolved Hide resolved
frame/staking/src/testing_utils.rs Show resolved Hide resolved
primitives/npos-elections/compact/src/lib.rs Outdated Show resolved Hide resolved
primitives/npos-elections/compact/src/lib.rs Outdated Show resolved Hide resolved
if step == 0 {
// We might have reduced less than expected due to rounding error. Reduce one last time.
while weight_with(voters) > max_weight {
voters -= 1;
Copy link
Contributor

@tomusdrw tomusdrw Sep 28, 2020

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This may underflow? if weight_with(0) > max_weight.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes this is a bit buggy

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed! Have a look at the test cases as well.

}
// For the opposite case.
while weight_with(voters + 1) < max_weight {
voters += 1;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This should be bounded by size.nominators - we may reach this point if weight_with(size.nominators) < max_weight, no?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes the final return is bounded, but I will add it here as well.

frame/staking/src/offchain_election.rs Outdated Show resolved Hide resolved
frame/staking/src/offchain_election.rs Outdated Show resolved Hide resolved
frame/staking/src/offchain_election.rs Outdated Show resolved Hide resolved
frame/staking/src/offchain_election.rs Outdated Show resolved Hide resolved
frame/staking/src/lib.rs Outdated Show resolved Hide resolved
frame/staking/src/lib.rs Outdated Show resolved Hide resolved
gui1117
gui1117 previously approved these changes Sep 30, 2020
Copy link
Contributor

@gui1117 gui1117 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nothing as changed in frame/system/src/extensions/check_weight.rs isn't it ?

apart from #7215 (comment)
EDIT: and also a guard so that only one transaction can be submitted by block author (as Tomasz said)
looks good to me

@gui1117 gui1117 dismissed their stale review September 30, 2020 15:01

I'm not certain about mandatory unsigned extrinsic

@kianenigma
Copy link
Contributor Author

nothing as changed in frame/system/src/extensions/check_weight.rs isn't it ?

No, just variable names etc.

@viniul
Copy link
Contributor

viniul commented Sep 30, 2020

We are done with our review for this PR and don't see any issues with it so far. We are happy to take another look once the discussion around setting the OffchainSolutionWeightLimit is resolved.

@kianenigma kianenigma added D1-audited 👍 PR contains changes to fund-managing logic that has been properly reviewed and externally audited and removed D9-needsaudit 👮 PR contains changes to fund-managing logic that should be properly reviewed and externally audited labels Oct 2, 2020
Copy link
Contributor

@gui1117 gui1117 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

looks good to me 👍

frame/staking/src/lib.rs Outdated Show resolved Hide resolved
Copy link
Contributor

@tomusdrw tomusdrw left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

looks good except for the unbounded loop!

frame/staking/src/offchain_election.rs Outdated Show resolved Hide resolved
@gavofyork
Copy link
Member

bot merge

@ghost
Copy link

ghost commented Oct 2, 2020

Trying merge.

@ghost ghost merged commit 7314a78 into master Oct 2, 2020
@ghost ghost deleted the kiz-staking-OCW-check-size branch October 2, 2020 13:45
liuchengxu pushed a commit to liuchengxu/substrate that referenced this pull request Oct 5, 2020
* Mockup

* Fix offchain election to respect the weight

* Fix builds a bit

* Update frame/staking/src/offchain_election.rs

Co-authored-by: Shawn Tabrizi <shawntabrizi@gmail.com>

* Update frame/staking/src/offchain_election.rs

Co-authored-by: Shawn Tabrizi <shawntabrizi@gmail.com>

* Make it build, binary search

* Fix a number of grumbles

* one more fix.

* remove unwrap.

* better alg.

* Better alg again.

* Final fixes

* Fix

* Rollback to normal

* Final touches.

* Better tests.

* Update frame/staking/src/lib.rs

Co-authored-by: Guillaume Thiolliere <gui.thiolliere@gmail.com>

* Proper maxExtWeight

* Final fix

* Final fix for the find_voter

Co-authored-by: Shawn Tabrizi <shawntabrizi@gmail.com>
Co-authored-by: Guillaume Thiolliere <gui.thiolliere@gmail.com>
ordian added a commit that referenced this pull request Oct 9, 2020
…up-updates

* master:
  Async keystore + Authority-Discovery async/await (#7000)
  Fixes logging of target names with dashes (#7281)
  seal: Add automated weights for contract API calls (#7017)
  add ss58 id for nodle (#7279)
  Refactor CurrencyToVote (#6896)
  bump-allocator: document & poison (#7277)
  Reset flaming fir network (#7274)
  reschedule (#6860)
  Drop system cache for trie benchmarks (#7242)
  client: improve log formatting (#7272)
  Rework `InspectState` (#7271)
  SystemOrigin trait (#7226)
  Update ss58 registry for Dock network (#7263)
  .maintain/monitoring: Add alert when continuous task ends (#7250)
  Rename `TRANSACTION_VERSION` to `EXTRINSIC_VERSION` (#7258)
  Split block announce processing into two parts (#6958)
  Fix offchain election to respect the weight (#7215)
This pull request was closed.
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
A0-please_review Pull request needs code review. D1-audited 👍 PR contains changes to fund-managing logic that has been properly reviewed and externally audited
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Staking OCW should not create solutions that are too big
6 participants