tisp

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

commit 99e99fe8625352b98aa4e1d20e59e67b8d8fd992
parent db3af47026b8efc406831519ec5b932904528d4e
Author: Ed van Bruggen <edvb@uw.edu>
Date:   Tue, 22 Oct 2019 01:41:23 -0700

Replace print primitive with write

Diffstat:
tibs/io.c | 53++++++++++++++++++++++++++++++++---------------------
tibs/lib.tsp | 3++-
tibs/repl.tsp | 7++-----
3 files changed, 36 insertions(+), 27 deletions(-)

diff --git a/tibs/io.c b/tibs/io.c @@ -18,45 +18,54 @@ * misrepresented as being the original software. * 3. This notice may not be removed or altered from any source distribution. */ +#include <string.h> #include <stdio.h> #include <stdlib.h> +#include <fcntl.h> #include "../tisp.h" -static void -print_str(Val v) { - if (v->t & STRING) /* don't print quotes around string */ - fprintf(stdout, "%s", v->v.s); - else - tisp_print(stdout, v); -} - +/* write all arguemnts to given file, or stdout/stderr, without newline */ static Val -prim_print(Env env, Val args) +prim_write(Env env, Val args) { Val v; + FILE *f; + tsp_arg_min(args, "write", 2); if (!(v = tisp_eval_list(env, args))) return NULL; - for (; !nilp(v); v = cdr(v)) { - if (v->t == PAIR) - print_str(car(v)); - else { - print_str(v); - break; - } - } - fflush(stdout); + + /* first argument can either be the symbol stdout or stderr, + * or the file as a string */ + if (car(v)->t == SYMBOL) + f = !strncmp(car(v)->v.s, "stdout", 7) ? stdout : stderr; + else if (car(v)->t != STRING) + tsp_warnf("write: expected file name as string, received %s", + type_str(car(v)->t)); + else if (!(f = fopen(car(v)->v.s, "w"))) + tsp_warnf("write: could not load file '%s'", car(v)->v.s); + if (f == stderr && strncmp(car(v)->v.s, "stderr", 7)) + tsp_warn("write: expected file name as string, " + "or symbol stdout/stderr"); + + for (v = cdr(v); !nilp(v); v = cdr(v)) + if (car(v)->t & STRING) /* don't print quotes around string */ + fprintf(f, "%s", car(v)->v.s); + else + tisp_print(f, car(v)); + fflush(f); return env->none; } +/* return string of given file or read from stdin */ static Val prim_read(Env env, Val args) { Val v; - char *file, *fname = NULL; + char *file, *fname = NULL; /* read from stdin by default */ if (list_len(args) > 1) tsp_warnf("read: expected 0 or 1 argument, received %d", list_len(args)); - if (list_len(args) == 1) { + if (list_len(args) == 1) { /* if file name given as string, read it */ if (!(v = tisp_eval(env, car(args)))) return NULL; tsp_arg_type(v, "read", STRING); @@ -67,6 +76,8 @@ prim_read(Env env, Val args) return mk_str(env, file); } +/* parse string as tisp expression, return (quit) if given nil */ +/* TODO parse more than 1 expression */ static Val prim_parse(Env env, Val args) { @@ -86,7 +97,7 @@ prim_parse(Env env, Val args) void tib_env_io(Env env) { - tsp_env_fn(print); + tsp_env_fn(write); tsp_env_fn(read); tsp_env_fn(parse); } diff --git a/tibs/lib.tsp b/tibs/lib.tsp @@ -191,7 +191,8 @@ 1 (* n (! (- n 1))))) -;;; Printing +;;; IO +(define (print . str) (apply write (cons 'stdout str))) (define (newline) (print "\n")) (define (disp . str) (apply print str) (newline)) (define (disp-string . str) diff --git a/tibs/repl.tsp b/tibs/repl.tsp @@ -7,10 +7,7 @@ (disp-string ans)) (repl))))) -;; simple repl +;; simple repl, only requires io c library (define (repl-simple) - (print "> ") - (print (eval (parse (read)))) - (newline) + (write 'stdout "> " (eval (parse (read))) "\n") (repl-simple)) -