new evaluator, y'all
[bpt/guile.git] / libguile / eval.c
1 /* Copyright (C) 1995,1996,1997,1998,1999,2000,2001,2002,2003,2004,2005,2006,2007,2008,2009
2 * Free Software Foundation, Inc.
3 *
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public License
6 * as published by the Free Software Foundation; either version 3 of
7 * the License, or (at your option) any later version.
8 *
9 * This library is distributed in the hope that it will be useful, but
10 * WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
13 *
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
17 * 02110-1301 USA
18 */
19
20 \f
21
22 #ifdef HAVE_CONFIG_H
23 # include <config.h>
24 #endif
25
26 #include <alloca.h>
27
28 #include "libguile/__scm.h"
29
30 #include <assert.h>
31 #include "libguile/_scm.h"
32 #include "libguile/alist.h"
33 #include "libguile/async.h"
34 #include "libguile/continuations.h"
35 #include "libguile/debug.h"
36 #include "libguile/deprecation.h"
37 #include "libguile/dynwind.h"
38 #include "libguile/eq.h"
39 #include "libguile/feature.h"
40 #include "libguile/fluids.h"
41 #include "libguile/goops.h"
42 #include "libguile/hash.h"
43 #include "libguile/hashtab.h"
44 #include "libguile/lang.h"
45 #include "libguile/list.h"
46 #include "libguile/macros.h"
47 #include "libguile/memoize.h"
48 #include "libguile/modules.h"
49 #include "libguile/ports.h"
50 #include "libguile/print.h"
51 #include "libguile/procprop.h"
52 #include "libguile/programs.h"
53 #include "libguile/root.h"
54 #include "libguile/smob.h"
55 #include "libguile/srcprop.h"
56 #include "libguile/stackchk.h"
57 #include "libguile/strings.h"
58 #include "libguile/threads.h"
59 #include "libguile/throw.h"
60 #include "libguile/validate.h"
61 #include "libguile/values.h"
62 #include "libguile/vectors.h"
63 #include "libguile/vm.h"
64
65 #include "libguile/eval.h"
66 #include "libguile/private-options.h"
67
68 \f
69
70
71 /* We have three levels of EVAL here:
72
73 - eval (exp, env)
74
75 evaluates EXP in environment ENV. ENV is a lexical environment
76 structure as used by the actual tree code evaluator. When ENV is
77 a top-level environment, then changes to the current module are
78 tracked by updating ENV so that it continues to be in sync with
79 the current module.
80
81 - scm_primitive_eval (exp)
82
83 evaluates EXP in the top-level environment as determined by the
84 current module. This is done by constructing a suitable
85 environment and calling eval. Thus, changes to the
86 top-level module are tracked normally.
87
88 - scm_eval (exp, mod)
89
90 evaluates EXP while MOD is the current module. This is done
91 by setting the current module to MOD_OR_STATE, invoking
92 scm_primitive_eval on EXP, and then restoring the current module
93 to the value it had previously. That is, while EXP is evaluated,
94 changes to the current module (or dynamic state) are tracked,
95 but these changes do not persist when scm_eval returns.
96
97 */
98
99
100 #if 0
101 #define CAR(x) SCM_CAR(x)
102 #define CDR(x) SCM_CDR(x)
103 #define CAAR(x) SCM_CAAR(x)
104 #define CADR(x) SCM_CADR(x)
105 #define CDAR(x) SCM_CDAR(x)
106 #define CDDR(x) SCM_CDDR(x)
107 #define CADDR(x) SCM_CADDR(x)
108 #define CDDDR(x) SCM_CDDDR(x)
109 #else
110 #define CAR(x) scm_car(x)
111 #define CDR(x) scm_cdr(x)
112 #define CAAR(x) scm_caar(x)
113 #define CADR(x) scm_cadr(x)
114 #define CDAR(x) scm_cdar(x)
115 #define CDDR(x) scm_cddr(x)
116 #define CADDR(x) scm_caddr(x)
117 #define CDDDR(x) scm_cdddr(x)
118 #endif
119
120
121 SCM_SYMBOL (scm_unbound_variable_key, "unbound-variable");
122
123 static void error_unbound_variable (SCM symbol) SCM_NORETURN;
124 static void error_unbound_variable (SCM symbol)
125 {
126 scm_error (scm_unbound_variable_key, NULL, "Unbound variable: ~S",
127 scm_list_1 (symbol), SCM_BOOL_F);
128 }
129
130 static void error_used_before_defined (void)
131 {
132 scm_error (scm_unbound_variable_key, NULL,
133 "Variable used before given a value", SCM_EOL, SCM_BOOL_F);
134 }
135
136 int
137 scm_badargsp (SCM formals, SCM args)
138 {
139 while (!scm_is_null (formals))
140 {
141 if (!scm_is_pair (formals))
142 return 0;
143 if (scm_is_null (args))
144 return 1;
145 formals = CDR (formals);
146 args = CDR (args);
147 }
148 return !scm_is_null (args) ? 1 : 0;
149 }
150
151 static SCM apply (SCM proc, SCM args);
152
153 /* the environment:
154 ((SYM . VAL) (SYM . VAL) ... . MOD)
155 If MOD is #f, it means the environment was captured before modules were
156 booted.
157 If MOD is the literal value '(), we are evaluating at the top level, and so
158 should track changes to the current module. You have to be careful in this
159 case, because further lexical contours should capture the current module.
160 */
161 #define CAPTURE_ENV(env) \
162 ((env == SCM_EOL) ? scm_current_module () : \
163 ((env == SCM_BOOL_F) ? scm_the_root_module () : env))
164
165 static SCM
166 eval (SCM x, SCM env)
167 {
168 SCM mx;
169 SCM proc = SCM_UNDEFINED, args = SCM_EOL;
170
171 loop:
172 SCM_TICK;
173 if (!SCM_MEMOIZED_P (x))
174 abort ();
175
176 mx = SCM_MEMOIZED_ARGS (x);
177 switch (SCM_MEMOIZED_TAG (x))
178 {
179 case SCM_M_BEGIN:
180 for (; !scm_is_null (CDR (mx)); mx = CDR (mx))
181 eval (CAR (mx), env);
182 x = CAR (mx);
183 goto loop;
184
185 case SCM_M_IF:
186 if (scm_is_true (eval (CAR (mx), env)))
187 x = CADR (mx);
188 else
189 x = CDDR (mx);
190 goto loop;
191
192 case SCM_M_LET:
193 {
194 SCM inits = CAR (mx);
195 SCM new_env = CAPTURE_ENV (env);
196 for (; scm_is_pair (inits); inits = CDR (inits))
197 new_env = scm_cons (eval (CAR (inits), env), new_env);
198 env = new_env;
199 x = CDR (mx);
200 goto loop;
201 }
202
203 case SCM_M_LAMBDA:
204 return scm_closure (mx, CAPTURE_ENV (env));
205
206 case SCM_M_QUOTE:
207 return mx;
208
209 case SCM_M_DEFINE:
210 scm_define (CAR (mx), eval (CDR (mx), env));
211 return SCM_UNSPECIFIED;
212
213 case SCM_M_APPLY:
214 /* Evaluate the procedure to be applied. */
215 proc = eval (CAR (mx), env);
216 /* Evaluate the argument holding the list of arguments */
217 args = eval (CADR (mx), env);
218
219 apply_proc:
220 /* Go here to tail-apply a procedure. PROC is the procedure and
221 * ARGS is the list of arguments. */
222 if (SCM_CLOSUREP (proc))
223 {
224 int nreq = SCM_CLOSURE_NUM_REQUIRED_ARGS (proc);
225 SCM new_env = SCM_ENV (proc);
226 if (SCM_CLOSURE_HAS_REST_ARGS (proc))
227 {
228 if (SCM_UNLIKELY (scm_ilength (args) < nreq))
229 scm_wrong_num_args (proc);
230 for (; nreq; nreq--, args = CDR (args))
231 new_env = scm_cons (CAR (args), new_env);
232 new_env = scm_cons (args, new_env);
233 }
234 else
235 {
236 if (SCM_UNLIKELY (scm_ilength (args) != nreq))
237 scm_wrong_num_args (proc);
238 for (; scm_is_pair (args); args = CDR (args))
239 new_env = scm_cons (CAR (args), new_env);
240 }
241 x = SCM_CLOSURE_BODY (proc);
242 env = new_env;
243 goto loop;
244 }
245 else
246 return apply (proc, args);
247
248 case SCM_M_CALL:
249 /* Evaluate the procedure to be applied. */
250 proc = eval (CAR (mx), env);
251
252 mx = CDR (mx);
253
254 if (SCM_CLOSUREP (proc))
255 {
256 int nreq = SCM_CLOSURE_NUM_REQUIRED_ARGS (proc);
257 SCM new_env = SCM_ENV (proc);
258 if (SCM_CLOSURE_HAS_REST_ARGS (proc))
259 {
260 if (SCM_UNLIKELY (scm_ilength (mx) < nreq))
261 scm_wrong_num_args (proc);
262 for (; nreq; nreq--, mx = CDR (mx))
263 new_env = scm_cons (eval (CAR (mx), env), new_env);
264 {
265 SCM rest = SCM_EOL;
266 for (; scm_is_pair (mx); mx = CDR (mx))
267 rest = scm_cons (eval (CAR (mx), env), rest);
268 new_env = scm_cons (scm_reverse (rest),
269 new_env);
270 }
271 }
272 else
273 {
274 for (; scm_is_pair (mx); mx = CDR (mx), nreq--)
275 new_env = scm_cons (eval (CAR (mx), env), new_env);
276 if (SCM_UNLIKELY (nreq != 0))
277 scm_wrong_num_args (proc);
278 }
279 x = SCM_CLOSURE_BODY (proc);
280 env = new_env;
281 goto loop;
282 }
283 else
284 {
285 SCM rest = SCM_EOL;
286 for (; scm_is_pair (mx); mx = CDR (mx))
287 rest = scm_cons (eval (CAR (mx), env), rest);
288 return apply (proc, scm_reverse (rest));
289 }
290
291 case SCM_M_CONT:
292 {
293 int first;
294 SCM val = scm_make_continuation (&first);
295
296 if (!first)
297 return val;
298 else
299 {
300 proc = eval (mx, env);
301 args = scm_list_1 (val);
302 goto apply_proc;
303 }
304 }
305
306 case SCM_M_CALL_WITH_VALUES:
307 {
308 SCM producer;
309 SCM v;
310
311 producer = eval (CAR (mx), env);
312 proc = eval (CDR (mx), env); /* proc is the consumer. */
313 v = apply (producer, SCM_EOL);
314 if (SCM_VALUESP (v))
315 args = scm_struct_ref (v, SCM_INUM0);
316 else
317 args = scm_list_1 (v);
318 goto apply_proc;
319 }
320
321 case SCM_M_LEXICAL_REF:
322 {
323 int n;
324 SCM ret;
325 for (n = SCM_I_INUM (mx); n; n--)
326 env = CDR (env);
327 ret = CAR (env);
328 if (SCM_UNLIKELY (SCM_UNBNDP (ret)))
329 /* we don't know what variable, though, because we don't have its
330 name */
331 error_used_before_defined ();
332 return ret;
333 }
334
335 case SCM_M_LEXICAL_SET:
336 {
337 int n;
338 SCM val = eval (CDR (mx), env);
339 for (n = SCM_I_INUM (CAR (mx)); n; n--)
340 env = CDR (env);
341 SCM_SETCAR (env, val);
342 return SCM_UNSPECIFIED;
343 }
344
345 case SCM_M_TOPLEVEL_REF:
346 if (SCM_VARIABLEP (mx))
347 return SCM_VARIABLE_REF (mx);
348 else
349 {
350 SCM var;
351 while (scm_is_pair (env))
352 env = scm_cdr (env);
353 var = scm_module_variable (CAPTURE_ENV (env), mx);
354 if (scm_is_false (var) || scm_is_false (scm_variable_bound_p (var)))
355 error_unbound_variable (mx);
356 SCM_SET_SMOB_OBJECT (x, var);
357 return SCM_VARIABLE_REF (var);
358 }
359
360 case SCM_M_TOPLEVEL_SET:
361 {
362 SCM var = CAR (mx);
363 SCM val = eval (CDR (mx), env);
364 if (SCM_VARIABLEP (var))
365 {
366 SCM_VARIABLE_SET (var, val);
367 return SCM_UNSPECIFIED;
368 }
369 else
370 {
371 while (scm_is_pair (env))
372 env = scm_cdr (env);
373 var = scm_module_variable (CAPTURE_ENV (env), var);
374 if (scm_is_false (var) || scm_is_false (scm_variable_bound_p (var)))
375 error_unbound_variable (CAR (mx));
376 SCM_SETCAR (mx, var);
377 SCM_VARIABLE_SET (var, val);
378 return SCM_UNSPECIFIED;
379 }
380 }
381
382 case SCM_M_MODULE_REF:
383 if (SCM_VARIABLEP (mx))
384 return SCM_VARIABLE_REF (mx);
385 else
386 {
387 SCM mod, var;
388 mod = scm_resolve_module (CAR (mx));
389 if (scm_is_true (CDDR (mx)))
390 mod = scm_module_public_interface (mod);
391 var = scm_module_lookup (mod, CADR (mx));
392 if (scm_is_true (scm_variable_bound_p (var)))
393 SCM_SET_SMOB_OBJECT (x, var);
394 return scm_variable_ref (var);
395 }
396
397 case SCM_M_MODULE_SET:
398 if (SCM_VARIABLEP (CDR (mx)))
399 {
400 SCM_VARIABLE_SET (CDR (mx), eval (CAR (mx), env));
401 return SCM_UNSPECIFIED;
402 }
403 else
404 {
405 SCM mod, var;
406 mod = scm_resolve_module (CADR (mx));
407 if (scm_is_true (CDDDR (mx)))
408 mod = scm_module_public_interface (mod);
409 var = scm_module_lookup (mod, CADDR (mx));
410 SCM_SET_SMOB_OBJECT (x, var);
411 SCM_VARIABLE_SET (var, eval (CAR (mx), env));
412 return SCM_UNSPECIFIED;
413 }
414
415 default:
416 abort ();
417 }
418 }
419
420 static SCM
421 apply (SCM proc, SCM args)
422 {
423 SCM arg1, arg2, arg3, rest;
424 unsigned int nargs;
425
426 SCM_ASRTGO (SCM_NIMP (proc), badproc);
427
428 /* Args contains a list of all args. */
429 {
430 int ilen = scm_ilength (args);
431 if (ilen < 0)
432 scm_wrong_num_args (proc);
433 nargs = ilen;
434 }
435
436 /* Parse args. */
437 switch (nargs)
438 {
439 case 0:
440 arg1 = SCM_UNDEFINED; arg2 = SCM_UNDEFINED;
441 arg3 = SCM_UNDEFINED; rest = SCM_EOL;
442 break;
443 case 1:
444 arg1 = CAR (args); arg2 = SCM_UNDEFINED;
445 arg3 = SCM_UNDEFINED; rest = SCM_EOL;
446 break;
447 case 2:
448 arg1 = CAR (args); arg2 = CADR (args);
449 arg3 = SCM_UNDEFINED; rest = SCM_EOL;
450 break;
451 default:
452 arg1 = CAR (args); arg2 = CADR (args);
453 arg3 = CADDR (args); rest = CDDDR (args);
454 break;
455 }
456
457 tail:
458 switch (SCM_TYP7 (proc))
459 {
460 case scm_tcs_closures:
461 {
462 int nreq = SCM_CLOSURE_NUM_REQUIRED_ARGS (proc);
463 SCM env = SCM_ENV (proc);
464 if (SCM_CLOSURE_HAS_REST_ARGS (proc))
465 {
466 if (SCM_UNLIKELY (scm_ilength (args) < nreq))
467 scm_wrong_num_args (proc);
468 for (; nreq; nreq--, args = CDR (args))
469 env = scm_cons (CAR (args), env);
470 env = scm_cons (args, env);
471 }
472 else
473 {
474 for (; scm_is_pair (args); args = CDR (args), nreq--)
475 env = scm_cons (CAR (args), env);
476 if (SCM_UNLIKELY (nreq != 0))
477 scm_wrong_num_args (proc);
478 }
479 return eval (SCM_CLOSURE_BODY (proc), env);
480 }
481 case scm_tc7_subr_2o:
482 if (nargs > 2 || nargs < 1) scm_wrong_num_args (proc);
483 return SCM_SUBRF (proc) (arg1, arg2);
484 case scm_tc7_subr_2:
485 if (nargs != 2) scm_wrong_num_args (proc);
486 return SCM_SUBRF (proc) (arg1, arg2);
487 case scm_tc7_subr_0:
488 if (nargs != 0) scm_wrong_num_args (proc);
489 return SCM_SUBRF (proc) ();
490 case scm_tc7_subr_1:
491 if (nargs != 1) scm_wrong_num_args (proc);
492 return SCM_SUBRF (proc) (arg1);
493 case scm_tc7_subr_1o:
494 if (nargs > 1) scm_wrong_num_args (proc);
495 return SCM_SUBRF (proc) (arg1);
496 case scm_tc7_dsubr:
497 if (nargs != 1) scm_wrong_num_args (proc);
498 if (SCM_I_INUMP (arg1))
499 return scm_from_double (SCM_DSUBRF (proc) ((double) SCM_I_INUM (arg1)));
500 else if (SCM_REALP (arg1))
501 return scm_from_double (SCM_DSUBRF (proc) (SCM_REAL_VALUE (arg1)));
502 else if (SCM_BIGP (arg1))
503 return scm_from_double (SCM_DSUBRF (proc) (scm_i_big2dbl (arg1)));
504 else if (SCM_FRACTIONP (arg1))
505 return scm_from_double (SCM_DSUBRF (proc) (scm_i_fraction2double (arg1)));
506 SCM_WTA_DISPATCH_1 (*SCM_SUBR_GENERIC (proc), arg1,
507 SCM_ARG1, scm_i_symbol_chars (SCM_SUBR_NAME (proc)));
508 case scm_tc7_cxr:
509 if (nargs != 1) scm_wrong_num_args (proc);
510 return scm_i_chase_pairs (arg1, (scm_t_bits) SCM_SUBRF (proc));
511 case scm_tc7_subr_3:
512 if (nargs != 3) scm_wrong_num_args (proc);
513 return SCM_SUBRF (proc) (arg1, arg2, arg3);
514 case scm_tc7_lsubr:
515 return SCM_SUBRF (proc) (args);
516 case scm_tc7_lsubr_2:
517 if (nargs < 2) scm_wrong_num_args (proc);
518 return SCM_SUBRF (proc) (arg1, arg2, scm_cddr (args));
519 case scm_tc7_asubr:
520 if (nargs < 2)
521 return SCM_SUBRF (proc) (arg1, SCM_UNDEFINED);
522 for (args = CDR (args); nargs > 1; args = CDR (args), nargs--)
523 arg1 = SCM_SUBRF (proc) (arg1, CAR (args));
524 return arg1;
525 case scm_tc7_program:
526 return scm_vm_apply (scm_the_vm (), proc, args);
527 case scm_tc7_rpsubr:
528 if (nargs == 0)
529 return SCM_BOOL_T;
530 for (args = CDR (args); nargs > 1;
531 arg1 = CAR (args), args = CDR (args), nargs--)
532 if (scm_is_false (SCM_SUBRF (proc) (arg1, CAR (args))))
533 return SCM_BOOL_F;
534 return SCM_BOOL_T;
535 case scm_tc7_smob:
536 if (!SCM_SMOB_APPLICABLE_P (proc))
537 goto badproc;
538 switch (nargs)
539 {
540 case 0:
541 return SCM_SMOB_APPLY_0 (proc);
542 case 1:
543 return SCM_SMOB_APPLY_1 (proc, arg1);
544 case 2:
545 return SCM_SMOB_APPLY_2 (proc, arg1, arg2);
546 default:
547 return SCM_SMOB_APPLY_3 (proc, arg1, arg2, scm_cddr (args));
548 }
549 case scm_tc7_gsubr:
550 return scm_i_gsubr_apply_list (proc, args);
551 case scm_tc7_pws:
552 return apply (SCM_PROCEDURE (proc), args);
553 case scm_tcs_struct:
554 if (SCM_STRUCT_APPLICABLE_P (proc))
555 {
556 proc = SCM_STRUCT_PROCEDURE (proc);
557 goto tail;
558 }
559 else
560 goto badproc;
561 default:
562 badproc:
563 scm_wrong_type_arg ("apply", SCM_ARG1, proc);
564 }
565 }
566
567
568 scm_t_option scm_eval_opts[] = {
569 { SCM_OPTION_INTEGER, "stack", 22000, "Size of thread stacks (in machine words)." },
570 { 0 }
571 };
572
573 scm_t_option scm_debug_opts[] = {
574 { SCM_OPTION_BOOLEAN, "cheap", 1,
575 "*This option is now obsolete. Setting it has no effect." },
576 { SCM_OPTION_BOOLEAN, "breakpoints", 0, "*Check for breakpoints." },
577 { SCM_OPTION_BOOLEAN, "trace", 0, "*Trace mode." },
578 { SCM_OPTION_BOOLEAN, "procnames", 1,
579 "Record procedure names at definition." },
580 { SCM_OPTION_BOOLEAN, "backwards", 0,
581 "Display backtrace in anti-chronological order." },
582 { SCM_OPTION_INTEGER, "width", 79, "Maximal width of backtrace." },
583 { SCM_OPTION_INTEGER, "indent", 10, "Maximal indentation in backtrace." },
584 { SCM_OPTION_INTEGER, "frames", 3,
585 "Maximum number of tail-recursive frames in backtrace." },
586 { SCM_OPTION_INTEGER, "maxdepth", 1000,
587 "Maximal number of stored backtrace frames." },
588 { SCM_OPTION_INTEGER, "depth", 20, "Maximal length of printed backtrace." },
589 { SCM_OPTION_BOOLEAN, "backtrace", 0, "Show backtrace on error." },
590 { SCM_OPTION_BOOLEAN, "debug", 0, "Use the debugging evaluator." },
591 /* This default stack limit will be overridden by debug.c:init_stack_limit(),
592 if we have getrlimit() and the stack limit is not INFINITY. But it is still
593 important, as some systems have both the soft and the hard limits set to
594 INFINITY; in that case we fall back to this value.
595
596 The situation is aggravated by certain compilers, which can consume
597 "beaucoup de stack", as they say in France.
598
599 See http://thread.gmane.org/gmane.lisp.guile.devel/8599/focus=8662 for
600 more discussion. This setting is 640 KB on 32-bit arches (should be enough
601 for anyone!) or a whoppin' 1280 KB on 64-bit arches.
602 */
603 { SCM_OPTION_INTEGER, "stack", 160000, "Stack size limit (measured in words; 0 = no check)." },
604 { SCM_OPTION_SCM, "show-file-name", (unsigned long)SCM_BOOL_T,
605 "Show file names and line numbers "
606 "in backtraces when not `#f'. A value of `base' "
607 "displays only base names, while `#t' displays full names."},
608 { SCM_OPTION_BOOLEAN, "warn-deprecated", 0,
609 "Warn when deprecated features are used." },
610 { 0 },
611 };
612
613
614 /*
615 * this ordering is awkward and illogical, but we maintain it for
616 * compatibility. --hwn
617 */
618 scm_t_option scm_evaluator_trap_table[] = {
619 { SCM_OPTION_BOOLEAN, "traps", 0, "Enable evaluator traps." },
620 { SCM_OPTION_BOOLEAN, "enter-frame", 0, "Trap when eval enters new frame." },
621 { SCM_OPTION_BOOLEAN, "apply-frame", 0, "Trap when entering apply." },
622 { SCM_OPTION_BOOLEAN, "exit-frame", 0, "Trap when exiting eval or apply." },
623 { SCM_OPTION_SCM, "enter-frame-handler", (unsigned long)SCM_BOOL_F, "Handler for enter-frame traps." },
624 { SCM_OPTION_SCM, "apply-frame-handler", (unsigned long)SCM_BOOL_F, "Handler for apply-frame traps." },
625 { SCM_OPTION_SCM, "exit-frame-handler", (unsigned long)SCM_BOOL_F, "Handler for exit-frame traps." },
626 { SCM_OPTION_BOOLEAN, "memoize-symbol", 0, "Trap when memoizing a symbol." },
627 { SCM_OPTION_SCM, "memoize-symbol-handler", (unsigned long)SCM_BOOL_F, "The handler for memoization." },
628 { 0 }
629 };
630
631
632 SCM_DEFINE (scm_eval_options_interface, "eval-options-interface", 0, 1, 0,
633 (SCM setting),
634 "Option interface for the evaluation options. Instead of using\n"
635 "this procedure directly, use the procedures @code{eval-enable},\n"
636 "@code{eval-disable}, @code{eval-set!} and @code{eval-options}.")
637 #define FUNC_NAME s_scm_eval_options_interface
638 {
639 SCM ans;
640
641 scm_dynwind_begin (0);
642 scm_dynwind_critical_section (SCM_BOOL_F);
643 ans = scm_options (setting,
644 scm_eval_opts,
645 FUNC_NAME);
646 scm_dynwind_end ();
647
648 return ans;
649 }
650 #undef FUNC_NAME
651
652
653 SCM_DEFINE (scm_evaluator_traps, "evaluator-traps-interface", 0, 1, 0,
654 (SCM setting),
655 "Option interface for the evaluator trap options.")
656 #define FUNC_NAME s_scm_evaluator_traps
657 {
658 SCM ans;
659
660
661 scm_options_try (setting,
662 scm_evaluator_trap_table,
663 FUNC_NAME, 1);
664 SCM_CRITICAL_SECTION_START;
665 ans = scm_options (setting,
666 scm_evaluator_trap_table,
667 FUNC_NAME);
668
669 /* njrev: same again. */
670 SCM_CRITICAL_SECTION_END;
671 return ans;
672 }
673 #undef FUNC_NAME
674
675
676
677 \f
678
679 /* Simple procedure calls
680 */
681
682 SCM
683 scm_call_0 (SCM proc)
684 {
685 if (SCM_PROGRAM_P (proc))
686 return scm_c_vm_run (scm_the_vm (), proc, NULL, 0);
687 else
688 return scm_apply (proc, SCM_EOL, SCM_EOL);
689 }
690
691 SCM
692 scm_call_1 (SCM proc, SCM arg1)
693 {
694 if (SCM_PROGRAM_P (proc))
695 return scm_c_vm_run (scm_the_vm (), proc, &arg1, 1);
696 else
697 return scm_apply (proc, arg1, scm_listofnull);
698 }
699
700 SCM
701 scm_call_2 (SCM proc, SCM arg1, SCM arg2)
702 {
703 if (SCM_PROGRAM_P (proc))
704 {
705 SCM args[] = { arg1, arg2 };
706 return scm_c_vm_run (scm_the_vm (), proc, args, 2);
707 }
708 else
709 return scm_apply (proc, arg1, scm_cons (arg2, scm_listofnull));
710 }
711
712 SCM
713 scm_call_3 (SCM proc, SCM arg1, SCM arg2, SCM arg3)
714 {
715 if (SCM_PROGRAM_P (proc))
716 {
717 SCM args[] = { arg1, arg2, arg3 };
718 return scm_c_vm_run (scm_the_vm (), proc, args, 3);
719 }
720 else
721 return scm_apply (proc, arg1, scm_cons2 (arg2, arg3, scm_listofnull));
722 }
723
724 SCM
725 scm_call_4 (SCM proc, SCM arg1, SCM arg2, SCM arg3, SCM arg4)
726 {
727 if (SCM_PROGRAM_P (proc))
728 {
729 SCM args[] = { arg1, arg2, arg3, arg4 };
730 return scm_c_vm_run (scm_the_vm (), proc, args, 4);
731 }
732 else
733 return scm_apply (proc, arg1, scm_cons2 (arg2, arg3,
734 scm_cons (arg4, scm_listofnull)));
735 }
736
737 /* Simple procedure applies
738 */
739
740 SCM
741 scm_apply_0 (SCM proc, SCM args)
742 {
743 return scm_apply (proc, args, SCM_EOL);
744 }
745
746 SCM
747 scm_apply_1 (SCM proc, SCM arg1, SCM args)
748 {
749 return scm_apply (proc, scm_cons (arg1, args), SCM_EOL);
750 }
751
752 SCM
753 scm_apply_2 (SCM proc, SCM arg1, SCM arg2, SCM args)
754 {
755 return scm_apply (proc, scm_cons2 (arg1, arg2, args), SCM_EOL);
756 }
757
758 SCM
759 scm_apply_3 (SCM proc, SCM arg1, SCM arg2, SCM arg3, SCM args)
760 {
761 return scm_apply (proc, scm_cons (arg1, scm_cons2 (arg2, arg3, args)),
762 SCM_EOL);
763 }
764
765 /* This code processes the arguments to apply:
766
767 (apply PROC ARG1 ... ARGS)
768
769 Given a list (ARG1 ... ARGS), this function conses the ARG1
770 ... arguments onto the front of ARGS, and returns the resulting
771 list. Note that ARGS is a list; thus, the argument to this
772 function is a list whose last element is a list.
773
774 Apply calls this function, and applies PROC to the elements of the
775 result. apply:nconc2last takes care of building the list of
776 arguments, given (ARG1 ... ARGS).
777
778 Rather than do new consing, apply:nconc2last destroys its argument.
779 On that topic, this code came into my care with the following
780 beautifully cryptic comment on that topic: "This will only screw
781 you if you do (scm_apply scm_apply '( ... ))" If you know what
782 they're referring to, send me a patch to this comment. */
783
784 SCM_DEFINE (scm_nconc2last, "apply:nconc2last", 1, 0, 0,
785 (SCM lst),
786 "Given a list (@var{arg1} @dots{} @var{args}), this function\n"
787 "conses the @var{arg1} @dots{} arguments onto the front of\n"
788 "@var{args}, and returns the resulting list. Note that\n"
789 "@var{args} is a list; thus, the argument to this function is\n"
790 "a list whose last element is a list.\n"
791 "Note: Rather than do new consing, @code{apply:nconc2last}\n"
792 "destroys its argument, so use with care.")
793 #define FUNC_NAME s_scm_nconc2last
794 {
795 SCM *lloc;
796 SCM_VALIDATE_NONEMPTYLIST (1, lst);
797 lloc = &lst;
798 while (!scm_is_null (SCM_CDR (*lloc))) /* Perhaps should be
799 SCM_NULL_OR_NIL_P, but not
800 needed in 99.99% of cases,
801 and it could seriously hurt
802 performance. - Neil */
803 lloc = SCM_CDRLOC (*lloc);
804 SCM_ASSERT (scm_ilength (SCM_CAR (*lloc)) >= 0, lst, SCM_ARG1, FUNC_NAME);
805 *lloc = SCM_CAR (*lloc);
806 return lst;
807 }
808 #undef FUNC_NAME
809
810
811
812 /* Typechecking for multi-argument MAP and FOR-EACH.
813
814 Verify that each element of the vector ARGV, except for the first,
815 is a proper list whose length is LEN. Attribute errors to WHO,
816 and claim that the i'th element of ARGV is WHO's i+2'th argument. */
817 static inline void
818 check_map_args (SCM argv,
819 long len,
820 SCM gf,
821 SCM proc,
822 SCM args,
823 const char *who)
824 {
825 long i;
826
827 for (i = SCM_SIMPLE_VECTOR_LENGTH (argv) - 1; i >= 1; i--)
828 {
829 SCM elt = SCM_SIMPLE_VECTOR_REF (argv, i);
830 long elt_len = scm_ilength (elt);
831
832 if (elt_len < 0)
833 {
834 if (gf)
835 scm_apply_generic (gf, scm_cons (proc, args));
836 else
837 scm_wrong_type_arg (who, i + 2, elt);
838 }
839
840 if (elt_len != len)
841 scm_out_of_range_pos (who, elt, scm_from_long (i + 2));
842 }
843 }
844
845
846 SCM_GPROC (s_map, "map", 2, 0, 1, scm_map, g_map);
847
848 /* Note: Currently, scm_map applies PROC to the argument list(s)
849 sequentially, starting with the first element(s). This is used in
850 evalext.c where the Scheme procedure `map-in-order', which guarantees
851 sequential behaviour, is implemented using scm_map. If the
852 behaviour changes, we need to update `map-in-order'.
853 */
854
855 SCM
856 scm_map (SCM proc, SCM arg1, SCM args)
857 #define FUNC_NAME s_map
858 {
859 long i, len;
860 SCM res = SCM_EOL;
861 SCM *pres = &res;
862
863 len = scm_ilength (arg1);
864 SCM_GASSERTn (len >= 0,
865 g_map, scm_cons2 (proc, arg1, args), SCM_ARG2, s_map);
866 SCM_VALIDATE_REST_ARGUMENT (args);
867 if (scm_is_null (args))
868 {
869 SCM_GASSERT2 (scm_is_true (scm_procedure_p (proc)), g_map, proc, arg1, SCM_ARG1, s_map);
870 while (SCM_NIMP (arg1))
871 {
872 *pres = scm_list_1 (scm_call_1 (proc, SCM_CAR (arg1)));
873 pres = SCM_CDRLOC (*pres);
874 arg1 = SCM_CDR (arg1);
875 }
876 return res;
877 }
878 if (scm_is_null (SCM_CDR (args)))
879 {
880 SCM arg2 = SCM_CAR (args);
881 int len2 = scm_ilength (arg2);
882 SCM_GASSERTn (scm_is_true (scm_procedure_p (proc)), g_map,
883 scm_cons2 (proc, arg1, args), SCM_ARG1, s_map);
884 SCM_GASSERTn (len2 >= 0,
885 g_map, scm_cons2 (proc, arg1, args), SCM_ARG3, s_map);
886 if (len2 != len)
887 SCM_OUT_OF_RANGE (3, arg2);
888 while (SCM_NIMP (arg1))
889 {
890 *pres = scm_list_1 (scm_call_2 (proc, SCM_CAR (arg1), SCM_CAR (arg2)));
891 pres = SCM_CDRLOC (*pres);
892 arg1 = SCM_CDR (arg1);
893 arg2 = SCM_CDR (arg2);
894 }
895 return res;
896 }
897 arg1 = scm_cons (arg1, args);
898 args = scm_vector (arg1);
899 check_map_args (args, len, g_map, proc, arg1, s_map);
900 while (1)
901 {
902 arg1 = SCM_EOL;
903 for (i = SCM_SIMPLE_VECTOR_LENGTH (args) - 1; i >= 0; i--)
904 {
905 SCM elt = SCM_SIMPLE_VECTOR_REF (args, i);
906 if (SCM_IMP (elt))
907 return res;
908 arg1 = scm_cons (SCM_CAR (elt), arg1);
909 SCM_SIMPLE_VECTOR_SET (args, i, SCM_CDR (elt));
910 }
911 *pres = scm_list_1 (scm_apply (proc, arg1, SCM_EOL));
912 pres = SCM_CDRLOC (*pres);
913 }
914 }
915 #undef FUNC_NAME
916
917
918 SCM_GPROC (s_for_each, "for-each", 2, 0, 1, scm_for_each, g_for_each);
919
920 SCM
921 scm_for_each (SCM proc, SCM arg1, SCM args)
922 #define FUNC_NAME s_for_each
923 {
924 long i, len;
925 len = scm_ilength (arg1);
926 SCM_GASSERTn (len >= 0, g_for_each, scm_cons2 (proc, arg1, args),
927 SCM_ARG2, s_for_each);
928 SCM_VALIDATE_REST_ARGUMENT (args);
929 if (scm_is_null (args))
930 {
931 SCM_GASSERT2 (scm_is_true (scm_procedure_p (proc)), g_for_each,
932 proc, arg1, SCM_ARG1, s_for_each);
933 while (SCM_NIMP (arg1))
934 {
935 scm_call_1 (proc, SCM_CAR (arg1));
936 arg1 = SCM_CDR (arg1);
937 }
938 return SCM_UNSPECIFIED;
939 }
940 if (scm_is_null (SCM_CDR (args)))
941 {
942 SCM arg2 = SCM_CAR (args);
943 int len2 = scm_ilength (arg2);
944 SCM_GASSERTn (scm_is_true (scm_procedure_p (proc)), g_for_each,
945 scm_cons2 (proc, arg1, args), SCM_ARG1, s_for_each);
946 SCM_GASSERTn (len2 >= 0, g_for_each,
947 scm_cons2 (proc, arg1, args), SCM_ARG3, s_for_each);
948 if (len2 != len)
949 SCM_OUT_OF_RANGE (3, arg2);
950 while (SCM_NIMP (arg1))
951 {
952 scm_call_2 (proc, SCM_CAR (arg1), SCM_CAR (arg2));
953 arg1 = SCM_CDR (arg1);
954 arg2 = SCM_CDR (arg2);
955 }
956 return SCM_UNSPECIFIED;
957 }
958 arg1 = scm_cons (arg1, args);
959 args = scm_vector (arg1);
960 check_map_args (args, len, g_for_each, proc, arg1, s_for_each);
961 while (1)
962 {
963 arg1 = SCM_EOL;
964 for (i = SCM_SIMPLE_VECTOR_LENGTH (args) - 1; i >= 0; i--)
965 {
966 SCM elt = SCM_SIMPLE_VECTOR_REF (args, i);
967 if (SCM_IMP (elt))
968 return SCM_UNSPECIFIED;
969 arg1 = scm_cons (SCM_CAR (elt), arg1);
970 SCM_SIMPLE_VECTOR_SET (args, i, SCM_CDR (elt));
971 }
972 scm_apply (proc, arg1, SCM_EOL);
973 }
974 }
975 #undef FUNC_NAME
976
977
978 SCM
979 scm_closure (SCM code, SCM env)
980 {
981 SCM z;
982 SCM closcar = scm_cons (code, SCM_EOL);
983 z = scm_immutable_cell (SCM_UNPACK (closcar) + scm_tc3_closure,
984 (scm_t_bits) env);
985 scm_remember_upto_here (closcar);
986 return z;
987 }
988
989
990 scm_t_bits scm_tc16_promise;
991
992 SCM_DEFINE (scm_make_promise, "make-promise", 1, 0, 0,
993 (SCM thunk),
994 "Create a new promise object.\n\n"
995 "@code{make-promise} is a procedural form of @code{delay}.\n"
996 "These two expressions are equivalent:\n"
997 "@lisp\n"
998 "(delay @var{exp})\n"
999 "(make-promise (lambda () @var{exp}))\n"
1000 "@end lisp\n")
1001 #define FUNC_NAME s_scm_make_promise
1002 {
1003 SCM_VALIDATE_THUNK (1, thunk);
1004 SCM_RETURN_NEWSMOB2 (scm_tc16_promise,
1005 SCM_UNPACK (thunk),
1006 scm_make_recursive_mutex ());
1007 }
1008 #undef FUNC_NAME
1009
1010 static int
1011 promise_print (SCM exp, SCM port, scm_print_state *pstate)
1012 {
1013 int writingp = SCM_WRITINGP (pstate);
1014 scm_puts ("#<promise ", port);
1015 SCM_SET_WRITINGP (pstate, 1);
1016 scm_iprin1 (SCM_PROMISE_DATA (exp), port, pstate);
1017 SCM_SET_WRITINGP (pstate, writingp);
1018 scm_putc ('>', port);
1019 return !0;
1020 }
1021
1022 SCM_DEFINE (scm_force, "force", 1, 0, 0,
1023 (SCM promise),
1024 "If the promise @var{x} has not been computed yet, compute and\n"
1025 "return @var{x}, otherwise just return the previously computed\n"
1026 "value.")
1027 #define FUNC_NAME s_scm_force
1028 {
1029 SCM_VALIDATE_SMOB (1, promise, promise);
1030 scm_lock_mutex (SCM_PROMISE_MUTEX (promise));
1031 if (!SCM_PROMISE_COMPUTED_P (promise))
1032 {
1033 SCM ans = scm_call_0 (SCM_PROMISE_DATA (promise));
1034 if (!SCM_PROMISE_COMPUTED_P (promise))
1035 {
1036 SCM_SET_PROMISE_DATA (promise, ans);
1037 SCM_SET_PROMISE_COMPUTED (promise);
1038 }
1039 }
1040 scm_unlock_mutex (SCM_PROMISE_MUTEX (promise));
1041 return SCM_PROMISE_DATA (promise);
1042 }
1043 #undef FUNC_NAME
1044
1045
1046 SCM_DEFINE (scm_promise_p, "promise?", 1, 0, 0,
1047 (SCM obj),
1048 "Return true if @var{obj} is a promise, i.e. a delayed computation\n"
1049 "(@pxref{Delayed evaluation,,,r5rs.info,The Revised^5 Report on Scheme}).")
1050 #define FUNC_NAME s_scm_promise_p
1051 {
1052 return scm_from_bool (SCM_TYP16_PREDICATE (scm_tc16_promise, obj));
1053 }
1054 #undef FUNC_NAME
1055
1056 SCM_DEFINE (scm_primitive_eval, "primitive-eval", 1, 0, 0,
1057 (SCM exp),
1058 "Evaluate @var{exp} in the top-level environment specified by\n"
1059 "the current module.")
1060 #define FUNC_NAME s_scm_primitive_eval
1061 {
1062 SCM transformer = scm_current_module_transformer ();
1063 if (scm_is_true (transformer))
1064 exp = scm_call_1 (transformer, exp);
1065 exp = scm_memoize_expression (exp);
1066 return eval (exp, SCM_EOL);
1067 }
1068 #undef FUNC_NAME
1069
1070
1071 /* Eval does not take the second arg optionally. This is intentional
1072 * in order to be R5RS compatible, and to prepare for the new module
1073 * system, where we would like to make the choice of evaluation
1074 * environment explicit. */
1075
1076 SCM_DEFINE (scm_eval, "eval", 2, 0, 0,
1077 (SCM exp, SCM module_or_state),
1078 "Evaluate @var{exp}, a list representing a Scheme expression,\n"
1079 "in the top-level environment specified by\n"
1080 "@var{module_or_state}.\n"
1081 "While @var{exp} is evaluated (using @code{primitive-eval}),\n"
1082 "@var{module_or_state} is made the current module when\n"
1083 "it is a module, or the current dynamic state when it is\n"
1084 "a dynamic state."
1085 "Example: (eval '(+ 1 2) (interaction-environment))")
1086 #define FUNC_NAME s_scm_eval
1087 {
1088 SCM res;
1089
1090 scm_dynwind_begin (SCM_F_DYNWIND_REWINDABLE);
1091 if (scm_is_dynamic_state (module_or_state))
1092 scm_dynwind_current_dynamic_state (module_or_state);
1093 else if (scm_module_system_booted_p)
1094 {
1095 SCM_VALIDATE_MODULE (2, module_or_state);
1096 scm_dynwind_current_module (module_or_state);
1097 }
1098 /* otherwise if the module system isn't booted, ignore the module arg */
1099
1100 res = scm_primitive_eval (exp);
1101
1102 scm_dynwind_end ();
1103 return res;
1104 }
1105 #undef FUNC_NAME
1106
1107
1108 static SCM f_apply;
1109
1110 /* Apply a function to a list of arguments.
1111
1112 This function is exported to the Scheme level as taking two
1113 required arguments and a tail argument, as if it were:
1114 (lambda (proc arg1 . args) ...)
1115 Thus, if you just have a list of arguments to pass to a procedure,
1116 pass the list as ARG1, and '() for ARGS. If you have some fixed
1117 args, pass the first as ARG1, then cons any remaining fixed args
1118 onto the front of your argument list, and pass that as ARGS. */
1119
1120 SCM
1121 scm_apply (SCM proc, SCM arg1, SCM args)
1122 {
1123 /* Fix things up so that args contains all args. */
1124 if (scm_is_null (args))
1125 args = arg1;
1126 else
1127 args = scm_cons_star (arg1, args);
1128
1129 return apply (proc, args);
1130 }
1131
1132
1133 void
1134 scm_init_eval ()
1135 {
1136 scm_init_opts (scm_evaluator_traps,
1137 scm_evaluator_trap_table);
1138 scm_init_opts (scm_eval_options_interface,
1139 scm_eval_opts);
1140
1141 scm_tc16_promise = scm_make_smob_type ("promise", 0);
1142 scm_set_smob_print (scm_tc16_promise, promise_print);
1143
1144 scm_listofnull = scm_list_1 (SCM_EOL);
1145
1146 f_apply = scm_c_define_subr ("apply", scm_tc7_lsubr_2, scm_apply);
1147 scm_permanent_object (f_apply);
1148
1149 #include "libguile/eval.x"
1150
1151 scm_add_feature ("delay");
1152 }
1153
1154 /*
1155 Local Variables:
1156 c-file-style: "gnu"
1157 End:
1158 */
1159