summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJohannes Weiner <hannes@cmpxchg.org>2009-12-15 12:13:34 +0100
committerJohannes Weiner <hannes@cmpxchg.org>2009-12-15 12:13:34 +0100
commit8ca5f5e2d3415f0e21724b211e1f9ee946571005 (patch)
treec8c5fd02abba93ccdf9c1bb989bfea296014f7f5
parentd5fe2bbd65de224e3e6da7fb13344583cc501f45 (diff)
eval: protect functions through callstack
Instead of growing the protection vector with the callstack, just use the callstack itself to protect the functions on it. Signed-off-by: Johannes Weiner <hannes@cmpxchg.org>
-rw-r--r--sheep/eval.c15
-rw-r--r--sheep/vm.c8
2 files changed, 9 insertions, 14 deletions
diff --git a/sheep/eval.c b/sheep/eval.c
index 45a5378..bedf17d 100644
--- a/sheep/eval.c
+++ b/sheep/eval.c
@@ -265,9 +265,8 @@ sheep_t sheep_eval(struct sheep_vm *vm, sheep_t function)
sheep_protect(vm, function);
current = sheep_function(function);
- codep = function_codep(current);
-
finalize_frame(vm, current);
+ codep = function_codep(current);
continue;
}
break;
@@ -286,12 +285,13 @@ sheep_t sheep_eval(struct sheep_vm *vm, sheep_t function)
sheep_vector_push(&vm->calls, (void *)basep);
sheep_vector_push(&vm->calls, function);
+ sheep_unprotect(vm, function);
function = tmp;
sheep_protect(vm, function);
current = sheep_function(function);
- codep = function_codep(current);
basep = finalize_frame(vm, current);
+ codep = function_codep(current);
nesting++;
continue;
@@ -316,6 +316,8 @@ sheep_t sheep_eval(struct sheep_vm *vm, sheep_t function)
goto out;
function = sheep_vector_pop(&vm->calls);
+ sheep_protect(vm, function);
+
current = sheep_function(function);
basep = (unsigned long)sheep_vector_pop(&vm->calls);
codep = sheep_vector_pop(&vm->calls);
@@ -342,13 +344,8 @@ out:
return sheep_vector_pop(&vm->stack);
err:
vm->stack.nr_items = 0;
+ vm->calls.nr_items -= 3 * nesting;
sheep_unprotect(vm, function);
- while (nesting--) {
- function = sheep_vector_pop(&vm->calls);
- sheep_unprotect(vm, function);
- sheep_vector_pop(&vm->calls); /* basep */
- sheep_vector_pop(&vm->calls); /* codep */
- }
return NULL;
}
diff --git a/sheep/vm.c b/sheep/vm.c
index 0ec03d7..2582129 100644
--- a/sheep/vm.c
+++ b/sheep/vm.c
@@ -24,17 +24,15 @@ void sheep_vm_mark(struct sheep_vm *vm)
unsigned int i;
for (i = 0; i < vm->globals.nr_items; i++)
- /*
- * Empty global slots occur with variable slots that
- * get reserved at compile time and initialized during
- * evaluation.
- */
if (vm->globals.items[i])
sheep_mark(vm->globals.items[i]);
for (i = 0; i < vm->stack.nr_items; i++)
if (vm->stack.items[i])
sheep_mark(vm->stack.items[i]);
+
+ for (i = 2; i < vm->calls.nr_items; i += 3)
+ sheep_mark(vm->calls.items[i]);
}
unsigned int sheep_vm_variable(struct sheep_vm *vm,