From 9fe6cd7c0e92ac5c5a711ed41e414ebbc1d50ad8 Mon Sep 17 00:00:00 2001 From: iamcheeseman Date: Tue, 14 Apr 2026 12:50:32 -0400 Subject: microscript: string indexing --- uscript/vm.c | 65 +++++++++++++++++++++++++++++++++++++++++++----------------- 1 file changed, 47 insertions(+), 18 deletions(-) (limited to 'uscript') diff --git a/uscript/vm.c b/uscript/vm.c index 26fccbe..e01d17d 100644 --- a/uscript/vm.c +++ b/uscript/vm.c @@ -76,6 +76,51 @@ void close_upvals(struct us_val *to) vm.open_upvals = upval; } +static +void index_val(struct us_val idx_val, struct us_val idxee_val) +{ + switch (idxee_val.type) { + case VAL_ARR: { + if (idx_val.type != VAL_NUM) + log_fatal(1, "arrays must be indexed by numbers"); + int idx = (int)get_num(idx_val); + struct us_arr *arr = get_arr(idxee_val); + if (idx < 0) + idx += da_len(arr->e); + if (idx < 0 || idx >= da_len(arr->e)) { + log_fatal( + 1, + "index out of range (%d/%d)", + idx, + da_len(arr->e) - 1 + ); + } + vm_push(arr->e[idx]); + break; + } + case VAL_STR: { + if (idx_val.type != VAL_NUM) + log_fatal(1, "strings must be indexed by numbers"); + int idx = (int)get_num(idx_val); + struct us_str *str = get_str(idxee_val); + if (idx < 0) + idx += str->len; + if (idx < 0 || (size_t)idx >= str->len) { + log_fatal( + 1, + "index out of range (%d/%d)", + idx, + str->len - 1 + ); + } + vm_push(wrap_str(copy_str(&str->chars[idx], 1))); + break; + } + default: + log_fatal(1, "cannot index that value"); + break; + } +} static void call_val(struct us_val callee, int argc) @@ -218,24 +263,8 @@ void us_exec(struct us_func *func) break; case BC_GET_INDEX: { struct us_val idx_val = vm_pop(); - struct us_val arr_val = vm_pop(); - if (idx_val.type != VAL_NUM) - log_fatal(1, "index type must be number"); - if (arr_val.type != VAL_ARR) - log_fatal(1, "only arrays can be indexed"); - int idx = (int)get_num(idx_val); - struct us_arr *arr = get_arr(arr_val); - if (idx < 0) - idx += da_len(arr->e); - if (idx < 0 || idx >= da_len(arr->e)) { - log_fatal( - 1, - "index out of range (%d/%d)", - idx, - da_len(arr->e) - 1 - ); - } - vm_push(arr->e[idx]); + struct us_val idxee_val = vm_pop(); + index_val(idx_val, idxee_val); break; } case BC_SET_INDEX: { -- cgit v1.3-2-g0d8e