✨ block with function do.
parent
61303f6825
commit
b8fa1df563
|
@ -0,0 +1,18 @@
|
||||||
|
(define a 4)
|
||||||
|
|
||||||
|
(do
|
||||||
|
(assert-eqv! 4 a)
|
||||||
|
(define a 'hello)
|
||||||
|
(assert-eqv! 'hello a)
|
||||||
|
|
||||||
|
(set! a 28)
|
||||||
|
(assert-eqv! 28 a)
|
||||||
|
)
|
||||||
|
|
||||||
|
(assert-eqv! 4 a)
|
||||||
|
|
||||||
|
(do
|
||||||
|
(set! a -63)
|
||||||
|
)
|
||||||
|
|
||||||
|
(assert-eqv! -63 a)
|
|
@ -12,6 +12,9 @@ void register_builtins(struct moka* moka)
|
||||||
moka_decl_native(moka, "array", mk_array, -1);
|
moka_decl_native(moka, "array", mk_array, -1);
|
||||||
moka_decl_native(moka, "assert-eqv!", mk_assert_eqv_mut, 2);
|
moka_decl_native(moka, "assert-eqv!", mk_assert_eqv_mut, 2);
|
||||||
|
|
||||||
|
moka_decl_native(moka, "do", mk_do, -1);
|
||||||
|
moka_decl_native(moka, "set!", mk_set_mut, 2);
|
||||||
|
|
||||||
moka_decl_native(moka, "<", mk_lt, 2);
|
moka_decl_native(moka, "<", mk_lt, 2);
|
||||||
moka_decl_native(moka, "<=", mk_le, 2);
|
moka_decl_native(moka, "<=", mk_le, 2);
|
||||||
moka_decl_native(moka, ">", mk_gt, 2);
|
moka_decl_native(moka, ">", mk_gt, 2);
|
||||||
|
@ -108,6 +111,48 @@ MOKA mk_assert_eqv_mut(struct moka* moka, struct vec* args)
|
||||||
return moka_push_bool(moka, true, line);
|
return moka_push_bool(moka, true, line);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
MOKA mk_do(struct moka* moka, struct vec* args)
|
||||||
|
{
|
||||||
|
assert(moka);
|
||||||
|
assert(args);
|
||||||
|
|
||||||
|
MOKA value = 0;
|
||||||
|
|
||||||
|
symtable_open_scope(&moka->symtable);
|
||||||
|
|
||||||
|
for (size_t i=0; i<args->size; i++)
|
||||||
|
{
|
||||||
|
value = MK_EVAL((MOKA) args->data[i]);
|
||||||
|
}
|
||||||
|
|
||||||
|
symtable_close_scope(&moka->symtable);
|
||||||
|
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
|
||||||
|
MOKA mk_set_mut(struct moka* moka, struct vec* args)
|
||||||
|
{
|
||||||
|
assert(moka);
|
||||||
|
assert(args);
|
||||||
|
|
||||||
|
MOKA mk_name = (MOKA) args->data[0];
|
||||||
|
MOKA value = MK_EVAL((MOKA)args->data[1]);
|
||||||
|
|
||||||
|
struct frame* frame = moka_frame(moka);
|
||||||
|
|
||||||
|
struct value* name = frame->local_values.data[mk_name];
|
||||||
|
struct node* node = name->data.lazy;
|
||||||
|
struct entry* entry = symtable_try_get(
|
||||||
|
&moka->symtable,
|
||||||
|
node->token->value
|
||||||
|
);
|
||||||
|
|
||||||
|
moka_push(moka, value);
|
||||||
|
entry->addr = frame->local_values.size - 1;
|
||||||
|
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
|
||||||
// Comparisons
|
// Comparisons
|
||||||
// ===========
|
// ===========
|
||||||
MOKA mk_lt(struct moka* moka, struct vec* args)
|
MOKA mk_lt(struct moka* moka, struct vec* args)
|
||||||
|
|
|
@ -13,6 +13,9 @@ MOKA mk_define(struct moka* moka, struct vec* args);
|
||||||
MOKA mk_array(struct moka* moka, struct vec* args);
|
MOKA mk_array(struct moka* moka, struct vec* args);
|
||||||
MOKA mk_assert_eqv_mut(struct moka* moka, struct vec* args);
|
MOKA mk_assert_eqv_mut(struct moka* moka, struct vec* args);
|
||||||
|
|
||||||
|
MOKA mk_do(struct moka* moka, struct vec* args);
|
||||||
|
MOKA mk_set_mut(struct moka* moka, struct vec* args);
|
||||||
|
|
||||||
// Comparisons
|
// Comparisons
|
||||||
// ===========
|
// ===========
|
||||||
MOKA mk_lt(struct moka* moka, struct vec* args);
|
MOKA mk_lt(struct moka* moka, struct vec* args);
|
||||||
|
|
|
@ -99,3 +99,25 @@ struct entry* symtable_try_get(struct symtable* self, char* name)
|
||||||
return env_try_get(self->root, name);
|
return env_try_get(self->root, name);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void symtable_open_scope(struct symtable* self)
|
||||||
|
{
|
||||||
|
struct env* env = malloc(sizeof(struct env));
|
||||||
|
env_init(env, self->root);
|
||||||
|
|
||||||
|
self->root = env;
|
||||||
|
}
|
||||||
|
|
||||||
|
void symtable_close_scope(struct symtable* self)
|
||||||
|
{
|
||||||
|
assert(self);
|
||||||
|
assert(self->root);
|
||||||
|
|
||||||
|
struct env* env = self->root->parent;
|
||||||
|
self->root->parent = NULL;
|
||||||
|
|
||||||
|
env_free(self->root);
|
||||||
|
free(self->root);
|
||||||
|
|
||||||
|
self->root = env;
|
||||||
|
}
|
||||||
|
|
|
@ -42,4 +42,7 @@ void symtable_declare(struct symtable* self,
|
||||||
|
|
||||||
struct entry* symtable_try_get(struct symtable* self, char* name);
|
struct entry* symtable_try_get(struct symtable* self, char* name);
|
||||||
|
|
||||||
|
void symtable_open_scope(struct symtable* self);
|
||||||
|
void symtable_close_scope(struct symtable* self);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
Loading…
Reference in New Issue