Draft in new 2.1 objects
This commit is contained in:
parent
fd775e3252
commit
123c6d7088
@ -1,121 +1,31 @@
|
||||
use super::partial_crosslink_record::PartialCrosslinkRecord;
|
||||
use super::recent_proposer_record::RecentPropserRecord;
|
||||
use super::rlp::{ RlpStream, Encodable };
|
||||
use super::rlp::encode as rlp_encode;
|
||||
use super::blake2::{ Blake2s, Digest };
|
||||
use super::utils::types::*;
|
||||
use super::utils::types::Hash256;
|
||||
use super::attestation_record::AttestationRecord;
|
||||
|
||||
#[derive(Clone)]
|
||||
pub struct ActiveState {
|
||||
pub height: u64,
|
||||
pub randao: Sha256Digest,
|
||||
pub ffg_voter_bitfield: Bitfield,
|
||||
pub recent_attesters: Vec<usize>, // TODO: should be u24
|
||||
pub partial_crosslinks: Vec<PartialCrosslinkRecord>,
|
||||
pub total_skip_count: u64,
|
||||
pub recent_proposers: Vec<RecentPropserRecord>
|
||||
pub pending_attestations: Vec<AttestationRecord>,
|
||||
pub recent_block_hashes: Vec<Hash256>,
|
||||
}
|
||||
|
||||
impl ActiveState {
|
||||
/// Returns a new instance where all fields are empty vectors.
|
||||
pub fn zero() -> Self {
|
||||
Self {
|
||||
height: 0,
|
||||
randao: Sha256Digest::zero(),
|
||||
ffg_voter_bitfield: Bitfield::new(),
|
||||
recent_attesters: Vec::new(),
|
||||
partial_crosslinks: Vec::new(),
|
||||
total_skip_count: 0,
|
||||
recent_proposers: Vec::new()
|
||||
pending_attestations: vec![],
|
||||
recent_block_hashes: vec![],
|
||||
}
|
||||
}
|
||||
|
||||
pub fn num_recent_proposers(&self) -> usize {
|
||||
self.recent_proposers.len()
|
||||
}
|
||||
|
||||
pub fn num_recent_attesters(&self) -> usize {
|
||||
self.recent_attesters.len()
|
||||
}
|
||||
|
||||
pub fn blake2s_hash(&self) -> Blake2sDigest {
|
||||
let mut hasher = Blake2s::new();
|
||||
hasher.input(&rlp_encode(self).into_vec());
|
||||
let mut digest = Blake2sDigest::new();
|
||||
digest.clone_from_slice(hasher.result().as_slice());
|
||||
digest
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* RLP Encoding
|
||||
*/
|
||||
impl Encodable for ActiveState {
|
||||
fn rlp_append(&self, s: &mut RlpStream) {
|
||||
s.append(&self.height);
|
||||
s.append(&self.randao);
|
||||
s.append(&self.ffg_voter_bitfield);
|
||||
s.append_list(&self.recent_attesters);
|
||||
s.append_list(&self.partial_crosslinks);
|
||||
s.append(&self.total_skip_count);
|
||||
s.append_list(&self.recent_proposers);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::super::rlp;
|
||||
use super::*;
|
||||
|
||||
#[test]
|
||||
fn test_zero_fn() {
|
||||
fn test_act_state_zero() {
|
||||
let a = ActiveState::zero();
|
||||
assert_eq!(a.height, 0);
|
||||
// TODO: test all the things
|
||||
assert_eq!(a.total_skip_count, 0);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_num_recent_proposers() {
|
||||
let mut a = ActiveState::zero();
|
||||
for _ in 1..5 {
|
||||
a.recent_proposers.push(RecentPropserRecord::new(
|
||||
1,
|
||||
Sha256Digest::random(),
|
||||
2));
|
||||
}
|
||||
assert_eq!(a.num_recent_proposers(), 4)
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_num_recent_attesters() {
|
||||
let mut a = ActiveState::zero();
|
||||
for _ in 1..5 {
|
||||
a.recent_attesters.push(1);
|
||||
}
|
||||
assert_eq!(a.num_recent_attesters(), 4)
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_rlp_serialization() {
|
||||
let a = ActiveState {
|
||||
height: 100,
|
||||
randao: Sha256Digest::zero(),
|
||||
ffg_voter_bitfield: Bitfield::new(),
|
||||
recent_attesters: Vec::new(),
|
||||
partial_crosslinks: Vec::new(),
|
||||
total_skip_count: 99,
|
||||
recent_proposers: Vec::new()
|
||||
};
|
||||
let e = rlp::encode(&a);
|
||||
assert_eq!(e.len(), 39);
|
||||
assert_eq!(e[0], 100);
|
||||
assert_eq!(e[1], 160);
|
||||
assert_eq!(e[2..34], [0; 32]);
|
||||
assert_eq!(e[34], 128);
|
||||
assert_eq!(e[35], 192);
|
||||
assert_eq!(e[36], 192);
|
||||
assert_eq!(e[37], 99);
|
||||
assert_eq!(e[38], 192);
|
||||
assert_eq!(a.pending_attestations.len(), 0);
|
||||
assert_eq!(a.recent_block_hashes.len(), 0);
|
||||
}
|
||||
}
|
||||
|
26
src/state/attestation_record.rs
Normal file
26
src/state/attestation_record.rs
Normal file
@ -0,0 +1,26 @@
|
||||
use super::utils::types::{ Hash256, Bitfield };
|
||||
use super::utils::bls::{ AggregateSignature };
|
||||
|
||||
|
||||
#[derive(Clone)]
|
||||
pub struct AttestationRecord {
|
||||
slot: u64,
|
||||
shard_id: u16,
|
||||
oblique_parent_hashes: Vec<Hash256>,
|
||||
shard_block_hash: Hash256,
|
||||
attester_bitfield: Bitfield,
|
||||
aggregate_sig: Option<AggregateSignature>,
|
||||
}
|
||||
|
||||
impl AttestationRecord {
|
||||
pub fn zero() -> Self {
|
||||
Self {
|
||||
slot: 0,
|
||||
shard_id: 0,
|
||||
oblique_parent_hashes: vec![],
|
||||
shard_block_hash: Hash256::zero(),
|
||||
attester_bitfield: Bitfield::new(),
|
||||
aggregate_sig: None,
|
||||
}
|
||||
}
|
||||
}
|
@ -1,114 +1,56 @@
|
||||
use super::utils::types::{ Sha256Digest, Bitfield, StateHash };
|
||||
use super::utils::types::Hash256;
|
||||
use super::utils::bls::{ Signature, AggregateSignature, Keypair, PublicKey };
|
||||
use super::aggregate_vote::AggregateVote;
|
||||
use super::rlp::{ RlpStream, Encodable } ;
|
||||
use super::attestation_record::AttestationRecord;
|
||||
use super::ssz;
|
||||
|
||||
use std::hash::{ Hash, Hasher };
|
||||
|
||||
const SSZ_BLOCK_LENGTH: usize = 192;
|
||||
|
||||
pub struct Block {
|
||||
pub parent_hash: Sha256Digest,
|
||||
pub skip_count: u64,
|
||||
pub randao_reveal: Sha256Digest,
|
||||
pub attestation_bitfield: Bitfield,
|
||||
pub attestation_aggregate_sig: AggregateSignature,
|
||||
pub shard_aggregate_votes: Vec<AggregateVote>,
|
||||
pub main_chain_ref: Sha256Digest,
|
||||
pub state_hash: StateHash,
|
||||
pub sig: Option<Signature>
|
||||
pub parent_hash: Hash256,
|
||||
pub slot_number: u64,
|
||||
pub randao_reveal: Hash256,
|
||||
pub attestations: Vec<AttestationRecord>,
|
||||
pub pow_chain_ref: Hash256,
|
||||
pub active_state_root: Hash256,
|
||||
pub crystallized_state_root: Hash256,
|
||||
}
|
||||
|
||||
impl Block {
|
||||
pub fn new(parent_hash: Sha256Digest,
|
||||
randao_reveal: Sha256Digest,
|
||||
main_chain_ref: Sha256Digest,
|
||||
state_hash: StateHash) -> Block {
|
||||
Block {
|
||||
parent_hash: parent_hash,
|
||||
skip_count: 0,
|
||||
randao_reveal: randao_reveal,
|
||||
attestation_bitfield: Bitfield::new(),
|
||||
attestation_aggregate_sig: AggregateSignature::new(),
|
||||
shard_aggregate_votes: Vec::new(),
|
||||
main_chain_ref: main_chain_ref,
|
||||
state_hash: state_hash,
|
||||
sig: None
|
||||
}
|
||||
}
|
||||
|
||||
pub fn zero() -> Block {
|
||||
Block {
|
||||
parent_hash: Sha256Digest::zero(),
|
||||
skip_count: 0,
|
||||
randao_reveal: Sha256Digest::zero(),
|
||||
attestation_bitfield: Bitfield::new(),
|
||||
attestation_aggregate_sig: AggregateSignature::new(),
|
||||
shard_aggregate_votes: vec![],
|
||||
main_chain_ref: Sha256Digest::zero(),
|
||||
state_hash: StateHash::zero(),
|
||||
sig: None
|
||||
pub fn zero() -> Self {
|
||||
Self {
|
||||
parent_hash: Hash256::zero(),
|
||||
slot_number: 0,
|
||||
randao_reveal: Hash256::zero(),
|
||||
attestations: vec![],
|
||||
pow_chain_ref: Hash256::zero(),
|
||||
active_state_root: Hash256::zero(),
|
||||
crystallized_state_root: Hash256::zero(),
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Take a Block and covert it into an array of u8 for BLS signing
|
||||
* or verfication. The `sig` field is purposefully omitted.
|
||||
*/
|
||||
pub fn encode_to_signable_message(&self) -> [u8; 9140] {
|
||||
// Using biggest avg. block size from v2 spec
|
||||
let mut message: [u8; 9140] = [0; 9140];
|
||||
|
||||
// Create the RLP vector
|
||||
let mut s = RlpStream::new();
|
||||
/// Returns a Vec<u8>
|
||||
pub fn ssz_encode_without_attestations(&self)
|
||||
-> [u8; SSZ_BLOCK_LENGTH]
|
||||
{
|
||||
let mut s = ssz::SszStream::new();
|
||||
s.append(&self.parent_hash);
|
||||
s.append(&self.skip_count);
|
||||
s.append(&self.slot_number);
|
||||
s.append(&self.randao_reveal);
|
||||
s.append(&self.attestation_bitfield);
|
||||
// s.append(&self.attestation_aggregate_sig); // TODO: RLP this
|
||||
s.append_list(&self.shard_aggregate_votes);
|
||||
s.append(&self.main_chain_ref);
|
||||
// TODO: state hash serialization is probably incorrect.
|
||||
s.append(&self.state_hash.crystallized_state);
|
||||
s.append(&self.state_hash.active_state);
|
||||
let rlp_vec = s.out();
|
||||
|
||||
// Parse the RLP vector into an array compatible with the BLS signer
|
||||
let len = rlp_vec.len();
|
||||
message[..len].copy_from_slice(&rlp_vec[..len]);
|
||||
message
|
||||
}
|
||||
|
||||
/*
|
||||
* Sign the block with the given keypair.
|
||||
*/
|
||||
pub fn sig_sign(&mut self, keypair: &Keypair) {
|
||||
let message = self.encode_to_signable_message();
|
||||
self.sig = Some(keypair.sign(&message));
|
||||
}
|
||||
|
||||
/*
|
||||
* Verify a block signature given some keypair.
|
||||
*/
|
||||
pub fn sig_verify(&self, pub_key: &PublicKey) -> bool {
|
||||
let message = self.encode_to_signable_message();
|
||||
match &self.sig {
|
||||
None => false,
|
||||
Some(sig) => {
|
||||
pub_key.verify(&message, &sig)
|
||||
},
|
||||
}
|
||||
s.append(&self.pow_chain_ref);
|
||||
s.append(&self.active_state_root);
|
||||
s.append(&self.crystallized_state_root);
|
||||
let vec = s.drain();
|
||||
let mut encoded = [0; SSZ_BLOCK_LENGTH];
|
||||
encoded.copy_from_slice(&vec); encoded
|
||||
}
|
||||
}
|
||||
|
||||
impl Encodable for Block {
|
||||
fn rlp_append(&self, s: &mut RlpStream) {
|
||||
s.append(&self.parent_hash);
|
||||
s.append(&self.skip_count);
|
||||
s.append(&self.randao_reveal);
|
||||
s.append(&self.attestation_bitfield);
|
||||
// s.append(&self.attestation_aggregate_sig); // TODO: RLP this
|
||||
s.append_list(&self.shard_aggregate_votes);
|
||||
s.append(&self.main_chain_ref);
|
||||
// TODO: state hash serialization is probably incorrect.
|
||||
s.append(&self.state_hash.crystallized_state);
|
||||
s.append(&self.state_hash.active_state);
|
||||
// s.append(&self.sig); // TODO: RLP this
|
||||
impl Hash for Block {
|
||||
fn hash<H: Hasher>(&self, state: &mut H) {
|
||||
let bytes = self.ssz_encode_without_attestations();
|
||||
bytes.hash(state);
|
||||
}
|
||||
}
|
||||
|
||||
@ -161,7 +103,7 @@ mod tests {
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_rlp_serialization() {
|
||||
fn test_ssz_serialization() {
|
||||
let b = Block {
|
||||
parent_hash: Sha256Digest::zero(),
|
||||
skip_count: 100,
|
||||
|
@ -1,59 +1,30 @@
|
||||
use super::utils::types::Sha256Digest;
|
||||
use super::rlp::{ RlpStream, Encodable };
|
||||
use super::utils::types::Hash256;
|
||||
|
||||
#[derive(Copy)]
|
||||
#[derive(Clone)]
|
||||
pub struct CrosslinkRecord {
|
||||
pub epoch: u64,
|
||||
pub hash: Sha256Digest
|
||||
pub dynasty: u64,
|
||||
pub hash: Hash256,
|
||||
}
|
||||
|
||||
impl CrosslinkRecord {
|
||||
pub fn new(epoch: u64, hash: Sha256Digest) -> CrosslinkRecord {
|
||||
CrosslinkRecord {
|
||||
epoch: epoch,
|
||||
hash: hash
|
||||
/// Generates a new instance where `dynasty` and `hash` are both zero.
|
||||
pub fn zero() -> Self {
|
||||
Self {
|
||||
dynasty: 0,
|
||||
hash: Hash256::zero(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Clone for CrosslinkRecord {
|
||||
fn clone(&self) -> CrosslinkRecord { *self }
|
||||
}
|
||||
|
||||
/*
|
||||
* RLP Encoding
|
||||
*/
|
||||
impl Encodable for CrosslinkRecord {
|
||||
fn rlp_append(&self, s: &mut RlpStream) {
|
||||
s.append(&self.epoch);
|
||||
s.append(&self.hash);
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::super::rlp;
|
||||
use super::*;
|
||||
|
||||
#[test]
|
||||
fn test_new() {
|
||||
let epoch = 1;
|
||||
let hash = Sha256Digest::random();
|
||||
let c = CrosslinkRecord::new(epoch, hash);
|
||||
assert_eq!(c.epoch, epoch);
|
||||
assert_eq!(c.hash, hash);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_rlp_serialization() {
|
||||
let c = CrosslinkRecord {
|
||||
epoch: 100,
|
||||
hash: Sha256Digest::zero()
|
||||
};
|
||||
let e = rlp::encode(&c);
|
||||
assert_eq!(e.len(), 34);
|
||||
assert_eq!(e[0], 100);
|
||||
assert_eq!(e[1], 160);
|
||||
assert_eq!(e[2..34], [0; 32]);
|
||||
fn test_crosslink_record_zero() {
|
||||
let c = CrosslinkRecord::zero();
|
||||
assert_eq!(c.dynasty, 0);
|
||||
assert!(c.hash.is_zero());
|
||||
}
|
||||
}
|
||||
|
@ -1,129 +1,66 @@
|
||||
use super::utils::types::{ Sha256Digest, Blake2sDigest };
|
||||
use super::validator_record::ValidatorRecord;
|
||||
use super::crosslink_record::CrosslinkRecord;
|
||||
use super::rlp::{ RlpStream, Encodable };
|
||||
use super::rlp::encode as rlp_encode;
|
||||
use super::shard_and_committee::ShardAndCommittee;
|
||||
use super::ethereum_types::U256;
|
||||
use super::blake2::{ Blake2s, Digest };
|
||||
use super::utils::types::{ Hash256 };
|
||||
|
||||
|
||||
#[derive(Clone)]
|
||||
pub struct CrystallizedState {
|
||||
pub active_validators: Vec<ValidatorRecord>,
|
||||
pub queued_validators: Vec<ValidatorRecord>,
|
||||
pub exited_validators: Vec<ValidatorRecord>,
|
||||
pub current_shuffling: Vec<usize>, // TODO: should be u24
|
||||
pub current_epoch: u64,
|
||||
pub last_justified_epoch: u64,
|
||||
pub last_finalized_epoch: u64,
|
||||
pub dynasty: u64,
|
||||
pub next_shard: u16,
|
||||
pub current_checkpoint: Sha256Digest,
|
||||
pub validators: Vec<ValidatorRecord>,
|
||||
pub epoch_number: u64,
|
||||
pub indicies_for_heights: Vec<ShardAndCommittee>,
|
||||
pub last_justified_slot: u64,
|
||||
pub justified_streak: u16,
|
||||
pub last_finalized_slot: u64,
|
||||
pub current_dynasty: u64,
|
||||
pub crosslinking_shard_start: u16,
|
||||
pub crosslink_records: Vec<CrosslinkRecord>,
|
||||
pub total_deposits: U256,
|
||||
pub dynasty_seed: Hash256,
|
||||
pub dynasty_seed_last_reset: u64,
|
||||
}
|
||||
|
||||
impl CrystallizedState {
|
||||
// Returns a new instance with all values set to zero.
|
||||
/// Returns a new instance where all fields are either zero or an
|
||||
/// empty vector.
|
||||
pub fn zero() -> Self {
|
||||
Self {
|
||||
active_validators: Vec::new(),
|
||||
queued_validators: Vec::new(),
|
||||
exited_validators: Vec::new(),
|
||||
current_shuffling: Vec::new(),
|
||||
current_epoch: 0,
|
||||
last_justified_epoch: 0,
|
||||
last_finalized_epoch: 0,
|
||||
dynasty: 0,
|
||||
next_shard: 0,
|
||||
current_checkpoint: Sha256Digest::zero(),
|
||||
crosslink_records: Vec::new(),
|
||||
validators: vec![],
|
||||
epoch_number: 0,
|
||||
indicies_for_heights: vec![],
|
||||
last_justified_slot: 0,
|
||||
justified_streak: 0,
|
||||
last_finalized_slot: 0,
|
||||
current_dynasty: 0,
|
||||
crosslinking_shard_start: 0,
|
||||
crosslink_records: vec![],
|
||||
total_deposits: U256::zero(),
|
||||
dynasty_seed: Hash256::zero(),
|
||||
dynasty_seed_last_reset: 0,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn finality_distance(&self) -> u64 {
|
||||
assert!(self.current_epoch >= self.last_finalized_epoch);
|
||||
self.current_epoch - self.last_finalized_epoch
|
||||
}
|
||||
|
||||
pub fn num_active_validators(&self) -> usize {
|
||||
self.active_validators.len()
|
||||
}
|
||||
|
||||
pub fn num_queued_validators(&self) -> usize {
|
||||
self.queued_validators.len()
|
||||
}
|
||||
|
||||
pub fn num_exited_validators(&self) -> usize {
|
||||
self.exited_validators.len()
|
||||
}
|
||||
|
||||
pub fn num_crosslink_records(&self) -> usize {
|
||||
self.crosslink_records.len()
|
||||
|
||||
}
|
||||
|
||||
pub fn blake2s_hash(&self) -> Blake2sDigest {
|
||||
let mut hasher = Blake2s::new();
|
||||
hasher.input(&rlp_encode(self).into_vec());
|
||||
let mut digest = Blake2sDigest::new();
|
||||
digest.clone_from_slice(hasher.result().as_slice());
|
||||
digest
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* RLP Encoding
|
||||
*/
|
||||
impl Encodable for CrystallizedState {
|
||||
fn rlp_append(&self, s: &mut RlpStream) {
|
||||
s.append_list(&self.active_validators);
|
||||
s.append_list(&self.queued_validators);
|
||||
s.append_list(&self.exited_validators);
|
||||
s.append_list(&self.current_shuffling);
|
||||
s.append(&self.current_epoch);
|
||||
s.append(&self.last_justified_epoch);
|
||||
s.append(&self.last_finalized_epoch);
|
||||
s.append(&self.dynasty);
|
||||
s.append(&self.next_shard);
|
||||
s.append(&self.current_checkpoint);
|
||||
s.append_list(&self.crosslink_records);
|
||||
s.append(&self.total_deposits);
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::super::rlp;
|
||||
use super::*;
|
||||
|
||||
#[test]
|
||||
fn test_rlp_serialization() {
|
||||
let a = CrystallizedState {
|
||||
active_validators: Vec::new(),
|
||||
queued_validators: Vec::new(),
|
||||
exited_validators: Vec::new(),
|
||||
current_shuffling: Vec::new(),
|
||||
current_epoch: 10,
|
||||
last_justified_epoch: 8,
|
||||
last_finalized_epoch: 2,
|
||||
dynasty: 3,
|
||||
next_shard: 12,
|
||||
current_checkpoint: Sha256Digest::zero(),
|
||||
crosslink_records: Vec::new(),
|
||||
total_deposits: U256::zero(),
|
||||
};
|
||||
let e = rlp::encode(&a);
|
||||
assert_eq!(e.len(), 44);
|
||||
assert_eq!(e[0..4], [192; 4]);
|
||||
assert_eq!(e[4], 10);
|
||||
assert_eq!(e[5], 8);
|
||||
assert_eq!(e[6], 2);
|
||||
assert_eq!(e[7], 3);
|
||||
assert_eq!(e[8], 12);
|
||||
assert_eq!(e[9], 160);
|
||||
assert_eq!(e[10..42], [0; 32]);
|
||||
assert_eq!(e[42], 192);
|
||||
assert_eq!(e[43], 128);
|
||||
fn test_cry_state_zero() {
|
||||
let c = CrystallizedState::zero();
|
||||
assert_eq!(c.validators.len(), 0);
|
||||
assert_eq!(c.epoch_number, 0);
|
||||
assert_eq!(c.indicies_for_heights.len(), 0);
|
||||
assert_eq!(c.last_justified_slot, 0);
|
||||
assert_eq!(c.justified_streak, 0);
|
||||
assert_eq!(c.last_finalized_slot, 0);
|
||||
assert_eq!(c.current_dynasty, 0);
|
||||
assert_eq!(c.crosslinking_shard_start, 0);
|
||||
assert_eq!(c.crosslink_records.len(), 0);
|
||||
assert!(c.total_deposits.is_zero());
|
||||
assert!(c.dynasty_seed.is_zero());
|
||||
assert_eq!(c.dynasty_seed_last_reset, 0);
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -2,17 +2,20 @@ extern crate rlp;
|
||||
extern crate ethereum_types;
|
||||
extern crate blake2;
|
||||
extern crate bytes;
|
||||
extern crate ssz;
|
||||
|
||||
use super::utils;
|
||||
use super::pubkeystore;
|
||||
// use super::pubkeystore;
|
||||
|
||||
pub mod active_state;
|
||||
pub mod attestation_record;
|
||||
pub mod crystallized_state;
|
||||
pub mod config;
|
||||
pub mod aggregate_vote;
|
||||
// pub mod aggregate_vote;
|
||||
pub mod block;
|
||||
pub mod crosslink_record;
|
||||
pub mod partial_crosslink_record;
|
||||
pub mod recent_proposer_record;
|
||||
pub mod transition;
|
||||
// pub mod partial_crosslink_record;
|
||||
// pub mod recent_proposer_record;
|
||||
// pub mod transition;
|
||||
pub mod shard_and_committee;
|
||||
pub mod validator_record;
|
||||
|
28
src/state/shard_and_committee.rs
Normal file
28
src/state/shard_and_committee.rs
Normal file
@ -0,0 +1,28 @@
|
||||
#[derive(Clone)]
|
||||
pub struct ShardAndCommittee {
|
||||
shard_id: u16,
|
||||
committee: Vec<u32>
|
||||
}
|
||||
|
||||
impl ShardAndCommittee {
|
||||
/// Returns a new instance where the `shard_id` is zero and the
|
||||
/// committee is an empty vector.
|
||||
pub fn zero() -> Self {
|
||||
Self {
|
||||
shard_id: 0,
|
||||
committee: vec![],
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
|
||||
#[test]
|
||||
fn test_shard_and_committee_zero() {
|
||||
let s = CrystallizedState::zero();
|
||||
assert_eq!(s.shard_id, 0);
|
||||
assert_eq!(s.committee.len(), 0);
|
||||
}
|
||||
}
|
@ -1,8 +1,7 @@
|
||||
extern crate rand;
|
||||
|
||||
use super::utils::types::{ Sha256Digest, Address, U256 };
|
||||
use super::utils::types::{ Hash256, Address, U256 };
|
||||
use super::utils::bls::{ PublicKey, Keypair };
|
||||
use super::rlp::{ RlpStream, Encodable };
|
||||
|
||||
use self::rand::thread_rng;
|
||||
|
||||
@ -10,43 +9,17 @@ pub struct ValidatorRecord {
|
||||
pub pubkey: PublicKey,
|
||||
pub withdrawal_shard: u16,
|
||||
pub withdrawal_address: Address,
|
||||
pub randao_commitment: Sha256Digest,
|
||||
pub randao_commitment: Hash256,
|
||||
pub balance: U256,
|
||||
pub switch_dynasty: u64
|
||||
pub start_dynasty: u64,
|
||||
pub end_dynasty: u64,
|
||||
}
|
||||
|
||||
impl ValidatorRecord {
|
||||
pub fn new(pubkey: PublicKey,
|
||||
withdrawal_shard: u16,
|
||||
withdrawal_address: Address,
|
||||
randao_commitment: Sha256Digest,
|
||||
balance: U256,
|
||||
switch_dynasty: u64)
|
||||
-> Self
|
||||
{
|
||||
Self {
|
||||
pubkey,
|
||||
withdrawal_shard,
|
||||
withdrawal_address,
|
||||
randao_commitment,
|
||||
balance,
|
||||
switch_dynasty
|
||||
}
|
||||
}
|
||||
|
||||
pub fn zero_with_thread_rand_pub_key() -> Self {
|
||||
let mut rng = thread_rng();
|
||||
let keypair = Keypair::generate(&mut rng);
|
||||
Self {
|
||||
pubkey: keypair.public,
|
||||
withdrawal_shard: 0,
|
||||
withdrawal_address: Address::zero(),
|
||||
randao_commitment: Sha256Digest::zero(),
|
||||
balance: U256::zero(),
|
||||
switch_dynasty: 0
|
||||
}
|
||||
}
|
||||
|
||||
/// Generates a new instance where the keypair is generated using
|
||||
/// `rand::thread_rng` entropy and all other fields are set to zero.
|
||||
///
|
||||
/// Returns the new instance and new keypair.
|
||||
pub fn zero_with_thread_rand_keypair() -> (Self, Keypair) {
|
||||
let mut rng = thread_rng();
|
||||
let keypair = Keypair::generate(&mut rng);
|
||||
@ -54,9 +27,10 @@ impl ValidatorRecord {
|
||||
pubkey: keypair.public.clone(),
|
||||
withdrawal_shard: 0,
|
||||
withdrawal_address: Address::zero(),
|
||||
randao_commitment: Sha256Digest::zero(),
|
||||
randao_commitment: Hash256::zero(),
|
||||
balance: U256::zero(),
|
||||
switch_dynasty: 0
|
||||
start_dynasty: 0,
|
||||
end_dynasty: 0,
|
||||
};
|
||||
(s, keypair)
|
||||
}
|
||||
@ -72,20 +46,6 @@ impl Clone for ValidatorRecord {
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* RLP Encoding
|
||||
*/
|
||||
impl Encodable for ValidatorRecord {
|
||||
fn rlp_append(&self, s: &mut RlpStream) {
|
||||
// s.append(&self.pubkey); // TODO: serialize this
|
||||
s.append(&self.withdrawal_shard);
|
||||
s.append(&self.withdrawal_address);
|
||||
s.append(&self.randao_commitment);
|
||||
s.append(&self.balance);
|
||||
s.append(&self.switch_dynasty);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
@ -97,50 +57,14 @@ mod tests {
|
||||
utils::test_helpers::get_dangerous_test_keypair;
|
||||
|
||||
#[test]
|
||||
fn test_new() {
|
||||
let keypair = get_dangerous_test_keypair();;
|
||||
let withdrawal_shard = 1;
|
||||
let withdrawal_address = Address::random();
|
||||
let randao_commitment = Sha256Digest::random();
|
||||
let balance = U256::from(100);
|
||||
let switch_dynasty = 10;
|
||||
|
||||
let v = ValidatorRecord::new(
|
||||
keypair.public,
|
||||
withdrawal_shard,
|
||||
withdrawal_address,
|
||||
randao_commitment,
|
||||
balance,
|
||||
switch_dynasty);
|
||||
// TODO: figure out how to compare keys
|
||||
// assert_eq!(v.pubkey, keypair.public);
|
||||
assert_eq!(v.withdrawal_shard, withdrawal_shard);
|
||||
assert_eq!(v.withdrawal_address, withdrawal_address);
|
||||
assert_eq!(v.randao_commitment, randao_commitment);
|
||||
assert_eq!(v.balance, balance);
|
||||
assert_eq!(v.switch_dynasty, switch_dynasty);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_rlp_serialization() {
|
||||
let keypair = get_dangerous_test_keypair();
|
||||
let v = ValidatorRecord {
|
||||
pubkey: keypair.public,
|
||||
withdrawal_shard: 100,
|
||||
withdrawal_address: Address::zero(),
|
||||
randao_commitment: Sha256Digest::zero(),
|
||||
balance: U256::from(120),
|
||||
switch_dynasty: 30
|
||||
};
|
||||
let e = rlp::encode(&v);
|
||||
assert_eq!(e.len(), 57); // TODO: fix when pubkey is serialized
|
||||
// TODO: test for serialized pubkey
|
||||
assert_eq!(e[0], 100);
|
||||
assert_eq!(e[1], 148);
|
||||
assert_eq!(e[2..22], [0; 20]);
|
||||
assert_eq!(e[22], 160);
|
||||
assert_eq!(e[23..55], [0; 32]);
|
||||
assert_eq!(e[55], 120);
|
||||
assert_eq!(e[56], 30);
|
||||
fn test_validator_record_zero_rand_keypair() {
|
||||
let (v, kp) = ValidatorRecord::zero_with_thread_rand_keypair();
|
||||
// TODO: check keys
|
||||
assert_eq!(v.withdrawal_shard, 0);
|
||||
assert!(v.withdrawal_address.is_zero());
|
||||
assert!(v.randao_commitment.is_zero());
|
||||
assert!(v.balance.is_zero());
|
||||
assert_eq!(v.start_dynasty, 0);
|
||||
assert_eq!(v.end_dynasty, 0);
|
||||
}
|
||||
}
|
||||
|
@ -11,6 +11,7 @@ pub use super::ethereum_types::U256;
|
||||
// which is bad. Make the compiler think they're incompatible.
|
||||
pub type Sha256Digest = H256;
|
||||
pub type Blake2sDigest = H256;
|
||||
pub type Hash256 = H256;
|
||||
|
||||
pub type Address = H160;
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user