Skip to content

Commit

Permalink
Update BlockHeader weight to BigUint and DagCBOR encoding for TipsetK…
Browse files Browse the repository at this point in the history
…eys (#191)

* update weight to BigUint and implment encoding/decoding for tipsets

* fix suggestion
  • Loading branch information
ec2 authored Jan 23, 2020
1 parent 8755ec1 commit 58f3e03
Show file tree
Hide file tree
Showing 7 changed files with 56 additions and 17 deletions.
1 change: 1 addition & 0 deletions blockchain/blocks/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -14,3 +14,4 @@ multihash = "0.9.3"
derive_builder = "0.9"
serde = { version = "1.0", features = ["derive"] }
encoding = { path = "../../encoding" }
num-bigint = { git = "https://github.com/austinabell/num-bigint", rev = "f7084a9ed5a2b08d9bfb67790cb4ce9212193f31" }
10 changes: 6 additions & 4 deletions blockchain/blocks/src/header.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ use crypto::Signature;
use derive_builder::Builder;
use encoding::{Cbor, Error as EncodingError};
use multihash::Hash;
use num_bigint::BigUint;
use serde::{Deserialize, Serialize};
use std::fmt;

Expand All @@ -20,13 +21,14 @@ use std::fmt;
/// use address::Address;
/// use cid::{Cid, Codec, Prefix, Version};
/// use clock::ChainEpoch;
/// use num_bigint::BigUint;
/// use crypto::Signature;
///
/// BlockHeader::builder()
/// .miner_address(Address::new_id(0).unwrap()) // optional
/// .bls_aggregate(Signature::new_bls(vec![])) // optional
/// .parents(TipSetKeys::default()) // optional
/// .weight(0) // optional
/// .weight(BigUint::from(0u8)) // optional
/// .epoch(ChainEpoch::default()) // optional
/// .messages(TxMeta::default()) // optional
/// .message_receipts(Cid::default()) // optional
Expand All @@ -48,7 +50,7 @@ pub struct BlockHeader {

/// weight is the aggregate chain weight of the parent set
#[builder(default)]
weight: u64,
weight: BigUint,

/// epoch is the period in which a new block is generated.
/// There may be multiple rounds in an epoch
Expand Down Expand Up @@ -136,8 +138,8 @@ impl BlockHeader {
&self.parents
}
/// Getter for BlockHeader weight
pub fn weight(&self) -> u64 {
self.weight
pub fn weight(&self) -> &BigUint {
&self.weight
}
/// Getter for BlockHeader epoch
pub fn epoch(&self) -> &ChainEpoch {
Expand Down
38 changes: 32 additions & 6 deletions blockchain/blocks/src/tipset.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,12 +7,17 @@
use super::{Block, BlockHeader, Error, Ticket};
use cid::Cid;
use clock::ChainEpoch;
use serde::{Deserialize, Serialize};
use encoding::{
de::{self, Deserializer},
ser::{self, Serializer},
};
use num_bigint::BigUint;
use serde::Deserialize;

/// A set of CIDs forming a unique key for a TipSet.
/// Equal keys will have equivalent iteration order, but note that the CIDs are *not* maintained in
/// the same order as the canonical iteration order of blocks in a tipset (which is by ticket)
#[derive(Clone, Debug, PartialEq, Eq, Hash, Default, Serialize, Deserialize)]
#[derive(Clone, Debug, PartialEq, Eq, Hash, Default)]
pub struct TipSetKeys {
pub cids: Vec<Cid>,
}
Expand All @@ -35,6 +40,26 @@ impl TipSetKeys {
}
}

impl ser::Serialize for TipSetKeys {
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
where
S: Serializer,
{
let value = self.cids.clone();
value.serialize(serializer)
}
}

impl<'de> de::Deserialize<'de> for TipSetKeys {
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
where
D: Deserializer<'de>,
{
let cids: Vec<Cid> = Deserialize::deserialize(deserializer)?;
Ok(TipSetKeys { cids })
}
}

/// An immutable set of blocks at the same height with the same parent set.
/// Blocks in a tipset are canonically ordered by ticket size.
#[derive(Clone, PartialEq, Debug, Default)]
Expand Down Expand Up @@ -158,8 +183,8 @@ impl Tipset {
&self.blocks[0].parents()
}
/// Returns the tipset's calculated weight
pub fn weight(&self) -> u64 {
self.blocks[0].weight()
pub fn weight(&self) -> &BigUint {
&self.blocks[0].weight()
}
/// Returns the tipset's epoch
pub fn tip_epoch(&self) -> &ChainEpoch {
Expand Down Expand Up @@ -198,6 +223,7 @@ mod tests {
use address::Address;
use cid::Cid;
use crypto::VRFResult;
use num_bigint::BigUint;

const WEIGHT: u64 = 1;
const CACHED_BYTES: [u8; 1] = [0];
Expand Down Expand Up @@ -228,7 +254,7 @@ mod tests {
.ticket(Ticket {
vrfproof: VRFResult::new(ticket_p),
})
.weight(WEIGHT)
.weight(BigUint::from(WEIGHT))
.cached_cid(cid)
.build()
.unwrap();
Expand Down Expand Up @@ -302,7 +328,7 @@ mod tests {
#[test]
fn weight_test() {
let tipset = setup();
assert_eq!(tipset.weight(), WEIGHT);
assert_eq!(tipset.weight(), &BigUint::from(WEIGHT));
}

#[test]
Expand Down
3 changes: 2 additions & 1 deletion blockchain/sync_manager/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -11,4 +11,5 @@ libp2p = { git = "https://github.com/SigP/rust-libp2p", rev = "776d13ef04635896
chain = { path ="../chain" }

[dev-dependencies]
cid = { package = "ferret_cid", path = "../../ipld/cid" }
cid = { package = "ferret_cid", path = "../../ipld/cid" }
num-bigint = { git = "https://github.com/austinabell/num-bigint", rev = "f7084a9ed5a2b08d9bfb67790cb4ce9212193f31" }
13 changes: 10 additions & 3 deletions blockchain/sync_manager/src/bucket.rs
Original file line number Diff line number Diff line change
Expand Up @@ -74,10 +74,11 @@ mod tests {
use super::*;
use blocks::BlockHeader;
use cid::Cid;
use num_bigint::BigUint;

fn create_header(weight: u64, parent_bz: &[u8], cached_bytes: &[u8]) -> BlockHeader {
let header = BlockHeader::builder()
.weight(weight)
.weight(BigUint::from(weight))
.cached_bytes(cached_bytes.to_vec())
.cached_cid(Cid::from_bytes_default(parent_bz).unwrap())
.build()
Expand All @@ -97,12 +98,18 @@ mod tests {

// Test the comparison of tipsets
let bucket = SyncBucket::new(vec![&l_tip, &h_tip]);
assert_eq!(bucket.heaviest_tipset().unwrap().weight(), 3);
assert_eq!(
bucket.heaviest_tipset().unwrap().weight(),
&BigUint::from(3u8)
);
assert_eq!(bucket.tips.len(), 2);

// assert bucket with just one tipset still resolves
let bucket = SyncBucket::new(vec![&l_tip]);
assert_eq!(bucket.heaviest_tipset().unwrap().weight(), 1);
assert_eq!(
bucket.heaviest_tipset().unwrap().weight(),
&BigUint::from(1u8)
);
}

#[test]
Expand Down
5 changes: 3 additions & 2 deletions blockchain/sync_manager/src/sync.rs
Original file line number Diff line number Diff line change
Expand Up @@ -42,9 +42,10 @@ impl<'a> Syncer<'a> {
// TODO send pubsub message indicating incoming blocks
// TODO Add peer to blocksync

// compare targetweight to heaviest weight stored; ignore otherwise
// compare target_weight to heaviest weight stored; ignore otherwise
let best_weight = self.chain_store.get_heaviest_tipset().blocks()[0].weight();
let target_weight = fts.tipset()?.blocks()[0].weight();
let target_weight = fts.blocks()[0].to_header().weight();

if !target_weight.lt(&best_weight) {
// Store incoming block header
self.chain_store.persist_headers(&fts.tipset()?).ok();
Expand Down
3 changes: 2 additions & 1 deletion blockchain/sync_manager/tests/manager_test.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,12 @@

use blocks::{BlockHeader, Tipset};
use cid::Cid;
use num_bigint::BigUint;
use sync_manager::SyncManager;

fn create_header(weight: u64, parent_bz: &[u8], cached_bytes: &[u8]) -> BlockHeader {
let header = BlockHeader::builder()
.weight(weight)
.weight(BigUint::from(weight))
.cached_bytes(cached_bytes.to_vec())
.cached_cid(Cid::from_bytes_default(parent_bz).unwrap())
.build()
Expand Down

0 comments on commit 58f3e03

Please sign in to comment.