-
Notifications
You must be signed in to change notification settings - Fork 973
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
RANDAO reveal slashing, custody period staggering and integration of custody and RANDAO reveals #880
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Added some tests and have a couple of questions.
Can we think about this a lot more before we put something like this in? I'm very worried about this approach because it means that if you propose a block, you are making yourself vulnerable to slashings if the chain forks, even if you did nothing wrong. In all other cases, the chain would need to reorg at least a week for that to happen. I would propose this alternative: if you make an early randao reveal, you face a small penalty (eg. a week's worth of rewards), with a rule that this penalty can be applied a maximum of once every 72 days. |
Also want to think more about combining the two kinds of slashing reveals as a single message type and a single verification function. |
I have an idea in that regard: the custody key for period N is also the randao subkey for the slot at the start of period N+2. Then, we could have a rule that revealing a randao subkey early (ie. any time before the start of period N+2) would only have a small penalty, but revealing any randao subkey more than one full period early (which coincides with when the randao subkey would be used as a PoC key if it's used that way) gets you slashed. So we get both covered with one message type and one function. |
Very interesting. I like this solution. So actually the custody key for the custody period starting at epoch N would then be the Randao reveal starting at epoch N+EPOCHS_PER_CUSTODY_PERIOD+2, right?
What's the reason for the 72 day rule? |
…ted more lenient penalty for not-to-early reveals
I now unified this with the Custody reveal and removed the masking logic from the Custody Reveal scheme, since all slashing can now be performed through the RANDAO reveal logic. I had to introduce another constant to do this:
|
Consensus of today was that we will merge this. Vitalik had some reservation about the length of CUSTODY_PERIOD_TO_RANDAO_PADDING and suggested possibly setting CUSTODY_PERIOD_TO_RANDAO_PADDING = EPOCHS_PER_CUSTODY_PERIOD. I prefer it being shorter, the code is written so that we can adjust this constant as we see fit. |
# Conflicts: # specs/core/0_beacon-chain.md
CUSTODY_PERIOD_TO_RANDAO_PADDING = EPOCHS_PER_CUSTODY_PERIOD
…dator record clean
I merged #934 into this, so now this implements:
|
specs/core/1_custody-game.md
Outdated
state=state, | ||
index=challenge.responder_index, | ||
epoch=slot_to_epoch(attestation.data.slot)), | ||
challenge.responder_index), |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
IMO we don't even need the verify_custody_key
function here; just use the one-liner we use in phase 0:
epoch=get_randao_epoch_for_custody_period(
get_validators_custody_reveal_period(
state=state,
index=challenge.responder_index,
epoch=slot_to_epoch(attestation.data.slot)),
challenge.responder_index)
assert bls_verify(responder.pubkey, hash_tree_root(epoch), challenge.responder_key, get_domain(state, DOMAIN_RANDAO, epoch))
This way we can remove the complexity of wrapping the custody key in a pointless reveal object with extraneous fields (the empty mask) and furthermore reduce the number of verify_custody_key
calls to 1, which allows the function to be removed entirely (see comment above).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, done
specs/core/1_custody-game.md
Outdated
|
||
# Case 2: masked punitive early reveal | ||
# Handle the case of a regular custody reveal | ||
process_custody_reveal(state, reveal) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe for symmetry put the logic below this into a separate function process_randao_key_punitive_reveal
and have the top-level function just be:
revealed_validator = state.validator_registry[reveal.revealed_index]
if reveal.mask == ZERO_HASH:
pubkeys = [revealed_validator.pubkey]
message_hashes = [hash_tree_root(reveal.epoch)]
else:
masker = state.validator_registry[reveal.masker_index]
pubkeys = [revealed_validator.pubkey, masker.pubkey]
message_hashes = [
hash_tree_root(reveal.epoch),
reveal.mask,
]
assert bls_verify_multiple(
pubkeys=pubkeys,
message_hashes=message_hashes,
signature=reveal.reveal,
domain=get_domain(
state=state,
domain_type=DOMAIN_RANDAO,
message_epoch=reveal.epoch,
),
)
if reveal.mask == ZERO_HASH:
process_custody_reveal(state, reveal)
else:
process_randao_key_punitive_reveal(state, reveal)
This, plus the suggestion below, would allow the verify_custody_key
function to be cut out entirely.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Though honestly if we have this parallel structure the right approach may be to just have two objects, a CustodyKeyReveal
and a EarlyReveal
, where only the latter has the masking mechanism and the former does not (the former would just be a thin wrapper {validator_index: uint64, custody_key: bytes96}
). This way we don't need the empty mask fields in legitimate key reveals, and the code can be separated out more instead of being an if statement that runs totally different code depending on what role the object is serving.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I did this using two objects now. Pls review and check if this is your preferred method :)
Co-Authored-By: dankrad <dankrad@ethereum.org>
…eals; append the cleanup of RANDAO reveals instead of adding a new function
TBD after call: |
The penalty for the early RANDAO reveal (that is not valid as a custody key anymore) is now proportional to the number of secrets already exposed. This is the simplest way of increasing punishment for a coordinated attack, and probably quite good because RANDAO reveals are useful to an attacker if they are all for the same epoch by different validators.
|
# Conflicts: # test_libs/pyspec/tests/helpers.py
specs/core/0_beacon-chain.md
Outdated
@@ -234,6 +236,9 @@ These configurations are updated for releases, but may be out of sync during `de | |||
| `MIN_VALIDATOR_WITHDRAWABILITY_DELAY` | `2**8` (= 256) | epochs | ~27 hours | | |||
| `PERSISTENT_COMMITTEE_PERIOD` | `2**11` (= 2,048) | epochs | 9 days | | |||
| `MAX_CROSSLINK_EPOCHS` | `2**6` (= 64) | epochs | ~7 hours | | |||
| `RANDAO_PENALTY_EPOCHS` | `2` | epochs | 12.8 minutes | |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Formatting here is inconsistent
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Now in 1_custody-game -- looks consistent to me? What is the problem?
Co-Authored-By: dankrad <dankrad@ethereum.org>
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Makes the formatting consistent
Co-Authored-By: dankrad <dankrad@ethereum.org>
Co-Authored-By: dankrad <dankrad@ethereum.org>
# Conflicts: # specs/core/1_custody-game.md
Currently, there is no mechanism to punish validators for revealing their Randao reveals. This could lead to a situation where these can easily bought and sold without risk for a long time in the future, which aggravates the attacks on Randao.
The logic is very similar to the early custody reveal logic.