1313#include "bc0.h"
1414#include "bc.h"
1515
16+ // Exception stack entry
17+ typedef struct _mp_exc_stack {
18+ const byte * handler ;
19+ // bit 0 is saved currently_in_except_block value
20+ machine_uint_t val_sp ;
21+ // We might only have 2 interesting cases here: SETUP_EXCEPT & SETUP_FINALLY,
22+ // consider storing it in bit 1 of val_sp. TODO: SETUP_WITH?
23+ byte opcode ;
24+ } mp_exc_stack ;
25+
1626// (value) stack grows down (to be compatible with native code when passing pointers to the stack), top element is pointed to
1727// exception stack grows up, top element is pointed to
1828
@@ -83,8 +93,8 @@ bool mp_execute_byte_code_2(const byte *code_info, const byte **ip_in_out, mp_ob
8393 nlr_buf_t nlr ;
8494
8595 volatile machine_uint_t currently_in_except_block = 0 ; // 0 or 1, to detect nested exceptions
86- machine_uint_t exc_stack [8 ]; // on the exception stack we store (ip, sp | X) for each block, X = previous value of currently_in_except_block
87- machine_uint_t * volatile exc_sp = & exc_stack [0 ] - 1 ; // stack grows up, exc_sp points to top of stack
96+ mp_exc_stack exc_stack [4 ];
97+ mp_exc_stack * volatile exc_sp = & exc_stack [0 ] - 1 ; // stack grows up, exc_sp points to top of stack
8898 const byte * volatile save_ip = ip ; // this is so we can access ip in the exception handler without making ip volatile (which means the compiler can't keep it in a register in the main loop)
8999
90100 // outer exception handling loop
@@ -318,9 +328,12 @@ bool mp_execute_byte_code_2(const byte *code_info, const byte **ip_in_out, mp_ob
318328
319329 // matched against: POP_BLOCK or POP_EXCEPT (anything else?)
320330 case MP_BC_SETUP_EXCEPT :
331+ case MP_BC_SETUP_FINALLY :
321332 DECODE_ULABEL ; // except labels are always forward
322- * ++ exc_sp = (machine_uint_t )ip + unum ;
323- * ++ exc_sp = (((machine_uint_t )sp ) | currently_in_except_block );
333+ ++ exc_sp ;
334+ exc_sp -> opcode = op ;
335+ exc_sp -> handler = ip + unum ;
336+ exc_sp -> val_sp = (((machine_uint_t )sp ) | currently_in_except_block );
324337 currently_in_except_block = 0 ; // in a try block now
325338 break ;
326339
@@ -359,8 +372,8 @@ bool mp_execute_byte_code_2(const byte *code_info, const byte **ip_in_out, mp_ob
359372 case MP_BC_POP_BLOCK :
360373 // we are exiting an exception handler, so pop the last one of the exception-stack
361374 assert (exc_sp >= & exc_stack [0 ]);
362- currently_in_except_block = (exc_sp [ 0 ] & 1 ); // restore previous state
363- exc_sp -= 2 ; // pop back to previous exception handler
375+ currently_in_except_block = (exc_sp -> val_sp & 1 ); // restore previous state
376+ exc_sp -- ; // pop back to previous exception handler
364377 break ;
365378
366379 // matched against: SETUP_EXCEPT
@@ -371,8 +384,8 @@ bool mp_execute_byte_code_2(const byte *code_info, const byte **ip_in_out, mp_ob
371384 assert (currently_in_except_block );
372385 //sp = (mp_obj_t*)(*exc_sp--);
373386 //exc_sp--; // discard ip
374- currently_in_except_block = (exc_sp [ 0 ] & 1 ); // restore previous state
375- exc_sp -= 2 ; // pop back to previous exception handler
387+ currently_in_except_block = (exc_sp -> val_sp & 1 ); // restore previous state
388+ exc_sp -- ; // pop back to previous exception handler
376389 //sp -= 3; // pop 3 exception values
377390 break ;
378391
@@ -550,17 +563,17 @@ bool mp_execute_byte_code_2(const byte *code_info, const byte **ip_in_out, mp_ob
550563 // at the moment we are just raising the very last exception (the one that caused the nested exception)
551564
552565 // move up to previous exception handler
553- currently_in_except_block = (exc_sp [ 0 ] & 1 ); // restore previous state
554- exc_sp -= 2 ; // pop back to previous exception handler
566+ currently_in_except_block = (exc_sp -> val_sp & 1 ); // restore previous state
567+ exc_sp -- ; // pop back to previous exception handler
555568 }
556569
557570 if (exc_sp >= & exc_stack [0 ]) {
558571 // set flag to indicate that we are now handling an exception
559572 currently_in_except_block = 1 ;
560573
561574 // catch exception and pass to byte code
562- sp = (mp_obj_t * )(exc_sp [ 0 ] & (~((machine_uint_t )1 )));
563- ip = ( const byte * )( exc_sp [ -1 ]) ;
575+ sp = (mp_obj_t * )(exc_sp -> val_sp & (~((machine_uint_t )1 )));
576+ ip = exc_sp -> handler ;
564577 // push(traceback, exc-val, exc-type)
565578 PUSH (mp_const_none );
566579 PUSH (nlr .ret_val );
0 commit comments