@@ -8,6 +8,14 @@ use sha2::{Digest, Sha256};
88/// A hash value in the Merkle tree (32 bytes from SHA-256).
99pub type MerkleHash = [ u8 ; 32 ] ;
1010
11+ /// A Merkle tree for verifying data integrity.
12+ #[ derive( Debug , Clone ) ]
13+ pub struct MerkleTree {
14+ /// All nodes in the tree, stored level by level from bottom to top.
15+ /// Index 0 contains the leaves, and the last element contains the root.
16+ nodes_by_level : Vec < Vec < MerkleHash > > ,
17+ }
18+
1119/// A Merkle proof that can be used to verify a leaf is part of the tree.
1220///
1321/// MerkleProof is succinct because it is sent over the wire, so it doesn't contain proof
@@ -18,6 +26,85 @@ pub struct MerkleProof {
1826 pub siblings : Vec < MerkleHash > ,
1927}
2028
29+ impl MerkleTree {
30+ /// Hash a data chunk to create a leaf hash.
31+ pub fn hash_leaf ( data : & [ u8 ] ) -> MerkleHash {
32+ let mut hasher = Sha256 :: new ( ) ;
33+ // TODO(AndrewL): Talk with the team about these hash wrappings and what to do with them.
34+ hasher. update ( b"<leaf>" ) ;
35+ hasher. update ( data) ;
36+ hasher. update ( b"</leaf>" ) ;
37+ hasher. finalize ( ) . into ( )
38+ }
39+
40+ /// Get the root hash of the tree.
41+ /// Returns `None` if the tree is empty.
42+ pub fn root ( & self ) -> Option < MerkleHash > {
43+ self . nodes_by_level . last ( ) . and_then ( |level| level. first ( ) . copied ( ) )
44+ }
45+
46+ /// Get the number of leaves in the tree.
47+ pub fn leaf_count ( & self ) -> usize {
48+ self . nodes_by_level . first ( ) . map ( |level| level. len ( ) ) . unwrap_or ( 0 )
49+ }
50+
51+ /// Get the leaves of the tree.
52+ /// Returns `None` if the tree is empty.
53+ pub fn leaves ( & self ) -> Option < & [ MerkleHash ] > {
54+ self . nodes_by_level . first ( ) . map ( |level| level. as_slice ( ) )
55+ }
56+
57+ // TODO(AndrewL): CRITICAL: make leaves have different depths instead of this hack.
58+
59+ /// Generate a Merkle proof for a specific leaf index.
60+ ///
61+ /// Returns `None` if the index is out of bounds.
62+ pub fn prove ( & self , leaf_index : usize ) -> Option < MerkleProof > {
63+ let leaves = self . nodes_by_level . first ( ) ?;
64+ if leaf_index >= leaves. len ( ) {
65+ return None ;
66+ }
67+
68+ let mut siblings = Vec :: new ( ) ;
69+ let mut index = leaf_index;
70+
71+ // Iterate through levels from bottom to top (excluding the root)
72+ for level in & self . nodes_by_level [ ..self . nodes_by_level . len ( ) - 1 ] {
73+ let level_size = level. len ( ) ;
74+
75+ // Check if sibling exists
76+ if level_size <= 1 {
77+ index /= 2 ;
78+ continue ;
79+ }
80+
81+ // If the index is even, take the left sibling, else take the right sibling
82+ let sibling_index = index ^ 1 ;
83+
84+ // Add sibling hash
85+ debug_assert ! ( index < level_size) ;
86+ let sibling_index = if sibling_index == level_size { index } else { sibling_index } ;
87+ // TODO(AndrewL): consider skipping the sibling if it is the same as the current node.
88+ siblings. push ( level[ sibling_index] ) ;
89+
90+ // Move to parent level
91+ index /= 2 ;
92+ }
93+
94+ Some ( MerkleProof { siblings } )
95+ }
96+
97+ /// Verify a Merkle proof against this tree's root.
98+ pub fn verify (
99+ & self ,
100+ leaf_hash : & MerkleHash ,
101+ proof : & MerkleProof ,
102+ leaf_index : usize ,
103+ ) -> Option < bool > {
104+ self . root ( ) . and_then ( |root| Some ( proof. verify ( & root, leaf_hash, leaf_index) ) )
105+ }
106+ }
107+
21108/// Hash a pair of nodes to create a parent hash.
22109fn hash_pair ( left : & MerkleHash , right : & MerkleHash ) -> MerkleHash {
23110 let mut hasher = Sha256 :: new ( ) ;
0 commit comments