Fixed parsing issues, added some parser tests.

This commit is contained in:
Dale Weiler 2012-04-10 01:03:52 -04:00
parent dfa3126233
commit 02e9098d3d
8 changed files with 93 additions and 64 deletions

12
alloc.c
View file

@ -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

21
gmqcc.h
View file

@ -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 *);

31
lex.c
View file

@ -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;
}

40
parse.c
View file

@ -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;
}

22
test/tree.qc Normal file
View file

@ -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 ( )
}

11
test/typedef.qc Normal file
View file

@ -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;

5
test/types.qc Normal file
View file

@ -0,0 +1,5 @@
float type_float;
vector type_vector;
string type_string;
entity type_entity;
void type_void;

View file

@ -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);