Allow for customizable recent genesis window

This commit is contained in:
Paul Hauner 2019-08-29 14:59:32 +10:00
parent 3acd75f876
commit 314780e634
No known key found for this signature in database
GPG Key ID: 5E2CFF9B75FA63DF
5 changed files with 37 additions and 10 deletions

View File

@ -22,8 +22,13 @@ pub struct BeaconChainBuilder<T: BeaconChainTypes> {
} }
impl<T: BeaconChainTypes> BeaconChainBuilder<T> { impl<T: BeaconChainTypes> BeaconChainBuilder<T> {
pub fn recent_genesis(validator_count: usize, spec: ChainSpec, log: Logger) -> Self { pub fn recent_genesis(
Self::quick_start(recent_genesis_time(), validator_count, spec, log) validator_count: usize,
minutes: u64,
spec: ChainSpec,
log: Logger,
) -> Self {
Self::quick_start(recent_genesis_time(minutes), validator_count, spec, log)
} }
pub fn quick_start( pub fn quick_start(
@ -123,12 +128,12 @@ fn genesis_block<T: EthSpec>(genesis_state: &BeaconState<T>, spec: &ChainSpec) -
/// Returns the system time, mod 30 minutes. /// Returns the system time, mod 30 minutes.
/// ///
/// Used for easily creating testnets. /// Used for easily creating testnets.
fn recent_genesis_time() -> u64 { fn recent_genesis_time(minutes: u64) -> u64 {
let now = SystemTime::now() let now = SystemTime::now()
.duration_since(SystemTime::UNIX_EPOCH) .duration_since(SystemTime::UNIX_EPOCH)
.unwrap() .unwrap()
.as_secs(); .as_secs();
let secs_after_last_period = now.checked_rem(30 * 60).unwrap_or(0); let secs_after_last_period = now.checked_rem(minutes * 60).unwrap_or(0);
// genesis is now the last 30 minute block. // genesis is now the last 15 minute block.
now - secs_after_last_period now - secs_after_last_period
} }

View File

@ -42,7 +42,10 @@ pub enum BeaconChainStartMethod {
/// Create a new beacon chain that can connect to mainnet. /// Create a new beacon chain that can connect to mainnet.
/// ///
/// Set the genesis time to be the start of the previous 30-minute window. /// Set the genesis time to be the start of the previous 30-minute window.
RecentGenesis { validator_count: usize }, RecentGenesis {
validator_count: usize,
minutes: u64,
},
/// Create a new beacon chain with `genesis_time` and `validator_count` validators, all with well-known /// Create a new beacon chain with `genesis_time` and `validator_count` validators, all with well-known
/// secret keys. /// secret keys.
Generated { Generated {

View File

@ -88,9 +88,15 @@ where
crit!(log, "No mainnet beacon chain startup specification."); crit!(log, "No mainnet beacon chain startup specification.");
return Err("Mainnet is not yet specified. We're working on it.".into()); return Err("Mainnet is not yet specified. We're working on it.".into());
} }
BeaconChainStartMethod::RecentGenesis { validator_count } => { BeaconChainStartMethod::RecentGenesis {
BeaconChainBuilder::recent_genesis(*validator_count, spec.clone(), log.clone()) validator_count,
} minutes,
} => BeaconChainBuilder::recent_genesis(
*validator_count,
*minutes,
spec.clone(),
log.clone(),
),
BeaconChainStartMethod::Generated { BeaconChainStartMethod::Generated {
validator_count, validator_count,
genesis_time, genesis_time,

View File

@ -120,8 +120,15 @@ fn process_testnet_subcommand(
.parse::<usize>() .parse::<usize>()
.map_err(|e| format!("Unable to parse validator_count: {:?}", e))?; .map_err(|e| format!("Unable to parse validator_count: {:?}", e))?;
let minutes = cli_args
.value_of("minutes")
.ok_or_else(|| "No recent genesis minutes supplied")?
.parse::<u64>()
.map_err(|e| format!("Unable to parse minutes: {:?}", e))?;
builder.set_beacon_chain_start_method(BeaconChainStartMethod::RecentGenesis { builder.set_beacon_chain_start_method(BeaconChainStartMethod::RecentGenesis {
validator_count, validator_count,
minutes,
}) })
} }
_ => return Err("No testnet method specified. See 'testnet --help'.".into()), _ => return Err("No testnet method specified. See 'testnet --help'.".into()),

View File

@ -259,11 +259,17 @@ fn main() {
*/ */
.subcommand(SubCommand::with_name("recent") .subcommand(SubCommand::with_name("recent")
.about("Creates a new genesis state where the genesis time was at the previous \ .about("Creates a new genesis state where the genesis time was at the previous \
30-minute boundary (e.g., 12:00, 12:30, 13:00, etc.)") MINUTES boundary (e.g., when MINUTES == 30; 12:00, 12:30, 13:00, etc.)")
.arg(Arg::with_name("validator_count") .arg(Arg::with_name("validator_count")
.value_name("VALIDATOR_COUNT") .value_name("VALIDATOR_COUNT")
.required(true) .required(true)
.help("The number of validators in the genesis state")) .help("The number of validators in the genesis state"))
.arg(Arg::with_name("minutes")
.short("m")
.value_name("MINUTES")
.required(true)
.default_value("15")
.help("The maximum number of minutes that will have elapsed before genesis"))
) )
.subcommand(SubCommand::with_name("yaml-genesis-state") .subcommand(SubCommand::with_name("yaml-genesis-state")
.about("Creates a new datadir where the genesis state is read from YAML. Will fail to parse \ .about("Creates a new datadir where the genesis state is read from YAML. Will fail to parse \