diff options
Diffstat (limited to 'src/parser.c')
-rw-r--r-- | src/parser.c | 57 |
1 files changed, 45 insertions, 12 deletions
diff --git a/src/parser.c b/src/parser.c index e16fc4a..2429f68 100644 --- a/src/parser.c +++ b/src/parser.c | |||
@@ -3,7 +3,13 @@ | |||
3 | 3 | ||
4 | static Object **objects = NULL; | 4 | static Object **objects = NULL; |
5 | static Root *roots = NULL; | 5 | static Root *roots = NULL; |
6 | static Environment **environments = NULL; | ||
6 | 7 | ||
8 | static char *builtins [] = { | ||
9 | "+", "-", "*", "/", "%", | ||
10 | "=", "<", ">", "<=", ">=", | ||
11 | "not", "and", "or", | ||
12 | }; | ||
7 | 13 | ||
8 | uint64_t | 14 | uint64_t |
9 | symbol_hash(const HashTable *table, void *key) { | 15 | symbol_hash(const HashTable *table, void *key) { |
@@ -382,9 +388,16 @@ parse_tree(Parser *parser, Errors *errors) { | |||
382 | return NULL; | 388 | return NULL; |
383 | } | 389 | } |
384 | 390 | ||
391 | void | ||
392 | scope_check(Environment *env) { | ||
393 | // STUB | ||
394 | } | ||
395 | |||
385 | Root * | 396 | Root * |
386 | parse(Token *tokens, Errors *errors) { | 397 | parse(Token *tokens, Errors *errors) { |
387 | array_init(roots, 0); | 398 | array_init(roots, 0); |
399 | array_init(objects, 0); | ||
400 | array_init(environments, 0); | ||
388 | Parser parser = { | 401 | Parser parser = { |
389 | .tokens = tokens, | 402 | .tokens = tokens, |
390 | .current = 0, | 403 | .current = 0, |
@@ -400,27 +413,39 @@ parse(Token *tokens, Errors *errors) { | |||
400 | array_push(roots, root); | 413 | array_push(roots, root); |
401 | } | 414 | } |
402 | 415 | ||
403 | // TEST INSERTION/LOOKUP. | 416 | // Prepare global environment of builtin functions. |
404 | HashTable *table = ht_init(symbol_hash, object_equal); | 417 | Environment *global_env = env_alloc(NULL); |
405 | ht_insert(table, &roots[0][0], &roots[1][0]); | 418 | size_t n_builtins = sizeof(builtins) / sizeof(char*); |
406 | ht_insert(table, &roots[2][0], &roots[3][0]); | 419 | for (size_t i = 0; i < n_builtins; i++) { |
407 | Object *val = ht_lookup(table, &roots[2][0]); | 420 | // Prepare builtin symbol. |
408 | object_display(val); | 421 | char *str = builtins[i]; |
409 | val = ht_lookup(table, &roots[0][0]); | 422 | size_t str_n = strlen(str); |
410 | object_display(val); | 423 | Object *symbol = object_alloc((Token){0}, OBJ_TYPE_SYMBOL); |
411 | ht_free(table); | 424 | array_init(symbol->text, str_n); |
425 | array_insert(symbol->text, str, str_n); | ||
426 | |||
427 | // Insert in global table. | ||
428 | ht_insert(global_env->table, symbol, symbol); | ||
429 | } | ||
412 | 430 | ||
413 | // Perform semantic analysis. | 431 | // Perform semantic analysis. |
432 | scope_check(global_env); | ||
414 | // TODO: Check that symbols are defined before usage. | 433 | // TODO: Check that symbols are defined before usage. |
415 | // TODO: Remove unnecessary statements. | 434 | // TODO: Remove unnecessary statements. |
416 | return roots; | 435 | return roots; |
417 | } | 436 | } |
418 | 437 | ||
438 | Environment * | ||
439 | env_alloc(Environment *parent) { | ||
440 | Environment *env = malloc(sizeof(Environment)); | ||
441 | env->table = ht_init(symbol_hash, (EqFunc*)object_equal); | ||
442 | env->parent = parent; | ||
443 | array_push(environments, env); | ||
444 | return env; | ||
445 | } | ||
446 | |||
419 | Object * | 447 | Object * |
420 | object_alloc(Token tok, ObjectType type) { | 448 | object_alloc(Token tok, ObjectType type) { |
421 | if (objects == NULL) { | ||
422 | array_init(objects, 0); | ||
423 | } | ||
424 | Object *node = malloc(sizeof(Object)); | 449 | Object *node = malloc(sizeof(Object)); |
425 | node->line = tok.line; | 450 | node->line = tok.line; |
426 | node->col = tok.col; | 451 | node->col = tok.col; |
@@ -452,6 +477,14 @@ free_objects(void) { | |||
452 | } | 477 | } |
453 | array_free(objects); | 478 | array_free(objects); |
454 | } | 479 | } |
480 | if (environments != NULL) { | ||
481 | for (size_t i = 0; i < array_size(environments); i++) { | ||
482 | Environment *env = environments[i]; | ||
483 | ht_free(env->table); | ||
484 | free(env); | ||
485 | } | ||
486 | array_free(environments); | ||
487 | } | ||
455 | array_free(roots); | 488 | array_free(roots); |
456 | } | 489 | } |
457 | 490 | ||