Allow defining and redefining local variables with "def"
This commit is contained in:
parent
6b8651145e
commit
58af636293
2 changed files with 36 additions and 7 deletions
|
@ -633,14 +633,33 @@ Result<Expression> Compiler::compile_def(Context& context, Symbol& op,
|
||||||
auto comp = TRY(compile_expr(context, var_expr));
|
auto comp = TRY(compile_expr(context, var_expr));
|
||||||
ex.add_code(comp.code);
|
ex.add_code(comp.code);
|
||||||
|
|
||||||
|
if (context.toplevel) {
|
||||||
TRY(ex.add_opcode(Oc::GlobalStore, {1, (int64_t)gname},
|
TRY(ex.add_opcode(Oc::GlobalStore, {1, (int64_t)gname},
|
||||||
{0, (int64_t)comp.reg}));
|
{0, (int64_t)comp.reg}));
|
||||||
|
|
||||||
ex.reg = comp.reg;
|
ex.reg = comp.reg;
|
||||||
|
return std::move(ex);
|
||||||
|
} else {
|
||||||
|
auto maybe_binding = context.get_var(varname_unwrapped);
|
||||||
|
|
||||||
|
if (maybe_binding.has_value()) {
|
||||||
|
auto reg = maybe_binding.value();
|
||||||
|
TRY(ex.add_opcode(Oc::Mov, {0, (int64_t)reg}, {0, (int64_t)comp.reg}));
|
||||||
|
ex.reg = comp.reg;
|
||||||
|
|
||||||
context.maxreg = maxreg + 1;
|
context.maxreg = maxreg + 1;
|
||||||
|
return std::move(ex);
|
||||||
|
} else {
|
||||||
|
context.maxreg = maxreg + 1;
|
||||||
|
auto reg = TRY(context.add_var(varname_unwrapped));
|
||||||
|
|
||||||
|
TRY(ex.add_opcode(Oc::Mov, {0, (int64_t)reg}, {0, (int64_t)comp.reg}));
|
||||||
|
ex.reg = reg;
|
||||||
|
context.maxreg = reg + 1;
|
||||||
|
|
||||||
return std::move(ex);
|
return std::move(ex);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
Result<Expression> Compiler::compile_quote(Context& context, Symbol& op,
|
Result<Expression> Compiler::compile_quote(Context& context, Symbol& op,
|
||||||
const Value& expr) {
|
const Value& expr) {
|
||||||
|
@ -905,7 +924,7 @@ Result<Expression> Compiler::compile_body(Context& context, const Value& expr) {
|
||||||
if (cur.is<Nil>()) {
|
if (cur.is<Nil>()) {
|
||||||
ex_res.reg = expr.reg;
|
ex_res.reg = expr.reg;
|
||||||
} else {
|
} else {
|
||||||
context.maxreg = maxreg;
|
// context.maxreg = maxreg;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -55,3 +55,13 @@
|
||||||
;; "do" form returns the value of last expression
|
;; "do" form returns the value of last expression
|
||||||
|
|
||||||
(assert (= (do 1 2 3) 3))
|
(assert (= (do 1 2 3) 3))
|
||||||
|
|
||||||
|
;; allow definition and redefinition of variables with "def"
|
||||||
|
|
||||||
|
(fn def-redef ()
|
||||||
|
(def x 1)
|
||||||
|
(def x (+ x 1))
|
||||||
|
(def y 4)
|
||||||
|
(+ x y))
|
||||||
|
|
||||||
|
(assert (= (def-redef) 6))
|
||||||
|
|
Loading…
Reference in a new issue