diff options
author | Andy Wingo <wingo@pobox.com> | 2010-03-04 11:37:03 +0100 |
---|---|---|
committer | Andy Wingo <wingo@pobox.com> | 2010-03-04 13:14:43 +0100 |
commit | 2b2746a831b5f74773d6eec91d2c30d43831e826 (patch) | |
tree | 0bc8698bfb45292a7ba9d4b33601fc27e228dfc9 | |
parent | bbb2ecd1d1966766aa5f3fed7d5084b46cf1e8a7 (diff) |
tighten up scm_i_dowinds, fixing invalid SCM_CAR (prompt)
* libguile/dynwind.c: Update comment regarding what can be on the wind
stack.
(scm_i_dowinds): Clean up to remove @bind and catch/throw-handler
cases, to add a case for prompts, and to be more strict in general
regarding the set of things that can be on the wind stack. Fixes a bug
whereby prompts were accessed via SCM_CAR; thanks to Ken Raeburn for
the report.
-rw-r--r-- | libguile/dynwind.c | 47 |
1 files changed, 15 insertions, 32 deletions
diff --git a/libguile/dynwind.c b/libguile/dynwind.c index 18e38b995..f4d19bd0a 100644 --- a/libguile/dynwind.c +++ b/libguile/dynwind.c @@ -26,6 +26,7 @@ #include <assert.h> #include "libguile/_scm.h" +#include "libguile/control.h" #include "libguile/eval.h" #include "libguile/alist.h" #include "libguile/fluids.h" @@ -41,10 +42,9 @@ #<frame> #<winder> + #<with-fluids> + #<prompt> (enter-proc . leave-proc) dynamic-wind - (tag . jmpbuf) catch - (tag . pre-unwind-data) throw-handler / lazy-catch - tag is either a symbol or a boolean */ @@ -240,7 +240,6 @@ scm_i_dowinds (SCM to, long delta, void (*turn_func) (void *), void *data) else if (delta < 0) { SCM wind_elt; - SCM wind_key; scm_i_dowinds (SCM_CDR (to), 1 + delta, turn_func, data); wind_elt = SCM_CAR (to); @@ -262,21 +261,13 @@ scm_i_dowinds (SCM to, long delta, void (*turn_func) (void *), void *data) scm_i_swap_with_fluids (wind_elt, SCM_I_CURRENT_THREAD->dynamic_state); } + else if (SCM_PROMPT_P (wind_elt)) + ; /* pass -- see vm_reinstate_partial_continuation */ + else if (scm_is_pair (wind_elt)) + scm_call_0 (SCM_CAR (wind_elt)); else - { - wind_key = SCM_CAR (wind_elt); - /* key = #t | symbol | thunk | list of variables */ - if (SCM_NIMP (wind_key)) - { - if (scm_is_pair (wind_key)) - { - if (SCM_VARIABLEP (SCM_CAR (wind_key))) - scm_swap_bindings (wind_key, SCM_CDR (wind_elt)); - } - else if (scm_is_true (scm_thunk_p (wind_key))) - scm_call_0 (wind_key); - } - } + /* trash on the wind list */ + abort (); scm_i_set_dynwinds (to); } @@ -284,7 +275,6 @@ scm_i_dowinds (SCM to, long delta, void (*turn_func) (void *), void *data) { SCM wind; SCM wind_elt; - SCM wind_key; wind = scm_i_dynwinds (); wind_elt = SCM_CAR (wind); @@ -304,20 +294,13 @@ scm_i_dowinds (SCM to, long delta, void (*turn_func) (void *), void *data) scm_i_swap_with_fluids (wind_elt, SCM_I_CURRENT_THREAD->dynamic_state); } + else if (SCM_PROMPT_P (wind_elt)) + ; /* pass -- though we could invalidate the prompt */ + else if (scm_is_pair (wind_elt)) + scm_call_0 (SCM_CDR (wind_elt)); else - { - wind_key = SCM_CAR (wind_elt); - if (SCM_NIMP (wind_key)) - { - if (scm_is_pair (wind_key)) - { - if (SCM_VARIABLEP (SCM_CAR (wind_key))) - scm_swap_bindings (wind_key, SCM_CDR (wind_elt)); - } - else if (scm_is_true (scm_thunk_p (wind_key))) - scm_call_0 (SCM_CDR (wind_elt)); - } - } + /* trash on the wind list */ + abort (); delta--; goto tail; /* scm_dowinds(to, delta-1); */ |