5 #include "ebisp/interpreter.h"
6 #include "ebisp/builtins.h"
7 #include "ebisp/scope.h"
12 lambda(Gc *gc, struct Expr args, struct Expr body)
16 CONS(gc, args, body));
19 static struct EvalResult
20 quasiquote(void *param, Gc *gc, struct Scope *scope, struct Expr args)
26 struct Expr expr = void_expr();
27 struct EvalResult result = match_list(gc, "e", args, &expr);
28 if (result.is_error) {
32 const char *unquote = NULL;
33 struct Expr unquote_expr = void_expr();
34 result = match_list(gc, "qe", expr, &unquote, &unquote_expr);
36 if (!result.is_error && strcmp(unquote, "unquote") == 0) {
37 return eval(gc, scope, unquote_expr);
38 } else if (cons_p(expr)) {
39 struct EvalResult left = quasiquote(param, gc, scope, CONS(gc, CAR(expr), NIL(gc)));
43 struct EvalResult right = quasiquote(param, gc, scope, CONS(gc, CDR(expr), NIL(gc)));
47 return eval_success(CONS(gc, left.expr, right.expr));
49 return eval_success(expr);
53 static struct EvalResult
54 unquote(void *param, Gc *gc, struct Scope *scope, struct Expr args)
61 return eval_failure(STRING(gc, "Using unquote outside of quasiquote."));
64 /* TODO(#536): greaterThan does not support arbitrary amount of arguments */
65 static struct EvalResult
66 greaterThan(void *param, Gc *gc, struct Scope *scope, struct Expr args)
72 long int x = 0, y = 0;
74 struct EvalResult result = match_list(gc, "dd", args, &x, &y);
75 if (result.is_error) {
80 return eval_success(T(gc));
82 return eval_success(NIL(gc));
86 static struct EvalResult
87 list_op(void *param, Gc *gc, struct Scope *scope, struct Expr args)
93 return eval_success(args);
96 static struct EvalResult
97 plus_op(void *param, Gc *gc, struct Scope *scope, struct Expr args)
103 long int result = 0L;
105 while (!nil_p(args)) {
107 return wrong_argument_type(gc, "consp", args);
110 if (!number_p(CAR(args))) {
111 return wrong_argument_type(gc, "numberp", CAR(args));
114 result += CAR(args).atom->num;
118 return eval_success(NUMBER(gc, result));
121 static struct EvalResult
122 assoc_op(void *param, Gc *gc, struct Scope *scope, struct Expr args)
128 struct Expr key = NIL(gc);
129 struct Expr alist = NIL(gc);
130 struct EvalResult result = match_list(gc, "ee", args, &key, &alist);
131 if (result.is_error) {
135 return eval_success(assoc(key, alist));
138 static struct EvalResult
139 set(void *param, Gc *gc, struct Scope *scope, struct Expr args)
145 const char *name = NULL;
146 struct Expr value = void_expr();
147 struct EvalResult result = match_list(gc, "qe", args, &name, &value);
148 if (result.is_error) {
152 result = eval(gc, scope, value);
153 if (result.is_error) {
157 set_scope_value(gc, scope, SYMBOL(gc, name), result.expr);
159 return eval_success(result.expr);
162 static struct EvalResult
163 quote(void *param, Gc *gc, struct Scope *scope, struct Expr args)
169 struct Expr expr = void_expr();
170 struct EvalResult result = match_list(gc, "e", args, &expr);
171 if (result.is_error) {
175 return eval_success(expr);
178 static struct EvalResult
179 begin(void *param, Gc *gc, struct Scope *scope, struct Expr args)
185 struct Expr block = void_expr();
186 struct EvalResult result = match_list(gc, "*", args, &block);
187 if (result.is_error) {
191 return eval_block(gc, scope, block);
194 static struct EvalResult
195 defun(void *param, Gc *gc, struct Scope *scope, struct Expr args)
201 struct Expr name = void_expr();
202 struct Expr args_list = void_expr();
203 struct Expr body = void_expr();
205 struct EvalResult result = match_list(gc, "ee*", args, &name, &args_list, &body);
206 if (result.is_error) {
210 return eval(gc, scope,
214 lambda(gc, args_list, body)));
217 static struct EvalResult
218 when(void *param, Gc *gc, struct Scope *scope, struct Expr args)
224 struct Expr condition = void_expr();
225 struct Expr body = void_expr();
227 struct EvalResult result = match_list(
228 gc, "e*", args, &condition, &body);
229 if (result.is_error) {
233 result = eval(gc, scope, condition);
234 if (result.is_error) {
238 if (!nil_p(result.expr)) {
239 return eval_block(gc, scope, body);
242 return eval_success(NIL(gc));
245 static struct EvalResult
246 lambda_op(void *param, Gc *gc, struct Scope *scope, struct Expr args)
252 struct Expr args_list = void_expr();
253 struct Expr body = void_expr();
255 struct EvalResult result = match_list(gc, "e*", args, &args_list, &body);
256 if (result.is_error) {
260 if (!list_of_symbols_p(args_list)) {
261 return wrong_argument_type(gc, "list-of-symbolsp", args_list);
264 return eval_success(lambda(gc, args_list, body));
267 void load_std_library(Gc *gc, struct Scope *scope)
269 set_scope_value(gc, scope, SYMBOL(gc, "car"), NATIVE(gc, car, NULL));
270 set_scope_value(gc, scope, SYMBOL(gc, ">"), NATIVE(gc, greaterThan, NULL));
271 set_scope_value(gc, scope, SYMBOL(gc, "+"), NATIVE(gc, plus_op, NULL));
272 set_scope_value(gc, scope, SYMBOL(gc, "list"), NATIVE(gc, list_op, NULL));
273 set_scope_value(gc, scope, SYMBOL(gc, "t"), SYMBOL(gc, "t"));
274 set_scope_value(gc, scope, SYMBOL(gc, "nil"), SYMBOL(gc, "nil"));
275 set_scope_value(gc, scope, SYMBOL(gc, "assoc"), NATIVE(gc, assoc_op, NULL));
276 set_scope_value(gc, scope, SYMBOL(gc, "quasiquote"), NATIVE(gc, quasiquote, NULL));
277 set_scope_value(gc, scope, SYMBOL(gc, "set"), NATIVE(gc, set, NULL));
278 set_scope_value(gc, scope, SYMBOL(gc, "quote"), NATIVE(gc, quote, NULL));
279 set_scope_value(gc, scope, SYMBOL(gc, "begin"), NATIVE(gc, begin, NULL));
280 set_scope_value(gc, scope, SYMBOL(gc, "defun"), NATIVE(gc, defun, NULL));
281 set_scope_value(gc, scope, SYMBOL(gc, "when"), NATIVE(gc, when, NULL));
282 set_scope_value(gc, scope, SYMBOL(gc, "lambda"), NATIVE(gc, lambda_op, NULL));
283 set_scope_value(gc, scope, SYMBOL(gc, "λ"), NATIVE(gc, lambda_op, NULL));
284 set_scope_value(gc, scope, SYMBOL(gc, "unquote"), NATIVE(gc, unquote, NULL));