fwrite(gens[i]->string, 1, gens[i]->string_length, stdout);
} else if(gens[i]->type == SN_TYPE_VOID) {
printf("<void>");
+ } else if(gens[i]->type == SN_TYPE_FUNCTION) {
}
fflush(stdout);
}
return gen;
}
+struct sn_generic* defvar_handler(struct sn_interpreter* sn, int args, struct sn_generic** gens) {
+ struct sn_generic* gen = malloc(sizeof(struct sn_generic));
+ int i;
+ if(args > 1) {
+ for(i = 1; i < args; i += 2) {
+ if(gens[i + 1] == NULL) break;
+ if(gens[i]->type == SN_TYPE_STRING) {
+ char* str = malloc(gens[i]->string_length + 1);
+ gens[i + 1]->used = true;
+ memcpy(str, gens[i]->string, gens[i]->string_length);
+ str[gens[i]->string_length] = 0;
+ sn_set_variable(sn, str, gens[i + 1]);
+ free(str);
+ }
+ }
+ }
+ gen->type = SN_TYPE_VOID;
+ return gen;
+}
+
struct sn_generic* eval_handler(struct sn_interpreter* sn, int args, struct sn_generic** gens) {
int i;
int result = 0;
sn_set_handler(sn, "/", math_handler);
sn_set_handler(sn, "print", print_handler);
sn_set_handler(sn, "eval", eval_handler);
+ sn_set_handler(sn, "define-var", defvar_handler);
return sn;
}
bool replaced = false;
for(i = 0; sn->variables[i] != NULL; i++) {
if(strcmp(sn->variables[i]->key, name) == 0) {
- sn_generic_free(sn->variables[i]->value);
sn->variables[i]->value = gen;
replaced = true;
break;
bool replaced = false;
for(i = 0; sn->variables[i] != NULL; i++) {
if(strcmp(sn->variables[i]->key, name) == 0) {
- sn_generic_free(sn->variables[i]->value);
sn->variables[i]->handler = handler;
replaced = true;
break;
if(sn_run(sn, gens[i]) != 0) {
r = 1;
}
- sn_generic_free(gens[i]);
}
}
+ for(i = 0; gens[i] != NULL; i++) sn_generic_free(gens[i]);
free(gens);
}
return r;
};
*/
+struct sn_generic* sn_generic_dup(struct sn_generic* g) {
+ if(g == NULL) return NULL;
+ struct sn_generic* r = malloc(sizeof(struct sn_generic));
+ r->type = g->type;
+ if(r->type == SN_TYPE_STRING) {
+ r->string = malloc(g->string_length);
+ r->string_length = g->string_length;
+ memcpy(r->string, g->string, r->string_length);
+ } else if(r->type == SN_TYPE_DOUBLE) {
+ r->number = g->number;
+ } else if(r->type == SN_TYPE_FUNCTION) {
+ r->name = sn_strdup(g->name);
+ }
+ return r;
+}
+
void push_stack_generic(struct sn_generic* gen, struct sn_generic* pushthis) {
if(gen->type == SN_TYPE_TREE) {
struct sn_generic** old_gen = gen->tree->args;
if(mode == SN_TYPE_STRING) {
newgen->string = sn_strdup(buf);
newgen->string_length = strlen(buf);
- } else if(mode == SN_TYPE_FUNCTION) {
+ } else if(mode == SN_TYPE_FUNCTION || mode == SN_TYPE_VARIABLE) {
newgen->name = sn_strdup(buf);
} else if(mode == SN_TYPE_DOUBLE) {
newgen->number = atof(buf);
gn_stack[br]->tree = malloc(sizeof(struct sn_tree));
gn_stack[br]->tree->args = malloc(sizeof(struct sn_generic*));
gn_stack[br]->tree->args[0] = NULL;
+ gn_stack[br]->used = false;
index_stack[br] = 0;
br++;
} else if(c == ')') {
if(argbufmode == SN_TYPE_VOID) {
if(c == '.' || (c >= '0' && c <= '9')) {
argbufmode = SN_TYPE_DOUBLE;
- } else {
+ } else if(index_stack[br - 1] == 0) {
argbufmode = SN_TYPE_FUNCTION;
+ } else {
+ argbufmode = SN_TYPE_VARIABLE;
}
}
}
free(g->string);
} else if(g->type == SN_TYPE_TREE) {
sn_tree_free(g->tree);
+ } else if(g->type == SN_TYPE_FUNCTION || g->type == SN_TYPE_VARIABLE) {
+ free(g->name);
}
free(g);
}
#ifndef __SERENADE_PARSER_H__
#define __SERENADE_PARSER_H__
-enum types { SN_TYPE_DOUBLE = 0, SN_TYPE_STRING, SN_TYPE_TREE, SN_TYPE_PTR, SN_TYPE_FUNCTION, SN_TYPE_VOID };
+#include <stdbool.h>
+
+enum types { SN_TYPE_DOUBLE = 0, SN_TYPE_STRING, SN_TYPE_TREE, SN_TYPE_PTR, SN_TYPE_FUNCTION, SN_TYPE_VOID, SN_TYPE_VARIABLE };
struct sn_generic {
int type;
void* ptr;
char* name;
struct sn_tree* tree;
+ bool used;
};
struct sn_tree {
struct sn_generic** sn_parse(char* data, unsigned long long size);
void sn_generic_free(struct sn_generic* g);
+struct sn_generic* sn_generic_dup(struct sn_generic* g);
void sn_tree_free(struct sn_tree* t);
#endif
if(op->type == SN_TYPE_TREE) {
op = _sn_run(sn, op);
}
- int j;
- for(j = 0; gen->tree->args[j]; j++)
- ;
- struct sn_generic** args = malloc(sizeof(struct sn_generic*) * (j));
- int argc = j;
- for(j = 0; gen->tree->args[j]; j++) {
- args[j] = _sn_run(sn, gen->tree->args[j]);
- }
struct sn_generic* r = malloc(sizeof(struct sn_generic));
r->type = SN_TYPE_VOID;
if(op->type != SN_TYPE_FUNCTION) {
fprintf(stderr, "Cannot call non-function (Type %d)\n", op->type);
- free(args);
free(r);
return NULL;
} else {
bool called = false;
+ int j;
+ for(j = 0; gen->tree->args[j]; j++)
+ ;
+ struct sn_generic** args = malloc(sizeof(struct sn_generic*) * (j));
+ int argc = j;
+ for(j = 0; gen->tree->args[j]; j++) {
+ args[j] = _sn_run(sn, gen->tree->args[j]);
+ }
for(j = 0; sn->variables[j] != NULL; j++) {
if(strcmp(sn->variables[j]->key, op->name) == 0) {
called = true;
free(r);
return NULL;
}
+ free(args);
+ }
+ return r;
+ } else if(gen->type == SN_TYPE_VARIABLE) {
+ struct sn_generic* r = malloc(sizeof(struct sn_generic));
+ r->type = SN_TYPE_VOID;
+ int i;
+ for(i = 0; sn->variables[i] != NULL; i++) {
+ if(strcmp(sn->variables[i]->key, gen->name) == 0) {
+ free(r);
+ struct sn_generic* var = sn->variables[i]->value;
+ if(var != NULL) {
+ return sn->variables[i]->value;
+ }
+ break;
+ }
}
- free(args);
return r;
} else {
return gen;