From 1ef1b15fd358880cb1ac9f8e71c3557ae14237b6 Mon Sep 17 00:00:00 2001 From: Bruce Hill Date: Sat, 30 Mar 2024 12:47:20 -0400 Subject: More repl functionality/fixes --- repl.c | 93 +++++++++++++++++++++++++++++++++++++++++++++++++++--------------- 1 file changed, 72 insertions(+), 21 deletions(-) (limited to 'repl.c') diff --git a/repl.c b/repl.c index 38ed05e6..a0c6126c 100644 --- a/repl.c +++ b/repl.c @@ -79,6 +79,10 @@ static void repl_err(ast_t *node, const char *fmt, ...) const TypeInfo *type_to_type_info(type_t *t) { switch (t->tag) { + case AbortType: return &$Abort; + case VoidType: return &$Void; + case MemoryType: return &$Memory; + case BoolType: return &$Bool; case IntType: switch (Match(t, IntType)->bits) { case 0: case 64: return &$Int; @@ -87,6 +91,29 @@ const TypeInfo *type_to_type_info(type_t *t) case 8: return &$Int8; default: errx(1, "Invalid bits"); } + case NumType: + switch (Match(t, NumType)->bits) { + case 0: case 64: return &$Num; + case 32: return &$Num32; + default: errx(1, "Invalid bits"); + } + case TextType: return &$Text; + case ArrayType: { + const TypeInfo *item_info = type_to_type_info(Match(t, ArrayType)->item_type); + return $ArrayInfo(item_info); + } + case TableType: { + const TypeInfo *key_info = type_to_type_info(Match(t, TableType)->key_type); + const TypeInfo *value_info = type_to_type_info(Match(t, TableType)->value_type); + return $TableInfo(key_info, value_info); + } + case PointerType: { + auto ptr = Match(t, PointerType); + CORD sigil = ptr->is_stack ? "&" : (ptr->is_optional ? "?" : "@"); + if (ptr->is_readonly) sigil = CORD_cat(sigil, "(readonly)"); + const TypeInfo *pointed_info = type_to_type_info(ptr->pointed); + return $PointerInfo(sigil, pointed_info); + } default: errx(1, "Unsupported type: %T", t); } } @@ -204,6 +231,7 @@ static CORD obj_to_text(type_t *t, const void *obj, bool use_color) if (!p) return CORD_cat("!", type_to_cord(ptr->pointed)); CORD sigil = ptr->is_stack ? "&" : (ptr->is_optional ? "?" : "@"); if (ptr->is_readonly) sigil = CORD_cat(sigil, "(readonly)"); + if (use_color) sigil = CORD_all("\x1b[34;1m", sigil, "\x1b[m"); return CORD_all(sigil, obj_to_text(ptr->pointed, p, use_color)); } case StructType: { @@ -367,28 +395,28 @@ void eval(env_t *env, ast_t *ast, void *dest) break; } #define CASE_OP(OP_NAME, C_OP) case BINOP_##OP_NAME: {\ - if (t->tag == IntType) { \ - int64_t lhs = ast_to_int(env, binop->lhs); \ - int64_t rhs = ast_to_int(env, binop->rhs); \ - switch (Match(t, IntType)->bits) { \ - case 64: *(int64_t*)dest = lhs C_OP rhs; break; \ - case 32: *(int32_t*)dest = (int32_t)(lhs C_OP rhs); break; \ - case 16: *(int16_t*)dest = (int16_t)(lhs C_OP rhs); break; \ - case 8: *(int8_t*)dest = (int8_t)(lhs C_OP rhs); break; \ - default: errx(1, "Invalid int bits"); \ + if (t->tag == IntType) { \ + int64_t lhs = ast_to_int(env, binop->lhs); \ + int64_t rhs = ast_to_int(env, binop->rhs); \ + switch (Match(t, IntType)->bits) { \ + case 64: *(int64_t*)dest = lhs C_OP rhs; break; \ + case 32: *(int32_t*)dest = (int32_t)(lhs C_OP rhs); break; \ + case 16: *(int16_t*)dest = (int16_t)(lhs C_OP rhs); break; \ + case 8: *(int8_t*)dest = (int8_t)(lhs C_OP rhs); break; \ + default: errx(1, "Invalid int bits"); \ + } \ + } else if (t->tag == NumType) { \ + double lhs = ast_to_num(env, binop->lhs); \ + double rhs = ast_to_num(env, binop->rhs); \ + if (Match(t, NumType)->bits == 64) \ + *(double*)dest = (double)(lhs C_OP rhs); \ + else \ + *(float*)dest = (float)(lhs C_OP rhs); \ + } else { \ + errx(1, "Binary ops are not yet supported for %W", ast); \ } \ - } else if (t->tag == NumType) { \ - double lhs = ast_to_num(env, binop->lhs); \ - double rhs = ast_to_num(env, binop->rhs); \ - if (Match(t, NumType)->bits == 64) \ - *(double*)dest = (double)(lhs C_OP rhs); \ - else \ - *(float*)dest = (float)(lhs C_OP rhs); \ - } else { \ - errx(1, "Binary ops are not yet supported for %W", ast); \ - } \ - break; \ -} + break; \ + } case BinaryOp: { auto binop = Match(ast, BinaryOp); switch (binop->op) { @@ -399,6 +427,29 @@ void eval(env_t *env, ast_t *ast, void *dest) } break; } + case Array: { + assert(t->tag == ArrayType); + array_t arr = {}; + size_t item_size = type_size(Match(t, ArrayType)->item_type); + char item_buf[item_size] = {}; + const TypeInfo *type_info = type_to_type_info(t); + for (ast_list_t *item = Match(ast, Array)->items; item; item = item->next) { + eval(env, item->ast, item_buf); + Array$insert(&arr, item_buf, 0, type_info); + } + memcpy(dest, &arr, sizeof(array_t)); + break; + } + case Block: { + auto block = Match(ast, Block); + for (ast_list_t *stmt = block->statements; stmt; stmt = stmt->next) { + if (stmt->next) + run(env, stmt->ast); + else + eval(env, stmt->ast, dest); + } + break; + } default: errx(1, "Eval not implemented for %W", ast); } -- cgit v1.2.3