From b935325eb4f1cfe6ca9eebe343e94171c22c1616 Mon Sep 17 00:00:00 2001 From: Kyler Date: Fri, 28 Nov 2025 23:25:25 -0700 Subject: [PATCH] The interpreter works! More builtins to be implemented. --- SLS_C/include/sls/builtin.h | 14 + SLS_C/include/sls/interpreter.h | 44 +- SLS_C/src/builtin.c | 1099 +++++++++++++++++++++++++++++++ SLS_C/src/interpreter.c | 29 +- SLS_C/src/repl.c | 53 +- 5 files changed, 1218 insertions(+), 21 deletions(-) create mode 100644 SLS_C/include/sls/builtin.h create mode 100644 SLS_C/src/builtin.c diff --git a/SLS_C/include/sls/builtin.h b/SLS_C/include/sls/builtin.h new file mode 100644 index 0000000..04ac9e8 --- /dev/null +++ b/SLS_C/include/sls/builtin.h @@ -0,0 +1,14 @@ +// Kyler Olsen +// YREA SLS +// Builtin Functions Header +// November 2025 + +#ifndef SLS_BUILTIN_FUNCTIONS_H +#define SLS_BUILTIN_FUNCTIONS_H + +#include "sls/bool.h" +#include "sls/interpreter.h" + +Boolean load_builtins(InterpreterState *interpreter_state); + +#endif // SLS_BUILTIN_FUNCTIONS_H diff --git a/SLS_C/include/sls/interpreter.h b/SLS_C/include/sls/interpreter.h index ae4788f..c7dc4fb 100644 --- a/SLS_C/include/sls/interpreter.h +++ b/SLS_C/include/sls/interpreter.h @@ -8,6 +8,7 @@ #include +#include "sls/bool.h" #include "sls/lexer.h" #include "sls/hash_table.h" @@ -34,20 +35,20 @@ extern const size_t STACK_TYPE_COUNT; typedef struct StackItem { StackType type; union { - Identifier identifier; - int64_t i64; - int32_t i32; - int16_t i16; - int8_t i8; - uint64_t u64; - uint32_t u32; - uint16_t u16; - uint8_t u8; - float f32; - double f64; - uint8_t character; - Boolean boolean; - TokenString token_string; + Identifier identifier; // type == STACK_IDENTIFIER + int64_t i64; // type == STACK_I64 + int32_t i32; // type == STACK_I32 + int16_t i16; // type == STACK_I16 + int8_t i8; // type == STACK_I8 + uint64_t u64; // type == STACK_U64 + uint32_t u32; // type == STACK_U32 + uint16_t u16; // type == STACK_U16 + uint8_t u8; // type == STACK_U8 + float f32; // type == STACK_FLOAT + double f64; // type == STACK_DOUBLE + uint8_t character; // type == STACK_CHARACTER + Boolean boolean; // type == STACK_BOOLEAN + TokenString token_string; // type == STACK_TOKEN_STRING }; struct StackItem *next; } StackItem; @@ -57,6 +58,21 @@ typedef struct { HashTable *functions; } InterpreterState; +typedef enum { + FUNCTION_TOKEN_STRING, + FUNCTION_BUILTIN, +} FunctionType; + +typedef struct { + FunctionType type; + union { + TokenString token_string; // type == FUNCTION_TOKEN_STRING + Boolean (*builtin)(InterpreterState *); // type == FUNCTION_BUILTIN + }; +} FunctionItem; + +Boolean push_token(InterpreterState *interpreter_state, Token token); + Boolean execute(InterpreterState *interpreter_state, LexerTokenResult *token); InterpreterState *interpreter_create(); void interpreter_delete(InterpreterState *interpreter_state); diff --git a/SLS_C/src/builtin.c b/SLS_C/src/builtin.c new file mode 100644 index 0000000..9f34468 --- /dev/null +++ b/SLS_C/src/builtin.c @@ -0,0 +1,1099 @@ +// Kyler Olsen +// YREA SLS +// Builtin Functions +// November 2025 + +#include + +#include "sls/bool.h" +#include "sls/builtin.h" +#include "sls/hash_table.h" +#include "sls/interpreter.h" +#include "sls/lexer.h" + +Boolean builtin_addition(InterpreterState *interpreter_state); +Boolean builtin_subtraction(InterpreterState *interpreter_state); +Boolean builtin_multiplication(InterpreterState *interpreter_state); +Boolean builtin_division(InterpreterState *interpreter_state); +Boolean builtin_modulus(InterpreterState *interpreter_state); +Boolean builtin_exponential(InterpreterState *interpreter_state); +Boolean builtin_greater_than(InterpreterState *interpreter_state); +Boolean builtin_greater_than_or_equal_to(InterpreterState *interpreter_state); +Boolean builtin_less_than(InterpreterState *interpreter_state); +Boolean builtin_less_than_or_equal_to(InterpreterState *interpreter_state); +Boolean builtin_equal_to(InterpreterState *interpreter_state); +Boolean builtin_not_equal_to(InterpreterState *interpreter_state); +Boolean builtin_abs(InterpreterState *interpreter_state); +Boolean builtin_acos(InterpreterState *interpreter_state); +Boolean builtin_asin(InterpreterState *interpreter_state); +Boolean builtin_assert(InterpreterState *interpreter_state); +Boolean builtin_at(InterpreterState *interpreter_state); +Boolean builtin_atan(InterpreterState *interpreter_state); +Boolean builtin_atan2(InterpreterState *interpreter_state); +Boolean builtin_bitand(InterpreterState *interpreter_state); +Boolean builtin_bitnot(InterpreterState *interpreter_state); +Boolean builtin_bitor(InterpreterState *interpreter_state); +Boolean builtin_bitxor(InterpreterState *interpreter_state); +Boolean builtin_ceil(InterpreterState *interpreter_state); +Boolean builtin_concat(InterpreterState *interpreter_state); +Boolean builtin_cos(InterpreterState *interpreter_state); +Boolean builtin_depth(InterpreterState *interpreter_state); +Boolean builtin_drop(InterpreterState *interpreter_state); +Boolean builtin_dup(InterpreterState *interpreter_state); +Boolean builtin_each(InterpreterState *interpreter_state); +Boolean builtin_ends_with(InterpreterState *interpreter_state); +Boolean builtin_enum(InterpreterState *interpreter_state); +Boolean builtin_enumerate(InterpreterState *interpreter_state); +Boolean builtin_eval(InterpreterState *interpreter_state); +Boolean builtin_filter(InterpreterState *interpreter_state); +Boolean builtin_find(InterpreterState *interpreter_state); +Boolean builtin_floor(InterpreterState *interpreter_state); +Boolean builtin_fn(InterpreterState *interpreter_state); +Boolean builtin_foldl(InterpreterState *interpreter_state); +Boolean builtin_foldr(InterpreterState *interpreter_state); +Boolean builtin_for(InterpreterState *interpreter_state); +Boolean builtin_format(InterpreterState *interpreter_state); +Boolean builtin_get(InterpreterState *interpreter_state); +Boolean builtin_if(InterpreterState *interpreter_state); +Boolean builtin_impl(InterpreterState *interpreter_state); +Boolean builtin_implements(InterpreterState *interpreter_state); +Boolean builtin_inher(InterpreterState *interpreter_state); +Boolean builtin_lambda(InterpreterState *interpreter_state); +Boolean builtin_length(InterpreterState *interpreter_state); +Boolean builtin_ln(InterpreterState *interpreter_state); +Boolean builtin_log(InterpreterState *interpreter_state); +Boolean builtin_logb(InterpreterState *interpreter_state); +Boolean builtin_map(InterpreterState *interpreter_state); +Boolean builtin_match(InterpreterState *interpreter_state); +Boolean builtin_max(InterpreterState *interpreter_state); +Boolean builtin_mean(InterpreterState *interpreter_state); +Boolean builtin_min(InterpreterState *interpreter_state); +Boolean builtin_not(InterpreterState *interpreter_state); +Boolean builtin_or(InterpreterState *interpreter_state); +Boolean builtin_over(InterpreterState *interpreter_state); +Boolean builtin_pick(InterpreterState *interpreter_state); +Boolean builtin_rand(InterpreterState *interpreter_state); +Boolean builtin_reduce(InterpreterState *interpreter_state); +Boolean builtin_replace(InterpreterState *interpreter_state); +Boolean builtin_reverse(InterpreterState *interpreter_state); +Boolean builtin_roll(InterpreterState *interpreter_state); +Boolean builtin_round(InterpreterState *interpreter_state); +Boolean builtin_seed(InterpreterState *interpreter_state); +Boolean builtin_set(InterpreterState *interpreter_state); +Boolean builtin_shl(InterpreterState *interpreter_state); +Boolean builtin_shr(InterpreterState *interpreter_state); +Boolean builtin_sin(InterpreterState *interpreter_state); +Boolean builtin_slice(InterpreterState *interpreter_state); +Boolean builtin_split(InterpreterState *interpreter_state); +Boolean builtin_sqrt(InterpreterState *interpreter_state); +Boolean builtin_starts_with(InterpreterState *interpreter_state); +Boolean builtin_struct(InterpreterState *interpreter_state); +Boolean builtin_substr(InterpreterState *interpreter_state); +Boolean builtin_sum(InterpreterState *interpreter_state); +Boolean builtin_swap(InterpreterState *interpreter_state); +Boolean builtin_tan(InterpreterState *interpreter_state); +Boolean builtin_trait(InterpreterState *interpreter_state); +Boolean builtin_transpose(InterpreterState *interpreter_state); +Boolean builtin_trim(InterpreterState *interpreter_state); +Boolean builtin_type_of(InterpreterState *interpreter_state); +Boolean builtin_union(InterpreterState *interpreter_state); +Boolean builtin_while(InterpreterState *interpreter_state); +Boolean builtin_window(InterpreterState *interpreter_state); +Boolean builtin_zip(InterpreterState *interpreter_state); + +static inline Boolean hash_table_put_funcs(HashTable *ht, SlsStr key, FunctionItem *item) { + return hash_table_put(ht, key, (void *)item); +} + +Boolean load_builtins(InterpreterState *interpreter_state) { + FunctionItem *func; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_addition}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("+"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_subtraction}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("-"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_multiplication}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("*"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_division}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("/"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_modulus}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("%"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_exponential}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("^"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_greater_than}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR(">"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_greater_than_or_equal_to}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR(">="), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_less_than}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("<"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_less_than_or_equal_to}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("<="), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_equal_to}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("=="), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_not_equal_to}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("!="), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_abs}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("abs"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_acos}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("acos"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_asin}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("asin"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_assert}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("assert"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_at}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("at"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_atan}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("atan"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_atan2}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("atan2"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_bitand}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("bitand"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_bitnot}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("bitnot"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_bitor}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("bitor"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_bitxor}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("bitxor"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_ceil}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("ceil"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_concat}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("concat"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_cos}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("cos"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_depth}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("depth"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_drop}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("drop"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_dup}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("dup"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_each}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("each"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_ends_with}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("ends_with"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_enum}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("enum"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_enumerate}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("enumerate"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_eval}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("eval"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_filter}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("filter"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_find}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("find"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_floor}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("floor"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_fn}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("fn"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_foldl}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("foldl"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_foldr}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("foldr"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_for}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("for"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_format}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("format"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_get}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("get"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_if}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("if"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_impl}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("impl"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_implements}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("implements"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_inher}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("inher"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_lambda}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("lambda"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_length}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("length"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_ln}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("ln"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_log}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("log"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_logb}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("logb"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_map}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("map"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_match}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("match"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_max}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("max"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_mean}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("mean"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_min}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("min"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_not}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("not"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_or}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("or"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_over}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("over"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_pick}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("pick"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_rand}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("rand"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_reduce}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("reduce"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_replace}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("replace"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_reverse}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("reverse"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_roll}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("roll"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_round}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("round"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_seed}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("seed"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_set}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("set"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_shl}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("shl"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_shr}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("shr"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_sin}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("sin"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_slice}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("slice"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_split}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("split"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_sqrt}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("sqrt"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_starts_with}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("starts_with"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_struct}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("struct"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_substr}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("substr"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_sum}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("sum"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_swap}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("swap"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_tan}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("tan"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_trait}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("trait"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_transpose}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("transpose"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_trim}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("trim"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_type_of}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("type_of"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_union}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("union"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_while}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("while"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_window}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("window"), func)) + return FALSE; + + func = (FunctionItem *)malloc(sizeof(FunctionItem)); + if (func == NULL) return FALSE; + *func = (FunctionItem){ .type = FUNCTION_BUILTIN, .builtin = *builtin_zip}; + if (!hash_table_put_funcs(interpreter_state->functions, SLS_STR("zip"), func)) + return FALSE; + + return TRUE; +} + +Boolean builtin_addition(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_subtraction(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_multiplication(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_division(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_modulus(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_exponential(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_greater_than(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_greater_than_or_equal_to(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_less_than(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_less_than_or_equal_to(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_equal_to(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_not_equal_to(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_abs(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_acos(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_asin(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_assert(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_at(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_atan(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_atan2(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_bitand(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_bitnot(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_bitor(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_bitxor(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_ceil(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_concat(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_cos(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_depth(InterpreterState *interpreter_state) { + size_t depth = 0; + for (StackItem *node = interpreter_state->stack; node; node = node->next) + depth++; + return push_token(interpreter_state, (Token){ + .type = TOKEN_INTEGER, + .integer_literal = (IntegerLiteral){ + .type = INTEGER_U64, + .value = (uint64_t)depth, + }, + }); +} + +Boolean builtin_drop(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_dup(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_each(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_ends_with(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_enum(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_enumerate(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_eval(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_filter(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_find(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_floor(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_fn(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_foldl(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_foldr(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_for(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_format(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_get(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_if(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_impl(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_implements(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_inher(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_lambda(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_length(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_ln(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_log(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_logb(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_map(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_match(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_max(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_mean(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_min(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_not(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_or(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_over(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_pick(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_rand(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_reduce(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_replace(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_reverse(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_roll(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_round(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_seed(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_set(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_shl(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_shr(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_sin(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_slice(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_split(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_sqrt(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_starts_with(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_struct(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_substr(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_sum(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_swap(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_tan(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_trait(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_transpose(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_trim(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_type_of(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_union(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_while(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_window(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} + +Boolean builtin_zip(InterpreterState *interpreter_state) { + (void)interpreter_state; + return FALSE; +} diff --git a/SLS_C/src/interpreter.c b/SLS_C/src/interpreter.c index 8aa473b..09519cb 100644 --- a/SLS_C/src/interpreter.c +++ b/SLS_C/src/interpreter.c @@ -9,6 +9,7 @@ #include "sls/interpreter.h" #include "sls/lexer.h" #include "sls/hash_table.h" +#include "sls/builtin.h" static const size_t HASH_TABLE_BUCKET_COUNT = 256; @@ -31,15 +32,15 @@ const char *STACK_TYPES_NAMES[] = { const size_t STACK_TYPE_COUNT = sizeof(STACK_TYPES_NAMES) / sizeof(*STACK_TYPES_NAMES); -static Boolean hash_table_put_funcs(HashTable *ht, SlsStr key, TokenString *item) { +static inline Boolean hash_table_put_funcs(HashTable *ht, SlsStr key, FunctionItem *item) { return hash_table_put(ht, key, (void *)item); } -static TokenString *hash_table_get_funcs(const HashTable *ht, SlsStr key, TokenString *default_item) { - return (TokenString*)hash_table_get(ht, key, (void *)default_item); +static inline FunctionItem *hash_table_get_funcs(const HashTable *ht, SlsStr key, FunctionItem *default_item) { + return (FunctionItem*)hash_table_get(ht, key, (void *)default_item); } -static Boolean push_token(InterpreterState *interpreter_state, Token token) { +Boolean push_token(InterpreterState *interpreter_state, Token token) { StackType type; switch (token.type) { case TOKEN_EOF: @@ -99,6 +100,7 @@ static Boolean push_token(InterpreterState *interpreter_state, Token token) { } StackItem *item = (StackItem *)malloc(sizeof(StackItem)); + if (item == NULL) return FALSE; item->type = type; item->next = interpreter_state->stack; interpreter_state->stack = item; @@ -147,10 +149,20 @@ static Boolean push_token(InterpreterState *interpreter_state, Token token) { item->token_string = copy_token_string(token.token_string); break; } + + return TRUE; } static Boolean execute_func(InterpreterState *interpreter_state, SlsStr key) { - + FunctionItem *func = hash_table_get_funcs(interpreter_state->functions, key, NULL); + if (func == NULL) return FALSE; + switch (func->type) { + case FUNCTION_BUILTIN: + return func->builtin(interpreter_state); + case FUNCTION_TOKEN_STRING: + return FALSE; + } + return FALSE; } Boolean execute(InterpreterState *interpreter_state, LexerTokenResult *token) { @@ -162,9 +174,14 @@ Boolean execute(InterpreterState *interpreter_state, LexerTokenResult *token) { InterpreterState *interpreter_create() { InterpreterState *interpreter_state = (InterpreterState *)malloc(sizeof(InterpreterState)); + if (interpreter_state == NULL) + return NULL; interpreter_state->stack = NULL; interpreter_state->functions = init_hash_table(HASH_TABLE_BUCKET_COUNT); - + if (!load_builtins(interpreter_state)) { + interpreter_delete(interpreter_state); + return NULL; + } return interpreter_state; } diff --git a/SLS_C/src/repl.c b/SLS_C/src/repl.c index 82ad5b1..5ea6d7c 100644 --- a/SLS_C/src/repl.c +++ b/SLS_C/src/repl.c @@ -16,6 +16,56 @@ static const SlsStr REPL_FILE_NAME = SLS_STR_CONST(""); +void print_top_of_stack(InterpreterState *interpreter_state) { + if (interpreter_state->stack == NULL) + return; + switch (interpreter_state->stack->type) { + case STACK_IDENTIFIER: + printf("#0: ::%s\n", interpreter_state->stack->identifier.name.str); + break; + case STACK_I64: + printf("#0: %ld\n", interpreter_state->stack->i64); + break; + case STACK_I32: + printf("#0: %d:i32\n", interpreter_state->stack->i32); + break; + case STACK_I16: + printf("#0: %d:i16\n", interpreter_state->stack->i16); + break; + case STACK_I8: + printf("#0: %d:8\n", interpreter_state->stack->i8); + break; + case STACK_U64: + printf("#0: %lu:u64\n", interpreter_state->stack->u64); + break; + case STACK_U32: + printf("#0: %u:32\n", interpreter_state->stack->u32); + break; + case STACK_U16: + printf("#0: %u:16\n", interpreter_state->stack->u16); + break; + case STACK_U8: + printf("#0: %u:8\n", interpreter_state->stack->u8); + break; + case STACK_FLOAT: + printf("#0: %f:f32\n", interpreter_state->stack->f32); + break; + case STACK_DOUBLE: + printf("#0: %f\n", interpreter_state->stack->f64); + break; + case STACK_CHARACTER: + printf("#0: %c\n", interpreter_state->stack->character); + break; + case STACK_BOOLEAN: + if (interpreter_state->stack->boolean) printf("#0: TRUE\n"); + else printf("#0: FALSE\n"); + break; + case STACK_TOKEN_STRING: + printf("#0: \n"); + break; + } +} + int repl(int argc, char *argv[]) { (void)argc; (void)argv; @@ -50,12 +100,13 @@ int repl(int argc, char *argv[]) { break; } else if (!execute(interpreter_state, head)) { - printf("A runtime error occurred!"); + printf("A runtime error occurred!\n"); break; } head = head->next; } clean_token_result(result.result); + print_top_of_stack(interpreter_state); } sls_str_free(&code); }