mirror of
https://github.com/pezkuwichain/pezkuwi-subxt.git
synced 2026-06-14 12:11:09 +00:00
more clear randomness API for BABE (#8180)
* more clear randomness API for BABE * babe: move randomness utilities to its own file * node: use babe::RandomnessFromOneEpochAgo in random_seed implementation * frame-support: annotate randomness trait with block number * pallet-randomness-collective-flip: fix for new randomness trait * pallet-society: fix randomness usage * pallet-lottery: fix randomness usage * pallet-contracts: fix randomness usage * pallet-babe: fix randomness usage we need to track when the current and previous epoch started so that we know the block number by each existing on-chain was known * node: fix random_seed * node-template: fix random_seed * frame-support: extend docs * babe: add test for epoch starting block number tracking * babe: fix epoch randomness docs * frame: add todos for dealing with randomness api changes Co-authored-by: André Silva <andrerfosilva@gmail.com>
This commit is contained in:
committed by
GitHub
parent
f3d4355a20
commit
e2960c383e
@@ -25,7 +25,7 @@ use codec::{Decode, Encode};
|
||||
use frame_support::{
|
||||
decl_error, decl_module, decl_storage,
|
||||
dispatch::DispatchResultWithPostInfo,
|
||||
traits::{FindAuthor, Get, KeyOwnerProofSystem, OneSessionHandler, Randomness as RandomnessT},
|
||||
traits::{FindAuthor, Get, KeyOwnerProofSystem, OneSessionHandler},
|
||||
weights::{Pays, Weight},
|
||||
Parameter,
|
||||
};
|
||||
@@ -33,7 +33,7 @@ use frame_system::{ensure_none, ensure_root, ensure_signed};
|
||||
use sp_application_crypto::Public;
|
||||
use sp_runtime::{
|
||||
generic::DigestItem,
|
||||
traits::{Hash, IsMember, One, SaturatedConversion, Saturating, Zero},
|
||||
traits::{IsMember, One, SaturatedConversion, Saturating, Zero},
|
||||
ConsensusEngineId, KeyTypeId,
|
||||
};
|
||||
use sp_session::{GetSessionNumber, GetValidatorCount};
|
||||
@@ -49,8 +49,9 @@ use sp_consensus_vrf::schnorrkel;
|
||||
|
||||
pub use sp_consensus_babe::{AuthorityId, PUBLIC_KEY_LENGTH, RANDOMNESS_LENGTH, VRF_OUTPUT_LENGTH};
|
||||
|
||||
mod equivocation;
|
||||
mod default_weights;
|
||||
mod equivocation;
|
||||
mod randomness;
|
||||
|
||||
#[cfg(any(feature = "runtime-benchmarks", test))]
|
||||
mod benchmarking;
|
||||
@@ -60,6 +61,9 @@ mod mock;
|
||||
mod tests;
|
||||
|
||||
pub use equivocation::{BabeEquivocationOffence, EquivocationHandler, HandleEquivocation};
|
||||
pub use randomness::{
|
||||
CurrentBlockRandomness, RandomnessFromOneEpochAgo, RandomnessFromTwoEpochsAgo,
|
||||
};
|
||||
|
||||
pub trait Config: pallet_timestamp::Config {
|
||||
/// The amount of time, in slots, that each epoch should last.
|
||||
@@ -220,6 +224,13 @@ decl_storage! {
|
||||
/// secondary plain slots are enabled (which don't contain a VRF output).
|
||||
AuthorVrfRandomness get(fn author_vrf_randomness): MaybeRandomness;
|
||||
|
||||
/// The block numbers when the last and current epoch have started, respectively `N-1` and
|
||||
/// `N`.
|
||||
/// NOTE: We track this is in order to annotate the block number when a given pool of
|
||||
/// entropy was fixed (i.e. it was known to chain observers). Since epochs are defined in
|
||||
/// slots, which may be skipped, the block numbers may not line up with the slot numbers.
|
||||
EpochStart: (T::BlockNumber, T::BlockNumber);
|
||||
|
||||
/// How late the current block is compared to its parent.
|
||||
///
|
||||
/// This entry is populated as part of block execution and is cleaned up
|
||||
@@ -343,31 +354,6 @@ decl_module! {
|
||||
}
|
||||
}
|
||||
|
||||
impl<T: Config> RandomnessT<<T as frame_system::Config>::Hash> for Module<T> {
|
||||
/// Some BABE blocks have VRF outputs where the block producer has exactly one bit of influence,
|
||||
/// either they make the block or they do not make the block and thus someone else makes the
|
||||
/// next block. Yet, this randomness is not fresh in all BABE blocks.
|
||||
///
|
||||
/// If that is an insufficient security guarantee then two things can be used to improve this
|
||||
/// randomness:
|
||||
///
|
||||
/// - Name, in advance, the block number whose random value will be used; ensure your module
|
||||
/// retains a buffer of previous random values for its subject and then index into these in
|
||||
/// order to obviate the ability of your user to look up the parent hash and choose when to
|
||||
/// transact based upon it.
|
||||
/// - Require your user to first commit to an additional value by first posting its hash.
|
||||
/// Require them to reveal the value to determine the final result, hashing it with the
|
||||
/// output of this random function. This reduces the ability of a cabal of block producers
|
||||
/// from conspiring against individuals.
|
||||
fn random(subject: &[u8]) -> T::Hash {
|
||||
let mut subject = subject.to_vec();
|
||||
subject.reserve(VRF_OUTPUT_LENGTH);
|
||||
subject.extend_from_slice(&Self::randomness()[..]);
|
||||
|
||||
<T as frame_system::Config>::Hashing::hash(&subject[..])
|
||||
}
|
||||
}
|
||||
|
||||
/// A BABE public key
|
||||
pub type BabeKey = [u8; PUBLIC_KEY_LENGTH];
|
||||
|
||||
@@ -492,6 +478,12 @@ impl<T: Config> Module<T> {
|
||||
// Update the next epoch authorities.
|
||||
NextAuthorities::put(&next_authorities);
|
||||
|
||||
// Update the start blocks of the previous and new current epoch.
|
||||
<EpochStart<T>>::mutate(|(previous_epoch_start_block, current_epoch_start_block)| {
|
||||
*previous_epoch_start_block = sp_std::mem::take(current_epoch_start_block);
|
||||
*current_epoch_start_block = <frame_system::Module<T>>::block_number();
|
||||
});
|
||||
|
||||
// After we update the current epoch, we signal the *next* epoch change
|
||||
// so that nodes can track changes.
|
||||
let next_randomness = NextRandomness::get();
|
||||
|
||||
Reference in New Issue
Block a user