@@ -40,107 +40,83 @@ impl<'a> GetTransactionsProofProcess<'a> {
40
40
41
41
let snapshot = self . protocol . shared . snapshot ( ) ;
42
42
43
- let last_hash = self . message . last_hash ( ) . to_entity ( ) ;
44
- let last_block = if let Some ( block) = snapshot. get_block ( & last_hash) {
45
- block
46
- } else {
43
+ let last_block_hash = self . message . last_hash ( ) . to_entity ( ) ;
44
+ if !snapshot. is_main_chain ( & last_block_hash) {
47
45
return self
48
46
. protocol
49
47
. reply_tip_state :: < packed:: SendTransactionsProof > ( self . peer , self . nc ) ;
50
- } ;
48
+ }
49
+ let last_block = snapshot
50
+ . get_block ( & last_block_hash)
51
+ . expect ( "block should be in store" ) ;
51
52
52
- let ( txs_in_blocks , missing_txs ) = self
53
+ let ( found , missing ) : ( Vec < _ > , Vec < _ > ) = self
53
54
. message
54
55
. tx_hashes ( )
55
56
. to_entity ( )
56
57
. into_iter ( )
57
- . map ( |tx_hash| {
58
- let tx_with_info = snapshot. get_transaction_with_info ( & tx_hash) ;
59
- ( tx_hash, tx_with_info)
60
- } )
61
- . fold (
62
- ( HashMap :: new ( ) , Vec :: new ( ) ) ,
63
- |( mut found, mut missing_txs) , ( tx_hash, tx_with_info) | {
64
- if let Some ( ( tx, tx_info) ) = tx_with_info {
65
- found
66
- . entry ( tx_info. block_hash )
67
- . or_insert_with ( Vec :: new)
68
- . push ( ( tx, tx_info. index ) ) ;
69
- } else {
70
- missing_txs. push ( tx_hash) ;
71
- }
72
- ( found, missing_txs)
73
- } ,
74
- ) ;
75
-
76
- let ( positions, filtered_blocks, missing_txs) = txs_in_blocks
77
- . into_iter ( )
78
- . map ( |( block_hash, txs_and_tx_indices) | {
58
+ . partition ( |tx_hash| {
79
59
snapshot
80
- . get_block_header ( & block_hash)
81
- . map ( |header| header. number ( ) )
82
- . filter ( |number| * number != last_block. number ( ) )
83
- . and_then ( |number| snapshot. get_ancestor ( & last_hash, number) )
84
- . filter ( |header| header. hash ( ) == block_hash)
85
- . and_then ( |_| snapshot. get_block ( & block_hash) )
86
- . map ( |block| ( block, txs_and_tx_indices. clone ( ) ) )
87
- . ok_or_else ( || {
88
- txs_and_tx_indices
89
- . into_iter ( )
90
- . map ( |( tx, _) | tx. hash ( ) )
91
- . collect :: < Vec < _ > > ( )
92
- } )
93
- } )
94
- . fold (
95
- ( Vec :: new ( ) , Vec :: new ( ) , missing_txs) ,
96
- |( mut positions, mut filtered_blocks, mut missing_txs) , result| {
97
- match result {
98
- Ok ( ( block, txs_and_tx_indices) ) => {
99
- let merkle_proof = CBMT :: build_merkle_proof (
100
- & block
101
- . transactions ( )
102
- . iter ( )
103
- . map ( |tx| tx. hash ( ) )
104
- . collect :: < Vec < _ > > ( ) ,
105
- & txs_and_tx_indices
106
- . iter ( )
107
- . map ( |( _, index) | * index as u32 )
108
- . collect :: < Vec < _ > > ( ) ,
109
- )
110
- . expect ( "build proof with verified inputs should be OK" ) ;
111
-
112
- let txs: Vec < _ > = txs_and_tx_indices
113
- . into_iter ( )
114
- . map ( |( tx, _) | tx. data ( ) )
115
- . collect ( ) ;
116
-
117
- let filtered_block = packed:: FilteredBlock :: new_builder ( )
118
- . header ( block. header ( ) . data ( ) )
119
- . witnesses_root ( block. calc_witnesses_root ( ) )
120
- . transactions ( txs. pack ( ) )
121
- . proof (
122
- packed:: MerkleProof :: new_builder ( )
123
- . indices ( merkle_proof. indices ( ) . to_owned ( ) . pack ( ) )
124
- . lemmas ( merkle_proof. lemmas ( ) . to_owned ( ) . pack ( ) )
125
- . build ( ) ,
126
- )
127
- . build ( ) ;
128
-
129
- positions. push ( leaf_index_to_pos ( block. number ( ) ) ) ;
130
- filtered_blocks. push ( filtered_block) ;
131
- }
132
- Err ( tx_hashes) => {
133
- missing_txs. extend ( tx_hashes) ;
134
- }
135
- }
136
- ( positions, filtered_blocks, missing_txs)
137
- } ,
138
- ) ;
60
+ . get_transaction_info ( tx_hash)
61
+ . map ( |tx_info| snapshot. is_main_chain ( & tx_info. block_hash ) )
62
+ . unwrap_or_default ( )
63
+ } ) ;
64
+
65
+ let mut txs_in_blocks = HashMap :: new ( ) ;
66
+ for tx_hash in found {
67
+ let ( tx, tx_info) = snapshot
68
+ . get_transaction_with_info ( & tx_hash)
69
+ . expect ( "tx exists" ) ;
70
+ txs_in_blocks
71
+ . entry ( tx_info. block_hash )
72
+ . or_insert_with ( Vec :: new)
73
+ . push ( ( tx, tx_info. index ) ) ;
74
+ }
75
+
76
+ let mut positions = Vec :: with_capacity ( txs_in_blocks. len ( ) ) ;
77
+ let mut filtered_blocks = Vec :: with_capacity ( txs_in_blocks. len ( ) ) ;
78
+ for ( block_hash, txs_and_tx_indices) in txs_in_blocks. into_iter ( ) {
79
+ let block = snapshot
80
+ . get_block ( & block_hash)
81
+ . expect ( "block should be in store" ) ;
82
+ let merkle_proof = CBMT :: build_merkle_proof (
83
+ & block
84
+ . transactions ( )
85
+ . iter ( )
86
+ . map ( |tx| tx. hash ( ) )
87
+ . collect :: < Vec < _ > > ( ) ,
88
+ & txs_and_tx_indices
89
+ . iter ( )
90
+ . map ( |( _, index) | * index as u32 )
91
+ . collect :: < Vec < _ > > ( ) ,
92
+ )
93
+ . expect ( "build proof with verified inputs should be OK" ) ;
94
+
95
+ let txs: Vec < _ > = txs_and_tx_indices
96
+ . into_iter ( )
97
+ . map ( |( tx, _) | tx. data ( ) )
98
+ . collect ( ) ;
99
+
100
+ let filtered_block = packed:: FilteredBlock :: new_builder ( )
101
+ . header ( block. header ( ) . data ( ) )
102
+ . witnesses_root ( block. calc_witnesses_root ( ) )
103
+ . transactions ( txs. pack ( ) )
104
+ . proof (
105
+ packed:: MerkleProof :: new_builder ( )
106
+ . indices ( merkle_proof. indices ( ) . to_owned ( ) . pack ( ) )
107
+ . lemmas ( merkle_proof. lemmas ( ) . to_owned ( ) . pack ( ) )
108
+ . build ( ) ,
109
+ )
110
+ . build ( ) ;
111
+
112
+ positions. push ( leaf_index_to_pos ( block. number ( ) ) ) ;
113
+ filtered_blocks. push ( filtered_block) ;
114
+ }
139
115
140
116
let proved_items = packed:: FilteredBlockVec :: new_builder ( )
141
117
. set ( filtered_blocks)
142
118
. build ( ) ;
143
- let missing_items = missing_txs . pack ( ) ;
119
+ let missing_items = missing . pack ( ) ;
144
120
145
121
self . protocol . reply_proof :: < packed:: SendTransactionsProof > (
146
122
self . peer ,
0 commit comments