aboutsummaryrefslogtreecommitdiff
path: root/src/ls_kw_impl.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/ls_kw_impl.c')
-rw-r--r--src/ls_kw_impl.c216
1 files changed, 2 insertions, 214 deletions
diff --git a/src/ls_kw_impl.c b/src/ls_kw_impl.c
index 9070ab7..6330be0 100644
--- a/src/ls_kw_impl.c
+++ b/src/ls_kw_impl.c
@@ -24,8 +24,6 @@
/// Call for keywords without implementations.
static void _no_impl(ls_t * self);
-static void _consume_to_eol(ls_t * self);
-
void ls_kw_fun_GOTO(ls_t * self);
// --- PUBLIC VARIABLES --------------------------------------------------------
@@ -47,85 +45,12 @@ void ls_kw_fun_COUNT(ls_t * self) { _no_impl(self); }
void ls_kw_fun_DATA(ls_t * self) { _no_impl(self); }
void ls_kw_fun_DEC(ls_t * self) { _no_impl(self); }
void ls_kw_fun_DEF(ls_t * self) { _no_impl(self); }
-
void ls_kw_fun_END(ls_t * self) { ls_throw_err(self, LS_STOPPED); }
-
void ls_kw_fun_EQV(ls_t * self) { _no_impl(self); }
void ls_kw_fun_ERASE(ls_t * self) { _no_impl(self); }
void ls_kw_fun_ERROR(ls_t * self) { _no_impl(self); }
void ls_kw_fun_FN(ls_t * self) { _no_impl(self); }
-
-void ls_kw_fun_FOR(ls_t * self)
-{
- // FOR ident = a TO b [STEP c]
- ls_value_t * ctx = ls_alloc(self);
- *ctx = (ls_value_t) {
- .ty = LS_TY_SCTX_FOR,
- .body.sctx_for = {
- .term = 0,
- .step = 1,
- .for_pc = LS_ADDR_NULL,
- },
- .prev = self->_callstack,
- .next = NULL,
- };
- self->_callstack = ctx;
-
- ls_value_t * iterator = ls_alloc(self);
- *iterator = (ls_value_t) {
- .ty = LS_TY_INT_VAR,
- .body.int_var = {{0}},
- };
-
- ctx->next = iterator;
-
- // FOR ident = a TO b [STEP c]
- if (ls_lex(self) != LS_TOK_WORD)
- ls_throw_err(self, LS_SYNTAX_ERROR);
-
- strncpy(iterator->body.int_var.ident, self->_token.word, LS_IDENT_LEN);
-
- if (ls_lex(self) != LS_OP_EQ)
- ls_throw_err(self, LS_SYNTAX_ERROR);
-
- ls_value_t val;
- ls_eval_expr(self, &val, LS_TOK_NONE);
- if (val.ty != LS_TY_INT)
- ls_throw_err(self, LS_SYNTAX_ERROR);
- iterator->body.int_var.value = val.body.integer.value;
-
- if (ls_lex(self) != LS_KW_TO)
- ls_throw_err(self, LS_SYNTAX_ERROR);
-
- ls_eval_expr(self, &val, LS_TOK_NONE);
- if (val.ty != LS_TY_INT)
- ls_throw_err(self, LS_SYNTAX_ERROR);
- ctx->body.sctx_for.term = val.body.integer.value;
-
- ls_token_t tok = ls_lex(self);
-
- if (tok == LS_KW_STEP)
- {
- ls_eval_expr(self, &val, LS_TOK_NONE);
- if (val.ty != LS_TY_INT)
- ls_throw_err(self, LS_SYNTAX_ERROR);
-
- if (val.body.integer.value > INT16_MAX ||
- val.body.integer.value < INT16_MIN)
- ls_throw_err(self, LS_FOR_STEP_TOO_LARGE);
-
- ctx->body.sctx_for.step = (int16_t) val.body.integer.value;
- tok = ls_lex(self);
- }
-
- if (tok == LS_TOK_STATEMENT_SEP)
- ctx->body.sctx_for.for_pc = self->_pc;
- else
- ls_throw_err(self, LS_SYNTAX_ERROR);
-}
-
void ls_kw_fun_HEX(ls_t * self) { _no_impl(self); }
-
void ls_kw_fun_IF(ls_t * self)
{
// TODO how to support ELSE - the current parsing method doesn't
@@ -138,7 +63,7 @@ void ls_kw_fun_IF(ls_t * self)
if (cond.body.integer.value == 0)
{
- _consume_to_eol(self);
+ ls_consume_to_eol(self);
return;
}
else
@@ -162,45 +87,6 @@ void ls_kw_fun_LEFT(ls_t * self) { _no_impl(self); }
void ls_kw_fun_LET(ls_t * self) { _no_impl(self); }
void ls_kw_fun_LOG(ls_t * self) { _no_impl(self); }
void ls_kw_fun_MID(ls_t * self) { _no_impl(self); }
-
-void ls_kw_fun_NEXT(ls_t * self)
-{
- if (self->_callstack->ty != LS_TY_SCTX_FOR)
- ls_throw_err(self, LS_FOR_NEXT_MISMATCH);
-
- ls_value_t * ctx = self->_callstack;
- ls_value_t * iterator = ctx->next;
- ls_int_t itval = iterator->body.int_var.value;
- ls_int_t term = ctx->body.sctx_for.term;
- ls_int_t step = (ls_int_t) ctx->body.sctx_for.step;
-
- bool done = false;
-
- if (step < 0)
- {
- if (itval <= term || (itval + step < term))
- done = true;
- }
- else
- {
- if (itval >= term || (itval + step > term))
- done = true;
- }
-
- if (done)
- {
- self->_callstack = ctx->prev;
- ls_free_val(self, ctx);
- _consume_to_eol(self);
- }
- else
- {
- self->_pc = ctx->body.sctx_for.for_pc;
- itval += step;
- iterator->body.int_var.value = itval;
- }
-}
-
void ls_kw_fun_NOT(ls_t * self) { _no_impl(self); }
void ls_kw_fun_OCT(ls_t * self) { _no_impl(self); }
void ls_kw_fun_ON(ls_t * self) { _no_impl(self); }
@@ -212,7 +98,7 @@ void ls_kw_fun_READ(ls_t * self) { _no_impl(self); }
void ls_kw_fun_REM(ls_t * self)
{
- _consume_to_eol(self);
+ ls_consume_to_eol(self);
}
void ls_kw_fun_RESTORE(ls_t * self) { _no_impl(self); }
@@ -228,93 +114,6 @@ void ls_kw_fun_TO(ls_t * self) { _no_impl(self); }
void ls_kw_fun_UNPACK(ls_t * self) { _no_impl(self); }
void ls_kw_fun_UNTIL(ls_t * self) { _no_impl(self); }
void ls_kw_fun_VAL(ls_t * self) { _no_impl(self); }
-
-void ls_kw_fun_WEND(ls_t * self)
-{
- if (self->_callstack->ty != LS_TY_SCTX_WHILE)
- ls_throw_err(self, LS_WHILE_WEND_MISMATCH);
-
- ls_addr_t pc_wend = self->_pc;
- self->_pc = self->_callstack->body.sctx_while.while_pc;
-
- ls_value_t cond;
- ls_eval_expr(self, &cond, LS_TOK_NONE);
-
- if (cond.ty != LS_TY_INT)
- ls_throw_err(self, LS_SYNTAX_ERROR);
-
- if (cond.body.integer.value == 0)
- {
- ls_value_t * ctx = self->_callstack;
- self->_callstack = ctx->prev;
- ls_free_val(self, ctx);
- self->_pc = pc_wend;
- }
-}
-
-void ls_kw_fun_WHILE(ls_t * self)
-{
- ls_addr_t pc_cond = self->_pc;
-
- ls_value_t cond;
- ls_eval_expr(self, &cond, LS_TOK_NONE);
-
- if (cond.ty != LS_TY_INT)
- ls_throw_err(self, LS_SYNTAX_ERROR);
-
- if (cond.body.integer.value != 0)
- {
- ls_value_t * ctx = ls_alloc(self);
- *ctx = (ls_value_t) {
- .ty = LS_TY_SCTX_WHILE,
- .body.sctx_while = {
- .while_pc = pc_cond,
- },
- .prev = self->_callstack,
- .next = NULL,
- };
- self->_callstack = ctx;
- }
- else
- {
- bool keyword_allowed = false;
- ls_token_t tok = LS_TOK_NUMBER;
- int8_t nest = 0;
-
- while (tok != LS_TOK_NONE)
- {
- tok = ls_lex(self);
-
- if (keyword_allowed)
- {
- if (tok == LS_KW_WHILE)
- nest++;
- else if (tok == LS_KW_WEND)
- if (nest)
- nest--;
- else
- break;
- else if (tok == LS_KW_REM)
- {
- _consume_to_eol(self);
- continue; // keep keyword true
- }
- }
-
- keyword_allowed =
- tok == LS_TOK_STR_LABEL ||
- tok == LS_TOK_NUM_LABEL ||
- tok == LS_TOK_STATEMENT_SEP;
- }
-
- if (tok == LS_TOK_NONE)
- {
- self->_pc = pc_cond;
- ls_throw_err(self, LS_WHILE_WEND_MISMATCH);
- }
- }
-}
-
void ls_kw_fun_WRITE(ls_t * self) { _no_impl(self); }
void ls_kw_fun_XOR(ls_t * self) { _no_impl(self); }
@@ -325,14 +124,3 @@ static void _no_impl(ls_t * self)
ls_throw_err(self, LS_BAD_KEYWORD);
}
-static void _consume_to_eol(ls_t * self)
-{
- for (;;) {
- ls_uchar uch = ls_fetch_rel(self, 0);
-
- if (uch == 0 || uch == '\n')
- return;
-
- self->_pc++;
- }
-}