Fix lexical and dynamic binding
This commit is contained in:
+16
-9
@@ -135,20 +135,27 @@ DEFSPECIAL(let, "let", (LispVal * bindings, LispVal *body),
|
||||
"(bindings &rest body)", "") {
|
||||
CHECK_LISTP(bindings);
|
||||
StackFrame *stack_ref = LISP_STACK_REF();
|
||||
LispVal *lexenv = Vlexical_environment;
|
||||
DOLIST(binding, bindings) {
|
||||
if (SYMBOLP(binding)) {
|
||||
lexenv = CONS(binding, CONS(Qnil, lexenv));
|
||||
} else if (CONSP(binding) && list_length_eq(binding, 2)) {
|
||||
lexenv = CONS(
|
||||
FIRST(binding),
|
||||
CONS(Feval(SECOND(binding), Vlexical_environment), lexenv));
|
||||
} else {
|
||||
if (CONSP(binding) && list_length_eq(binding, 2)) {
|
||||
if (!SYMBOLP(XCAR(binding))) {
|
||||
// TODO better error
|
||||
abort();
|
||||
}
|
||||
RPLACA(XCDR(binding), Feval(SECOND(binding), Vlexical_environment));
|
||||
} else if (!SYMBOLP(binding)) {
|
||||
// TODO better error
|
||||
abort();
|
||||
}
|
||||
}
|
||||
push_dynamic_binding(Qlexical_environment, lexenv);
|
||||
push_copy_lexenv();
|
||||
DOLIST(binding, bindings) {
|
||||
// we already checked that all bindings are well formed
|
||||
if (SYMBOLP(binding)) {
|
||||
new_lexical_variable(binding, Qnil);
|
||||
} else {
|
||||
new_lexical_variable(FIRST(binding), SECOND(binding));
|
||||
}
|
||||
}
|
||||
return UNWIND_AND_RETURN(stack_ref, Fprogn(body));
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user