Browse Source

Merge pull request #94 from 0xPolygonMiden/vlopes11-merkle-store-derive

refactor: add derive proc macros to merkle store
al-gkr-basic-workflow
Victor Lopes 2 years ago
committed by GitHub
parent
commit
931bcc3cc3
No known key found for this signature in database GPG Key ID: 4AEE18F83AFDEB23
1 changed files with 55 additions and 13 deletions
  1. +55
    -13
      src/merkle/store.rs

+ 55
- 13
src/merkle/store.rs

@ -8,12 +8,13 @@ use super::{
RpoDigest, SimpleSmt, Vec, Word, RpoDigest, SimpleSmt, Vec, Word,
}; };
#[derive(Debug)]
#[derive(Debug, Default, Copy, Clone, Eq, PartialEq)]
pub struct Node { pub struct Node {
left: RpoDigest, left: RpoDigest,
right: RpoDigest, right: RpoDigest,
} }
#[derive(Debug, Clone, Eq, PartialEq)]
pub struct MerkleStore { pub struct MerkleStore {
nodes: BTreeMap<RpoDigest, Node>, nodes: BTreeMap<RpoDigest, Node>,
} }
@ -30,22 +31,59 @@ impl MerkleStore {
/// Creates an empty `MerkleStore` instance. /// Creates an empty `MerkleStore` instance.
pub fn new() -> MerkleStore { pub fn new() -> MerkleStore {
let mut nodes = BTreeMap::new();
// pre-populate the store with the empty hashes // pre-populate the store with the empty hashes
let subtrees = EmptySubtreeRoots::empty_hashes(64); let subtrees = EmptySubtreeRoots::empty_hashes(64);
for (child, parent) in subtrees.iter().zip(subtrees.iter().skip(1)) {
nodes.insert(
*parent,
Node {
left: *child,
right: *child,
},
);
}
let nodes = subtrees
.iter()
.copied()
.zip(subtrees.iter().skip(1).copied())
.map(|(child, parent)| {
(
parent,
Node {
left: child,
right: child,
},
)
})
.collect();
MerkleStore { nodes } MerkleStore { nodes }
} }
/// Appends the provided merkle tree represented by its `leaves` to the set.
pub fn with_merkle_tree<I>(mut self, leaves: I) -> Result<Self, MerkleError>
where
I: IntoIterator<Item = Word>,
{
self.add_merkle_tree(leaves)?;
Ok(self)
}
/// Appends the provided sparse merkle tree represented by its `entries` to the set.
pub fn with_sparse_merkle_tree<R, I>(mut self, entries: R) -> Result<Self, MerkleError>
where
R: IntoIterator<IntoIter = I>,
I: Iterator<Item = (u64, Word)> + ExactSizeIterator,
{
self.add_sparse_merkle_tree(entries)?;
Ok(self)
}
/// Appends the provided merkle path set.
pub fn with_merkle_path(
mut self,
index_value: u64,
node: Word,
path: MerklePath,
) -> Result<Self, MerkleError> {
self.add_merkle_path(index_value, node, path)?;
Ok(self)
}
// STATE MUTATORS
// --------------------------------------------------------------------------------------------
/// Adds all the nodes of a Merkle tree represented by `leaves`. /// Adds all the nodes of a Merkle tree represented by `leaves`.
/// ///
/// This will instantiate a Merkle tree using `leaves` and include all the nodes into the /// This will instantiate a Merkle tree using `leaves` and include all the nodes into the
@ -56,7 +94,11 @@ impl MerkleStore {
/// This method may return the following errors: /// This method may return the following errors:
/// - `DepthTooSmall` if leaves is empty or contains only 1 element /// - `DepthTooSmall` if leaves is empty or contains only 1 element
/// - `NumLeavesNotPowerOfTwo` if the number of leaves is not a power-of-two /// - `NumLeavesNotPowerOfTwo` if the number of leaves is not a power-of-two
pub fn add_merkle_tree(&mut self, leaves: Vec<Word>) -> Result<Word, MerkleError> {
pub fn add_merkle_tree<I>(&mut self, leaves: I) -> Result<Word, MerkleError>
where
I: IntoIterator<Item = Word>,
{
let leaves: Vec<_> = leaves.into_iter().collect();
let layers = leaves.len().ilog2(); let layers = leaves.len().ilog2();
let tree = MerkleTree::new(leaves)?; let tree = MerkleTree::new(leaves)?;

Loading…
Cancel
Save