From 17d8755c06e7770674ed3b1c051dde79d4222d00 Mon Sep 17 00:00:00 2001 From: nishi <nishi@0f02c867-ac3d-714e-8a88-971ba1f6efcf> Date: Tue, 30 Apr 2024 00:34:57 +0000 Subject: [PATCH] trying to fix git-svn-id: file:///raid/svn-main/nishi-serenade/trunk@81 0f02c867-ac3d-714e-8a88-971ba1f6efcf --- Serenade/interpreter.c | 8 ++--- Serenade/parser.c | 78 +++++++++++++++++++++++++++++++++++++++--- Serenade/parser.h | 4 +-- 3 files changed, 79 insertions(+), 11 deletions(-) diff --git a/Serenade/interpreter.c b/Serenade/interpreter.c index f485d79..460586d 100644 --- a/Serenade/interpreter.c +++ b/Serenade/interpreter.c @@ -182,14 +182,14 @@ void sn_interpreter_free(struct sn_interpreter* sn) { int i; for(i = 0; sn->variables[i] != NULL; i++) { free(sn->variables[i]->key); - if(sn->variables[i]->value != NULL) sn_generic_free(sn->variables[i]->value); + if(sn->variables[i]->value != NULL) sn_generic_free(sn, sn->variables[i]->value); free(sn->variables[i]); } free(sn->variables); for(i = 0; sn->generics[i] != NULL; i++) { int j; for(j = 0; sn->generics[i][j] != NULL; j++){ - sn_generic_free(sn->generics[i][j]); + sn_generic_free(sn, sn->generics[i][j]); } free(sn->generics[i]); } @@ -214,7 +214,7 @@ struct sn_interpreter_kv* sn_set_variable(struct sn_interpreter* sn, const char* if(!global) { for(i = 0; sn->local_variables[i] != NULL; i++) { if(strcmp(sn->local_variables[i]->key, name) == 0) { - sn->local_variables[i]->value = sn_generic_dup(gen); + sn->local_variables[i]->value = gen; replaced = true; return sn->local_variables[i]; } @@ -229,7 +229,7 @@ struct sn_interpreter_kv* sn_set_variable(struct sn_interpreter* sn, const char* } sn->local_variables[i] = malloc(sizeof(struct sn_generic)); sn->local_variables[i]->key = sn_strdup(name); - sn->local_variables[i]->value = sn_generic_dup(gen); + sn->local_variables[i]->value = gen; sn->local_variables[i]->handler = NULL; if(gen != NULL && gen->type == SN_TYPE_FUNCTION) sn->local_variables[i]->handler = gen->handler; sn->local_variables[i + 1] = NULL; diff --git a/Serenade/parser.c b/Serenade/parser.c index 7ebb9c0..92b7b60 100644 --- a/Serenade/parser.c +++ b/Serenade/parser.c @@ -229,23 +229,91 @@ struct sn_generic** sn_parse(char* data, unsigned long long size) { return gens; } -void sn_generic_free(struct sn_generic* g) { +void sn_generic_free(struct sn_interpreter* sn, struct sn_generic* g) { if(g->type == SN_TYPE_STRING) { free(g->string); } else if(g->type == SN_TYPE_TREE) { - sn_tree_free(g->tree); + sn_tree_free(sn, g->tree); } else if(g->type == SN_TYPE_FUNCTION || g->type == SN_TYPE_VARIABLE) { free(g->name); } - fprintf(stderr, "type %d free\n", g->type); + printf("freed type %d\n", g->type); free(g); + if(sn == NULL) return; + int i; + for(i = 0; sn->generics[i] != NULL; i++); + struct sn_generic*** gens = malloc(sizeof(struct sn_generic**) * (i + 1)); + for(i = 0; sn->generics[i] != NULL; i++) gens[i] = sn->generics[i]; + gens[i] = NULL; + for(i = 0; sn->generics[i] != NULL; i++){ + int j; + for(j = 0; sn->generics[i][j] != NULL; j++){ + struct sn_generic** oldgens = gens[i]; + int k; + int count = 0; + int matched = 0; + for(k = 0; oldgens[k] != NULL; k++){ + if(oldgens[k] != g){ + count++; + }else{ + matched++; + } + } + if(matched == 0) continue; + gens[i] = malloc(sizeof(struct sn_generic*) * (count + 1)); + count = 0; + for(k = 0; oldgens[k] != NULL; k++){ + if(oldgens[k] != g){ + gens[i][count] = oldgens[k]; + count++; + } + } + gens[i][count] = NULL; + free(oldgens[k]); + } + } + free(sn->generics); + sn->generics = gens; + + for(i = 0; sn->variables[i] != NULL; i++); + struct sn_interpreter_kv** kvs = malloc(sizeof(struct sn_interpreter_kv*) * (i + 1)); + for(i = 0; sn->variables[i] != NULL; i++) kvs[i] = sn->variables[i]; + kvs[i] = NULL; + for(i = 0; sn->variables[i] != NULL; i++){ + struct sn_interpreter_kv** oldkvs = kvs; + int j; + int count = 0; + int matched = 0; + for(j = 0; oldkvs[j] != NULL; j++){ + if(oldkvs[j]->value != g){ + count++; + }else{ + matched++; + } + } + if(matched == 0) continue; + kvs = malloc(sizeof(struct sn_interpreter_kv*) * (count + 1)); + count = 0; + for(j = 0; oldkvs[j] != NULL; j++){ + if(oldkvs[j]->value != g){ + kvs[count] = oldkvs[j]; + count++; + }else{ + free(oldkvs[j]->key); + } + } + kvs[count] = NULL; + free(oldkvs); + } + free(sn->variables); + sn->variables = kvs; } -void sn_tree_free(struct sn_tree* t) { +void sn_tree_free(struct sn_interpreter* sn, struct sn_tree* t) { if(t->args != NULL) { int i; for(i = 0; t->args[i] != NULL; i++) { - sn_generic_free(t->args[i]); + sn_generic_free(sn, t->args[i]); } free(t->args); } diff --git a/Serenade/parser.h b/Serenade/parser.h index 373542c..7bd9101 100644 --- a/Serenade/parser.h +++ b/Serenade/parser.h @@ -58,8 +58,8 @@ struct sn_tree { }; struct sn_generic** sn_parse(char* data, unsigned long long size); -void sn_generic_free(struct sn_generic* g); +void sn_generic_free(struct sn_interpreter* sn, struct sn_generic* g); struct sn_generic* sn_generic_dup(struct sn_generic* g); -void sn_tree_free(struct sn_tree* t); +void sn_tree_free(struct sn_interpreter* sn, struct sn_tree* t); #endif -- 2.43.0