From 02e9098d3dfc679137641c977bb9938ad9bacebb Mon Sep 17 00:00:00 2001 From: Dale Weiler Date: Tue, 10 Apr 2012 01:03:52 -0400 Subject: [PATCH] Fixed parsing issues, added some parser tests. --- alloc.c | 12 ------------ gmqcc.h | 21 ++++++++++++--------- lex.c | 31 +++++++++++++++++++------------ parse.c | 40 +++++++++++++--------------------------- test/tree.qc | 22 ++++++++++++++++++++++ test/typedef.qc | 11 +++++++++++ test/types.qc | 5 +++++ typedef.c | 15 +++++++++++---- 8 files changed, 93 insertions(+), 64 deletions(-) create mode 100644 test/tree.qc create mode 100644 test/typedef.qc create mode 100644 test/types.qc diff --git a/alloc.c b/alloc.c index 807936a..ca6504a 100644 --- a/alloc.c +++ b/alloc.c @@ -52,15 +52,3 @@ void memory_d(void *ptrn, unsigned int line, const char *file) { printf("[MEM] released: %08u (bytes) at %s:%u\n", info->byte, file, line); free(data); } - -/* - * Ensure the macros are not already defined otherwise the memory - * tracker will fail. I hate trying to fix macro bugs, this should - * help stop any of that from occuring. - */ -#ifdef mem_a -#undef mem_a -#endif -#ifdef mem_d -#undef mem_d -#endif diff --git a/gmqcc.h b/gmqcc.h index 681e539..5acfbd5 100644 --- a/gmqcc.h +++ b/gmqcc.h @@ -155,21 +155,23 @@ struct lex_file { #define TOKEN_GOTO 7 #define TOKEN_FOR 8 // extension #define TOKEN_TYPEDEF 9 // extension -#define TOKEN_VOID 10 -#define TOKEN_STRING 11 -#define TOKEN_FLOAT 12 -#define TOKEN_VECTOR 13 -#define TOKEN_ENTITY 14 + + +#define TOKEN_FLOAT 110 +#define TOKEN_VECTOR 111 +#define TOKEN_STRING 112 +#define TOKEN_ENTITY 113 +#define TOKEN_VOID 114 /* * Lexer state constants, these are numbers for where exactly in * the lexing the lexer is at. Or where it decided to stop if a lexer * error occurs. */ -#define LEX_COMMENT 128 /* higher than ascii */ -#define LEX_CHRLIT 129 -#define LEX_STRLIT 130 -#define LEX_IDENT 131 +#define LEX_COMMENT 1128 /* higher than ascii */ +#define LEX_CHRLIT 1129 +#define LEX_STRLIT 1130 +#define LEX_IDENT 1131 int lex_token(struct lex_file *); void lex_reset(struct lex_file *); @@ -197,6 +199,7 @@ typedef struct typedef_node_t { } typedef_node; void typedef_init(); +void typedef_clear(); typedef_node *typedef_find(const char *); int typedef_add (const char *, const char *); diff --git a/lex.c b/lex.c index 76cfbf0..afe5db7 100644 --- a/lex.c +++ b/lex.c @@ -34,14 +34,7 @@ static const char *const lex_keywords[] = { "do", "else", "if", "while", "break", "continue", "return", "goto", - "for", "typedef", - - /* types */ - "void", - "string", - "float", - "vector", - "entity", + "for", "typedef" }; struct lex_file *lex_open(FILE *fp) { @@ -289,12 +282,26 @@ int lex_token(struct lex_file *file) { if (!strncmp(file->lastok, lex_keywords[it], sizeof(lex_keywords[it]))) return it; + /* try a type? */ + #define TEST_TYPE(X) \ + do { \ + if (!strncmp(X, "float", sizeof("float"))) \ + return TOKEN_FLOAT; \ + if (!strncmp(X, "vector", sizeof("vector"))) \ + return TOKEN_VECTOR; \ + if (!strncmp(X, "string", sizeof("string"))) \ + return TOKEN_STRING; \ + if (!strncmp(X, "entity", sizeof("entity"))) \ + return TOKEN_ENTITY; \ + if (!strncmp(X, "void" , sizeof("void"))) \ + return TOKEN_VOID; \ + } while(0) + + TEST_TYPE(file->lastok); + /* try the hashtable for typedefs? */ if (typedef_find(file->lastok)) - for (it = 0; it < sizeof(lex_keywords)/sizeof(*lex_keywords); it++) - if (!strncmp(typedef_find(file->lastok)->name, lex_keywords[it], sizeof(lex_keywords[it]))) - return it; - + TEST_TYPE(typedef_find(file->lastok)->name); return LEX_IDENT; } diff --git a/parse.c b/parse.c index 2e681ba..4927013 100644 --- a/parse.c +++ b/parse.c @@ -92,34 +92,12 @@ "." , "<" , ">" , "&" , "|" , #endif -#define STORE(X) { \ - int total = fill; \ - while (total-->0) { \ - putchar(' '); \ - } \ - printf(X); \ - break; \ -} -#define STORE1(X) { \ - int total = fill; \ - while (total-->0) { \ - putchar(' '); \ - } \ - fill += 4; \ - break; \ -} -#define STORE2(X) { \ - fill -= 4; \ - int total = fill; \ - while (total-->0) { \ - putchar(' '); \ - } \ - printf(X); \ - break; \ +#define STORE(X) { \ + printf(X); \ + break; \ } void parse_debug(struct parsenode *tree) { - int fill = 0; while (tree) { switch (tree->type) { case PARSE_TYPE_ADD: STORE("OPERATOR: ADD \n"); @@ -195,6 +173,9 @@ void parse_clear(struct parsenode *tree) { tree = tree->next; mem_d (temp); } + + /* free any potential typedefs */ + typedef_clear(); } int parse(struct lex_file *file) { @@ -263,8 +244,13 @@ int parse(struct lex_file *file) { typedef_add(f, t); /* free stdup strings */ - mem_d(f); - mem_d(t); + //mem_d(f); + //mem_d(t); + free(f); + free(t); + + while (token != '\n') + token = lex_token(file); break; } diff --git a/test/tree.qc b/test/tree.qc new file mode 100644 index 0000000..1d9601f --- /dev/null +++ b/test/tree.qc @@ -0,0 +1,22 @@ +if { + if { + return 0; + } else { + return 1; + } +} else { + for { + if { + return 2; + } else { + continue; + } + } + do { + if { + break; + } else { + goto finish; + } + } while ( ) +} diff --git a/test/typedef.qc b/test/typedef.qc new file mode 100644 index 0000000..f60bf77 --- /dev/null +++ b/test/typedef.qc @@ -0,0 +1,11 @@ +typedef float my_float; +typedef vector my_vector; +typedef string my_string; +typedef entity my_entity; +typedef void my_void; + +my_float type_float; +my_vector type_vector; +my_string type_string; +my_entity type_entity; +my_void type_void; diff --git a/test/types.qc b/test/types.qc new file mode 100644 index 0000000..a0234a5 --- /dev/null +++ b/test/types.qc @@ -0,0 +1,5 @@ +float type_float; +vector type_vector; +string type_string; +entity type_entity; +void type_void; diff --git a/typedef.c b/typedef.c index 5f52903..9486576 100644 --- a/typedef.c +++ b/typedef.c @@ -160,6 +160,13 @@ typedef_node *typedef_find(const char *s) { return find; } +void typedef_clear() { + int i; + for(i = 1024; i > 0; i--) + if(typedef_table[i]) + mem_d(typedef_table[i]); +} + int typedef_add(const char *from, const char *to) { unsigned int hash = typedef_hash(to); typedef_node *find = typedef_table[hash]; @@ -167,11 +174,11 @@ int typedef_add(const char *from, const char *to) { return error(ERROR_PARSE, "typedef for %s already exists\n", to); /* check if the type exists first */ - if (strncmp(from, "void", sizeof("void")) == 0 || - strncmp(from, "string", sizeof("string")) == 0 || - strncmp(from, "float", sizeof("float")) == 0 || + if (strncmp(from, "float", sizeof("float")) == 0 || strncmp(from, "vector", sizeof("vector")) == 0 || - strncmp(from, "entity", sizeof("entity")) == 0) { + strncmp(from, "string", sizeof("string")) == 0 || + strncmp(from, "entity", sizeof("entity")) == 0 || + strncmp(from, "void", sizeof("void")) == 0) { typedef_table[hash] = mem_a(sizeof(typedef_node)); typedef_table[hash]->name = strdup(from); -- 2.39.2