@@ -12,39 +12,77 @@ private enum TrieNodeType {
1212
1313private struct TrieNode {
1414 let hash : Data32
15- let left : Data32
16- let right : Data32
15+ let left : Data32 // Original child hash/data
16+ let right : Data32 // Original child hash/data
1717 let type : TrieNodeType
1818 let isNew : Bool
1919 let rawValue : Data ?
2020
21- init ( hash: Data32 , data: Data64 , isNew: Bool = false ) {
21+ // Constructor for loading from storage (65-byte format: [type][left-32][right-32])
22+ init ( hash: Data32 , data: Data , isNew: Bool = false ) {
2223 self . hash = hash
23- left = Data32 ( data. data. prefix ( 32 ) ) !
24- right = Data32 ( data. data. suffix ( 32 ) ) !
2524 self . isNew = isNew
2625 rawValue = nil
27- switch data. data. first! & 0b1100_0000 {
28- case 0b1000_0000 :
26+
27+ let typeByte = data [ relative: 0 ]
28+ switch typeByte {
29+ case 0 :
30+ type = . branch
31+ case 1 :
2932 type = . embeddedLeaf
30- case 0b1100_0000 :
33+ case 2 :
3134 type = . regularLeaf
3235 default :
3336 type = . branch
3437 }
38+
39+ left = Data32 ( data [ relative: 1 ..< 33 ] ) ! // bytes 1-32
40+ right = Data32 ( data [ relative: 33 ..< 65 ] ) ! // bytes 33-64
3541 }
3642
43+ // Constructor for pure trie operations
3744 private init ( left: Data32 , right: Data32 , type: TrieNodeType , isNew: Bool , rawValue: Data ? ) {
38- hash = Blake2b256 . hash ( left. data , right. data )
39- self . left = left
40- self . right = right
45+ hash = Self . calculateHash ( left: left , right: right , type : type )
46+ self . left = left // Store original data
47+ self . right = right // Store original data
4148 self . type = type
4249 self . isNew = isNew
4350 self . rawValue = rawValue
4451 }
4552
46- var encodedData : Data64 {
47- Data64 ( left. data + right. data) !
53+ // JAM spec compliant hash calculation
54+ private static func calculateHash( left: Data32 , right: Data32 , type: TrieNodeType ) -> Data32 {
55+ switch type {
56+ case . branch:
57+ var leftForHashing = left. data
58+ leftForHashing [ leftForHashing. startIndex] = leftForHashing [ leftForHashing. startIndex] & 0b0111_1111
59+ return Blake2b256 . hash ( leftForHashing, right. data)
60+ case . embeddedLeaf:
61+ var leftForHashing = left. data
62+ let valueLength = leftForHashing [ leftForHashing. startIndex]
63+ leftForHashing [ leftForHashing. startIndex] = 0b1000_0000 | valueLength
64+ return Blake2b256 . hash ( leftForHashing, right. data)
65+ case . regularLeaf:
66+ var leftForHashing = left. data
67+ leftForHashing [ leftForHashing. startIndex] = 0b1100_0000
68+ return Blake2b256 . hash ( leftForHashing, right. data)
69+ }
70+ }
71+
72+ // New 65-byte storage format: [type:1][left:32][right:32]
73+ var storageData : Data {
74+ var data = Data ( capacity: 65 )
75+
76+ switch type {
77+ case . branch: data. append ( 0 )
78+ case . embeddedLeaf: data. append ( 1 )
79+ case . regularLeaf: data. append ( 2 )
80+ }
81+
82+ data. append ( left. data)
83+ data. append ( right. data)
84+
85+ return data
4886 }
4987
5088 var isBranch : Bool {
@@ -66,27 +104,30 @@ private struct TrieNode {
66104 guard type == . embeddedLeaf else {
67105 return nil
68106 }
69- let len = left. data. first! & 0b0011_1111
107+ // For embedded leaves: length is stored in first byte
108+ let len = left. data [ relative: 0 ]
70109 return right. data [ relative: 0 ..< Int ( len) ]
71110 }
72111
73112 static func leaf( key: Data31 , value: Data ) -> TrieNode {
74- var newKey = Data ( capacity: 32 )
75113 if value. count <= 32 {
76- newKey. append ( 0b1000_0000 | UInt8 ( value. count) )
77- newKey += key. data
78- let newValue = value + Data( repeating: 0 , count: 32 - value. count)
79- return . init( left: Data32 ( newKey) !, right: Data32 ( newValue) !, type: . embeddedLeaf, isNew: true , rawValue: value)
114+ // Embedded leaf: store length + key, padded value
115+ var keyData = Data ( capacity: 32 )
116+ keyData. append ( UInt8 ( value. count) ) // Store length in first byte
117+ keyData += key. data
118+ let paddedValue = value + Data( repeating: 0 , count: 32 - value. count)
119+ return . init( left: Data32 ( keyData) !, right: Data32 ( paddedValue) !, type: . embeddedLeaf, isNew: true , rawValue: value)
120+ } else {
121+ // Regular leaf: store key, value hash
122+ var keyData = Data ( capacity: 32 )
123+ keyData. append ( 0x00 ) // Placeholder for first byte
124+ keyData += key. data
125+ return . init( left: Data32 ( keyData) !, right: value. blake2b256hash ( ) , type: . regularLeaf, isNew: true , rawValue: value)
80126 }
81- newKey. append ( 0b1100_0000 )
82- newKey += key. data
83- return . init( left: Data32 ( newKey) !, right: value. blake2b256hash ( ) , type: . regularLeaf, isNew: true , rawValue: value)
84127 }
85128
86129 static func branch( left: Data32 , right: Data32 ) -> TrieNode {
87- var left = left. data
88- left [ left. startIndex] = left [ left. startIndex] & 0b0111_1111 // clear the highest bit
89- return . init( left: Data32 ( left) !, right: right, type: . branch, isNew: true , rawValue: nil )
130+ . init( left: left, right: right, type: . branch, isNew: true , rawValue: nil )
90131 }
91132}
92133
@@ -148,12 +189,10 @@ public actor StateTrie {
148189 guard let data = try await backend. read ( key: id) else {
149190 return nil
150191 }
151-
152- guard let data64 = Data64 ( data) else {
192+ guard data. count == 65 else {
153193 throw StateTrieError . invalidData
154194 }
155-
156- let node = TrieNode ( hash: hash, data: data64)
195+ let node = TrieNode ( hash: hash, data: data)
157196 saveNode ( node: node)
158197 return node
159198 }
@@ -189,7 +228,7 @@ public actor StateTrie {
189228 deleted. removeAll ( )
190229
191230 for node in nodes. values where node. isNew {
192- ops. append ( . write( key: node. hash. data. suffix ( 31 ) , value: node. encodedData . data ) )
231+ ops. append ( . write( key: node. hash. data. suffix ( 31 ) , value: node. storageData ) )
193232 if node. type == . regularLeaf {
194233 try ops. append ( . writeRawValue( key: node. right, value: node. rawValue. unwrap ( ) ) )
195234 }
@@ -256,7 +295,7 @@ public actor StateTrie {
256295 return newLeaf. hash
257296 }
258297
259- let existingKeyBit = bitAt ( existing. left. data [ 1 ... ] , position: depth)
298+ let existingKeyBit = bitAt ( existing. left. data [ relative : 1 ... ] , position: depth)
260299 let newKeyBit = bitAt ( newKey. data, position: depth)
261300
262301 if existingKeyBit == newKeyBit {
@@ -306,6 +345,30 @@ public actor StateTrie {
306345 if left == Data32 ( ) , right == Data32 ( ) {
307346 // this branch is empty
308347 return Data32 ( )
348+ } else if left == Data32 ( ) {
349+ // only right child remains - check if we can collapse
350+ let rightNode = try await get ( hash: right)
351+ if let rightNode, rightNode. isLeaf {
352+ // Can collapse: right child is a leaf
353+ return right
354+ } else {
355+ // Cannot collapse: right child is a branch that needs to maintain its depth
356+ let newBranch = TrieNode . branch ( left: left, right: right)
357+ saveNode ( node: newBranch)
358+ return newBranch. hash
359+ }
360+ } else if right == Data32 ( ) {
361+ // only left child remains - check if we can collapse
362+ let leftNode = try await get ( hash: left)
363+ if let leftNode, leftNode. isLeaf {
364+ // Can collapse: left child is a leaf
365+ return left
366+ } else {
367+ // Cannot collapse: left child is a branch that needs to maintain its depth
368+ let newBranch = TrieNode . branch ( left: left, right: right)
369+ saveNode ( node: newBranch)
370+ return newBranch. hash
371+ }
309372 }
310373
311374 let newBranch = TrieNode . branch ( left: left, right: right)
@@ -331,7 +394,7 @@ public actor StateTrie {
331394 private func saveNode( node: TrieNode ) {
332395 let id = node. hash. data. suffix ( 31 )
333396 nodes [ id] = node
334- deleted. remove ( id) // TODO: maybe this is not needed
397+ deleted. remove ( id)
335398 }
336399
337400 public func debugPrint( ) async throws {
0 commit comments