Skip to content

Commit

Permalink
Fix errors; remove HistoryTree usage
Browse files Browse the repository at this point in the history
  • Loading branch information
conradoplg committed Jul 15, 2021
1 parent 7651ea6 commit 510c1af
Show file tree
Hide file tree
Showing 4 changed files with 37 additions and 84 deletions.
6 changes: 6 additions & 0 deletions zebra-chain/src/orchard/tree.rs
Original file line number Diff line number Diff line change
Expand Up @@ -111,6 +111,12 @@ impl From<Root> for [u8; 32] {
}
}

impl From<&Root> for [u8; 32] {
fn from(root: &Root) -> Self {
(*root).into()
}
}

impl Hash for Root {
fn hash<H: Hasher>(&self, state: &mut H) {
self.0.to_bytes().hash(state)
Expand Down
25 changes: 21 additions & 4 deletions zebra-chain/src/sprout/tree.rs
Original file line number Diff line number Diff line change
Expand Up @@ -104,10 +104,22 @@ impl From<Root> for [u8; 32] {
}
}

impl From<&[u8; 32]> for Root {
fn from(bytes: &[u8; 32]) -> Root {
(*bytes).into()
}
}

impl From<&Root> for [u8; 32] {
fn from(root: &Root) -> Self {
(*root).into()
}
}

/// Sprout Note Commitment Tree
#[derive(Clone, Debug, Default, Eq, PartialEq)]
#[cfg_attr(any(test, feature = "proptest-impl"), derive(Arbitrary))]
struct NoteCommitmentTree {
pub struct NoteCommitmentTree {
/// The root node of the tree (often used as an anchor).
root: Root,
/// The height of the tree (maximum height for Sprout is 29).
Expand Down Expand Up @@ -164,8 +176,13 @@ impl From<Vec<NoteCommitment>> for NoteCommitmentTree {
impl NoteCommitmentTree {
/// Get the Jubjub-based Pedersen hash of root node of this merkle tree of
/// commitment notes.
pub fn hash(&self) -> [u8; 32] {
self.root.0
pub fn hash(&self) -> Root {
self.root
}

/// Add a note commitment to the tree.
pub fn append(&self, _cm: &NoteCommitment) {
// TODO
}
}

Expand Down Expand Up @@ -277,7 +294,7 @@ mod tests {

let tree = NoteCommitmentTree::from(leaves.clone());

assert_eq!(hex::encode(tree.hash()), roots[i]);
assert_eq!(hex::encode(<[u8; 32]>::from(tree.hash())), roots[i]);
}
}
}
3 changes: 3 additions & 0 deletions zebra-state/src/service.rs
Original file line number Diff line number Diff line change
Expand Up @@ -726,6 +726,9 @@ impl Service<Request> for StateService {
.collect();
async move { Ok(Response::BlockHeaders(res)) }.boxed()
}
Request::AwaitSproutAnchor(_) => todo!(),
Request::AwaitSaplingAnchor(_) => todo!(),
Request::AwaitOrchardAnchor(_) => todo!(),
}
}
}
Expand Down
87 changes: 7 additions & 80 deletions zebra-state/src/service/non_finalized_state/chain.rs
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ use zebra_chain::{

use crate::{service::check, PreparedBlock, ValidateContextError};

#[derive(Debug, Default, Clone)]
#[derive(Debug, Clone, Default)]
pub struct Chain {
pub blocks: BTreeMap<block::Height, PreparedBlock>,
pub height_by_hash: HashMap<block::Hash, block::Height>,
Expand All @@ -26,8 +26,6 @@ pub struct Chain {
sapling_note_commitment_tree: sapling::tree::NoteCommitmentTree,
orchard_note_commitment_tree: orchard::tree::NoteCommitmentTree,

pub(crate) history_tree: HistoryTree,

pub(super) sprout_anchors: HashSet<sprout::tree::Root>,
pub(super) sapling_anchors: HashSet<sapling::tree::Root>,
pub(super) orchard_anchors: HashSet<orchard::tree::Root>,
Expand All @@ -40,30 +38,6 @@ pub struct Chain {
}

impl Chain {
/// Is the internal state of `self` the same as `other`?
///
/// The history tree must contain the history of the previous (finalized) blocks.
pub fn new(history_tree: HistoryTree) -> Self {
Chain {
blocks: Default::default(),
height_by_hash: Default::default(),
tx_by_hash: Default::default(),
created_utxos: Default::default(),
spent_utxos: Default::default(),
sprout_note_commitment_tree: Default::default(),
sapling_note_commitment_tree: Default::default(),
orchard_note_commitment_tree: Default::default(),
sprout_anchors: Default::default(),
sapling_anchors: Default::default(),
orchard_anchors: Default::default(),
sprout_nullifiers: Default::default(),
sapling_nullifiers: Default::default(),
orchard_nullifiers: Default::default(),
partial_cumulative_work: Default::default(),
history_tree,
}
}

/// Is the internal state of `self` the same as `other`?
///
/// [`Chain`] has custom [`Eq`] and [`Ord`] implementations based on proof of work,
Expand Down Expand Up @@ -152,20 +126,6 @@ impl Chain {
forked.pop_tip();
}

// Rebuild the history tree starting from the finalized tip tree.
// TODO: change to a more efficient approach by removing nodes
// from the tree of the original chain (in `pop_tip()`).
// See https://github.com/ZcashFoundation/zebra/issues/2378
forked
.history_tree
.try_extend(forked.blocks.values().map(|prepared_block| {
(
prepared_block.block.clone(),
&forked.sapling_note_commitment_tree.root(),
Some(&forked.orchard_note_commitment_tree.root()),
)
}))?;

Ok(Some(forked))
}

Expand Down Expand Up @@ -205,35 +165,6 @@ impl Chain {
pub fn is_empty(&self) -> bool {
self.blocks.is_empty()
}

pub fn history_root_hash(&self) -> ChainHistoryMmrRootHash {
self.history_tree.hash()
}

/// Clone the Chain but not the history tree, using the history tree
/// specified instead.
///
/// Useful when forking, where the history tree is rebuilt anyway.
fn with_history_tree(&self, history_tree: HistoryTree) -> Self {
Chain {
blocks: self.blocks.clone(),
height_by_hash: self.height_by_hash.clone(),
tx_by_hash: self.tx_by_hash.clone(),
created_utxos: self.created_utxos.clone(),
spent_utxos: self.spent_utxos.clone(),
sprout_note_commitment_tree: self.sprout_note_commitment_tree.clone(),
sapling_note_commitment_tree: self.sapling_note_commitment_tree.clone(),
orchard_note_commitment_tree: self.orchard_note_commitment_tree.clone(),
sprout_anchors: self.sprout_anchors.clone(),
sapling_anchors: self.sapling_anchors.clone(),
orchard_anchors: self.orchard_anchors.clone(),
sprout_nullifiers: self.sprout_nullifiers.clone(),
sapling_nullifiers: self.sapling_nullifiers.clone(),
orchard_nullifiers: self.orchard_nullifiers.clone(),
partial_cumulative_work: self.partial_cumulative_work,
history_tree,
}
}
}

/// Helper trait to organize inverse operations done on the `Chain` type. Used to
Expand Down Expand Up @@ -341,17 +272,13 @@ impl UpdateWith<PreparedBlock> for Chain {
// Having updated all the note commitment trees and nullifier sets in
// this block, the roots of the note commitment trees as of the last
// transaction are the treestates of this block.
let sprout_root = self.sprout_note_commitment_tree.root();
let sprout_root = self.sprout_note_commitment_tree.hash();
let sapling_root = self.sapling_note_commitment_tree.root();
let orchard_root = self.orchard_note_commitment_tree.root();

self.sprout_anchors.insert(&sprout_root);
self.sapling_anchors.insert(&sapling_root);
self.orchard_anchors.insert(&orchard_root);

// TODO: pass Sapling and Orchard roots
self.history_tree
.push(prepared.block.clone(), &sapling_root, Some(&orchard_root))?;
self.sprout_anchors.insert(sprout_root);
self.sapling_anchors.insert(sapling_root);
self.orchard_anchors.insert(orchard_root);

Ok(())
}
Expand Down Expand Up @@ -530,7 +457,7 @@ where
) -> Result<(), ValidateContextError> {
if let Some(sapling_shielded_data) = sapling_shielded_data {
for cm_u in sapling_shielded_data.note_commitments() {
self.sapling_note_commitment_tree.append(cm_u);
self.sapling_note_commitment_tree.append(*cm_u);
}

for nullifier in sapling_shielded_data.nullifiers() {
Expand Down Expand Up @@ -564,7 +491,7 @@ impl UpdateWith<Option<orchard::ShieldedData>> for Chain {
) -> Result<(), ValidateContextError> {
if let Some(orchard_shielded_data) = orchard_shielded_data {
for cm_x in orchard_shielded_data.note_commitments() {
self.orchard_note_commitment_tree.append(cm_x);
self.orchard_note_commitment_tree.append(*cm_x);
}

// TODO: check orchard nullifiers are unique (#2231)
Expand Down

0 comments on commit 510c1af

Please sign in to comment.