miden-crypto/src/merkle/path.rs
src/merkle/path.rsRaw
1use super::{vec, NodeIndex, Rpo256, Vec, Word};
2use core::ops::{Deref, DerefMut};
3
4// MERKLE PATH
5// ================================================================================================
6
7/// A merkle path container, composed of a sequence of nodes of a Merkle tree.
8#[derive(Clone, Debug, Default, PartialEq, Eq)]
9pub struct MerklePath {
10 nodes: Vec<Word>,
11}
12
13impl MerklePath {
14 // CONSTRUCTORS
15 // --------------------------------------------------------------------------------------------
16
17 /// Creates a new Merkle path from a list of nodes.
18 pub fn new(nodes: Vec<Word>) -> Self {
19 Self { nodes }
20 }
21
22 // PROVIDERS
23 // --------------------------------------------------------------------------------------------
24
25 /// Computes the merkle root for this opening.
26 pub fn compute_root(&self, index_value: u64, node: Word) -> Word {
27 let mut index = NodeIndex::new(self.depth(), index_value);
28 self.nodes.iter().copied().fold(node, |node, sibling| {
29 // compute the node and move to the next iteration.
30 let input = index.build_node(node.into(), sibling.into());
31 index.move_up();
32 Rpo256::merge(&input).into()
33 })
34 }
35
36 /// Returns the depth in which this Merkle path proof is valid.
37 pub fn depth(&self) -> u8 {
38 self.nodes.len() as u8
39 }
40
41 /// Verifies the Merkle opening proof towards the provided root.
42 ///
43 /// Returns `true` if `node` exists at `index` in a Merkle tree with `root`.
44 pub fn verify(&self, index: u64, node: Word, root: &Word) -> bool {
45 root == &self.compute_root(index, node)
46 }
47}
48
49impl From<Vec<Word>> for MerklePath {
50 fn from(path: Vec<Word>) -> Self {
51 Self::new(path)
52 }
53}
54
55impl Deref for MerklePath {
56 // we use `Vec` here instead of slice so we can call vector mutation methods directly from the
57 // merkle path (example: `Vec::remove`).
58 type Target = Vec<Word>;
59
60 fn deref(&self) -> &Self::Target {
61 &self.nodes
62 }
63}
64
65impl DerefMut for MerklePath {
66 fn deref_mut(&mut self) -> &mut Self::Target {
67 &mut self.nodes
68 }
69}
70
71impl FromIterator<Word> for MerklePath {
72 fn from_iter<T: IntoIterator<Item = Word>>(iter: T) -> Self {
73 Self::new(iter.into_iter().collect())
74 }
75}
76
77impl IntoIterator for MerklePath {
78 type Item = Word;
79 type IntoIter = vec::IntoIter<Word>;
80
81 fn into_iter(self) -> Self::IntoIter {
82 self.nodes.into_iter()
83 }
84}