@@ -18,7 +18,8 @@ use ethrex_common::{
1818 } ,
1919} ;
2020use ethrex_levm:: EVMConfig ;
21- use ethrex_levm:: constants:: { SYS_CALL_GAS_LIMIT , TX_BASE_COST } ;
21+ use ethrex_levm:: call_frame:: Stack ;
22+ use ethrex_levm:: constants:: { STACK_LIMIT , SYS_CALL_GAS_LIMIT , TX_BASE_COST } ;
2223use ethrex_levm:: db:: gen_db:: GeneralizedDatabase ;
2324use ethrex_levm:: errors:: { InternalError , TxValidationError } ;
2425use ethrex_levm:: tracing:: LevmCallTracer ;
@@ -99,6 +100,8 @@ impl LEVM {
99100 ) -> Result < BlockExecutionResult , EvmError > {
100101 Self :: prepare_block ( block, db, vm_type) ?;
101102
103+ let mut shared_stack_pool = Vec :: with_capacity ( STACK_LIMIT ) ;
104+
102105 let mut receipts = Vec :: new ( ) ;
103106 let mut cumulative_gas_used = 0 ;
104107
@@ -113,7 +116,14 @@ impl LEVM {
113116 ) ) ) ;
114117 }
115118
116- let report = Self :: execute_tx ( tx, tx_sender, & block. header , db, vm_type) ?;
119+ let report = Self :: execute_tx_in_block (
120+ tx,
121+ tx_sender,
122+ & block. header ,
123+ db,
124+ vm_type,
125+ & mut shared_stack_pool,
126+ ) ?;
117127 LEVM :: send_state_transitions_tx ( & merkleizer, db, queue_length) ?;
118128
119129 cumulative_gas_used += report. gas_used ;
@@ -218,7 +228,7 @@ impl LEVM {
218228 pub fn execute_tx (
219229 // The transaction to execute.
220230 tx : & Transaction ,
221- // The transactions recovered address
231+ // The transaction's recovered address
222232 tx_sender : Address ,
223233 // The block header for the current block.
224234 block_header : & BlockHeader ,
@@ -231,6 +241,27 @@ impl LEVM {
231241 vm. execute ( ) . map_err ( VMError :: into)
232242 }
233243
244+ // Like execute_tx but allows reusing the stack pool
245+ fn execute_tx_in_block (
246+ // The transaction to execute.
247+ tx : & Transaction ,
248+ // The transaction's recovered address
249+ tx_sender : Address ,
250+ // The block header for the current block.
251+ block_header : & BlockHeader ,
252+ db : & mut GeneralizedDatabase ,
253+ vm_type : VMType ,
254+ stack_pool : & mut Vec < Stack > ,
255+ ) -> Result < ExecutionReport , EvmError > {
256+ let env = Self :: setup_env ( tx, tx_sender, block_header, db, vm_type) ?;
257+ let mut vm = VM :: new ( env, db, tx, LevmCallTracer :: disabled ( ) , vm_type) ?;
258+
259+ std:: mem:: swap ( & mut vm. stack_pool , stack_pool) ;
260+ let result = vm. execute ( ) . map_err ( VMError :: into) ;
261+ std:: mem:: swap ( & mut vm. stack_pool , stack_pool) ;
262+ result
263+ }
264+
234265 pub fn undo_last_tx ( db : & mut GeneralizedDatabase ) -> Result < ( ) , EvmError > {
235266 db. undo_last_transaction ( ) ?;
236267 Ok ( ( ) )
0 commit comments