diff options
author | kdx <kdx@42l.fr> | 2023-03-17 02:26:25 +0100 |
---|---|---|
committer | kdx <kdx@42l.fr> | 2023-03-17 02:26:25 +0100 |
commit | 4160e9650bcfe7449beb150cdf8196b768a92eb3 (patch) | |
tree | 14d4e2d4131d3c7a198466ba899efa5978808686 | |
parent | a60f03db9ef3eb65b8898a9bf0ad70fbc2d2cc53 (diff) | |
download | golem-4160e9650bcfe7449beb150cdf8196b768a92eb3.tar.gz |
extract scope
-rwxr-xr-x | debug.sh | 2 | ||||
-rw-r--r-- | group.c | 23 | ||||
-rw-r--r-- | group.h | 2 | ||||
-rw-r--r-- | main.c | 18 | ||||
-rw-r--r-- | scope.c | 27 | ||||
-rw-r--r-- | scope.h | 4 | ||||
-rw-r--r-- | token.c | 31 | ||||
-rw-r--r-- | token.h | 2 |
8 files changed, 101 insertions, 8 deletions
diff --git a/debug.sh b/debug.sh new file mode 100755 index 0000000..eb8f5ab --- /dev/null +++ b/debug.sh @@ -0,0 +1,2 @@ +#!/bin/sh +gcc -O0 -g -std=c99 -Wall -Wextra -o golem *.c @@ -48,6 +48,7 @@ group_create(Token **list, Token *begin, Token *end) group->type = TOK_GROUP; group->group.type = GROUP_NONE; group->group.tokens = begin; + group->group.scope = NULL; group->prev = begin->prev; group->next = end->next; begin->prev = NULL; @@ -61,6 +62,28 @@ group_create(Token **list, Token *begin, Token *end) return group; } +void +group_extract(Token **list, Token *group) +{ + if (group->type != TOK_GROUP) + return; + if (group->group.scope != NULL) + token_destroy(group->group.scope); + if (*list == group) { + if ((*list)->next != NULL) { + (*list)->next->prev = group->group.tokens; + token_last(group->group.tokens)->next = (*list)->next; + } + *list = group->group.tokens; + } else { + if (group->prev != NULL) + group->prev->next = group->group.tokens; + if (group->next != NULL) + group->next->prev = token_last(group->group.tokens); + } + free(group); +} + int group_scope(Token **list) { @@ -20,9 +20,11 @@ struct Token; typedef struct { unsigned int type; struct Token *tokens; + struct Token *scope; } Group; struct Token *group_create(struct Token **l, struct Token *b, struct Token *e); +void group_extract(struct Token **list, struct Token *group); int group_scope(struct Token **list); int group_funcall(struct Token **list); int group_deref(struct Token **list); @@ -5,6 +5,7 @@ #include "group.h" #include "identify.h" #include "check.h" +#include "scope.h" #include <stdio.h> #include <stdlib.h> @@ -48,10 +49,21 @@ main(int argc, char **argv) identify(tokens, identify_else, GROUP_ELSE, 1); identify(tokens, identify_while, GROUP_WHILE, 1); identify(tokens, identify_expression, GROUP_EXPRESSION, 1); - if (check_atom(tokens)) - fprintf(stderr, "unidentified atoms are left\n"); - else + do { + if (check_atom(tokens)) { + fprintf(stderr, "unidentified atoms are left\n"); + break; + } + Token *group = group_create(&tokens, tokens, + token_last(tokens)); + if (group == NULL) { + fprintf(stderr, "group_create failed\n"); + break; + } + group->group.type = GROUP_SCOPE; + scope_extract(tokens); token_print(tokens, 1, 0); + } while(0); token_destroy(tokens); } @@ -0,0 +1,27 @@ +#include "scope.h" +#include "group.h" +#include "token.h" +#include <stdio.h> + +void +scope_extract(Token *list) +{ + // Recurse in child scopes. + for (Token *e = list->group.tokens; e != NULL; e = e->next) + if (e->type == TOK_GROUP) + scope_extract(e); + if (!token_isgroup(list, GROUP_SCOPE)) + return; + + // Extract let groups. + Token *e = list->group.tokens; + while (e != NULL) + if (token_isgroup(e, GROUP_LET)) { + token_append(&list->group.scope, + token_extract(&list->group.tokens, e)); + group_extract(&list->group.scope, + token_last(list->group.scope)); + e = list->group.tokens; // XXX: this is slow + } else + e = e->next; +} @@ -0,0 +1,4 @@ +#pragma once +#include "token.h" + +void scope_extract(Token *list); @@ -24,8 +24,10 @@ token_destroy(Token *token) { while (token != NULL) { Token *next = token->next; - if (token->type == TOK_GROUP) + if (token->type == TOK_GROUP) { token_destroy(token->group.tokens); + token_destroy(token->group.scope); + } free(token); token = next; } @@ -39,9 +41,7 @@ token_append(Token **list, Token *elem) return *list; } - Token *end = *list; - while (end->next != NULL) - end = end->next; + Token *end = token_last(*list); end->next = elem; elem->prev = end; return *list; @@ -50,13 +50,22 @@ token_append(Token **list, Token *elem) void token_delete(Token **list, Token *elem) { + token_extract(list, elem); + free(elem); +} + +Token * +token_extract(Token **list, Token *elem) +{ if (elem->prev != NULL) elem->prev->next = elem->next; if (elem->next != NULL) elem->next->prev = elem->prev; if (*list == elem) *list = elem->next; - free(elem); + elem->prev = NULL; + elem->next = NULL; + return elem; } Token * @@ -97,6 +106,8 @@ token_print(Token *token, int recurse, int depth) if (token->type == TOK_GROUP) { printf("type: TOK_GROUP group.type: %c\n", token->group.type); + if (token->group.scope != NULL) + token_print(token->group.scope, 1, depth); token_print(token->group.tokens, 1, depth + 1); } else { printf("type: %c slice: ", token->type); @@ -125,3 +136,13 @@ token_len(Token *token) } return len; } + +Token * +token_last(Token *token) +{ + if (token == NULL) + return NULL; + while (token->next != NULL) + token = token->next; + return token; +} @@ -39,8 +39,10 @@ Token *token_create(Slice slice, unsigned int type); void token_destroy(Token *token); Token *token_append(Token **list, Token *elem); void token_delete(Token **list, Token *elem); +Token *token_extract(Token **list, Token *elem); Token *token_search(Token *list, unsigned int type); Token *token_search_closing(Token *list, unsigned int type, unsigned int opn); Token *token_print(Token *token, int recurse, int depth); int token_isgroup(Token *token, unsigned int type); int token_len(Token *token); +Token *token_last(Token *token); |