From 288727f09a1b3458c268497d111349e608c3f9fa Mon Sep 17 00:00:00 2001 From: "bozo.kopic" Date: Tue, 2 Aug 2022 01:20:12 +0200 Subject: init --- src_c/ctx.c | 231 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 231 insertions(+) create mode 100644 src_c/ctx.c (limited to 'src_c/ctx.c') diff --git a/src_c/ctx.c b/src_c/ctx.c new file mode 100644 index 0000000..693ea53 --- /dev/null +++ b/src_c/ctx.c @@ -0,0 +1,231 @@ +#include "ctx.h" +#include "function.h" +#include "syntax.h" + + +static lsp_bool_t contains_symbol(lsp_mem_t *m, lsp_addr_t ctx, + lsp_addr_t symbol) { + while (ctx != m->nil) { + lsp_addr_t entry = lsp_mem_get_pair_first(m, ctx); + lsp_addr_t entry_symbol = lsp_mem_get_pair_first(m, entry); + + if (lsp_mem_eq(m, entry_symbol, symbol)) + return true; + + ctx = lsp_mem_get_pair_second(m, ctx); + } + + return false; +} + + +static lsp_status_t remove_symbol(lsp_mem_t *m, lsp_addr_t ctx, + lsp_addr_t symbol) { + lsp_addr_t list = lsp_mem_get_pair_first(m, ctx); + + lsp_addr_t result = m->nil; + lsp_addr_t result_last = m->nil; + lsp_status_t status = LSP_SUCCESS; + + while (list != m->nil) { + lsp_addr_t entry = lsp_mem_get_pair_first(m, list); + lsp_addr_t entry_symbol = lsp_mem_get_pair_first(m, entry); + list = lsp_mem_get_pair_second(m, list); + + if (lsp_mem_eq(m, entry_symbol, symbol)) { + if (result == m->nil) { + result = list; + status = lsp_mem_inc_ref(m, list); + + } else { + lsp_mem_set_pair_second(m, result_last, list); + } + + break; + } + + lsp_addr_t new_result_last; + status = lsp_mem_create_pair(m, entry, m->nil, &new_result_last); + if (status != LSP_SUCCESS) + break; + + if (result == m->nil) { + result = new_result_last; + + } else { + lsp_mem_set_pair_second(m, result_last, new_result_last); + lsp_mem_dec_ref(m, new_result_last); + } + + result_last = new_result_last; + } + + if (status == LSP_SUCCESS) + lsp_mem_set_pair_first(m, ctx, result); + + lsp_mem_dec_ref(m, result); + return status; +} + + +lsp_status_t lsp_ctx_create(lsp_mem_t *m, lsp_addr_t *ctx) { + lsp_addr_t list = m->nil; + lsp_addr_t list_last = m->nil; + lsp_status_t status = LSP_SUCCESS; + + for (uint8_t i = 0; status == LSP_SUCCESS && lsp_syntaxes[i].name; ++i) { + lsp_addr_t symbol; + status = + lsp_mem_create_symbol_from_char(m, lsp_syntaxes[i].name, &symbol); + if (status != LSP_SUCCESS) + break; + + lsp_addr_t value; + status = lsp_mem_create_builtin_syntax(m, i, &value); + if (status != LSP_SUCCESS) { + lsp_mem_dec_ref(m, symbol); + break; + } + + lsp_addr_t entry; + status = lsp_mem_create_pair(m, symbol, value, &entry); + lsp_mem_dec_ref(m, symbol); + lsp_mem_dec_ref(m, value); + if (status != LSP_SUCCESS) + break; + + lsp_addr_t new_list_last; + status = lsp_mem_create_pair(m, entry, m->nil, &new_list_last); + lsp_mem_dec_ref(m, entry); + if (status != LSP_SUCCESS) + break; + + if (list == m->nil) { + list = new_list_last; + + } else { + lsp_mem_set_pair_second(m, list_last, new_list_last); + lsp_mem_dec_ref(m, new_list_last); + } + + list_last = new_list_last; + } + + for (uint8_t i = 0; status == LSP_SUCCESS && lsp_functions[i].name; ++i) { + lsp_addr_t symbol; + status = + lsp_mem_create_symbol_from_char(m, lsp_functions[i].name, &symbol); + if (status != LSP_SUCCESS) + break; + + lsp_addr_t value; + status = lsp_mem_create_builtin_function(m, i, &value); + if (status != LSP_SUCCESS) { + lsp_mem_dec_ref(m, symbol); + break; + } + + lsp_addr_t entry; + status = lsp_mem_create_pair(m, symbol, value, &entry); + lsp_mem_dec_ref(m, symbol); + lsp_mem_dec_ref(m, value); + if (status != LSP_SUCCESS) + break; + + lsp_addr_t new_list_last; + status = lsp_mem_create_pair(m, entry, m->nil, &new_list_last); + lsp_mem_dec_ref(m, entry); + if (status != LSP_SUCCESS) + break; + + if (list == m->nil) { + list = new_list_last; + + } else { + lsp_mem_set_pair_second(m, list_last, new_list_last); + lsp_mem_dec_ref(m, new_list_last); + } + + list_last = new_list_last; + } + + if (status == LSP_SUCCESS) + status = lsp_mem_create_pair(m, list, m->nil, ctx); + + lsp_mem_dec_ref(m, list); + return status; +} + + +lsp_status_t lsp_ctx_copy(lsp_mem_t *m, lsp_addr_t ctx, lsp_addr_t *result) { + lsp_addr_t list = lsp_mem_get_pair_first(m, ctx); + return lsp_mem_create_pair(m, list, m->nil, result); +} + + +lsp_status_t lsp_ctx_add(lsp_mem_t *m, lsp_addr_t ctx, lsp_addr_t symbol, + lsp_addr_t value) { + lsp_status_t status; + + if (contains_symbol(m, ctx, symbol)) { + status = remove_symbol(m, ctx, symbol); + if (status != LSP_SUCCESS) + return status; + } + + lsp_addr_t list = lsp_mem_get_pair_first(m, ctx); + + lsp_addr_t entry; + status = lsp_mem_create_pair(m, symbol, value, &entry); + if (status != LSP_SUCCESS) + return status; + + status = lsp_mem_create_pair(m, entry, list, &list); + lsp_mem_dec_ref(m, entry); + if (status != LSP_SUCCESS) + return status; + + lsp_mem_set_pair_first(m, ctx, list); + lsp_mem_dec_ref(m, list); + return LSP_SUCCESS; +} + + +lsp_status_t lsp_ctx_set(lsp_mem_t *m, lsp_addr_t ctx, lsp_addr_t symbol, + lsp_addr_t value) { + lsp_addr_t list = lsp_mem_get_pair_first(m, ctx); + + while (list != m->nil) { + lsp_addr_t entry = lsp_mem_get_pair_first(m, list); + lsp_addr_t entry_symbol = lsp_mem_get_pair_first(m, entry); + + if (lsp_mem_eq(m, symbol, entry_symbol)) { + lsp_mem_set_pair_second(m, entry, value); + return LSP_SUCCESS; + } + + list = lsp_mem_get_pair_second(m, list); + } + + return LSP_ERR_CTX; +} + + +lsp_status_t lsp_ctx_get(lsp_mem_t *m, lsp_addr_t ctx, lsp_addr_t symbol, + lsp_addr_t *value) { + lsp_addr_t list = lsp_mem_get_pair_first(m, ctx); + + while (list != m->nil) { + lsp_addr_t entry = lsp_mem_get_pair_first(m, list); + lsp_addr_t entry_symbol = lsp_mem_get_pair_first(m, entry); + + if (lsp_mem_eq(m, symbol, entry_symbol)) { + *value = lsp_mem_get_pair_second(m, entry); + return lsp_mem_inc_ref(m, *value); + } + + list = lsp_mem_get_pair_second(m, list); + } + + return LSP_ERR_CTX; +} -- cgit v1.2.3-70-g09d2