iris

small scheme interpreter
git clone git://git.2f30.org/iris
Log | Files | Refs | LICENSE

commit 2a05ed0a3743603003afeb9f36fa5912bdb9c10d
parent 4db212d423da3639af21f77dce6bf2d897d8fcc3
Author: sin <sin@2f30.org>
Date:   Thu, 15 May 2014 17:03:03 +0100

Add diff

Diffstat:
Mparser.c | 27+++++++++++++++++++++++++++
1 file changed, 27 insertions(+), 0 deletions(-)

diff --git a/parser.c b/parser.c @@ -60,6 +60,7 @@ struct object { }; static struct object *evaldefine(struct object *); +static struct object *evaldiff(struct object *); static struct object *evalif(struct object *); static struct object *evalok(struct object *); static struct object *evalplus(struct object *); @@ -72,6 +73,7 @@ struct { struct object *(*fn)(struct object *); } builtins[] = { { .name = "define", .fn = evaldefine }, + { .name = "diff", .fn = evaldiff }, { .name = "if", .fn = evalif }, { .name = "ok", .fn = evalok }, { .name = "plus", .fn = evalplus }, @@ -324,6 +326,31 @@ evaldefine(struct object *o) } static struct object * +dodiff(struct object *o, struct object *n) +{ + if (!car(o)) + return n; + if (car(o)->type != ONumber) + return error("expected number"); + n->d.n.v -= car(o)->d.n.v; + return dodiff(cdr(o), n); +} + +static struct object * +evaldiff(struct object *o) +{ + struct object *ocar; + + if (o->type != OPair) + return NULL; + ocar = car(o); + if (ocar->type != OIdentifier || + strcmp(ocar->d.i.s, "diff") != 0) + return NULL; + return dodiff(cdr(o), number(0)); +} + +static struct object * evalif(struct object *o) { struct object *ocar;