diff --git a/Makefile b/Makefile index 67c72c8..0a28862 100644 --- a/Makefile +++ b/Makefile @@ -3,9 +3,11 @@ HDRS = lispobj.h SRCS = test_lispobj.c lispobj.c -all: test +all: test test: $(SRCS) gcc -Wall -g $(HDRS) $(SRCS) -o test + +tag: gtags -v lint: diff --git a/lispobj.c b/lispobj.c index 562dbc3..183fac5 100644 --- a/lispobj.c +++ b/lispobj.c @@ -511,11 +511,13 @@ lispobj *eval(lispobj *exp, environment *env) else { fprintf(stderr, "eval error: not applicable\n"); + abort(); } } else { fprintf(stderr, "eval error: can not evaluate\n"); + abort(); } return result; @@ -770,6 +772,32 @@ int delete_tokens(list *tokens) return 1; } +bool get_current_exp(list *tokens, cell **tail) +{ + bool result; + char *s; + + if(tokens == NULL) + { + *tail = NULL; + result = false; + } + else + { + s = car(tokens); + if(s[0] == '(') + { + *tail = close_token(tokens, 0); + } + else + { + *tail = tokens; + } + result = true; + } + return result; +} + list *close_token(list *tokens, int count) { list *result = NULL; @@ -846,73 +874,61 @@ lispobj *new_lispobj(char *exp) return result; } -list *read_tokens(list *tokens) +lispobj* read_tokens(list *tokens) { lispobj *obj; char *s; if(tokens == NULL) { - obj = NULL; + return NULL; + } + + s = car(tokens); + + if(s[0] == '(') + { + cell *closer; + get_current_exp(tokens, &closer); + obj = read_listtokens(cdr(tokens), closer); } else { - s = car(tokens); - - if(s[0] == '(') - { - cell *closer = close_token(tokens, 0); - obj = read_listtokens(tokens, closer); - } - else - { - obj = new_lispobj(s); - } + obj = new_lispobj(car(tokens)); } return obj; } -/*@null@*/ -list *read_listtokens(cell *tokens, cell *tail) +list *read_listtokens(list *tokens, cell *tail) { - list *result = NULL; + lispobj *obj; + cell *closer; if(tokens == NULL) { - return NULL; + return NULL; } - - if(tokens == tail) + else if(tokens == tail) { return NULL; } - - char *s = car(tokens); - if(s[0] == '(') + + get_current_exp(tokens, &closer); + + if(tokens == closer) { - cell *next = cdr(tokens); - s = car(next); - if(s[0] == '(') - { - cell *closer = close_token(next, 0); - result = cons( - read_listtokens(next, closer), - read_listtokens(cdr(closer), tail)); - } - else - { - result = cons( - new_lispobj(s), - read_listtokens(cdr(next), tail)); - } + obj = cons( + new_lispobj(car(tokens)), + read_listtokens(cdr(tokens), tail)); } else { - result = cons( - new_lispobj(s), - read_listtokens(cdr(tokens), tail)); + obj = cons( + read_listtokens(cdr(tokens), closer), + read_listtokens(cdr(closer), tail)); } - return result; + + return obj; } bool print_lispobj(lispobj *obj) diff --git a/lispobj.h b/lispobj.h index 21a647b..485951e 100644 --- a/lispobj.h +++ b/lispobj.h @@ -114,6 +114,7 @@ list *tokenize(char *exp); int print_token(list *tokens); int delete_tokens(list *tokens); list *read_tokens(list *tokens); +list *get_closer(list *tokens, int count); list *close_token(list *tokens, int count); list *read_listtokens(cell *head, cell *tail); bool print_lispobj(lispobj* obj); diff --git a/test_lispobj.c b/test_lispobj.c index a5e199d..58b13a2 100644 --- a/test_lispobj.c +++ b/test_lispobj.c @@ -282,7 +282,6 @@ int test_read_tokens() l = tokenize("10"); i = read_tokens(l); - print_lispobj(i); assert(integer_to_int(i) == 10); @@ -290,22 +289,22 @@ int test_read_tokens() r = read_tokens(l); i = eval(r, env); assert(integer_to_int(i) == 10); - printf("----\n"); - printf("----\n"); + l = tokenize("(+ (+ 1 4) (+ 2 3))"); r = read_tokens(l); - print_lispobj(car(r)); - printf("-\n"); - print_lispobj(cdr(r)); - printf("-\n"); - print_lispobj(car(cdr(r))); - printf("-\n"); - i = eval(r, env); assert(integer_to_int(i) == 10); - printf("----\n"); + l = tokenize("(+ (+ 1 2) (+ 2 3) (+ 3 4))"); + r = read_tokens(l); + i = eval(r, env); + assert(integer_to_int(i) == 15); + + l = tokenize("(+ (+ (+ 1 2) (+ 2 3)) (+ 3 4))"); + r = read_tokens(l); + i = eval(r, env); + assert(integer_to_int(i) == 15); return 1; }