diff options
-rw-r--r-- | ChangeLog | 16 | ||||
-rw-r--r-- | unwind.c | 9 | ||||
-rw-r--r-- | unwind.h | 10 |
3 files changed, 24 insertions, 11 deletions
@@ -1,5 +1,21 @@ 2011-12-20 Kaz Kylheku <kaz@kylheku.com> + Bug #35137 + + * unwind.c (uw_unwind_to_exit_point): When jumping to a catch frame, + do not mark it invisible. + + * unwind.h (uw_catch): Flip the matches to nil so that this catch + frame can no longer be identified as an unwind point by uw_throw, + and thus will not be re-entered for the purposes of handling + an exception. It remains visible for the purposes of running the + clean up code. + (uw_unwind): Prior to executing cleanup forms, flip the visibility + to 0. This means that the frame will no longer be re-entered + for any reason. + +2011-12-20 Kaz Kylheku <kaz@kylheku.com> + Streamlining exception handling macros a little bit. * eval.c (op_unwind_protect): Use uw_simple_catch_begin, @@ -65,11 +65,6 @@ static void uw_unwind_to_exit_point(void) uw_stack->ca.sym = nil; uw_stack->ca.exception = nil; uw_stack->ca.cont = uw_exit_point; - /* This catch frame is no longer - visible. If the unwind section - throws something, it cannot - be caught in the same frame. */ - uw_stack->ca.visible = 0; /* 1 means unwind only. */ longjmp(uw_stack->ca.jb, 1); abort(); @@ -94,10 +89,6 @@ static void uw_unwind_to_exit_point(void) case UW_ENV: /* env frame cannot be exit point */ abort(); case UW_CATCH: - /* Catch frame is no longer visible. - If a catch or unwind throw something, - it cannot go back to the same catch. */ - uw_stack->ca.visible = 0; /* 2 means actual catch, not just unwind */ longjmp(uw_stack->ca.jb, 2); default: @@ -155,11 +155,17 @@ noreturn val type_mismatch(val, ...); break; \ case 2: \ EXCVAR = uw_catch.ca.exception; \ - SYMVAR = uw_catch.ca.sym; + SYMVAR = uw_catch.ca.sym; \ + /* prevent looping */ \ + uw_catch.ca.matches = nil; #define uw_unwind \ + /* suppress unused label warning */ \ + goto uw_unwind_label; \ uw_unwind_label: \ - case 1: + case 1: \ + /* prevent looping */ \ + uw_catch.ca.visible = 0; #define uw_catch_end \ break; \ |