summaryrefslogtreecommitdiff
path: root/libguile/vm-engine.c
diff options
context:
space:
mode:
Diffstat (limited to 'libguile/vm-engine.c')
-rw-r--r--libguile/vm-engine.c24
1 files changed, 21 insertions, 3 deletions
diff --git a/libguile/vm-engine.c b/libguile/vm-engine.c
index 12e62d52d..159310250 100644
--- a/libguile/vm-engine.c
+++ b/libguile/vm-engine.c
@@ -53,10 +53,10 @@ VM_NAME (SCM vm, SCM program, SCM *argv, int nargs)
SCM *stack_limit = vp->stack_limit; /* stack limit address */
scm_i_thread *current_thread = SCM_I_CURRENT_THREAD;
- scm_t_int64 vm_cookie = vp->cookie++;
/* Internal variables */
int nvalues = 0;
+ scm_i_jmp_buf registers; /* used for prompts */
#ifdef HAVE_LABELS_AS_VALUES
static const void **jump_table_pointer = NULL;
@@ -86,6 +86,24 @@ VM_NAME (SCM vm, SCM program, SCM *argv, int nargs)
jump_table = jump_table_pointer;
#endif
+ if (SCM_I_SETJMP (registers))
+ {
+ /* Non-local return. Cache the VM registers back from the vp, and
+ go to the handler.
+
+ Note, at this point, we must assume that any variable local to
+ vm_engine that can be assigned *has* been assigned. So we need to pull
+ all our state back from the ip/fp/sp.
+ */
+ CACHE_REGISTER ();
+ program = SCM_FRAME_PROGRAM (fp);
+ CACHE_PROGRAM ();
+ /* The stack contains the values returned to this continuation,
+ along with a number-of-values marker -- like an MV return. */
+ ABORT_CONTINUATION_HOOK ();
+ NEXT;
+ }
+
/* Initial frame */
CACHE_REGISTER ();
PUSH (SCM_PACK (fp)); /* dynamic link */
@@ -113,7 +131,7 @@ VM_NAME (SCM vm, SCM program, SCM *argv, int nargs)
{
if (SCM_STRUCTP (program) && SCM_STRUCT_APPLICABLE_P (program))
fp[-1] = SCM_STRUCT_PROCEDURE (program);
- else if (SCM_NIMP (program) && SCM_TYP7 (program) == scm_tc7_smob
+ else if (SCM_HAS_TYP7 (program, scm_tc7_smob)
&& SCM_SMOB_APPLICABLE_P (program))
{
/* (smob arg0 ... argN) => (apply-smob smob arg0 ... argN) */
@@ -121,7 +139,7 @@ VM_NAME (SCM vm, SCM program, SCM *argv, int nargs)
PUSH (SCM_BOOL_F);
for (i = sp - fp; i >= 0; i--)
fp[i] = fp[i - 1];
- fp[-1] = SCM_SMOB_DESCRIPTOR (program).apply_trampoline_objcode;
+ fp[-1] = SCM_SMOB_DESCRIPTOR (program).apply_trampoline;
}
else
{