tisp

tiny lisp
git clone git://edryd.org/tisp
Log | Files | Refs | LICENSE

commit 1715f48abd1f7070eb0ae0ba44fde2a9483a6c41
parent 0f61313c2da4475e6f114570e14f03f9add56b07
Author: Ed van Bruggen <edvb@uw.edu>
Date:   Thu,  3 Jan 2019 20:28:02 -0800

Write unit tests in C

Diffstat:
Makefile | 19+++++++++++--------
t/math/add.expect | 3---
t/math/add.tsp | 3---
t/math/compare.expect | 12------------
t/math/compare.tsp | 12------------
t/math/sub.expect | 5-----
t/math/sub.tsp | 5-----
t/prim/cond.expect | 8--------
t/prim/cond.tsp | 8--------
t/prim/cons.expect | 6------
t/prim/cons.tsp | 6------
t/prim/cxr.expect | 11-----------
t/prim/cxr.tsp | 14--------------
t/prim/define.expect | 3---
t/prim/define.tsp | 6------
t/prim/eq.expect | 29-----------------------------
t/prim/eq.tsp | 29-----------------------------
t/prim/lambda.expect | 5-----
t/prim/lambda.tsp | 5-----
t/prim/quote.expect | 10----------
t/prim/quote.tsp | 11-----------
t/simple/comments.expect | 2--
t/simple/comments.tsp | 11-----------
t/simple/frac.expect | 11-----------
t/simple/frac.tsp | 11-----------
t/simple/self.expect | 14--------------
t/simple/self.tsp | 14--------------
t/t | 24------------------------
test.c | 240+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
29 files changed, 251 insertions(+), 286 deletions(-)

diff --git a/Makefile b/Makefile @@ -4,9 +4,10 @@ include config.mk EXE = tisp -SRC = $(wildcard *.c */*.c) -OBJ = $(SRC:.c=.o) -LIB = tib/libtibmath.so +SRC = tisp.c main.c util.c extern/linenoise.c +TIB = tib/math.c tib/io.c +OBJ = $(SRC:.c=.o) $(TIB:.c=.o) +LIB = tib/libtibmath.so tib/libtibio.so all: options $(EXE) @@ -29,7 +30,7 @@ config.h: @echo creating $@ from config.def.h @cp config.def.h $@ -$(LIB): $(wildcard tib/*.c) +$(LIB): $(TIB) @echo $(CC) -o $@ @gcc -shared -o $@ $(OBJ) @@ -39,7 +40,7 @@ $(EXE): $(OBJ) $(LIB) clean: @echo cleaning - @rm -f $(OBJ) $(LIB) $(EXE) + @rm -f $(OBJ) $(LIB) $(EXE) test test.o test.out install: all @echo installing $(EXE) to $(DESTDIR)$(PREFIX)/bin @@ -62,9 +63,11 @@ uninstall: @echo removing libraries from $(DESTDIR)$(PREFIX)/lib/tisp @rm -rf $(DESTDIR)$(PREFIX)/lib/tisp/ -test: $(EXE) +test: $(OBJ) $(LIB) test.o @echo running tests - @cd t && ./t + @echo $(CC) -o test + @$(CC) -o test tisp.o tib/math.o util.o test.o $(LDFLAGS) + @./test man: @echo -n updating man page $(EXE).1 ... @@ -79,4 +82,4 @@ man: md2roff - | sed "9s/]/]\ /g" | sed "9s/|/|\ /g" > $(EXE).1 @echo \ done -.PHONY: all options clean install uninstall man +.PHONY: all options clean install uninstall test man diff --git a/t/math/add.expect b/t/math/add.expect @@ -1,3 +0,0 @@ -2 -4 -1312 diff --git a/t/math/add.tsp b/t/math/add.tsp @@ -1,3 +0,0 @@ -(+ 1 1) -(+ 1 (+ 1 2)) -(+ 1029 283) diff --git a/t/math/compare.expect b/t/math/compare.expect @@ -1,12 +0,0 @@ -t -() -() -t -t -() -t -() -() -t -t -() diff --git a/t/math/compare.tsp b/t/math/compare.tsp @@ -1,12 +0,0 @@ -(< 2 3) -(< 3 3) -(< 4 3) -(<= -2 +4) -(<= -2 -2) -(<= 4 -2) -(> 89 34) -(> 48 48) -(> 98 183) -(>= +4 -282) -(>= 39 39) -(>= -32 -30) diff --git a/t/math/sub.expect b/t/math/sub.expect @@ -1,5 +0,0 @@ --3 --3 -289 -1 --35 diff --git a/t/math/sub.tsp b/t/math/sub.tsp @@ -1,5 +0,0 @@ -(- 3) -(- +3) -(- -289) -(- 5 4) -(- 53 88) diff --git a/t/prim/cond.expect b/t/prim/cond.expect @@ -1,8 +0,0 @@ -() -1 -1 -3 -2 -() -2 -() diff --git a/t/prim/cond.tsp b/t/prim/cond.tsp @@ -1,8 +0,0 @@ -(cond) -(cond (t 1)) -(cond ((= 1 1) 1) ((= 1 2) 2) (t 3)) -(cond ((= 1 2) 1) ((= 1 2) 2) (t (+ 1 2))) -(cond ((= 1 2) 1) ((= 1 1) 2) (t 3)) -(cond ((= 1 2) 1) ((= 1 3) 2)) -(cond ((= 1 2) 1) ("foo" 2) (t 3)) -(cond (() (+ 1 2))) diff --git a/t/prim/cons.expect b/t/prim/cons.expect @@ -1,6 +0,0 @@ -(1 . 2) -(1 2 . 3) -(1 2 3 . 4) -("foo" . "bar") -(3 . 3) -((1 . 2) 3 . 4) diff --git a/t/prim/cons.tsp b/t/prim/cons.tsp @@ -1,6 +0,0 @@ -(cons 1 2) -(cons 1 (cons 2 3)) -(cons 1 (cons 2 (cons 3 4))) -(cons "foo" "bar") -(cons (+ 1 2) 3) -(cons (cons 1 2) (cons 3 4)) diff --git a/t/prim/cxr.expect b/t/prim/cxr.expect @@ -1,11 +0,0 @@ -1 -2 -1 -2 -3 -4 -(2 3 4) -(3 4) -1 -(2 . 3) -3 diff --git a/t/prim/cxr.tsp b/t/prim/cxr.tsp @@ -1,14 +0,0 @@ -(car (cons 1 2)) -(cdr (cons 1 2)) - -(car (quote (1 2 3 4))) -(car (cdr (quote (1 2 3 4)))) -(car (cdr (cdr (quote (1 2 3 4))))) -(car (cdr (cdr (cdr (quote (1 2 3 4)))))) - -(cdr (quote (1 2 3 4))) -(cdr (cdr (quote (1 2 3 4)))) - -(car (cons 1 (cons 2 3))) -(cdr (cons 1 (cons 2 3))) -(cdr (cdr (cons 1 (cons 2 3)))) diff --git a/t/prim/define.expect b/t/prim/define.expect @@ -1,3 +0,0 @@ -4 -4 -8 diff --git a/t/prim/define.tsp b/t/prim/define.tsp @@ -1,6 +0,0 @@ -(define foo 4) -foo -(define bar foo) -bar -(define add +) -(add foo bar) diff --git a/t/prim/eq.expect b/t/prim/eq.expect @@ -1,29 +0,0 @@ -t -t -t -t -t -() -() -() -() -t -t -t -t -() -() -() -() -t -t -() -t -() -() -() -() -t -t -() -t diff --git a/t/prim/eq.tsp b/t/prim/eq.tsp @@ -1,29 +0,0 @@ -(=) -(= 1) -(= "foo") -(= 1 1) -(= 1 1 1 1 1 1) -(= 1 2) -(= 1 1 2 1 1 1) -(= 1 1 1 1 1 2) -(= 2 1 1 1 1 1) -(= 4/5 4/5) -(= 2/1 2) -(= 2/4 1/2) -(= 2/4 1/2 4/8 3/6) -(= 1/2 4/5) -(= 5/4 4/5) -(= 3 3/2) -(= 3 3/2 3 3 3) -(= (+ 1 1) (+ 2 0)) -(= "foo" "foo") -(= "foo" "bar") -(= "foo" "foo" "foo" "foo" "foo") -(= "foo" "bar" "foo" "foo" "foo") -(= "foo" 3) -(= "foo" "foo" 4 "foo" "foo") -(= "foo" "FOO") -(= t t) -(= car car) -(= car cdr) -(= quote quote quote) diff --git a/t/prim/lambda.expect b/t/prim/lambda.expect @@ -1,5 +0,0 @@ -3 -3 -9 -4 -5 diff --git a/t/prim/lambda.tsp b/t/prim/lambda.tsp @@ -1,5 +0,0 @@ -((lambda (x) x) 3) -((lambda (x) x) (+ 1 2)) -((lambda (x) (+ x 1)) 8) -((lambda (a b) (+ a b)) 2 2) -((lambda () 5)) diff --git a/t/prim/quote.expect b/t/prim/quote.expect @@ -1,10 +0,0 @@ -1 -9234 -"foo" -bar -(1 2 3 4) -(quote 1) -(+ 2 2) -12 -foo -(1 2 3 4) diff --git a/t/prim/quote.tsp b/t/prim/quote.tsp @@ -1,11 +0,0 @@ -(quote 1) -(quote 9234) -(quote "foo") -(quote bar) -(quote (1 2 3 4)) -(quote (quote 1)) -(quote (+ 2 2)) - -'12 -'foo -'(1 2 3 4) diff --git a/t/simple/comments.expect b/t/simple/comments.expect @@ -1,2 +0,0 @@ -2 -4 diff --git a/t/simple/comments.tsp b/t/simple/comments.tsp @@ -1,11 +0,0 @@ -; commment -; (+ 1 1) -(+ 1 ; more comments - 1) - - ; white space too - (+ 2 2) - - - -; another comment diff --git a/t/simple/frac.expect b/t/simple/frac.expect @@ -1,11 +0,0 @@ -3/4 -4/3 -1/2 -2 -2 -1/2 -1192/3619 --1/2 --1/2 --2 -2 diff --git a/t/simple/frac.tsp b/t/simple/frac.tsp @@ -1,11 +0,0 @@ -3/4 -4/3 -1/2 -2/1 -8/4 -4/8 -02384/7238 --1/2 -1/-2 --6/3 --6/-3 diff --git a/t/simple/self.expect b/t/simple/self.expect @@ -1,14 +0,0 @@ -1 -2 -0 -30 -12 --4 --83 -0 -4 -123 -"foo" -"foo bar" -t -() diff --git a/t/simple/self.tsp b/t/simple/self.tsp @@ -1,14 +0,0 @@ -1 -2 -0 -30 -12 --4 --083 --0 -+4 -+123 -"foo" -"foo bar" -t -() diff --git a/t/t b/t/t @@ -1,24 +0,0 @@ -#!/usr/bin/env bash - -total=0 -pass=0 - -export LD_LIBRARY_PATH="$PWD/../tib:$LD_LIBRARY_PATH" - -for file in */*.tsp; do - expect=${file%.tsp}.expect - - echo -n "testing $file ... " - if [[ $(../tisp "$file" 2>&1 | diff -q "$expect" - 2>&1 ) ]]; then - echo fail - else - echo ok - ((pass++)) - fi - ((total++)) -done - -echo "$pass/$total tests passed" - -[[ $pass == $total ]] && exit 0 -exit 1 diff --git a/test.c b/test.c @@ -0,0 +1,240 @@ +/* See LICENSE file for copyright and license details. */ +#include <assert.h> +#include <stdio.h> +#include <stdarg.h> +#include <string.h> +#include <unistd.h> + +#include "../util.h" +#include "../tisp.h" +#include "../tib/math.h" + +int +tisp_test(Env env, const char *input, const char *expect) +{ + struct Str str; + Val v; + FILE *f = fopen("test.out", "w"); + size_t nread; + char buf[BUFSIZ] = {0}; + + str.d = strdup(input); + v = tisp_read(env, &str); + if (!(v = tisp_eval(env, v))) + return 0; + + tisp_print(f, v); + fclose(f); + f = fopen("test.out", "r"); + while ((nread = fread(buf, 1, sizeof(buf), f)) > 0) ; + + return strcmp(buf, expect) == 0; +} + +/* TODO mark and show which lines error-ed */ +char *tests[][2] = { + + { "self", NULL }, + { "1", "1" }, + { "2", "2" }, + { "0", "0" }, + { "30", "30" }, + { "12", "12" }, + { "-4", "-4" }, + { "-083", "-83" }, + { "-0", "0" }, + { "+4", "4" }, + { "+123", "123" }, + { "12.0", "12.0" }, + { "08", "8" }, + { "+12.34", "12.3" }, + { ".34", "0.3" }, + { "2.", "2.0" }, + { "1e0", "1" }, + { "1E+0", "1" }, + { "1e-0", "1" }, + { "1E4", "10000" }, + { ".1e-4", "0.0" }, + { "-5.0e006", "-5000000.0" }, + { "-5.E+16", "-50000000000000000.0" }, + { "-.05", "-0.1" }, + { "-.0", "-0.0" }, + { "-1.e6", "-1000000.0" }, + { "\"foo\"", "\"foo\"" }, + { "\"foo bar\"", "\"foo bar\"" }, + { "t", "t" }, + { "()", "()" }, + + { "frac", NULL }, + { "3/4", "3/4" }, + { "4/3", "4/3" }, + { "+1/2", "1/2" }, + { "2/1", "2" }, + { "8/+1", "8" }, + { "8/4", "2" }, + { "4/8", "1/2" }, + { "02384/7238", "1192/3619" }, + { "-1/2", "-1/2" }, + { "1/-2", "-1/2" }, + { "-6/3", "-2" }, + { "-6/-3", "2" }, + + { "comments", NULL }, + { "; commment", "()" }, + { "; (+ 1 1)", "()" }, + { "(+ 1 ; more comments\n1)", "2" }, + + { "whitespace", NULL }, + { "\t \n \n\n\t\n \t\n", "()" }, + { "\t \t(+ \t\t5 \n \n5 \n\t)", "10" }, + + { "quote", NULL }, + { "(quote 1)", "1" }, + { "(quote 9234)", "9234" }, + { "(quote \"foo\")", "\"foo\"" }, + { "(quote bar)", "bar" }, + { "(quote (1 2 3 4))", "(1 2 3 4)" }, + { "(quote (quote 1))", "(quote 1)" }, + { "(quote (+ 2 2))", "(+ 2 2)" }, + { "'12", "12" }, + { "'foo", "foo" }, + { "'(1 2 3 4)", "(1 2 3 4)" }, + + { "cons", NULL }, + { "(cons 1 2)", "(1 . 2)" }, + { "(cons 1 (cons 2 3))", "(1 2 . 3)" }, + { "(cons 1 (cons 2 (cons 3 4)))", "(1 2 3 . 4)" }, + { "(cons \"foo\" \"bar\")", "(\"foo\" . \"bar\")" }, + { "(cons (+ 1 2) 3)", "(3 . 3)" }, + { "(cons (cons 1 2) (cons 3 4))", "((1 . 2) 3 . 4)" }, + + { "cxr", NULL }, + { "(car (cons 1 2))", "1" }, + { "(cdr (cons 1 2))", "2" }, + { "(car (quote (1 2 3 4)))", "1" }, + { "(car (cdr (quote (1 2 3 4))))", "2" }, + { "(car (cdr (cdr (quote (1 2 3 4)))))", "3" }, + { "(car (cdr (cdr (cdr (quote (1 2 3 4))))))", "4" }, + { "(cdr (quote (1 2 3 4)))", "(2 3 4)" }, + { "(cdr (cdr (quote (1 2 3 4))))", "(3 4)" }, + { "(car (cons 1 (cons 2 3)))", "1" }, + { "(cdr (cons 1 (cons 2 3)))", "(2 . 3)" }, + { "(cdr (cdr (cons 1 (cons 2 3))))", "3" }, + + { "cond", NULL }, + { "(cond)", "()" }, + { "(cond (t 1))", "1" }, + { "(cond ((= 1 1) 1) ((= 1 2) 2) (t 3))", "1" }, + { "(cond ((= 1 2) 1) ((= 1 2) 2) (t (+ 1 2)))", "3" }, + { "(cond ((= 1 2) 1) ((= 1 1) 2) (t 3))", "2" }, + { "(cond ((= 1 2) 1) ((= 1 3) 2))", "()" }, + { "(cond ((= 1 2) 1) (\"foo\" 2) (t 3))", "2" }, + { "(cond (() (+ 1 2)))", "()" }, + + { "eq", NULL }, + { "(=)", "t" }, + { "(= 1)", "t" }, + { "(= \"foo\")", "t" }, + { "(= 1 1)", "t" }, + { "(= 1 1 1 1 1 1)", "t" }, + { "(= 1 2)", "()" }, + { "(= 1 1 2 1 1 1)", "()" }, + { "(= 1 1 1 1 1 2)", "()" }, + { "(= 2 1 1 1 1 1)", "()" }, + { "(= 4/5 4/5)", "t" }, + { "(= 2/1 2)", "t" }, + { "(= 2/4 1/2)", "t" }, + { "(= 2/4 1/2 4/8 3/6)", "t" }, + { "(= 1/2 4/5)", "()" }, + { "(= 5/4 4/5)", "()" }, + { "(= 3 3/2)", "()" }, + { "(= 3 3/2 3 3 3)", "()" }, + { "(= (+ 1 1) (+ 2 0))", "t" }, + { "(= \"foo\" \"foo\")", "t" }, + { "(= \"foo\" \"bar\")", "()" }, + { "(= \"foo\" \"foo\" \"foo\" \"foo\" \"foo\")", "t" }, + { "(= \"foo\" \"bar\" \"foo\" \"foo\" \"foo\")", "()" }, + { "(= \"foo\" 3)", "()" }, + { "(= \"foo\" \"foo\" 4 \"foo\" \"foo\")", "()" }, + { "(= \"foo\" \"FOO\")", "()" }, + { "(= t t)", "t" }, + { "(= car car)", "t" }, + { "(= car cdr)", "()" }, + { "(= quote quote quote)", "t" }, + + { "define", NULL }, + { "(define foo 4)", "" }, + { "foo", "4" }, + { "(define bar foo)", "" }, + { "bar", "4" }, + { "(define add +)", "" }, + { "(add foo bar)", "8" }, + { "(define (one x) (add x 1))", "" }, + { "(one foo)", "5" }, + + { "lambda", NULL }, + { "((lambda (x) x) 3)", "3" }, + { "((lambda (x) x) (+ 1 2))", "3" }, + { "((lambda (x) (+ x 1)) 8)", "9" }, + { "((lambda (a b) (+ a b)) 2 2)", "4" }, + { "((lambda () 5))", "5" }, + + { "add", NULL }, + { "(+ 1 1)", "2" }, + { "(+ 1 (+ 1 2))", "4" }, + { "(+ 1029 283)", "1312" }, + + { "sub", NULL }, + { "(- 3)", "-3" }, + { "(- +3)", "-3" }, + { "(- -289)", "289" }, + { "(- 5 4)", "1" }, + { "(- 53 88)", "-35" }, + + { "compare", NULL }, + { "(< 2 3)", "t" }, + { "(< 3 3)", "()" }, + { "(< 4 3)", "()" }, + { "(<= -2 +4)", "t" }, + { "(<= -2 -2)", "t" }, + { "(<= 4 -2)", "()" }, + { "(> 89 34)", "t" }, + { "(> 48 48)", "()" }, + { "(> 98 183)", "()" }, + { "(>= +4 -282)", "t" }, + { "(>= 39 39)", "t" }, + { "(>= -32 -30)", "()" }, + + { NULL, NULL }, +}; + +int +main(void) +{ + int correct = 0, total = 0, seccorrect = 0, sectotal = 0; + Env env = tisp_env_init(64); + tib_env_math(env); + + for (int i = 0; ; i++) { + if (!tests[i][1]) { + if (i != 0) + printf("%d/%d\n", seccorrect, sectotal); + if (!tests[i][0]) + break; + printf("%-10s ", tests[i][0]); + seccorrect = 0; + sectotal = 0; + } else { + if (tisp_test(env, tests[i][0], tests[i][1])) { + correct++; + seccorrect++; + } + total++; + sectotal++; + } + } + printf("%-10s %d/%d\n", "total", correct, total); + + tisp_env_free(env); + return correct != total; +}