Skip to content

Commit

Permalink
refactor: remove block vrf verification from epoch manager (#12447)
Browse files Browse the repository at this point in the history
Removes block vrf verification from epoch manager

---------

Co-authored-by: Anton Puhach <[email protected]>
  • Loading branch information
stedfn and pugachAG authored Dec 9, 2024
1 parent 28cc977 commit fd24348
Show file tree
Hide file tree
Showing 4 changed files with 49 additions and 52 deletions.
14 changes: 6 additions & 8 deletions chain/chain/src/chain.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,9 @@ use crate::rayon_spawner::RayonAsyncComputationSpawner;
use crate::resharding::manager::ReshardingManager;
use crate::resharding::types::ReshardingSender;
use crate::sharding::shuffle_receipt_proofs;
use crate::signature_verification::verify_chunk_header_signature_with_epoch_manager;
use crate::signature_verification::{
verify_block_vrf, verify_chunk_header_signature_with_epoch_manager,
};
use crate::state_request_tracker::StateRequestTracker;
use crate::state_snapshot_actor::SnapshotCallbacks;
use crate::stateless_validation::chunk_endorsement::{
Expand Down Expand Up @@ -2284,13 +2286,9 @@ impl Chain {
// Check the header is valid before we proceed with the full block.
self.validate_header(header, provenance, challenges)?;

self.epoch_manager.verify_block_vrf(
header.epoch_id(),
header.height(),
&prev_random_value,
block.vrf_value(),
block.vrf_proof(),
)?;
let validator =
self.epoch_manager.get_block_producer_info(header.epoch_id(), header.height())?;
verify_block_vrf(validator, &prev_random_value, block.vrf_value(), block.vrf_proof())?;

if header.random_value() != &hash(block.vrf_value().0.as_ref()) {
return Err(Error::InvalidRandomnessBeaconOutput);
Expand Down
18 changes: 17 additions & 1 deletion chain/chain/src/signature_verification.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,25 @@ use near_primitives::{
hash::CryptoHash,
sharding::{ChunkHash, ShardChunkHeader},
stateless_validation::ChunkProductionKey,
types::{BlockHeight, EpochId, ShardId},
types::{validator_stake::ValidatorStake, BlockHeight, EpochId, ShardId},
};

pub fn verify_block_vrf(
validator: ValidatorStake,
prev_random_value: &CryptoHash,
vrf_value: &near_crypto::vrf::Value,
vrf_proof: &near_crypto::vrf::Proof,
) -> Result<(), Error> {
let public_key =
near_crypto::key_conversion::convert_public_key(validator.public_key().unwrap_as_ed25519())
.unwrap();

if !public_key.is_vrf_valid(&prev_random_value.as_ref(), vrf_value, vrf_proof) {
return Err(Error::InvalidRandomnessBeaconOutput);
}
Ok(())
}

/// Verify chunk header signature.
/// return false if the header signature does not match the key for the assigned chunk producer
/// for this chunk, or if the chunk producer has been slashed
Expand Down
21 changes: 9 additions & 12 deletions chain/chain/src/test_utils/kv_runtime.rs
Original file line number Diff line number Diff line change
Expand Up @@ -777,8 +777,16 @@ impl EpochManagerAdapter for MockEpochManager {
epoch_id: &EpochId,
height: BlockHeight,
) -> Result<AccountId, EpochError> {
self.get_block_producer_info(epoch_id, height).map(|validator| validator.take_account_id())
}

fn get_block_producer_info(
&self,
epoch_id: &EpochId,
height: BlockHeight,
) -> Result<ValidatorStake, EpochError> {
let validators = self.get_block_producers(self.get_valset_for_epoch(epoch_id)?);
Ok(validators[(height as usize) % validators.len()].account_id().clone())
Ok(validators[(height as usize) % validators.len()].clone())
}

fn get_chunk_producer_info(
Expand Down Expand Up @@ -888,17 +896,6 @@ impl EpochManagerAdapter for MockEpochManager {
false
}

fn verify_block_vrf(
&self,
_epoch_id: &EpochId,
_block_height: BlockHeight,
_prev_random_value: &CryptoHash,
_vrf_value: &near_crypto::vrf::Value,
_vrf_proof: &near_crypto::vrf::Proof,
) -> Result<(), Error> {
Ok(())
}

fn verify_validator_signature(
&self,
_epoch_id: &EpochId,
Expand Down
48 changes: 17 additions & 31 deletions chain/epoch-manager/src/adapter.rs
Original file line number Diff line number Diff line change
Expand Up @@ -233,12 +233,20 @@ pub trait EpochManagerAdapter: Send + Sync {
) -> Result<Vec<ValidatorStake>, EpochError>;

/// Block producers for given height for the main block. Return EpochError if outside of known boundaries.
/// TODO: Deprecate in favour of get_block_producer_info
fn get_block_producer(
&self,
epoch_id: &EpochId,
height: BlockHeight,
) -> Result<AccountId, EpochError>;

/// Block producers and stake for given height for the main block. Return EpochError if outside of known boundaries.
fn get_block_producer_info(
&self,
epoch_id: &EpochId,
height: BlockHeight,
) -> Result<ValidatorStake, EpochError>;

/// Chunk producer info for given height for given shard. Return EpochError if outside of known boundaries.
fn get_chunk_producer_info(
&self,
Expand Down Expand Up @@ -331,15 +339,6 @@ pub trait EpochManagerAdapter: Send + Sync {
true
}

fn verify_block_vrf(
&self,
epoch_id: &EpochId,
block_height: BlockHeight,
prev_random_value: &CryptoHash,
vrf_value: &near_crypto::vrf::Value,
vrf_proof: &near_crypto::vrf::Proof,
) -> Result<(), Error>;

/// Verify validator signature for the given epoch.
/// Note: doesn't account for slashed accounts within given epoch. USE WITH CAUTION.
fn verify_validator_signature(
Expand Down Expand Up @@ -760,8 +759,16 @@ impl EpochManagerAdapter for EpochManagerHandle {
epoch_id: &EpochId,
height: BlockHeight,
) -> Result<AccountId, EpochError> {
self.get_block_producer_info(epoch_id, height).map(|validator| validator.take_account_id())
}

fn get_block_producer_info(
&self,
epoch_id: &EpochId,
height: BlockHeight,
) -> Result<ValidatorStake, EpochError> {
let epoch_manager = self.read();
Ok(epoch_manager.get_block_producer_info(epoch_id, height)?.take_account_id())
Ok(epoch_manager.get_block_producer_info(epoch_id, height)?)
}

fn get_chunk_producer_info(
Expand Down Expand Up @@ -860,27 +867,6 @@ impl EpochManagerAdapter for EpochManagerHandle {
)
}

fn verify_block_vrf(
&self,
epoch_id: &EpochId,
block_height: BlockHeight,
prev_random_value: &CryptoHash,
vrf_value: &near_crypto::vrf::Value,
vrf_proof: &near_crypto::vrf::Proof,
) -> Result<(), Error> {
let epoch_manager = self.read();
let validator = epoch_manager.get_block_producer_info(epoch_id, block_height)?;
let public_key = near_crypto::key_conversion::convert_public_key(
validator.public_key().unwrap_as_ed25519(),
)
.unwrap();

if !public_key.is_vrf_valid(&prev_random_value.as_ref(), vrf_value, vrf_proof) {
return Err(Error::InvalidRandomnessBeaconOutput);
}
Ok(())
}

fn verify_validator_signature(
&self,
epoch_id: &EpochId,
Expand Down

0 comments on commit fd24348

Please sign in to comment.