* Removed unused object parameter from SCM_ASSYNT.
[bpt/guile.git] / libguile / eval.c
1 /* Copyright (C) 1995, 96, 97, 98, 99, 2000, 2001 Free Software Foundation, Inc.
2 *
3 * This program is free software; you can redistribute it and/or modify
4 * it under the terms of the GNU General Public License as published by
5 * the Free Software Foundation; either version 2, or (at your option)
6 * any later version.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this software; see the file COPYING. If not, write to
15 * the Free Software Foundation, Inc., 59 Temple Place, Suite 330,
16 * Boston, MA 02111-1307 USA
17 *
18 * As a special exception, the Free Software Foundation gives permission
19 * for additional uses of the text contained in its release of GUILE.
20 *
21 * The exception is that, if you link the GUILE library with other files
22 * to produce an executable, this does not by itself cause the
23 * resulting executable to be covered by the GNU General Public License.
24 * Your use of that executable is in no way restricted on account of
25 * linking the GUILE library code into it.
26 *
27 * This exception does not however invalidate any other reasons why
28 * the executable file might be covered by the GNU General Public License.
29 *
30 * This exception applies only to the code released by the
31 * Free Software Foundation under the name GUILE. If you copy
32 * code from other Free Software Foundation releases into a copy of
33 * GUILE, as the General Public License permits, the exception does
34 * not apply to the code that you add in this way. To avoid misleading
35 * anyone as to the status of such modified files, you must delete
36 * this exception notice from them.
37 *
38 * If you write modifications of your own for GUILE, it is your choice
39 * whether to permit this exception to apply to your modifications.
40 * If you do not wish that, delete this exception notice. */
41
42 /* Software engineering face-lift by Greg J. Badros, 11-Dec-1999,
43 gjb@cs.washington.edu, http://www.cs.washington.edu/homes/gjb */
44
45 \f
46
47 /* This file is read twice in order to produce debugging versions of
48 * scm_ceval and scm_apply. These functions, scm_deval and
49 * scm_dapply, are produced when we define the preprocessor macro
50 * DEVAL. The file is divided into sections which are treated
51 * differently with respect to DEVAL. The heads of these sections are
52 * marked with the string "SECTION:".
53 */
54
55
56 /* SECTION: This code is compiled once.
57 */
58
59 #ifndef DEVAL
60
61 /* We need this to get the definitions for HAVE_ALLOCA_H, etc. */
62 #include "libguile/scmconfig.h"
63
64 /* AIX requires this to be the first thing in the file. The #pragma
65 directive is indented so pre-ANSI compilers will ignore it, rather
66 than choke on it. */
67 #ifndef __GNUC__
68 # if HAVE_ALLOCA_H
69 # include <alloca.h>
70 # else
71 # ifdef _AIX
72 #pragma alloca
73 # else
74 # ifndef alloca /* predefined by HP cc +Olibcalls */
75 char *alloca ();
76 # endif
77 # endif
78 # endif
79 #endif
80
81 #include "libguile/_scm.h"
82 #include "libguile/debug.h"
83 #include "libguile/dynwind.h"
84 #include "libguile/alist.h"
85 #include "libguile/eq.h"
86 #include "libguile/continuations.h"
87 #include "libguile/throw.h"
88 #include "libguile/smob.h"
89 #include "libguile/macros.h"
90 #include "libguile/procprop.h"
91 #include "libguile/hashtab.h"
92 #include "libguile/hash.h"
93 #include "libguile/srcprop.h"
94 #include "libguile/stackchk.h"
95 #include "libguile/objects.h"
96 #include "libguile/async.h"
97 #include "libguile/feature.h"
98 #include "libguile/modules.h"
99 #include "libguile/ports.h"
100 #include "libguile/root.h"
101 #include "libguile/vectors.h"
102 #include "libguile/fluids.h"
103
104 #include "libguile/validate.h"
105 #include "libguile/eval.h"
106
107 \f
108
109 /* The evaluator contains a plethora of EVAL symbols.
110 * This is an attempt at explanation.
111 *
112 * The following macros should be used in code which is read twice
113 * (where the choice of evaluator is hard soldered):
114 *
115 * SCM_CEVAL is the symbol used within one evaluator to call itself.
116 * Originally, it is defined to scm_ceval, but is redefined to
117 * scm_deval during the second pass.
118 *
119 * SIDEVAL corresponds to SCM_CEVAL, but is used in situations where
120 * only side effects of expressions matter. All immediates are
121 * ignored.
122 *
123 * SCM_EVALIM is used when it is known that the expression is an
124 * immediate. (This macro never calls an evaluator.)
125 *
126 * EVALCAR evaluates the car of an expression.
127 *
128 * EVALCELLCAR is like EVALCAR, but is used when it is known that the
129 * car is a lisp cell.
130 *
131 * The following macros should be used in code which is read once
132 * (where the choice of evaluator is dynamic):
133 *
134 * SCM_XEVAL takes care of immediates without calling an evaluator. It
135 * then calls scm_ceval *or* scm_deval, depending on the debugging
136 * mode.
137 *
138 * SCM_XEVALCAR corresponds to EVALCAR, but uses scm_ceval *or* scm_deval
139 * depending on the debugging mode.
140 *
141 * The main motivation for keeping this plethora is efficiency
142 * together with maintainability (=> locality of code).
143 */
144
145 #define SCM_CEVAL scm_ceval
146 #define SIDEVAL(x, env) if (SCM_NIMP (x)) SCM_CEVAL((x), (env))
147
148 #define EVALCELLCAR(x, env) (SCM_SYMBOLP (SCM_CAR (x)) \
149 ? *scm_lookupcar (x, env, 1) \
150 : SCM_CEVAL (SCM_CAR (x), env))
151
152 #define EVALCAR(x, env) (SCM_NCELLP (SCM_CAR (x)) \
153 ? (SCM_IMP (SCM_CAR (x)) \
154 ? SCM_EVALIM (SCM_CAR (x), env) \
155 : SCM_GLOC_VAL (SCM_CAR (x))) \
156 : EVALCELLCAR (x, env))
157
158 #define EXTEND_ENV SCM_EXTEND_ENV
159
160 #ifdef MEMOIZE_LOCALS
161
162 SCM *
163 scm_ilookup (SCM iloc, SCM env)
164 {
165 register int ir = SCM_IFRAME (iloc);
166 register SCM er = env;
167 for (; 0 != ir; --ir)
168 er = SCM_CDR (er);
169 er = SCM_CAR (er);
170 for (ir = SCM_IDIST (iloc); 0 != ir; --ir)
171 er = SCM_CDR (er);
172 if (SCM_ICDRP (iloc))
173 return SCM_CDRLOC (er);
174 return SCM_CARLOC (SCM_CDR (er));
175 }
176 #endif
177
178 #ifdef USE_THREADS
179
180 /* The Lookup Car Race
181 - by Eva Luator
182
183 Memoization of variables and special forms is done while executing
184 the code for the first time. As long as there is only one thread
185 everything is fine, but as soon as two threads execute the same
186 code concurrently `for the first time' they can come into conflict.
187
188 This memoization includes rewriting variable references into more
189 efficient forms and expanding macros. Furthermore, macro expansion
190 includes `compiling' special forms like `let', `cond', etc. into
191 tree-code instructions.
192
193 There shouldn't normally be a problem with memoizing local and
194 global variable references (into ilocs and glocs), because all
195 threads will mutate the code in *exactly* the same way and (if I
196 read the C code correctly) it is not possible to observe a half-way
197 mutated cons cell. The lookup procedure can handle this
198 transparently without any critical sections.
199
200 It is different with macro expansion, because macro expansion
201 happens outside of the lookup procedure and can't be
202 undone. Therefore it can't cope with it. It has to indicate
203 failure when it detects a lost race and hope that the caller can
204 handle it. Luckily, it turns out that this is the case.
205
206 An example to illustrate this: Suppose that the follwing form will
207 be memoized concurrently by two threads
208
209 (let ((x 12)) x)
210
211 Let's first examine the lookup of X in the body. The first thread
212 decides that it has to find the symbol "x" in the environment and
213 starts to scan it. Then the other thread takes over and actually
214 overtakes the first. It looks up "x" and substitutes an
215 appropriate iloc for it. Now the first thread continues and
216 completes its lookup. It comes to exactly the same conclusions as
217 the second one and could - without much ado - just overwrite the
218 iloc with the same iloc.
219
220 But let's see what will happen when the race occurs while looking
221 up the symbol "let" at the start of the form. It could happen that
222 the second thread interrupts the lookup of the first thread and not
223 only substitutes a gloc for it but goes right ahead and replaces it
224 with the compiled form (#@let* (x 12) x). Now, when the first
225 thread completes its lookup, it would replace the #@let* with a
226 gloc pointing to the "let" binding, effectively reverting the form
227 to (let (x 12) x). This is wrong. It has to detect that it has
228 lost the race and the evaluator has to reconsider the changed form
229 completely.
230
231 This race condition could be resolved with some kind of traffic
232 light (like mutexes) around scm_lookupcar, but I think that it is
233 best to avoid them in this case. They would serialize memoization
234 completely and because lookup involves calling arbitrary Scheme
235 code (via the lookup-thunk), threads could be blocked for an
236 arbitrary amount of time or even deadlock. But with the current
237 solution a lot of unnecessary work is potentially done. */
238
239 /* SCM_LOOKUPCAR1 is was SCM_LOOKUPCAR used to be but is allowed to
240 return NULL to indicate a failed lookup due to some race conditions
241 between threads. This only happens when VLOC is the first cell of
242 a special form that will eventually be memoized (like `let', etc.)
243 In that case the whole lookup is bogus and the caller has to
244 reconsider the complete special form.
245
246 SCM_LOOKUPCAR is still there, of course. It just calls
247 SCM_LOOKUPCAR1 and aborts on recieving NULL. So SCM_LOOKUPCAR
248 should only be called when it is known that VLOC is not the first
249 pair of a special form. Otherwise, use SCM_LOOKUPCAR1 and check
250 for NULL. I think I've found the only places where this
251 applies. */
252
253 #endif /* USE_THREADS */
254
255 SCM_SYMBOL (scm_unbound_variable_key, "unbound-variable");
256
257 #ifdef USE_THREADS
258 static SCM *
259 scm_lookupcar1 (SCM vloc, SCM genv, int check)
260 #else
261 SCM *
262 scm_lookupcar (SCM vloc, SCM genv, int check)
263 #endif
264 {
265 SCM env = genv;
266 register SCM *al, fl, var = SCM_CAR (vloc);
267 #ifdef USE_THREADS
268 register SCM var2 = var;
269 #endif
270 #ifdef MEMOIZE_LOCALS
271 register SCM iloc = SCM_ILOC00;
272 #endif
273 for (; SCM_NIMP (env); env = SCM_CDR (env))
274 {
275 if (!SCM_CONSP (SCM_CAR (env)))
276 break;
277 al = SCM_CARLOC (env);
278 for (fl = SCM_CAR (*al); SCM_NIMP (fl); fl = SCM_CDR (fl))
279 {
280 if (SCM_NCONSP (fl))
281 {
282 if (SCM_EQ_P (fl, var))
283 {
284 #ifdef MEMOIZE_LOCALS
285 #ifdef USE_THREADS
286 if (! SCM_EQ_P (SCM_CAR (vloc), var))
287 goto race;
288 #endif
289 SCM_SET_CELL_WORD_0 (vloc, SCM_UNPACK (iloc) + SCM_ICDR);
290 #endif
291 return SCM_CDRLOC (*al);
292 }
293 else
294 break;
295 }
296 al = SCM_CDRLOC (*al);
297 if (SCM_EQ_P (SCM_CAR (fl), var))
298 {
299 #ifdef MEMOIZE_LOCALS
300 #ifndef SCM_RECKLESS /* letrec inits to SCM_UNDEFINED */
301 if (SCM_UNBNDP (SCM_CAR (*al)))
302 {
303 env = SCM_EOL;
304 goto errout;
305 }
306 #endif
307 #ifdef USE_THREADS
308 if (SCM_CAR (vloc) != var)
309 goto race;
310 #endif
311 SCM_SETCAR (vloc, iloc);
312 #endif
313 return SCM_CARLOC (*al);
314 }
315 #ifdef MEMOIZE_LOCALS
316 iloc = SCM_PACK (SCM_UNPACK (iloc) + SCM_IDINC);
317 #endif
318 }
319 #ifdef MEMOIZE_LOCALS
320 iloc = SCM_PACK ((~SCM_IDSTMSK) & (SCM_UNPACK(iloc) + SCM_IFRINC));
321 #endif
322 }
323 {
324 SCM top_thunk, vcell;
325 if (SCM_NIMP (env))
326 {
327 top_thunk = SCM_CAR (env); /* env now refers to a top level env thunk */
328 env = SCM_CDR (env);
329 }
330 else
331 top_thunk = SCM_BOOL_F;
332 vcell = scm_sym2vcell (var, top_thunk, SCM_BOOL_F);
333 if (SCM_FALSEP (vcell))
334 goto errout;
335 else
336 var = vcell;
337 }
338 #ifndef SCM_RECKLESS
339 if (SCM_NNULLP (env) || SCM_UNBNDP (SCM_CDR (var)))
340 {
341 var = SCM_CAR (var);
342 errout:
343 /* scm_everr (vloc, genv,...) */
344 if (check)
345 {
346 if (SCM_NULLP (env))
347 scm_error (scm_unbound_variable_key, NULL, "Unbound variable: ~S",
348 scm_cons (var, SCM_EOL), SCM_BOOL_F);
349 else
350 scm_misc_error (NULL, "Damaged environment: ~S",
351 scm_cons (var, SCM_EOL));
352 }
353 else {
354 /* A variable could not be found, but we shall not throw an error. */
355 static SCM undef_object = SCM_UNDEFINED;
356 return &undef_object;
357 }
358 }
359 #endif
360 #ifdef USE_THREADS
361 if (SCM_CAR (vloc) != var2)
362 {
363 /* Some other thread has changed the very cell we are working
364 on. In effect, it must have done our job or messed it up
365 completely. */
366 race:
367 var = SCM_CAR (vloc);
368 if (SCM_ITAG3 (var) == scm_tc3_cons_gloc)
369 return SCM_GLOC_VAL_LOC (var);
370 #ifdef MEMOIZE_LOCALS
371 if (SCM_ITAG7 (var) == SCM_ITAG7 (SCM_ILOC00))
372 return scm_ilookup (var, genv);
373 #endif
374 /* We can't cope with anything else than glocs and ilocs. When
375 a special form has been memoized (i.e. `let' into `#@let') we
376 return NULL and expect the calling function to do the right
377 thing. For the evaluator, this means going back and redoing
378 the dispatch on the car of the form. */
379 return NULL;
380 }
381 #endif /* USE_THREADS */
382
383 SCM_SET_CELL_WORD_0 (vloc, SCM_UNPACK (var) + scm_tc3_cons_gloc);
384 /* Except wait...what if the var is not a vcell,
385 * but syntax or something.... */
386 return SCM_CDRLOC (var);
387 }
388
389 #ifdef USE_THREADS
390 SCM *
391 scm_lookupcar (SCM vloc, SCM genv, int check)
392 {
393 SCM *loc = scm_lookupcar1 (vloc, genv, check);
394 if (loc == NULL)
395 abort ();
396 return loc;
397 }
398 #endif
399
400 #define unmemocar scm_unmemocar
401
402 SCM
403 scm_unmemocar (SCM form, SCM env)
404 {
405 SCM c;
406
407 if (SCM_IMP (form))
408 return form;
409 c = SCM_CAR (form);
410 if (SCM_ITAG3 (c) == scm_tc3_cons_gloc)
411 SCM_SETCAR (form, SCM_GLOC_SYM (c));
412 #ifdef MEMOIZE_LOCALS
413 #ifdef DEBUG_EXTENSIONS
414 else if (SCM_ILOCP (c))
415 {
416 int ir;
417
418 for (ir = SCM_IFRAME (c); ir != 0; --ir)
419 env = SCM_CDR (env);
420 env = SCM_CAR (SCM_CAR (env));
421 for (ir = SCM_IDIST (c); ir != 0; --ir)
422 env = SCM_CDR (env);
423 SCM_SETCAR (form, SCM_ICDRP (c) ? env : SCM_CAR (env));
424 }
425 #endif
426 #endif
427 return form;
428 }
429
430
431 SCM
432 scm_eval_car (SCM pair, SCM env)
433 {
434 return SCM_XEVALCAR (pair, env);
435 }
436
437 \f
438 /*
439 * The following rewrite expressions and
440 * some memoized forms have different syntax
441 */
442
443 const char scm_s_expression[] = "missing or extra expression";
444 const char scm_s_test[] = "bad test";
445 const char scm_s_body[] = "bad body";
446 const char scm_s_bindings[] = "bad bindings";
447 const char scm_s_duplicate_bindings[] = "duplicate bindings";
448 const char scm_s_variable[] = "bad variable";
449 const char scm_s_clauses[] = "bad or missing clauses";
450 const char scm_s_formals[] = "bad formals";
451 const char scm_s_duplicate_formals[] = "duplicate formals";
452
453 SCM_GLOBAL_SYMBOL (scm_sym_dot, ".");
454 SCM_GLOBAL_SYMBOL (scm_sym_arrow, "=>");
455 SCM_GLOBAL_SYMBOL (scm_sym_else, "else");
456 SCM_GLOBAL_SYMBOL (scm_sym_unquote, "unquote");
457 SCM_GLOBAL_SYMBOL (scm_sym_uq_splicing, "unquote-splicing");
458
459 SCM scm_f_apply;
460
461 #ifdef DEBUG_EXTENSIONS
462 SCM_GLOBAL_SYMBOL (scm_sym_enter_frame, "enter-frame");
463 SCM_GLOBAL_SYMBOL (scm_sym_apply_frame, "apply-frame");
464 SCM_GLOBAL_SYMBOL (scm_sym_exit_frame, "exit-frame");
465 SCM_GLOBAL_SYMBOL (scm_sym_trace, "trace");
466 #endif
467
468
469 /* Check that the body denoted by XORIG is valid and rewrite it into
470 its internal form. The internal form of a body is just the body
471 itself, but prefixed with an ISYM that denotes to what kind of
472 outer construct this body belongs. A lambda body starts with
473 SCM_IM_LAMBDA, for example, a body of a let starts with SCM_IM_LET,
474 etc. The one exception is a body that belongs to a letrec that has
475 been formed by rewriting internal defines: it starts with
476 SCM_IM_DEFINE. */
477
478 /* XXX - Besides controlling the rewriting of internal defines, the
479 additional ISYM could be used for improved error messages.
480 This is not done yet. */
481
482 static SCM
483 scm_m_body (SCM op, SCM xorig, const char *what)
484 {
485 SCM_ASSYNT (scm_ilength (xorig) >= 1, scm_s_expression, what);
486
487 /* Don't add another ISYM if one is present already. */
488 if (SCM_ISYMP (SCM_CAR (xorig)))
489 return xorig;
490
491 /* Retain possible doc string. */
492 if (!SCM_CONSP (SCM_CAR (xorig)))
493 {
494 if (SCM_NNULLP (SCM_CDR(xorig)))
495 return scm_cons (SCM_CAR (xorig),
496 scm_m_body (op, SCM_CDR(xorig), what));
497 return xorig;
498 }
499
500 return scm_cons (op, xorig);
501 }
502
503 SCM_SYNTAX(s_quote,"quote", scm_makmmacro, scm_m_quote);
504 SCM_GLOBAL_SYMBOL(scm_sym_quote, s_quote);
505
506 SCM
507 scm_m_quote (SCM xorig, SCM env)
508 {
509 SCM x = scm_copy_tree (SCM_CDR (xorig));
510
511 SCM_ASSYNT (scm_ilength (SCM_CDR (xorig)) == 1, scm_s_expression, s_quote);
512 return scm_cons (SCM_IM_QUOTE, x);
513 }
514
515
516
517 SCM_SYNTAX(s_begin, "begin", scm_makmmacro, scm_m_begin);
518 SCM_GLOBAL_SYMBOL(scm_sym_begin, s_begin);
519
520 SCM
521 scm_m_begin (SCM xorig, SCM env)
522 {
523 SCM_ASSYNT (scm_ilength (SCM_CDR (xorig)) >= 1, scm_s_expression, s_begin);
524 return scm_cons (SCM_IM_BEGIN, SCM_CDR (xorig));
525 }
526
527 SCM_SYNTAX(s_if, "if", scm_makmmacro, scm_m_if);
528 SCM_GLOBAL_SYMBOL(scm_sym_if, s_if);
529
530 SCM
531 scm_m_if (SCM xorig, SCM env)
532 {
533 int len = scm_ilength (SCM_CDR (xorig));
534 SCM_ASSYNT (len >= 2 && len <= 3, scm_s_expression, "if");
535 return scm_cons (SCM_IM_IF, SCM_CDR (xorig));
536 }
537
538
539 /* Will go into the RnRS module when Guile is factorized.
540 SCM_SYNTAX(scm_s_set_x,"set!", scm_makmmacro, scm_m_set_x); */
541 const char scm_s_set_x[] = "set!";
542 SCM_GLOBAL_SYMBOL(scm_sym_set_x, scm_s_set_x);
543
544 SCM
545 scm_m_set_x (SCM xorig, SCM env)
546 {
547 SCM x = SCM_CDR (xorig);
548 SCM_ASSYNT (2 == scm_ilength (x), scm_s_expression, scm_s_set_x);
549 SCM_ASSYNT (SCM_SYMBOLP (SCM_CAR (x)), scm_s_variable, scm_s_set_x);
550 return scm_cons (SCM_IM_SET_X, x);
551 }
552
553
554 SCM_SYNTAX(s_and, "and", scm_makmmacro, scm_m_and);
555 SCM_GLOBAL_SYMBOL(scm_sym_and, s_and);
556
557 SCM
558 scm_m_and (SCM xorig, SCM env)
559 {
560 int len = scm_ilength (SCM_CDR (xorig));
561 SCM_ASSYNT (len >= 0, scm_s_test, s_and);
562 if (len >= 1)
563 return scm_cons (SCM_IM_AND, SCM_CDR (xorig));
564 else
565 return SCM_BOOL_T;
566 }
567
568 SCM_SYNTAX(s_or,"or", scm_makmmacro, scm_m_or);
569 SCM_GLOBAL_SYMBOL(scm_sym_or,s_or);
570
571 SCM
572 scm_m_or (SCM xorig, SCM env)
573 {
574 int len = scm_ilength (SCM_CDR (xorig));
575 SCM_ASSYNT (len >= 0, scm_s_test, s_or);
576 if (len >= 1)
577 return scm_cons (SCM_IM_OR, SCM_CDR (xorig));
578 else
579 return SCM_BOOL_F;
580 }
581
582
583 SCM_SYNTAX(s_case, "case", scm_makmmacro, scm_m_case);
584 SCM_GLOBAL_SYMBOL(scm_sym_case, s_case);
585
586 SCM
587 scm_m_case (SCM xorig, SCM env)
588 {
589 SCM proc, cdrx = scm_list_copy (SCM_CDR (xorig)), x = cdrx;
590 SCM_ASSYNT (scm_ilength (x) >= 2, scm_s_clauses, s_case);
591 while (SCM_NIMP (x = SCM_CDR (x)))
592 {
593 proc = SCM_CAR (x);
594 SCM_ASSYNT (scm_ilength (proc) >= 2, scm_s_clauses, s_case);
595 SCM_ASSYNT (scm_ilength (SCM_CAR (proc)) >= 0
596 || (SCM_EQ_P (scm_sym_else, SCM_CAR (proc))
597 && SCM_NULLP (SCM_CDR (x))),
598 scm_s_clauses, s_case);
599 }
600 return scm_cons (SCM_IM_CASE, cdrx);
601 }
602
603
604 SCM_SYNTAX(s_cond, "cond", scm_makmmacro, scm_m_cond);
605 SCM_GLOBAL_SYMBOL(scm_sym_cond, s_cond);
606
607
608 SCM
609 scm_m_cond (SCM xorig, SCM env)
610 {
611 SCM arg1, cdrx = scm_list_copy (SCM_CDR (xorig)), x = cdrx;
612 int len = scm_ilength (x);
613 SCM_ASSYNT (len >= 1, scm_s_clauses, s_cond);
614 while (SCM_NIMP (x))
615 {
616 arg1 = SCM_CAR (x);
617 len = scm_ilength (arg1);
618 SCM_ASSYNT (len >= 1, scm_s_clauses, s_cond);
619 if (SCM_EQ_P (scm_sym_else, SCM_CAR (arg1)))
620 {
621 SCM_ASSYNT (SCM_NULLP (SCM_CDR (x)) && len >= 2,
622 "bad ELSE clause", s_cond);
623 SCM_SETCAR (arg1, SCM_BOOL_T);
624 }
625 if (len >= 2 && SCM_EQ_P (scm_sym_arrow, SCM_CAR (SCM_CDR (arg1))))
626 SCM_ASSYNT (3 == len && SCM_NIMP (SCM_CAR (SCM_CDR (SCM_CDR (arg1)))),
627 "bad recipient", s_cond);
628 x = SCM_CDR (x);
629 }
630 return scm_cons (SCM_IM_COND, cdrx);
631 }
632
633 SCM_SYNTAX(s_lambda, "lambda", scm_makmmacro, scm_m_lambda);
634 SCM_GLOBAL_SYMBOL(scm_sym_lambda, s_lambda);
635
636 /* Return #t if OBJ is `eq?' to one of the elements of LIST or to the
637 cdr of the last cons. (Thus, LIST is not required to be a proper
638 list and when OBJ also found in the improper ending.) */
639
640 static int
641 scm_c_improper_memq (SCM obj, SCM list)
642 {
643 for (; SCM_CONSP (list); list = SCM_CDR (list))
644 {
645 if (SCM_EQ_P (SCM_CAR (list), obj))
646 return SCM_BOOL_T;
647 }
648 return SCM_EQ_P (list, obj);
649 }
650
651 SCM
652 scm_m_lambda (SCM xorig, SCM env)
653 {
654 SCM proc, x = SCM_CDR (xorig);
655 if (scm_ilength (x) < 2)
656 goto badforms;
657 proc = SCM_CAR (x);
658 if (SCM_NULLP (proc))
659 goto memlambda;
660 if (SCM_EQ_P (SCM_IM_LET, proc)) /* named let */
661 goto memlambda;
662 if (SCM_IMP (proc))
663 goto badforms;
664 if (SCM_SYMBOLP (proc))
665 goto memlambda;
666 if (SCM_NCONSP (proc))
667 goto badforms;
668 while (SCM_NIMP (proc))
669 {
670 if (SCM_NCONSP (proc))
671 {
672 if (!SCM_SYMBOLP (proc))
673 goto badforms;
674 else
675 goto memlambda;
676 }
677 if (!SCM_SYMBOLP (SCM_CAR (proc)))
678 goto badforms;
679 else if (scm_c_improper_memq (SCM_CAR(proc), SCM_CDR(proc)))
680 scm_misc_error (s_lambda, scm_s_duplicate_formals, SCM_EOL);
681 proc = SCM_CDR (proc);
682 }
683 if (SCM_NNULLP (proc))
684 {
685 badforms:
686 scm_misc_error (s_lambda, scm_s_formals, SCM_EOL);
687 }
688
689 memlambda:
690 return scm_cons2 (SCM_IM_LAMBDA, SCM_CAR (x),
691 scm_m_body (SCM_IM_LAMBDA, SCM_CDR (x), s_lambda));
692 }
693
694 SCM_SYNTAX(s_letstar,"let*", scm_makmmacro, scm_m_letstar);
695 SCM_GLOBAL_SYMBOL(scm_sym_letstar,s_letstar);
696
697
698 SCM
699 scm_m_letstar (SCM xorig, SCM env)
700 {
701 SCM x = SCM_CDR (xorig), arg1, proc, vars = SCM_EOL, *varloc = &vars;
702 int len = scm_ilength (x);
703 SCM_ASSYNT (len >= 2, scm_s_body, s_letstar);
704 proc = SCM_CAR (x);
705 SCM_ASSYNT (scm_ilength (proc) >= 0, scm_s_bindings, s_letstar);
706 while (SCM_NIMP (proc))
707 {
708 arg1 = SCM_CAR (proc);
709 SCM_ASSYNT (2 == scm_ilength (arg1), scm_s_bindings, s_letstar);
710 SCM_ASSYNT (SCM_SYMBOLP (SCM_CAR (arg1)), scm_s_variable, s_letstar);
711 *varloc = scm_cons2 (SCM_CAR (arg1), SCM_CAR (SCM_CDR (arg1)), SCM_EOL);
712 varloc = SCM_CDRLOC (SCM_CDR (*varloc));
713 proc = SCM_CDR (proc);
714 }
715 x = scm_cons (vars, SCM_CDR (x));
716
717 return scm_cons2 (SCM_IM_LETSTAR, SCM_CAR (x),
718 scm_m_body (SCM_IM_LETSTAR, SCM_CDR (x), s_letstar));
719 }
720
721 /* DO gets the most radically altered syntax
722 (do ((<var1> <init1> <step1>)
723 (<var2> <init2>)
724 ... )
725 (<test> <return>)
726 <body>)
727 ;; becomes
728 (do_mem (varn ... var2 var1)
729 (<init1> <init2> ... <initn>)
730 (<test> <return>)
731 (<body>)
732 <step1> <step2> ... <stepn>) ;; missing steps replaced by var
733 */
734
735 SCM_SYNTAX(s_do, "do", scm_makmmacro, scm_m_do);
736 SCM_GLOBAL_SYMBOL(scm_sym_do, s_do);
737
738 SCM
739 scm_m_do (SCM xorig, SCM env)
740 {
741 SCM x = SCM_CDR (xorig), arg1, proc;
742 SCM vars = SCM_EOL, inits = SCM_EOL, steps = SCM_EOL;
743 SCM *initloc = &inits, *steploc = &steps;
744 int len = scm_ilength (x);
745 SCM_ASSYNT (len >= 2, scm_s_test, "do");
746 proc = SCM_CAR (x);
747 SCM_ASSYNT (scm_ilength (proc) >= 0, scm_s_bindings, "do");
748 while (SCM_NIMP(proc))
749 {
750 arg1 = SCM_CAR (proc);
751 len = scm_ilength (arg1);
752 SCM_ASSYNT (2 == len || 3 == len, scm_s_bindings, "do");
753 SCM_ASSYNT (SCM_SYMBOLP (SCM_CAR (arg1)), scm_s_variable, "do");
754 /* vars reversed here, inits and steps reversed at evaluation */
755 vars = scm_cons (SCM_CAR (arg1), vars); /* variable */
756 arg1 = SCM_CDR (arg1);
757 *initloc = scm_cons (SCM_CAR (arg1), SCM_EOL); /* init */
758 initloc = SCM_CDRLOC (*initloc);
759 arg1 = SCM_CDR (arg1);
760 *steploc = scm_cons (SCM_IMP (arg1) ? SCM_CAR (vars) : SCM_CAR (arg1), SCM_EOL); /* step */
761 steploc = SCM_CDRLOC (*steploc);
762 proc = SCM_CDR (proc);
763 }
764 x = SCM_CDR (x);
765 SCM_ASSYNT (scm_ilength (SCM_CAR (x)) >= 1, scm_s_test, "do");
766 x = scm_cons2 (SCM_CAR (x), SCM_CDR (x), steps);
767 x = scm_cons2 (vars, inits, x);
768 return scm_cons (SCM_IM_DO, x);
769 }
770
771 /* evalcar is small version of inline EVALCAR when we don't care about
772 * speed
773 */
774 #define evalcar scm_eval_car
775
776
777 static SCM iqq (SCM form, SCM env, int depth);
778
779 SCM_SYNTAX(s_quasiquote, "quasiquote", scm_makacro, scm_m_quasiquote);
780 SCM_GLOBAL_SYMBOL(scm_sym_quasiquote, s_quasiquote);
781
782 SCM
783 scm_m_quasiquote (SCM xorig, SCM env)
784 {
785 SCM x = SCM_CDR (xorig);
786 SCM_ASSYNT (scm_ilength (x) == 1, scm_s_expression, s_quasiquote);
787 return iqq (SCM_CAR (x), env, 1);
788 }
789
790
791 static SCM
792 iqq (SCM form,SCM env,int depth)
793 {
794 SCM tmp;
795 int edepth = depth;
796 if (SCM_IMP(form))
797 return form;
798 if (SCM_VECTORP (form))
799 {
800 long i = SCM_VECTOR_LENGTH (form);
801 SCM *data = SCM_VELTS (form);
802 tmp = SCM_EOL;
803 for (; --i >= 0;)
804 tmp = scm_cons (data[i], tmp);
805 return scm_vector (iqq (tmp, env, depth));
806 }
807 if (SCM_NCONSP(form))
808 return form;
809 tmp = SCM_CAR (form);
810 if (SCM_EQ_P (scm_sym_quasiquote, tmp))
811 {
812 depth++;
813 goto label;
814 }
815 if (SCM_EQ_P (scm_sym_unquote, tmp))
816 {
817 --depth;
818 label:
819 form = SCM_CDR (form);
820 SCM_ASSERT (SCM_ECONSP (form) && SCM_NULLP (SCM_CDR (form)),
821 form, SCM_ARG1, s_quasiquote);
822 if (0 == depth)
823 return evalcar (form, env);
824 return scm_cons2 (tmp, iqq (SCM_CAR (form), env, depth), SCM_EOL);
825 }
826 if (SCM_NIMP (tmp) && (SCM_EQ_P (scm_sym_uq_splicing, SCM_CAR (tmp))))
827 {
828 tmp = SCM_CDR (tmp);
829 if (0 == --edepth)
830 return scm_append (scm_cons2 (evalcar (tmp, env), iqq (SCM_CDR (form), env, depth), SCM_EOL));
831 }
832 return scm_cons (iqq (SCM_CAR (form), env, edepth), iqq (SCM_CDR (form), env, depth));
833 }
834
835 /* Here are acros which return values rather than code. */
836
837 SCM_SYNTAX (s_delay, "delay", scm_makmmacro, scm_m_delay);
838 SCM_GLOBAL_SYMBOL (scm_sym_delay, s_delay);
839
840 SCM
841 scm_m_delay (SCM xorig, SCM env)
842 {
843 SCM_ASSYNT (scm_ilength (xorig) == 2, scm_s_expression, s_delay);
844 return scm_cons2 (SCM_IM_DELAY, SCM_EOL, SCM_CDR (xorig));
845 }
846
847
848 SCM_SYNTAX(s_define, "define", scm_makmmacro, scm_m_define);
849 SCM_GLOBAL_SYMBOL(scm_sym_define, s_define);
850
851 SCM
852 scm_m_define (SCM x, SCM env)
853 {
854 SCM proc, arg1 = x;
855 x = SCM_CDR (x);
856 SCM_ASSYNT (scm_ilength (x) >= 2, scm_s_expression, s_define);
857 proc = SCM_CAR (x);
858 x = SCM_CDR (x);
859 while (SCM_CONSP (proc))
860 { /* nested define syntax */
861 x = scm_cons (scm_cons2 (scm_sym_lambda, SCM_CDR (proc), x), SCM_EOL);
862 proc = SCM_CAR (proc);
863 }
864 SCM_ASSYNT (SCM_SYMBOLP (proc), scm_s_variable, s_define);
865 SCM_ASSYNT (1 == scm_ilength (x), scm_s_expression, s_define);
866 if (SCM_TOP_LEVEL (env))
867 {
868 x = evalcar (x, env);
869 #ifdef DEBUG_EXTENSIONS
870 if (SCM_REC_PROCNAMES_P && SCM_NIMP (x))
871 {
872 arg1 = x;
873 proc:
874 if (SCM_CLOSUREP (arg1)
875 /* Only the first definition determines the name. */
876 && SCM_FALSEP (scm_procedure_property (arg1, scm_sym_name)))
877 scm_set_procedure_property_x (arg1, scm_sym_name, proc);
878 else if (SCM_TYP16 (arg1) == scm_tc16_macro
879 && !SCM_EQ_P (SCM_CDR (arg1), arg1))
880 {
881 arg1 = SCM_CDR (arg1);
882 goto proc;
883 }
884 }
885 #endif
886 arg1 = scm_sym2vcell (proc, scm_env_top_level (env), SCM_BOOL_T);
887 SCM_SETCDR (arg1, x);
888 #ifdef SICP
889 return scm_cons2 (scm_sym_quote, SCM_CAR (arg1), SCM_EOL);
890 #else
891 return SCM_UNSPECIFIED;
892 #endif
893 }
894 return scm_cons2 (SCM_IM_DEFINE, proc, x);
895 }
896
897 /* end of acros */
898
899 static SCM
900 scm_m_letrec1 (SCM op, SCM imm, SCM xorig, SCM env)
901 {
902 SCM cdrx = SCM_CDR (xorig); /* locally mutable version of form */
903 char *what = SCM_SYMBOL_CHARS (SCM_CAR (xorig));
904 SCM x = cdrx, proc, arg1; /* structure traversers */
905 SCM vars = SCM_EOL, inits = SCM_EOL, *initloc = &inits;
906
907 proc = SCM_CAR (x);
908 SCM_ASSYNT (scm_ilength (proc) >= 1, scm_s_bindings, what);
909 do
910 {
911 /* vars scm_list reversed here, inits reversed at evaluation */
912 arg1 = SCM_CAR (proc);
913 SCM_ASSYNT (2 == scm_ilength (arg1), scm_s_bindings, what);
914 SCM_ASSYNT (SCM_SYMBOLP (SCM_CAR (arg1)), scm_s_variable, what);
915 if (scm_c_improper_memq (SCM_CAR (arg1), vars))
916 scm_misc_error (what, scm_s_duplicate_bindings, SCM_EOL);
917 vars = scm_cons (SCM_CAR (arg1), vars);
918 *initloc = scm_cons (SCM_CAR (SCM_CDR (arg1)), SCM_EOL);
919 initloc = SCM_CDRLOC (*initloc);
920 }
921 while (SCM_NIMP (proc = SCM_CDR (proc)));
922
923 return scm_cons2 (op, vars,
924 scm_cons (inits, scm_m_body (imm, SCM_CDR (x), what)));
925 }
926
927 SCM_SYNTAX(s_letrec, "letrec", scm_makmmacro, scm_m_letrec);
928 SCM_GLOBAL_SYMBOL(scm_sym_letrec, s_letrec);
929
930 SCM
931 scm_m_letrec (SCM xorig, SCM env)
932 {
933 SCM x = SCM_CDR (xorig);
934 SCM_ASSYNT (scm_ilength (x) >= 2, scm_s_body, s_letrec);
935
936 if (SCM_NULLP (SCM_CAR (x))) /* null binding, let* faster */
937 return scm_m_letstar (scm_cons2 (SCM_CAR (xorig), SCM_EOL,
938 scm_m_body (SCM_IM_LETREC,
939 SCM_CDR (x),
940 s_letrec)),
941 env);
942 else
943 return scm_m_letrec1 (SCM_IM_LETREC, SCM_IM_LETREC, xorig, env);
944 }
945
946 SCM_SYNTAX(s_let, "let", scm_makmmacro, scm_m_let);
947 SCM_GLOBAL_SYMBOL(scm_sym_let, s_let);
948
949 SCM
950 scm_m_let (SCM xorig, SCM env)
951 {
952 SCM cdrx = SCM_CDR (xorig); /* locally mutable version of form */
953 SCM x = cdrx, proc, arg1, name; /* structure traversers */
954 SCM vars = SCM_EOL, inits = SCM_EOL, *varloc = &vars, *initloc = &inits;
955
956 SCM_ASSYNT (scm_ilength (x) >= 2, scm_s_body, s_let);
957 proc = SCM_CAR (x);
958 if (SCM_NULLP (proc)
959 || (SCM_CONSP (proc)
960 && SCM_CONSP (SCM_CAR (proc)) && SCM_NULLP (SCM_CDR (proc))))
961 {
962 /* null or single binding, let* is faster */
963 return scm_m_letstar (scm_cons2 (SCM_CAR (xorig), proc,
964 scm_m_body (SCM_IM_LET,
965 SCM_CDR (x),
966 s_let)),
967 env);
968 }
969
970 SCM_ASSYNT (SCM_NIMP (proc), scm_s_bindings, s_let);
971 if (SCM_CONSP (proc))
972 {
973 /* plain let, proc is <bindings> */
974 return scm_m_letrec1 (SCM_IM_LET, SCM_IM_LET, xorig, env);
975 }
976
977 if (!SCM_SYMBOLP (proc))
978 scm_misc_error (s_let, scm_s_bindings, SCM_EOL); /* bad let */
979 name = proc; /* named let, build equiv letrec */
980 x = SCM_CDR (x);
981 SCM_ASSYNT (scm_ilength (x) >= 2, scm_s_body, s_let);
982 proc = SCM_CAR (x); /* bindings list */
983 SCM_ASSYNT (scm_ilength (proc) >= 0, scm_s_bindings, s_let);
984 while (SCM_NIMP (proc))
985 { /* vars and inits both in order */
986 arg1 = SCM_CAR (proc);
987 SCM_ASSYNT (2 == scm_ilength (arg1), scm_s_bindings, s_let);
988 SCM_ASSYNT (SCM_SYMBOLP (SCM_CAR (arg1)), scm_s_variable, s_let);
989 *varloc = scm_cons (SCM_CAR (arg1), SCM_EOL);
990 varloc = SCM_CDRLOC (*varloc);
991 *initloc = scm_cons (SCM_CAR (SCM_CDR (arg1)), SCM_EOL);
992 initloc = SCM_CDRLOC (*initloc);
993 proc = SCM_CDR (proc);
994 }
995
996 proc = scm_cons2 (scm_sym_lambda, vars,
997 scm_m_body (SCM_IM_LET, SCM_CDR (x), "let"));
998 proc = scm_cons2 (scm_sym_let, scm_cons (scm_cons2 (name, proc, SCM_EOL),
999 SCM_EOL),
1000 scm_acons (name, inits, SCM_EOL));
1001 return scm_m_letrec1 (SCM_IM_LETREC, SCM_IM_LET, proc, env);
1002 }
1003
1004
1005 SCM_SYNTAX (s_atapply,"@apply", scm_makmmacro, scm_m_apply);
1006 SCM_GLOBAL_SYMBOL (scm_sym_atapply, s_atapply);
1007 SCM_GLOBAL_SYMBOL (scm_sym_apply, s_atapply + 1);
1008
1009 SCM
1010 scm_m_apply (SCM xorig, SCM env)
1011 {
1012 SCM_ASSYNT (scm_ilength (SCM_CDR (xorig)) == 2, scm_s_expression, s_atapply);
1013 return scm_cons (SCM_IM_APPLY, SCM_CDR (xorig));
1014 }
1015
1016
1017 SCM_SYNTAX(s_atcall_cc,"@call-with-current-continuation", scm_makmmacro, scm_m_cont);
1018 SCM_GLOBAL_SYMBOL(scm_sym_atcall_cc,s_atcall_cc);
1019
1020
1021 SCM
1022 scm_m_cont (SCM xorig, SCM env)
1023 {
1024 SCM_ASSYNT (scm_ilength (SCM_CDR (xorig)) == 1,
1025 scm_s_expression, s_atcall_cc);
1026 return scm_cons (SCM_IM_CONT, SCM_CDR (xorig));
1027 }
1028
1029 /* Multi-language support */
1030
1031 SCM scm_lisp_nil;
1032 SCM scm_lisp_t;
1033
1034 SCM_SYNTAX (s_nil_cond, "nil-cond", scm_makmmacro, scm_m_nil_cond);
1035
1036 SCM
1037 scm_m_nil_cond (SCM xorig, SCM env)
1038 {
1039 int len = scm_ilength (SCM_CDR (xorig));
1040 SCM_ASSYNT (len >= 1 && (len & 1) == 1, scm_s_expression, "nil-cond");
1041 return scm_cons (SCM_IM_NIL_COND, SCM_CDR (xorig));
1042 }
1043
1044 SCM_SYNTAX (s_nil_ify, "nil-ify", scm_makmmacro, scm_m_nil_ify);
1045
1046 SCM
1047 scm_m_nil_ify (SCM xorig, SCM env)
1048 {
1049 SCM_ASSYNT (scm_ilength (SCM_CDR (xorig)) == 1, scm_s_expression, "nil-ify");
1050 return scm_cons (SCM_IM_NIL_IFY, SCM_CDR (xorig));
1051 }
1052
1053 SCM_SYNTAX (s_t_ify, "t-ify", scm_makmmacro, scm_m_t_ify);
1054
1055 SCM
1056 scm_m_t_ify (SCM xorig, SCM env)
1057 {
1058 SCM_ASSYNT (scm_ilength (SCM_CDR (xorig)) == 1, scm_s_expression, "t-ify");
1059 return scm_cons (SCM_IM_T_IFY, SCM_CDR (xorig));
1060 }
1061
1062 SCM_SYNTAX (s_0_cond, "0-cond", scm_makmmacro, scm_m_0_cond);
1063
1064 SCM
1065 scm_m_0_cond (SCM xorig, SCM env)
1066 {
1067 int len = scm_ilength (SCM_CDR (xorig));
1068 SCM_ASSYNT (len >= 1 && (len & 1) == 1, scm_s_expression, "0-cond");
1069 return scm_cons (SCM_IM_0_COND, SCM_CDR (xorig));
1070 }
1071
1072 SCM_SYNTAX (s_0_ify, "0-ify", scm_makmmacro, scm_m_0_ify);
1073
1074 SCM
1075 scm_m_0_ify (SCM xorig, SCM env)
1076 {
1077 SCM_ASSYNT (scm_ilength (SCM_CDR (xorig)) == 1, scm_s_expression, "0-ify");
1078 return scm_cons (SCM_IM_0_IFY, SCM_CDR (xorig));
1079 }
1080
1081 SCM_SYNTAX (s_1_ify, "1-ify", scm_makmmacro, scm_m_1_ify);
1082
1083 SCM
1084 scm_m_1_ify (SCM xorig, SCM env)
1085 {
1086 SCM_ASSYNT (scm_ilength (SCM_CDR (xorig)) == 1, scm_s_expression, "1-ify");
1087 return scm_cons (SCM_IM_1_IFY, SCM_CDR (xorig));
1088 }
1089
1090 SCM_SYNTAX (s_atfop, "@fop", scm_makmmacro, scm_m_atfop);
1091
1092 SCM
1093 scm_m_atfop (SCM xorig, SCM env)
1094 {
1095 SCM x = SCM_CDR (xorig), vcell;
1096 SCM_ASSYNT (scm_ilength (x) >= 1, scm_s_expression, "@fop");
1097 vcell = scm_symbol_fref (SCM_CAR (x));
1098 SCM_ASSYNT (SCM_CONSP (vcell),
1099 "Symbol's function definition is void", NULL);
1100 SCM_SET_CELL_WORD_0 (x, SCM_UNPACK (vcell) + scm_tc3_cons_gloc);
1101 return x;
1102 }
1103
1104 SCM_SYNTAX (s_atbind, "@bind", scm_makmmacro, scm_m_atbind);
1105
1106 SCM
1107 scm_m_atbind (SCM xorig, SCM env)
1108 {
1109 SCM x = SCM_CDR (xorig);
1110 SCM_ASSYNT (scm_ilength (x) > 1, scm_s_expression, "@bind");
1111
1112 if (SCM_IMP (env))
1113 env = SCM_BOOL_F;
1114 else
1115 {
1116 while (SCM_NIMP (SCM_CDR (env)))
1117 env = SCM_CDR (env);
1118 env = SCM_CAR (env);
1119 if (SCM_CONSP (env))
1120 env = SCM_BOOL_F;
1121 }
1122
1123 x = SCM_CAR (x);
1124 while (SCM_NIMP (x))
1125 {
1126 SCM_SET_CELL_WORD_0 (x, SCM_UNPACK (scm_sym2vcell (SCM_CAR (x), env, SCM_BOOL_T)) + scm_tc3_cons_gloc);
1127 x = SCM_CDR (x);
1128 }
1129 return scm_cons (SCM_IM_BIND, SCM_CDR (xorig));
1130 }
1131
1132 SCM
1133 scm_m_expand_body (SCM xorig, SCM env)
1134 {
1135 SCM form, x = SCM_CDR (xorig), defs = SCM_EOL;
1136 char *what = SCM_ISYMCHARS (SCM_CAR (xorig)) + 2;
1137
1138 while (SCM_NIMP (x))
1139 {
1140 form = SCM_CAR (x);
1141 if (SCM_IMP (form) || SCM_NCONSP (form))
1142 break;
1143 if (SCM_IMP (SCM_CAR (form)))
1144 break;
1145 if (!SCM_SYMBOLP (SCM_CAR (form)))
1146 break;
1147
1148 form = scm_macroexp (scm_cons_source (form,
1149 SCM_CAR (form),
1150 SCM_CDR (form)),
1151 env);
1152
1153 if (SCM_EQ_P (SCM_IM_DEFINE, SCM_CAR (form)))
1154 {
1155 defs = scm_cons (SCM_CDR (form), defs);
1156 x = SCM_CDR(x);
1157 }
1158 else if (SCM_NIMP(defs))
1159 {
1160 break;
1161 }
1162 else if (SCM_EQ_P (SCM_IM_BEGIN, SCM_CAR (form)))
1163 {
1164 x = scm_append (scm_cons2 (SCM_CDR (form), SCM_CDR (x), SCM_EOL));
1165 }
1166 else
1167 {
1168 x = scm_cons (form, SCM_CDR(x));
1169 break;
1170 }
1171 }
1172
1173 SCM_ASSYNT (SCM_NIMP (x), scm_s_body, what);
1174 if (SCM_NIMP (defs))
1175 {
1176 x = scm_cons (scm_m_letrec1 (SCM_IM_LETREC,
1177 SCM_IM_DEFINE,
1178 scm_cons2 (scm_sym_define, defs, x),
1179 env),
1180 SCM_EOL);
1181 }
1182
1183 SCM_DEFER_INTS;
1184 SCM_SETCAR (xorig, SCM_CAR (x));
1185 SCM_SETCDR (xorig, SCM_CDR (x));
1186 SCM_ALLOW_INTS;
1187
1188 return xorig;
1189 }
1190
1191 SCM
1192 scm_macroexp (SCM x, SCM env)
1193 {
1194 SCM res, proc;
1195
1196 /* Don't bother to produce error messages here. We get them when we
1197 eventually execute the code for real. */
1198
1199 macro_tail:
1200 if (!SCM_SYMBOLP (SCM_CAR (x)))
1201 return x;
1202
1203 #ifdef USE_THREADS
1204 {
1205 SCM *proc_ptr = scm_lookupcar1 (x, env, 0);
1206 if (proc_ptr == NULL)
1207 {
1208 /* We have lost the race. */
1209 goto macro_tail;
1210 }
1211 proc = *proc_ptr;
1212 }
1213 #else
1214 proc = *scm_lookupcar (x, env, 0);
1215 #endif
1216
1217 /* Only handle memoizing macros. `Acros' and `macros' are really
1218 special forms and should not be evaluated here. */
1219
1220 if (SCM_IMP (proc)
1221 || scm_tc16_macro != SCM_TYP16 (proc)
1222 || (SCM_CELL_WORD_0 (proc) >> 16) != 2)
1223 return x;
1224
1225 unmemocar (x, env);
1226 res = scm_apply (SCM_CDR (proc), x, scm_cons (env, scm_listofnull));
1227
1228 if (scm_ilength (res) <= 0)
1229 res = scm_cons2 (SCM_IM_BEGIN, res, SCM_EOL);
1230
1231 SCM_DEFER_INTS;
1232 SCM_SETCAR (x, SCM_CAR (res));
1233 SCM_SETCDR (x, SCM_CDR (res));
1234 SCM_ALLOW_INTS;
1235
1236 goto macro_tail;
1237 }
1238
1239 /* scm_unmemocopy takes a memoized expression together with its
1240 * environment and rewrites it to its original form. Thus, it is the
1241 * inversion of the rewrite rules above. The procedure is not
1242 * optimized for speed. It's used in scm_iprin1 when printing the
1243 * code of a closure, in scm_procedure_source, in display_frame when
1244 * generating the source for a stackframe in a backtrace, and in
1245 * display_expression.
1246 */
1247
1248 /* We should introduce an anti-macro interface so that it is possible
1249 * to plug in transformers in both directions from other compilation
1250 * units. unmemocopy could then dispatch to anti-macro transformers.
1251 * (Those transformers could perhaps be written in slightly more
1252 * readable style... :)
1253 */
1254
1255 #define SCM_BIT8(x) (127 & SCM_UNPACK (x))
1256
1257 static SCM
1258 unmemocopy (SCM x, SCM env)
1259 {
1260 SCM ls, z;
1261 #ifdef DEBUG_EXTENSIONS
1262 SCM p;
1263 #endif
1264 if (SCM_NCELLP (x) || SCM_NECONSP (x))
1265 return x;
1266 #ifdef DEBUG_EXTENSIONS
1267 p = scm_whash_lookup (scm_source_whash, x);
1268 #endif
1269 switch (SCM_TYP7 (x))
1270 {
1271 case SCM_BIT8(SCM_IM_AND):
1272 ls = z = scm_cons (scm_sym_and, SCM_UNSPECIFIED);
1273 break;
1274 case SCM_BIT8(SCM_IM_BEGIN):
1275 ls = z = scm_cons (scm_sym_begin, SCM_UNSPECIFIED);
1276 break;
1277 case SCM_BIT8(SCM_IM_CASE):
1278 ls = z = scm_cons (scm_sym_case, SCM_UNSPECIFIED);
1279 break;
1280 case SCM_BIT8(SCM_IM_COND):
1281 ls = z = scm_cons (scm_sym_cond, SCM_UNSPECIFIED);
1282 break;
1283 case SCM_BIT8(SCM_IM_DO):
1284 ls = scm_cons (scm_sym_do, SCM_UNSPECIFIED);
1285 goto transform;
1286 case SCM_BIT8(SCM_IM_IF):
1287 ls = z = scm_cons (scm_sym_if, SCM_UNSPECIFIED);
1288 break;
1289 case SCM_BIT8(SCM_IM_LET):
1290 ls = scm_cons (scm_sym_let, SCM_UNSPECIFIED);
1291 goto transform;
1292 case SCM_BIT8(SCM_IM_LETREC):
1293 {
1294 SCM f, v, e, s;
1295 ls = scm_cons (scm_sym_letrec, SCM_UNSPECIFIED);
1296 transform:
1297 x = SCM_CDR (x);
1298 /* binding names */
1299 f = v = SCM_CAR (x);
1300 x = SCM_CDR (x);
1301 z = EXTEND_ENV (f, SCM_EOL, env);
1302 /* inits */
1303 e = scm_reverse (unmemocopy (SCM_CAR (x),
1304 SCM_EQ_P (SCM_CAR (ls), scm_sym_letrec) ? z : env));
1305 env = z;
1306 /* increments */
1307 s = SCM_EQ_P (SCM_CAR (ls), scm_sym_do)
1308 ? scm_reverse (unmemocopy (SCM_CDR (SCM_CDR (SCM_CDR (x))), env))
1309 : f;
1310 /* build transformed binding list */
1311 z = SCM_EOL;
1312 while (SCM_NIMP (v))
1313 {
1314 z = scm_acons (SCM_CAR (v),
1315 scm_cons (SCM_CAR (e),
1316 SCM_EQ_P (SCM_CAR (s), SCM_CAR (v))
1317 ? SCM_EOL
1318 : scm_cons (SCM_CAR (s), SCM_EOL)),
1319 z);
1320 v = SCM_CDR (v);
1321 e = SCM_CDR (e);
1322 s = SCM_CDR (s);
1323 }
1324 z = scm_cons (z, SCM_UNSPECIFIED);
1325 SCM_SETCDR (ls, z);
1326 if (SCM_EQ_P (SCM_CAR (ls), scm_sym_do))
1327 {
1328 x = SCM_CDR (x);
1329 /* test clause */
1330 SCM_SETCDR (z, scm_cons (unmemocopy (SCM_CAR (x), env),
1331 SCM_UNSPECIFIED));
1332 z = SCM_CDR (z);
1333 x = (SCM) (SCM_CARLOC (SCM_CDR (x)) - 1);
1334 /* body forms are now to be found in SCM_CDR (x)
1335 (this is how *real* code look like! :) */
1336 }
1337 break;
1338 }
1339 case SCM_BIT8(SCM_IM_LETSTAR):
1340 {
1341 SCM b, y;
1342 x = SCM_CDR (x);
1343 b = SCM_CAR (x);
1344 y = SCM_EOL;
1345 if SCM_IMP (b)
1346 {
1347 env = EXTEND_ENV (SCM_EOL, SCM_EOL, env);
1348 goto letstar;
1349 }
1350 y = z = scm_acons (SCM_CAR (b),
1351 unmemocar (
1352 scm_cons (unmemocopy (SCM_CAR (SCM_CDR (b)), env), SCM_EOL), env),
1353 SCM_UNSPECIFIED);
1354 env = EXTEND_ENV (SCM_CAR (b), SCM_BOOL_F, env);
1355 b = SCM_CDR (SCM_CDR (b));
1356 if (SCM_IMP (b))
1357 {
1358 SCM_SETCDR (y, SCM_EOL);
1359 ls = scm_cons (scm_sym_let, z = scm_cons (y, SCM_UNSPECIFIED));
1360 break;
1361 }
1362 do
1363 {
1364 SCM_SETCDR (z, scm_acons (SCM_CAR (b),
1365 unmemocar (
1366 scm_cons (unmemocopy (SCM_CAR (SCM_CDR (b)), env), SCM_EOL), env),
1367 SCM_UNSPECIFIED));
1368 z = SCM_CDR (z);
1369 env = EXTEND_ENV (SCM_CAR (b), SCM_BOOL_F, env);
1370 b = SCM_CDR (SCM_CDR (b));
1371 }
1372 while (SCM_NIMP (b));
1373 SCM_SETCDR (z, SCM_EOL);
1374 letstar:
1375 ls = scm_cons (scm_sym_letstar, z = scm_cons (y, SCM_UNSPECIFIED));
1376 break;
1377 }
1378 case SCM_BIT8(SCM_IM_OR):
1379 ls = z = scm_cons (scm_sym_or, SCM_UNSPECIFIED);
1380 break;
1381 case SCM_BIT8(SCM_IM_LAMBDA):
1382 x = SCM_CDR (x);
1383 ls = scm_cons (scm_sym_lambda,
1384 z = scm_cons (SCM_CAR (x), SCM_UNSPECIFIED));
1385 env = EXTEND_ENV (SCM_CAR (x), SCM_EOL, env);
1386 break;
1387 case SCM_BIT8(SCM_IM_QUOTE):
1388 ls = z = scm_cons (scm_sym_quote, SCM_UNSPECIFIED);
1389 break;
1390 case SCM_BIT8(SCM_IM_SET_X):
1391 ls = z = scm_cons (scm_sym_set_x, SCM_UNSPECIFIED);
1392 break;
1393 case SCM_BIT8(SCM_IM_DEFINE):
1394 {
1395 SCM n;
1396 x = SCM_CDR (x);
1397 ls = scm_cons (scm_sym_define,
1398 z = scm_cons (n = SCM_CAR (x), SCM_UNSPECIFIED));
1399 if (SCM_NNULLP (env))
1400 SCM_SETCAR (SCM_CAR (env), scm_cons (n, SCM_CAR (SCM_CAR (env))));
1401 break;
1402 }
1403 case SCM_BIT8(SCM_MAKISYM (0)):
1404 z = SCM_CAR (x);
1405 if (!SCM_ISYMP (z))
1406 goto unmemo;
1407 switch (SCM_ISYMNUM (z))
1408 {
1409 case (SCM_ISYMNUM (SCM_IM_APPLY)):
1410 ls = z = scm_cons (scm_sym_atapply, SCM_UNSPECIFIED);
1411 goto loop;
1412 case (SCM_ISYMNUM (SCM_IM_CONT)):
1413 ls = z = scm_cons (scm_sym_atcall_cc, SCM_UNSPECIFIED);
1414 goto loop;
1415 case (SCM_ISYMNUM (SCM_IM_DELAY)):
1416 ls = z = scm_cons (scm_sym_delay, SCM_UNSPECIFIED);
1417 x = SCM_CDR (x);
1418 goto loop;
1419 default:
1420 /* appease the Sun compiler god: */ ;
1421 }
1422 unmemo:
1423 default:
1424 ls = z = unmemocar (scm_cons (unmemocopy (SCM_CAR (x), env),
1425 SCM_UNSPECIFIED),
1426 env);
1427 }
1428 loop:
1429 while (SCM_CELLP (x = SCM_CDR (x)) && SCM_ECONSP (x))
1430 {
1431 if (SCM_ISYMP (SCM_CAR (x)))
1432 /* skip body markers */
1433 continue;
1434 SCM_SETCDR (z, unmemocar (scm_cons (unmemocopy (SCM_CAR (x), env),
1435 SCM_UNSPECIFIED),
1436 env));
1437 z = SCM_CDR (z);
1438 }
1439 SCM_SETCDR (z, x);
1440 #ifdef DEBUG_EXTENSIONS
1441 if (SCM_NFALSEP (p))
1442 scm_whash_insert (scm_source_whash, ls, p);
1443 #endif
1444 return ls;
1445 }
1446
1447
1448 SCM
1449 scm_unmemocopy (SCM x, SCM env)
1450 {
1451 if (SCM_NNULLP (env))
1452 /* Make a copy of the lowest frame to protect it from
1453 modifications by SCM_IM_DEFINE */
1454 return unmemocopy (x, scm_cons (SCM_CAR (env), SCM_CDR (env)));
1455 else
1456 return unmemocopy (x, env);
1457 }
1458
1459 #ifndef SCM_RECKLESS
1460
1461 int
1462 scm_badargsp (SCM formals, SCM args)
1463 {
1464 while (SCM_NIMP (formals))
1465 {
1466 if (SCM_NCONSP (formals))
1467 return 0;
1468 if (SCM_IMP(args))
1469 return 1;
1470 formals = SCM_CDR (formals);
1471 args = SCM_CDR (args);
1472 }
1473 return SCM_NNULLP (args) ? 1 : 0;
1474 }
1475 #endif
1476
1477 static int
1478 scm_badformalsp (SCM closure, int n)
1479 {
1480 SCM formals = SCM_CAR (SCM_CODE (closure));
1481 while (SCM_NIMP (formals))
1482 {
1483 if (SCM_NCONSP (formals))
1484 return 0;
1485 if (n == 0)
1486 return 1;
1487 --n;
1488 formals = SCM_CDR (formals);
1489 }
1490 return n;
1491 }
1492
1493 \f
1494 SCM
1495 scm_eval_args (SCM l, SCM env, SCM proc)
1496 {
1497 SCM results = SCM_EOL, *lloc = &results, res;
1498 while (SCM_NIMP (l))
1499 {
1500 #ifdef SCM_CAUTIOUS
1501 if (SCM_CONSP (l))
1502 {
1503 if (SCM_IMP (SCM_CAR (l)))
1504 res = SCM_EVALIM (SCM_CAR (l), env);
1505 else
1506 res = EVALCELLCAR (l, env);
1507 }
1508 else if (SCM_TYP3 (l) == scm_tc3_cons_gloc)
1509 {
1510 scm_bits_t vcell = SCM_STRUCT_VTABLE_DATA (l) [scm_vtable_index_vcell];
1511 if (vcell == 0)
1512 res = SCM_CAR (l); /* struct planted in code */
1513 else
1514 res = SCM_PACK (vcell);
1515 }
1516 else
1517 goto wrongnumargs;
1518 #else
1519 res = EVALCAR (l, env);
1520 #endif
1521 *lloc = scm_cons (res, SCM_EOL);
1522 lloc = SCM_CDRLOC (*lloc);
1523 l = SCM_CDR (l);
1524 }
1525 #ifdef SCM_CAUTIOUS
1526 if (SCM_NNULLP (l))
1527 {
1528 wrongnumargs:
1529 scm_wrong_num_args (proc);
1530 }
1531 #endif
1532 return results;
1533 }
1534
1535 SCM
1536 scm_eval_body (SCM code, SCM env)
1537 {
1538 SCM next;
1539 again:
1540 next = code;
1541 while (SCM_NNULLP (next = SCM_CDR (next)))
1542 {
1543 if (SCM_IMP (SCM_CAR (code)))
1544 {
1545 if (SCM_ISYMP (SCM_CAR (code)))
1546 {
1547 code = scm_m_expand_body (code, env);
1548 goto again;
1549 }
1550 }
1551 else
1552 SCM_XEVAL (SCM_CAR (code), env);
1553 code = next;
1554 }
1555 return SCM_XEVALCAR (code, env);
1556 }
1557
1558
1559 #endif /* !DEVAL */
1560
1561
1562 /* SECTION: This code is specific for the debugging support. One
1563 * branch is read when DEVAL isn't defined, the other when DEVAL is
1564 * defined.
1565 */
1566
1567 #ifndef DEVAL
1568
1569 #define SCM_APPLY scm_apply
1570 #define PREP_APPLY(proc, args)
1571 #define ENTER_APPLY
1572 #define RETURN(x) return x;
1573 #ifdef STACK_CHECKING
1574 #ifndef NO_CEVAL_STACK_CHECKING
1575 #define EVAL_STACK_CHECKING
1576 #endif
1577 #endif
1578
1579 #else /* !DEVAL */
1580
1581 #undef SCM_CEVAL
1582 #define SCM_CEVAL scm_deval /* Substitute all uses of scm_ceval */
1583 #undef SCM_APPLY
1584 #define SCM_APPLY scm_dapply
1585 #undef PREP_APPLY
1586 #define PREP_APPLY(p, l) \
1587 { ++debug.info; debug.info->a.proc = p; debug.info->a.args = l; }
1588 #undef ENTER_APPLY
1589 #define ENTER_APPLY \
1590 do { \
1591 SCM_SET_ARGSREADY (debug);\
1592 if (CHECK_APPLY && SCM_TRAPS_P)\
1593 if (SCM_APPLY_FRAME_P || (SCM_TRACE_P && PROCTRACEP (proc)))\
1594 {\
1595 SCM tmp, tail = SCM_BOOL(SCM_TRACED_FRAME_P (debug)); \
1596 SCM_SET_TRACED_FRAME (debug); \
1597 if (SCM_CHEAPTRAPS_P)\
1598 {\
1599 tmp = scm_make_debugobj (&debug);\
1600 scm_ithrow (scm_sym_apply_frame, scm_cons2 (tmp, tail, SCM_EOL), 0);\
1601 }\
1602 else\
1603 {\
1604 int first;\
1605 tmp = scm_make_continuation (&first);\
1606 if (first)\
1607 scm_ithrow (scm_sym_apply_frame, scm_cons2 (tmp, tail, SCM_EOL), 0);\
1608 }\
1609 }\
1610 } while (0)
1611 #undef RETURN
1612 #define RETURN(e) {proc = (e); goto exit;}
1613 #ifdef STACK_CHECKING
1614 #ifndef EVAL_STACK_CHECKING
1615 #define EVAL_STACK_CHECKING
1616 #endif
1617 #endif
1618
1619 /* scm_ceval_ptr points to the currently selected evaluator.
1620 * *fixme*: Although efficiency is important here, this state variable
1621 * should probably not be a global. It should be related to the
1622 * current repl.
1623 */
1624
1625
1626 SCM (*scm_ceval_ptr) (SCM x, SCM env);
1627
1628 /* scm_last_debug_frame contains a pointer to the last debugging
1629 * information stack frame. It is accessed very often from the
1630 * debugging evaluator, so it should probably not be indirectly
1631 * addressed. Better to save and restore it from the current root at
1632 * any stack swaps.
1633 */
1634
1635 #ifndef USE_THREADS
1636 scm_debug_frame *scm_last_debug_frame;
1637 #endif
1638
1639 /* scm_debug_eframe_size is the number of slots available for pseudo
1640 * stack frames at each real stack frame.
1641 */
1642
1643 int scm_debug_eframe_size;
1644
1645 int scm_debug_mode, scm_check_entry_p, scm_check_apply_p, scm_check_exit_p;
1646
1647 int scm_eval_stack;
1648
1649 scm_option scm_eval_opts[] = {
1650 { SCM_OPTION_INTEGER, "stack", 22000, "Size of thread stacks (in machine words)." }
1651 };
1652
1653 scm_option scm_debug_opts[] = {
1654 { SCM_OPTION_BOOLEAN, "cheap", 1,
1655 "*Flyweight representation of the stack at traps." },
1656 { SCM_OPTION_BOOLEAN, "breakpoints", 0, "*Check for breakpoints." },
1657 { SCM_OPTION_BOOLEAN, "trace", 0, "*Trace mode." },
1658 { SCM_OPTION_BOOLEAN, "procnames", 1,
1659 "Record procedure names at definition." },
1660 { SCM_OPTION_BOOLEAN, "backwards", 0,
1661 "Display backtrace in anti-chronological order." },
1662 { SCM_OPTION_INTEGER, "width", 79, "Maximal width of backtrace." },
1663 { SCM_OPTION_INTEGER, "indent", 10, "Maximal indentation in backtrace." },
1664 { SCM_OPTION_INTEGER, "frames", 3,
1665 "Maximum number of tail-recursive frames in backtrace." },
1666 { SCM_OPTION_INTEGER, "maxdepth", 1000,
1667 "Maximal number of stored backtrace frames." },
1668 { SCM_OPTION_INTEGER, "depth", 20, "Maximal length of printed backtrace." },
1669 { SCM_OPTION_BOOLEAN, "backtrace", 0, "Show backtrace on error." },
1670 { SCM_OPTION_BOOLEAN, "debug", 0, "Use the debugging evaluator." },
1671 { SCM_OPTION_INTEGER, "stack", 20000, "Stack size limit (measured in words; 0 = no check)." }
1672 };
1673
1674 scm_option scm_evaluator_trap_table[] = {
1675 { SCM_OPTION_BOOLEAN, "traps", 0, "Enable evaluator traps." },
1676 { SCM_OPTION_BOOLEAN, "enter-frame", 0, "Trap when eval enters new frame." },
1677 { SCM_OPTION_BOOLEAN, "apply-frame", 0, "Trap when entering apply." },
1678 { SCM_OPTION_BOOLEAN, "exit-frame", 0, "Trap when exiting eval or apply." }
1679 };
1680
1681 SCM_DEFINE (scm_eval_options_interface, "eval-options-interface", 0, 1, 0,
1682 (SCM setting),
1683 "Option interface for the evaluation options. Instead of using\n"
1684 "this procedure directly, use the procedures @code{eval-enable},\n"
1685 "@code{eval-disable}, @code{eval-set!} and @var{eval-options}.")
1686 #define FUNC_NAME s_scm_eval_options_interface
1687 {
1688 SCM ans;
1689 SCM_DEFER_INTS;
1690 ans = scm_options (setting,
1691 scm_eval_opts,
1692 SCM_N_EVAL_OPTIONS,
1693 FUNC_NAME);
1694 scm_eval_stack = SCM_EVAL_STACK * sizeof (void *);
1695 SCM_ALLOW_INTS;
1696 return ans;
1697 }
1698 #undef FUNC_NAME
1699
1700 SCM_DEFINE (scm_evaluator_traps, "evaluator-traps-interface", 0, 1, 0,
1701 (SCM setting),
1702 "Option interface for the evaluator trap options.")
1703 #define FUNC_NAME s_scm_evaluator_traps
1704 {
1705 SCM ans;
1706 SCM_DEFER_INTS;
1707 ans = scm_options (setting,
1708 scm_evaluator_trap_table,
1709 SCM_N_EVALUATOR_TRAPS,
1710 FUNC_NAME);
1711 SCM_RESET_DEBUG_MODE;
1712 SCM_ALLOW_INTS;
1713 return ans;
1714 }
1715 #undef FUNC_NAME
1716
1717 SCM
1718 scm_deval_args (SCM l, SCM env, SCM proc, SCM *lloc)
1719 {
1720 SCM *results = lloc, res;
1721 while (SCM_NIMP (l))
1722 {
1723 #ifdef SCM_CAUTIOUS
1724 if (SCM_CONSP (l))
1725 {
1726 if (SCM_IMP (SCM_CAR (l)))
1727 res = SCM_EVALIM (SCM_CAR (l), env);
1728 else
1729 res = EVALCELLCAR (l, env);
1730 }
1731 else if (SCM_TYP3 (l) == scm_tc3_cons_gloc)
1732 {
1733 scm_bits_t vcell = SCM_STRUCT_VTABLE_DATA (l) [scm_vtable_index_vcell];
1734 if (vcell == 0)
1735 res = SCM_CAR (l); /* struct planted in code */
1736 else
1737 res = SCM_PACK (vcell);
1738 }
1739 else
1740 goto wrongnumargs;
1741 #else
1742 res = EVALCAR (l, env);
1743 #endif
1744 *lloc = scm_cons (res, SCM_EOL);
1745 lloc = SCM_CDRLOC (*lloc);
1746 l = SCM_CDR (l);
1747 }
1748 #ifdef SCM_CAUTIOUS
1749 if (SCM_NNULLP (l))
1750 {
1751 wrongnumargs:
1752 scm_wrong_num_args (proc);
1753 }
1754 #endif
1755 return *results;
1756 }
1757
1758 #endif /* !DEVAL */
1759
1760
1761 /* SECTION: Some local definitions for the evaluator.
1762 */
1763
1764 /* Update the toplevel environment frame ENV so that it refers to the
1765 current module.
1766 */
1767 #define UPDATE_TOPLEVEL_ENV(env) \
1768 do { \
1769 SCM p = scm_current_module_lookup_closure (); \
1770 if (p != SCM_CAR(env)) \
1771 env = scm_top_level_env (p); \
1772 } while (0)
1773
1774 #ifndef DEVAL
1775 #define CHECK_EQVISH(A,B) (SCM_EQ_P ((A), (B)) || (SCM_NFALSEP (scm_eqv_p ((A), (B)))))
1776 #endif /* DEVAL */
1777
1778 #define BUILTIN_RPASUBR /* Handle rpsubrs and asubrs without calling apply */
1779
1780 /* SECTION: This is the evaluator. Like any real monster, it has
1781 * three heads. This code is compiled twice.
1782 */
1783
1784 #if 0
1785
1786 SCM
1787 scm_ceval (SCM x, SCM env)
1788 {}
1789 #endif
1790 #if 0
1791
1792 SCM
1793 scm_deval (SCM x, SCM env)
1794 {}
1795 #endif
1796
1797 SCM
1798 SCM_CEVAL (SCM x, SCM env)
1799 {
1800 union
1801 {
1802 SCM *lloc;
1803 SCM arg1;
1804 } t;
1805 SCM proc, arg2;
1806 #ifdef DEVAL
1807 scm_debug_frame debug;
1808 scm_debug_info *debug_info_end;
1809 debug.prev = scm_last_debug_frame;
1810 debug.status = scm_debug_eframe_size;
1811 /*
1812 * The debug.vect contains twice as much scm_debug_info frames as the
1813 * user has specified with (debug-set! frames <n>).
1814 *
1815 * Even frames are eval frames, odd frames are apply frames.
1816 */
1817 debug.vect = (scm_debug_info *) alloca (scm_debug_eframe_size
1818 * sizeof (debug.vect[0]));
1819 debug.info = debug.vect;
1820 debug_info_end = debug.vect + scm_debug_eframe_size;
1821 scm_last_debug_frame = &debug;
1822 #endif
1823 #ifdef EVAL_STACK_CHECKING
1824 if (scm_stack_checking_enabled_p
1825 && SCM_STACK_OVERFLOW_P ((SCM_STACKITEM *) &proc))
1826 {
1827 #ifdef DEVAL
1828 debug.info->e.exp = x;
1829 debug.info->e.env = env;
1830 #endif
1831 scm_report_stack_overflow ();
1832 }
1833 #endif
1834 #ifdef DEVAL
1835 goto start;
1836 #endif
1837 loopnoap:
1838 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
1839 loop:
1840 #ifdef DEVAL
1841 SCM_CLEAR_ARGSREADY (debug);
1842 if (SCM_OVERFLOWP (debug))
1843 --debug.info;
1844 /*
1845 * In theory, this should be the only place where it is necessary to
1846 * check for space in debug.vect since both eval frames and
1847 * available space are even.
1848 *
1849 * For this to be the case, however, it is necessary that primitive
1850 * special forms which jump back to `loop', `begin' or some similar
1851 * label call PREP_APPLY. A convenient way to do this is to jump to
1852 * `loopnoap' or `cdrxnoap'.
1853 */
1854 else if (++debug.info >= debug_info_end)
1855 {
1856 SCM_SET_OVERFLOW (debug);
1857 debug.info -= 2;
1858 }
1859 start:
1860 debug.info->e.exp = x;
1861 debug.info->e.env = env;
1862 if (CHECK_ENTRY && SCM_TRAPS_P)
1863 if (SCM_ENTER_FRAME_P || (SCM_BREAKPOINTS_P && SRCBRKP (x)))
1864 {
1865 SCM tail = SCM_BOOL(SCM_TAILRECP (debug));
1866 SCM_SET_TAILREC (debug);
1867 if (SCM_CHEAPTRAPS_P)
1868 t.arg1 = scm_make_debugobj (&debug);
1869 else
1870 {
1871 int first;
1872 SCM val = scm_make_continuation (&first);
1873
1874 if (first)
1875 t.arg1 = val;
1876 else
1877 {
1878 x = val;
1879 if (SCM_IMP (x))
1880 {
1881 RETURN (x);
1882 }
1883 else
1884 /* This gives the possibility for the debugger to
1885 modify the source expression before evaluation. */
1886 goto dispatch;
1887 }
1888 }
1889 scm_ithrow (scm_sym_enter_frame,
1890 scm_cons2 (t.arg1, tail,
1891 scm_cons (scm_unmemocopy (x, env), SCM_EOL)),
1892 0);
1893 }
1894 #endif
1895 #if defined (USE_THREADS) || defined (DEVAL)
1896 dispatch:
1897 #endif
1898 SCM_TICK;
1899 switch (SCM_TYP7 (x))
1900 {
1901 case scm_tc7_symbol:
1902 /* Only happens when called at top level.
1903 */
1904 x = scm_cons (x, SCM_UNDEFINED);
1905 goto retval;
1906
1907 case SCM_BIT8(SCM_IM_AND):
1908 x = SCM_CDR (x);
1909 t.arg1 = x;
1910 while (SCM_NNULLP (t.arg1 = SCM_CDR (t.arg1)))
1911 if (SCM_FALSEP (EVALCAR (x, env)))
1912 {
1913 RETURN (SCM_BOOL_F);
1914 }
1915 else
1916 x = t.arg1;
1917 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
1918 goto carloop;
1919
1920 case SCM_BIT8(SCM_IM_BEGIN):
1921 /* (currently unused)
1922 cdrxnoap: */
1923 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
1924 /* (currently unused)
1925 cdrxbegin: */
1926 x = SCM_CDR (x);
1927
1928 begin:
1929 /* If we are on toplevel with a lookup closure, we need to sync
1930 with the current module. */
1931 if (SCM_CONSP(env) && !SCM_CONSP(SCM_CAR(env)))
1932 {
1933 t.arg1 = x;
1934 UPDATE_TOPLEVEL_ENV (env);
1935 while (SCM_NNULLP (t.arg1 = SCM_CDR (t.arg1)))
1936 {
1937 EVALCAR (x, env);
1938 x = t.arg1;
1939 UPDATE_TOPLEVEL_ENV (env);
1940 }
1941 goto carloop;
1942 }
1943 else
1944 goto nontoplevel_begin;
1945
1946 nontoplevel_cdrxnoap:
1947 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
1948 nontoplevel_cdrxbegin:
1949 x = SCM_CDR (x);
1950 nontoplevel_begin:
1951 t.arg1 = x;
1952 while (SCM_NNULLP (t.arg1 = SCM_CDR (t.arg1)))
1953 {
1954 if (SCM_IMP (SCM_CAR (x)))
1955 {
1956 if (SCM_ISYMP (SCM_CAR (x)))
1957 {
1958 x = scm_m_expand_body (x, env);
1959 goto nontoplevel_begin;
1960 }
1961 else
1962 SCM_EVALIM2 (SCM_CAR(x));
1963 }
1964 else
1965 SCM_CEVAL (SCM_CAR (x), env);
1966 x = t.arg1;
1967 }
1968
1969 carloop: /* scm_eval car of last form in list */
1970 if (SCM_NCELLP (SCM_CAR (x)))
1971 {
1972 x = SCM_CAR (x);
1973 RETURN (SCM_IMP (x) ? SCM_EVALIM (x, env) : SCM_GLOC_VAL (x))
1974 }
1975
1976 if (SCM_SYMBOLP (SCM_CAR (x)))
1977 {
1978 retval:
1979 RETURN (*scm_lookupcar (x, env, 1))
1980 }
1981
1982 x = SCM_CAR (x);
1983 goto loop; /* tail recurse */
1984
1985
1986 case SCM_BIT8(SCM_IM_CASE):
1987 x = SCM_CDR (x);
1988 t.arg1 = EVALCAR (x, env);
1989 while (SCM_NIMP (x = SCM_CDR (x)))
1990 {
1991 proc = SCM_CAR (x);
1992 if (SCM_EQ_P (scm_sym_else, SCM_CAR (proc)))
1993 {
1994 x = SCM_CDR (proc);
1995 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
1996 goto begin;
1997 }
1998 proc = SCM_CAR (proc);
1999 while (SCM_NIMP (proc))
2000 {
2001 if (CHECK_EQVISH (SCM_CAR (proc), t.arg1))
2002 {
2003 x = SCM_CDR (SCM_CAR (x));
2004 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
2005 goto begin;
2006 }
2007 proc = SCM_CDR (proc);
2008 }
2009 }
2010 RETURN (SCM_UNSPECIFIED)
2011
2012
2013 case SCM_BIT8(SCM_IM_COND):
2014 while (SCM_NIMP (x = SCM_CDR (x)))
2015 {
2016 proc = SCM_CAR (x);
2017 t.arg1 = EVALCAR (proc, env);
2018 if (SCM_NFALSEP (t.arg1))
2019 {
2020 x = SCM_CDR (proc);
2021 if SCM_NULLP (x)
2022 {
2023 RETURN (t.arg1)
2024 }
2025 if (! SCM_EQ_P (scm_sym_arrow, SCM_CAR (x)))
2026 {
2027 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
2028 goto begin;
2029 }
2030 proc = SCM_CDR (x);
2031 proc = EVALCAR (proc, env);
2032 SCM_ASRTGO (SCM_NIMP (proc), badfun);
2033 PREP_APPLY (proc, scm_cons (t.arg1, SCM_EOL));
2034 ENTER_APPLY;
2035 if (SCM_CLOSUREP(proc) && scm_badformalsp (proc, 1))
2036 goto umwrongnumargs;
2037 goto evap1;
2038 }
2039 }
2040 RETURN (SCM_UNSPECIFIED)
2041
2042
2043 case SCM_BIT8(SCM_IM_DO):
2044 x = SCM_CDR (x);
2045 proc = SCM_CAR (SCM_CDR (x)); /* inits */
2046 t.arg1 = SCM_EOL; /* values */
2047 while (SCM_NIMP (proc))
2048 {
2049 t.arg1 = scm_cons (EVALCAR (proc, env), t.arg1);
2050 proc = SCM_CDR (proc);
2051 }
2052 env = EXTEND_ENV (SCM_CAR (x), t.arg1, env);
2053 x = SCM_CDR (SCM_CDR (x));
2054 while (proc = SCM_CAR (x), SCM_FALSEP (EVALCAR (proc, env)))
2055 {
2056 for (proc = SCM_CADR (x); SCM_NIMP (proc); proc = SCM_CDR (proc))
2057 {
2058 t.arg1 = SCM_CAR (proc); /* body */
2059 SIDEVAL (t.arg1, env);
2060 }
2061 for (t.arg1 = SCM_EOL, proc = SCM_CDDR (x);
2062 SCM_NIMP (proc);
2063 proc = SCM_CDR (proc))
2064 t.arg1 = scm_cons (EVALCAR (proc, env), t.arg1); /* steps */
2065 env = EXTEND_ENV (SCM_CAR (SCM_CAR (env)), t.arg1, SCM_CDR (env));
2066 }
2067 x = SCM_CDR (proc);
2068 if (SCM_NULLP (x))
2069 RETURN (SCM_UNSPECIFIED);
2070 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
2071 goto nontoplevel_begin;
2072
2073
2074 case SCM_BIT8(SCM_IM_IF):
2075 x = SCM_CDR (x);
2076 if (SCM_NFALSEP (EVALCAR (x, env)))
2077 x = SCM_CDR (x);
2078 else if (SCM_IMP (x = SCM_CDR (SCM_CDR (x))))
2079 {
2080 RETURN (SCM_UNSPECIFIED);
2081 }
2082 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
2083 goto carloop;
2084
2085
2086 case SCM_BIT8(SCM_IM_LET):
2087 x = SCM_CDR (x);
2088 proc = SCM_CAR (SCM_CDR (x));
2089 t.arg1 = SCM_EOL;
2090 do
2091 {
2092 t.arg1 = scm_cons (EVALCAR (proc, env), t.arg1);
2093 }
2094 while (SCM_NIMP (proc = SCM_CDR (proc)));
2095 env = EXTEND_ENV (SCM_CAR (x), t.arg1, env);
2096 x = SCM_CDR (x);
2097 goto nontoplevel_cdrxnoap;
2098
2099
2100 case SCM_BIT8(SCM_IM_LETREC):
2101 x = SCM_CDR (x);
2102 env = EXTEND_ENV (SCM_CAR (x), scm_undefineds, env);
2103 x = SCM_CDR (x);
2104 proc = SCM_CAR (x);
2105 t.arg1 = SCM_EOL;
2106 do
2107 {
2108 t.arg1 = scm_cons (EVALCAR (proc, env), t.arg1);
2109 }
2110 while (SCM_NIMP (proc = SCM_CDR (proc)));
2111 SCM_SETCDR (SCM_CAR (env), t.arg1);
2112 goto nontoplevel_cdrxnoap;
2113
2114
2115 case SCM_BIT8(SCM_IM_LETSTAR):
2116 x = SCM_CDR (x);
2117 proc = SCM_CAR (x);
2118 if (SCM_IMP (proc))
2119 {
2120 env = EXTEND_ENV (SCM_EOL, SCM_EOL, env);
2121 goto nontoplevel_cdrxnoap;
2122 }
2123 do
2124 {
2125 t.arg1 = SCM_CAR (proc);
2126 proc = SCM_CDR (proc);
2127 env = EXTEND_ENV (t.arg1, EVALCAR (proc, env), env);
2128 }
2129 while (SCM_NIMP (proc = SCM_CDR (proc)));
2130 goto nontoplevel_cdrxnoap;
2131
2132 case SCM_BIT8(SCM_IM_OR):
2133 x = SCM_CDR (x);
2134 t.arg1 = x;
2135 while (SCM_NNULLP (t.arg1 = SCM_CDR (t.arg1)))
2136 {
2137 x = EVALCAR (x, env);
2138 if (SCM_NFALSEP (x))
2139 {
2140 RETURN (x);
2141 }
2142 x = t.arg1;
2143 }
2144 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
2145 goto carloop;
2146
2147
2148 case SCM_BIT8(SCM_IM_LAMBDA):
2149 RETURN (scm_closure (SCM_CDR (x), env));
2150
2151
2152 case SCM_BIT8(SCM_IM_QUOTE):
2153 RETURN (SCM_CAR (SCM_CDR (x)));
2154
2155
2156 case SCM_BIT8(SCM_IM_SET_X):
2157 x = SCM_CDR (x);
2158 proc = SCM_CAR (x);
2159 switch (SCM_ITAG3 (proc))
2160 {
2161 case scm_tc3_cons:
2162 t.lloc = scm_lookupcar (x, env, 1);
2163 break;
2164 case scm_tc3_cons_gloc:
2165 t.lloc = SCM_GLOC_VAL_LOC (proc);
2166 break;
2167 #ifdef MEMOIZE_LOCALS
2168 case scm_tc3_imm24:
2169 t.lloc = scm_ilookup (proc, env);
2170 break;
2171 #endif
2172 }
2173 x = SCM_CDR (x);
2174 *t.lloc = EVALCAR (x, env);
2175 #ifdef SICP
2176 RETURN (*t.lloc);
2177 #else
2178 RETURN (SCM_UNSPECIFIED);
2179 #endif
2180
2181
2182 case SCM_BIT8(SCM_IM_DEFINE): /* only for internal defines */
2183 scm_misc_error (NULL, "Bad define placement", SCM_EOL);
2184
2185 /* new syntactic forms go here. */
2186 case SCM_BIT8(SCM_MAKISYM (0)):
2187 proc = SCM_CAR (x);
2188 SCM_ASRTGO (SCM_ISYMP (proc), badfun);
2189 switch SCM_ISYMNUM (proc)
2190 {
2191 case (SCM_ISYMNUM (SCM_IM_APPLY)):
2192 proc = SCM_CDR (x);
2193 proc = EVALCAR (proc, env);
2194 SCM_ASRTGO (SCM_NIMP (proc), badfun);
2195 if (SCM_CLOSUREP (proc))
2196 {
2197 SCM argl, tl;
2198 PREP_APPLY (proc, SCM_EOL);
2199 t.arg1 = SCM_CDR (SCM_CDR (x));
2200 t.arg1 = EVALCAR (t.arg1, env);
2201 #ifdef DEVAL
2202 debug.info->a.args = t.arg1;
2203 #endif
2204 #ifndef SCM_RECKLESS
2205 if (scm_badargsp (SCM_CAR (SCM_CODE (proc)), t.arg1))
2206 goto wrongnumargs;
2207 #endif
2208 ENTER_APPLY;
2209 /* Copy argument list */
2210 if (SCM_IMP (t.arg1))
2211 argl = t.arg1;
2212 else
2213 {
2214 argl = tl = scm_cons (SCM_CAR (t.arg1), SCM_UNSPECIFIED);
2215 while (SCM_NIMP (t.arg1 = SCM_CDR (t.arg1))
2216 && SCM_CONSP (t.arg1))
2217 {
2218 SCM_SETCDR (tl, scm_cons (SCM_CAR (t.arg1),
2219 SCM_UNSPECIFIED));
2220 tl = SCM_CDR (tl);
2221 }
2222 SCM_SETCDR (tl, t.arg1);
2223 }
2224
2225 env = EXTEND_ENV (SCM_CAR (SCM_CODE (proc)), argl, SCM_ENV (proc));
2226 x = SCM_CODE (proc);
2227 goto nontoplevel_cdrxbegin;
2228 }
2229 proc = scm_f_apply;
2230 goto evapply;
2231
2232 case (SCM_ISYMNUM (SCM_IM_CONT)):
2233 {
2234 int first;
2235 SCM val = scm_make_continuation (&first);
2236
2237 if (first)
2238 t.arg1 = val;
2239 else
2240 RETURN (val);
2241 }
2242 proc = SCM_CDR (x);
2243 proc = evalcar (proc, env);
2244 SCM_ASRTGO (SCM_NIMP (proc), badfun);
2245 PREP_APPLY (proc, scm_cons (t.arg1, SCM_EOL));
2246 ENTER_APPLY;
2247 if (SCM_CLOSUREP(proc) && scm_badformalsp (proc, 1))
2248 goto umwrongnumargs;
2249 goto evap1;
2250
2251 case (SCM_ISYMNUM (SCM_IM_DELAY)):
2252 RETURN (scm_makprom (scm_closure (SCM_CDR (x), env)))
2253
2254 case (SCM_ISYMNUM (SCM_IM_DISPATCH)):
2255 proc = SCM_CADR (x); /* unevaluated operands */
2256 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
2257 if (SCM_IMP (proc))
2258 arg2 = *scm_ilookup (proc, env);
2259 else if (SCM_NCONSP (proc))
2260 {
2261 if (SCM_NCELLP (proc))
2262 arg2 = SCM_GLOC_VAL (proc);
2263 else
2264 arg2 = *scm_lookupcar (SCM_CDR (x), env, 1);
2265 }
2266 else
2267 {
2268 arg2 = scm_cons (EVALCAR (proc, env), SCM_EOL);
2269 t.lloc = SCM_CDRLOC (arg2);
2270 while (SCM_NIMP (proc = SCM_CDR (proc)))
2271 {
2272 *t.lloc = scm_cons (EVALCAR (proc, env), SCM_EOL);
2273 t.lloc = SCM_CDRLOC (*t.lloc);
2274 }
2275 }
2276
2277 type_dispatch:
2278 /* The type dispatch code is duplicated here
2279 * (c.f. objects.c:scm_mcache_compute_cmethod) since that
2280 * cuts down execution time for type dispatch to 50%.
2281 */
2282 {
2283 int i, n, end, mask;
2284 SCM z = SCM_CDDR (x);
2285 n = SCM_INUM (SCM_CAR (z)); /* maximum number of specializers */
2286 proc = SCM_CADR (z);
2287
2288 if (SCM_NIMP (proc))
2289 {
2290 /* Prepare for linear search */
2291 mask = -1;
2292 i = 0;
2293 end = SCM_VECTOR_LENGTH (proc);
2294 }
2295 else
2296 {
2297 /* Compute a hash value */
2298 int hashset = SCM_INUM (proc);
2299 int j = n;
2300 mask = SCM_INUM (SCM_CAR (z = SCM_CDDR (z)));
2301 proc = SCM_CADR (z);
2302 i = 0;
2303 t.arg1 = arg2;
2304 if (SCM_NIMP (t.arg1))
2305 do
2306 {
2307 i += SCM_STRUCT_DATA (scm_class_of (SCM_CAR (t.arg1)))
2308 [scm_si_hashsets + hashset];
2309 t.arg1 = SCM_CDR (t.arg1);
2310 }
2311 while (j-- && SCM_NIMP (t.arg1));
2312 i &= mask;
2313 end = i;
2314 }
2315
2316 /* Search for match */
2317 do
2318 {
2319 int j = n;
2320 z = SCM_VELTS (proc)[i];
2321 t.arg1 = arg2; /* list of arguments */
2322 if (SCM_NIMP (t.arg1))
2323 do
2324 {
2325 /* More arguments than specifiers => CLASS != ENV */
2326 if (! SCM_EQ_P (scm_class_of (SCM_CAR (t.arg1)), SCM_CAR (z)))
2327 goto next_method;
2328 t.arg1 = SCM_CDR (t.arg1);
2329 z = SCM_CDR (z);
2330 }
2331 while (j-- && SCM_NIMP (t.arg1));
2332 /* Fewer arguments than specifiers => CAR != ENV */
2333 if (!(SCM_IMP (SCM_CAR (z)) || SCM_CONSP (SCM_CAR (z))))
2334 goto next_method;
2335 apply_cmethod:
2336 env = EXTEND_ENV (SCM_CAR (SCM_CMETHOD_CODE (z)),
2337 arg2,
2338 SCM_CMETHOD_ENV (z));
2339 x = SCM_CMETHOD_CODE (z);
2340 goto nontoplevel_cdrxbegin;
2341 next_method:
2342 i = (i + 1) & mask;
2343 } while (i != end);
2344
2345 z = scm_memoize_method (x, arg2);
2346 goto apply_cmethod;
2347 }
2348
2349 case (SCM_ISYMNUM (SCM_IM_SLOT_REF)):
2350 x = SCM_CDR (x);
2351 t.arg1 = EVALCAR (x, env);
2352 RETURN (SCM_PACK (SCM_STRUCT_DATA (t.arg1) [SCM_INUM (SCM_CADR (x))]))
2353
2354 case (SCM_ISYMNUM (SCM_IM_SLOT_SET_X)):
2355 x = SCM_CDR (x);
2356 t.arg1 = EVALCAR (x, env);
2357 x = SCM_CDR (x);
2358 proc = SCM_CDR (x);
2359 SCM_STRUCT_DATA (t.arg1) [SCM_INUM (SCM_CAR (x))]
2360 = SCM_UNPACK (EVALCAR (proc, env));
2361 RETURN (SCM_UNSPECIFIED)
2362
2363 case (SCM_ISYMNUM (SCM_IM_NIL_COND)):
2364 proc = SCM_CDR (x);
2365 while (SCM_NIMP (x = SCM_CDR (proc)))
2366 {
2367 if (!(SCM_FALSEP (t.arg1 = EVALCAR (proc, env))
2368 || SCM_EQ_P (t.arg1, scm_lisp_nil)))
2369 {
2370 if (SCM_EQ_P (SCM_CAR (x), SCM_UNSPECIFIED))
2371 RETURN (t.arg1);
2372 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
2373 goto carloop;
2374 }
2375 proc = SCM_CDR (x);
2376 }
2377 x = proc;
2378 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
2379 goto carloop;
2380
2381 case (SCM_ISYMNUM (SCM_IM_NIL_IFY)):
2382 x = SCM_CDR (x);
2383 RETURN ((SCM_FALSEP (proc = EVALCAR (x, env)) || SCM_NULLP (proc))
2384 ? scm_lisp_nil
2385 : proc)
2386
2387 case (SCM_ISYMNUM (SCM_IM_T_IFY)):
2388 x = SCM_CDR (x);
2389 RETURN (SCM_NFALSEP (EVALCAR (x, env)) ? scm_lisp_t : scm_lisp_nil)
2390
2391 case (SCM_ISYMNUM (SCM_IM_0_COND)):
2392 proc = SCM_CDR (x);
2393 while (SCM_NIMP (x = SCM_CDR (proc)))
2394 {
2395 if (!(SCM_FALSEP (t.arg1 = EVALCAR (proc, env))
2396 || SCM_EQ_P (t.arg1, SCM_INUM0)))
2397 {
2398 if (SCM_EQ_P (SCM_CAR (x), SCM_UNSPECIFIED))
2399 RETURN (t.arg1);
2400 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
2401 goto carloop;
2402 }
2403 proc = SCM_CDR (x);
2404 }
2405 x = proc;
2406 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
2407 goto carloop;
2408
2409 case (SCM_ISYMNUM (SCM_IM_0_IFY)):
2410 x = SCM_CDR (x);
2411 RETURN (SCM_FALSEP (proc = EVALCAR (x, env))
2412 ? SCM_INUM0
2413 : proc)
2414
2415 case (SCM_ISYMNUM (SCM_IM_1_IFY)):
2416 x = SCM_CDR (x);
2417 RETURN (SCM_NFALSEP (EVALCAR (x, env))
2418 ? SCM_MAKINUM (1)
2419 : SCM_INUM0)
2420
2421 case (SCM_ISYMNUM (SCM_IM_BIND)):
2422 x = SCM_CDR (x);
2423
2424 t.arg1 = SCM_CAR (x);
2425 arg2 = SCM_CDAR (env);
2426 while (SCM_NIMP (arg2))
2427 {
2428 proc = SCM_GLOC_VAL (SCM_CAR (t.arg1));
2429 SCM_SETCDR (SCM_PACK (SCM_UNPACK (SCM_CAR (t.arg1)) - 1L),
2430 SCM_CAR (arg2));
2431 SCM_SETCAR (arg2, proc);
2432 t.arg1 = SCM_CDR (t.arg1);
2433 arg2 = SCM_CDR (arg2);
2434 }
2435 t.arg1 = SCM_CAR (x);
2436 scm_dynwinds = scm_acons (t.arg1, SCM_CDAR (env), scm_dynwinds);
2437
2438 arg2 = x = SCM_CDR (x);
2439 while (SCM_NNULLP (arg2 = SCM_CDR (arg2)))
2440 {
2441 SIDEVAL (SCM_CAR (x), env);
2442 x = arg2;
2443 }
2444 proc = EVALCAR (x, env);
2445
2446 scm_dynwinds = SCM_CDR (scm_dynwinds);
2447 arg2 = SCM_CDAR (env);
2448 while (SCM_NIMP (arg2))
2449 {
2450 SCM_SETCDR (SCM_PACK (SCM_UNPACK (SCM_CAR (t.arg1)) - 1L),
2451 SCM_CAR (arg2));
2452 t.arg1 = SCM_CDR (t.arg1);
2453 arg2 = SCM_CDR (arg2);
2454 }
2455
2456 RETURN (proc)
2457
2458 default:
2459 goto badfun;
2460 }
2461
2462 default:
2463 proc = x;
2464 badfun:
2465 /* scm_everr (x, env,...) */
2466 scm_misc_error (NULL, "Wrong type to apply: ~S", SCM_LIST1 (proc));
2467 case scm_tc7_vector:
2468 case scm_tc7_wvect:
2469 #ifdef HAVE_ARRAYS
2470 case scm_tc7_bvect:
2471 case scm_tc7_byvect:
2472 case scm_tc7_svect:
2473 case scm_tc7_ivect:
2474 case scm_tc7_uvect:
2475 case scm_tc7_fvect:
2476 case scm_tc7_dvect:
2477 case scm_tc7_cvect:
2478 #ifdef HAVE_LONG_LONGS
2479 case scm_tc7_llvect:
2480 #endif
2481 #endif
2482 case scm_tc7_string:
2483 case scm_tc7_substring:
2484 case scm_tc7_smob:
2485 case scm_tcs_closures:
2486 case scm_tc7_cclo:
2487 case scm_tc7_pws:
2488 case scm_tcs_subrs:
2489 RETURN (x);
2490
2491 #ifdef MEMOIZE_LOCALS
2492 case SCM_BIT8(SCM_ILOC00):
2493 proc = *scm_ilookup (SCM_CAR (x), env);
2494 SCM_ASRTGO (SCM_NIMP (proc), badfun);
2495 #ifndef SCM_RECKLESS
2496 #ifdef SCM_CAUTIOUS
2497 goto checkargs;
2498 #endif
2499 #endif
2500 break;
2501 #endif /* ifdef MEMOIZE_LOCALS */
2502
2503
2504 case scm_tcs_cons_gloc: {
2505 scm_bits_t vcell = SCM_STRUCT_VTABLE_DATA (x) [scm_vtable_index_vcell];
2506 if (vcell == 0) {
2507 /* This is a struct implanted in the code, not a gloc. */
2508 RETURN (x);
2509 } else {
2510 proc = SCM_PACK (vcell);
2511 SCM_ASRTGO (SCM_NIMP (proc), badfun);
2512 #ifndef SCM_RECKLESS
2513 #ifdef SCM_CAUTIOUS
2514 goto checkargs;
2515 #endif
2516 #endif
2517 }
2518 break;
2519 }
2520
2521 case scm_tcs_cons_nimcar:
2522 if (SCM_SYMBOLP (SCM_CAR (x)))
2523 {
2524 #ifdef USE_THREADS
2525 t.lloc = scm_lookupcar1 (x, env, 1);
2526 if (t.lloc == NULL)
2527 {
2528 /* we have lost the race, start again. */
2529 goto dispatch;
2530 }
2531 proc = *t.lloc;
2532 #else
2533 proc = *scm_lookupcar (x, env, 1);
2534 #endif
2535
2536 if (SCM_IMP (proc))
2537 {
2538 unmemocar (x, env);
2539 goto badfun;
2540 }
2541 if (scm_tc16_macro == SCM_TYP16 (proc))
2542 {
2543 unmemocar (x, env);
2544
2545 handle_a_macro:
2546 #ifdef DEVAL
2547 /* Set a flag during macro expansion so that macro
2548 application frames can be deleted from the backtrace. */
2549 SCM_SET_MACROEXP (debug);
2550 #endif
2551 t.arg1 = SCM_APPLY (SCM_CDR (proc), x,
2552 scm_cons (env, scm_listofnull));
2553
2554 #ifdef DEVAL
2555 SCM_CLEAR_MACROEXP (debug);
2556 #endif
2557 switch (SCM_CELL_WORD_0 (proc) >> 16)
2558 {
2559 case 2:
2560 if (scm_ilength (t.arg1) <= 0)
2561 t.arg1 = scm_cons2 (SCM_IM_BEGIN, t.arg1, SCM_EOL);
2562 #ifdef DEVAL
2563 if (!SCM_CLOSUREP (SCM_CDR (proc)))
2564 {
2565 SCM_DEFER_INTS;
2566 SCM_SETCAR (x, SCM_CAR (t.arg1));
2567 SCM_SETCDR (x, SCM_CDR (t.arg1));
2568 SCM_ALLOW_INTS;
2569 goto dispatch;
2570 }
2571 /* Prevent memoizing of debug info expression. */
2572 debug.info->e.exp = scm_cons_source (debug.info->e.exp,
2573 SCM_CAR (x),
2574 SCM_CDR (x));
2575 #endif
2576 SCM_DEFER_INTS;
2577 SCM_SETCAR (x, SCM_CAR (t.arg1));
2578 SCM_SETCDR (x, SCM_CDR (t.arg1));
2579 SCM_ALLOW_INTS;
2580 goto loopnoap;
2581 case 1:
2582 if (SCM_NIMP (x = t.arg1))
2583 goto loopnoap;
2584 case 0:
2585 RETURN (t.arg1);
2586 }
2587 }
2588 }
2589 else
2590 proc = SCM_CEVAL (SCM_CAR (x), env);
2591 SCM_ASRTGO (SCM_NIMP (proc), badfun);
2592 #ifndef SCM_RECKLESS
2593 #ifdef SCM_CAUTIOUS
2594 checkargs:
2595 #endif
2596 if (SCM_CLOSUREP (proc))
2597 {
2598 arg2 = SCM_CAR (SCM_CODE (proc));
2599 t.arg1 = SCM_CDR (x);
2600 while (SCM_NIMP (arg2))
2601 {
2602 if (SCM_NCONSP (arg2))
2603 goto evapply;
2604 if (SCM_IMP (t.arg1))
2605 goto umwrongnumargs;
2606 arg2 = SCM_CDR (arg2);
2607 t.arg1 = SCM_CDR (t.arg1);
2608 }
2609 if (SCM_NNULLP (t.arg1))
2610 goto umwrongnumargs;
2611 }
2612 else if (scm_tc16_macro == SCM_TYP16 (proc))
2613 goto handle_a_macro;
2614 #endif
2615 }
2616
2617
2618 evapply:
2619 PREP_APPLY (proc, SCM_EOL);
2620 if (SCM_NULLP (SCM_CDR (x))) {
2621 ENTER_APPLY;
2622 evap0:
2623 switch (SCM_TYP7 (proc))
2624 { /* no arguments given */
2625 case scm_tc7_subr_0:
2626 RETURN (SCM_SUBRF (proc) ());
2627 case scm_tc7_subr_1o:
2628 RETURN (SCM_SUBRF (proc) (SCM_UNDEFINED));
2629 case scm_tc7_lsubr:
2630 RETURN (SCM_SUBRF (proc) (SCM_EOL));
2631 case scm_tc7_rpsubr:
2632 RETURN (SCM_BOOL_T);
2633 case scm_tc7_asubr:
2634 RETURN (SCM_SUBRF (proc) (SCM_UNDEFINED, SCM_UNDEFINED));
2635 case scm_tc7_smob:
2636 if (!SCM_SMOB_APPLICABLE_P (proc))
2637 goto badfun;
2638 RETURN (SCM_SMOB_APPLY_0 (proc));
2639 case scm_tc7_cclo:
2640 t.arg1 = proc;
2641 proc = SCM_CCLO_SUBR (proc);
2642 #ifdef DEVAL
2643 debug.info->a.proc = proc;
2644 debug.info->a.args = scm_cons (t.arg1, SCM_EOL);
2645 #endif
2646 goto evap1;
2647 case scm_tc7_pws:
2648 proc = SCM_PROCEDURE (proc);
2649 #ifdef DEVAL
2650 debug.info->a.proc = proc;
2651 #endif
2652 if (!SCM_CLOSUREP (proc))
2653 goto evap0;
2654 if (scm_badformalsp (proc, 0))
2655 goto umwrongnumargs;
2656 case scm_tcs_closures:
2657 x = SCM_CODE (proc);
2658 env = EXTEND_ENV (SCM_CAR (x), SCM_EOL, SCM_ENV (proc));
2659 goto nontoplevel_cdrxbegin;
2660 case scm_tcs_cons_gloc:
2661 if (SCM_OBJ_CLASS_FLAGS (proc) & SCM_CLASSF_PURE_GENERIC)
2662 {
2663 x = SCM_ENTITY_PROCEDURE (proc);
2664 arg2 = SCM_EOL;
2665 goto type_dispatch;
2666 }
2667 else if (!SCM_I_OPERATORP (proc))
2668 goto badfun;
2669 else
2670 {
2671 t.arg1 = proc;
2672 proc = (SCM_I_ENTITYP (proc)
2673 ? SCM_ENTITY_PROCEDURE (proc)
2674 : SCM_OPERATOR_PROCEDURE (proc));
2675 #ifdef DEVAL
2676 debug.info->a.proc = proc;
2677 debug.info->a.args = scm_cons (t.arg1, SCM_EOL);
2678 #endif
2679 if (SCM_NIMP (proc))
2680 goto evap1;
2681 else
2682 goto badfun;
2683 }
2684 case scm_tc7_subr_1:
2685 case scm_tc7_subr_2:
2686 case scm_tc7_subr_2o:
2687 case scm_tc7_cxr:
2688 case scm_tc7_subr_3:
2689 case scm_tc7_lsubr_2:
2690 umwrongnumargs:
2691 unmemocar (x, env);
2692 wrongnumargs:
2693 /* scm_everr (x, env,...) */
2694 scm_wrong_num_args (proc);
2695 default:
2696 /* handle macros here */
2697 goto badfun;
2698 }
2699 }
2700
2701 /* must handle macros by here */
2702 x = SCM_CDR (x);
2703 #ifdef SCM_CAUTIOUS
2704 if (SCM_IMP (x))
2705 goto wrongnumargs;
2706 else if (SCM_CONSP (x))
2707 {
2708 if (SCM_IMP (SCM_CAR (x)))
2709 t.arg1 = SCM_EVALIM (SCM_CAR (x), env);
2710 else
2711 t.arg1 = EVALCELLCAR (x, env);
2712 }
2713 else if (SCM_TYP3 (x) == scm_tc3_cons_gloc)
2714 {
2715 scm_bits_t vcell = SCM_STRUCT_VTABLE_DATA (x) [scm_vtable_index_vcell];
2716 if (vcell == 0)
2717 t.arg1 = SCM_CAR (x); /* struct planted in code */
2718 else
2719 t.arg1 = SCM_PACK (vcell);
2720 }
2721 else
2722 goto wrongnumargs;
2723 #else
2724 t.arg1 = EVALCAR (x, env);
2725 #endif
2726 #ifdef DEVAL
2727 debug.info->a.args = scm_cons (t.arg1, SCM_EOL);
2728 #endif
2729 x = SCM_CDR (x);
2730 if (SCM_NULLP (x))
2731 {
2732 ENTER_APPLY;
2733 evap1:
2734 switch (SCM_TYP7 (proc))
2735 { /* have one argument in t.arg1 */
2736 case scm_tc7_subr_2o:
2737 RETURN (SCM_SUBRF (proc) (t.arg1, SCM_UNDEFINED));
2738 case scm_tc7_subr_1:
2739 case scm_tc7_subr_1o:
2740 RETURN (SCM_SUBRF (proc) (t.arg1));
2741 case scm_tc7_cxr:
2742 if (SCM_SUBRF (proc))
2743 {
2744 if (SCM_INUMP (t.arg1))
2745 {
2746 RETURN (scm_make_real (SCM_DSUBRF (proc) ((double) SCM_INUM (t.arg1))));
2747 }
2748 SCM_ASRTGO (SCM_NIMP (t.arg1), floerr);
2749 if (SCM_REALP (t.arg1))
2750 {
2751 RETURN (scm_make_real (SCM_DSUBRF (proc) (SCM_REAL_VALUE (t.arg1))));
2752 }
2753 #ifdef SCM_BIGDIG
2754 if (SCM_BIGP (t.arg1))
2755 {
2756 RETURN (scm_make_real (SCM_DSUBRF (proc) (scm_big2dbl (t.arg1))));
2757 }
2758 #endif
2759 floerr:
2760 SCM_WTA_DISPATCH_1 (*SCM_SUBR_GENERIC (proc), t.arg1,
2761 SCM_ARG1, SCM_SYMBOL_CHARS (SCM_SNAME (proc)));
2762 }
2763 proc = SCM_SNAME (proc);
2764 {
2765 char *chrs = SCM_SYMBOL_CHARS (proc) + SCM_SYMBOL_LENGTH (proc) - 1;
2766 while ('c' != *--chrs)
2767 {
2768 SCM_ASSERT (SCM_CONSP (t.arg1),
2769 t.arg1, SCM_ARG1, SCM_SYMBOL_CHARS (proc));
2770 t.arg1 = ('a' == *chrs) ? SCM_CAR (t.arg1) : SCM_CDR (t.arg1);
2771 }
2772 RETURN (t.arg1);
2773 }
2774 case scm_tc7_rpsubr:
2775 RETURN (SCM_BOOL_T);
2776 case scm_tc7_asubr:
2777 RETURN (SCM_SUBRF (proc) (t.arg1, SCM_UNDEFINED));
2778 case scm_tc7_lsubr:
2779 #ifdef DEVAL
2780 RETURN (SCM_SUBRF (proc) (debug.info->a.args))
2781 #else
2782 RETURN (SCM_SUBRF (proc) (scm_cons (t.arg1, SCM_EOL)));
2783 #endif
2784 case scm_tc7_smob:
2785 if (!SCM_SMOB_APPLICABLE_P (proc))
2786 goto badfun;
2787 RETURN (SCM_SMOB_APPLY_1 (proc, t.arg1));
2788 case scm_tc7_cclo:
2789 arg2 = t.arg1;
2790 t.arg1 = proc;
2791 proc = SCM_CCLO_SUBR (proc);
2792 #ifdef DEVAL
2793 debug.info->a.args = scm_cons (t.arg1, debug.info->a.args);
2794 debug.info->a.proc = proc;
2795 #endif
2796 goto evap2;
2797 case scm_tc7_pws:
2798 proc = SCM_PROCEDURE (proc);
2799 #ifdef DEVAL
2800 debug.info->a.proc = proc;
2801 #endif
2802 if (!SCM_CLOSUREP (proc))
2803 goto evap1;
2804 if (scm_badformalsp (proc, 1))
2805 goto umwrongnumargs;
2806 case scm_tcs_closures:
2807 /* clos1: */
2808 x = SCM_CODE (proc);
2809 #ifdef DEVAL
2810 env = EXTEND_ENV (SCM_CAR (x), debug.info->a.args, SCM_ENV (proc));
2811 #else
2812 env = EXTEND_ENV (SCM_CAR (x), scm_cons (t.arg1, SCM_EOL), SCM_ENV (proc));
2813 #endif
2814 goto nontoplevel_cdrxbegin;
2815 case scm_tcs_cons_gloc:
2816 if (SCM_OBJ_CLASS_FLAGS (proc) & SCM_CLASSF_PURE_GENERIC)
2817 {
2818 x = SCM_ENTITY_PROCEDURE (proc);
2819 #ifdef DEVAL
2820 arg2 = debug.info->a.args;
2821 #else
2822 arg2 = scm_cons (t.arg1, SCM_EOL);
2823 #endif
2824 goto type_dispatch;
2825 }
2826 else if (!SCM_I_OPERATORP (proc))
2827 goto badfun;
2828 else
2829 {
2830 arg2 = t.arg1;
2831 t.arg1 = proc;
2832 proc = (SCM_I_ENTITYP (proc)
2833 ? SCM_ENTITY_PROCEDURE (proc)
2834 : SCM_OPERATOR_PROCEDURE (proc));
2835 #ifdef DEVAL
2836 debug.info->a.args = scm_cons (t.arg1, debug.info->a.args);
2837 debug.info->a.proc = proc;
2838 #endif
2839 if (SCM_NIMP (proc))
2840 goto evap2;
2841 else
2842 goto badfun;
2843 }
2844 case scm_tc7_subr_2:
2845 case scm_tc7_subr_0:
2846 case scm_tc7_subr_3:
2847 case scm_tc7_lsubr_2:
2848 goto wrongnumargs;
2849 default:
2850 goto badfun;
2851 }
2852 }
2853 #ifdef SCM_CAUTIOUS
2854 if (SCM_IMP (x))
2855 goto wrongnumargs;
2856 else if (SCM_CONSP (x))
2857 {
2858 if (SCM_IMP (SCM_CAR (x)))
2859 arg2 = SCM_EVALIM (SCM_CAR (x), env);
2860 else
2861 arg2 = EVALCELLCAR (x, env);
2862 }
2863 else if (SCM_TYP3 (x) == scm_tc3_cons_gloc)
2864 {
2865 scm_bits_t vcell = SCM_STRUCT_VTABLE_DATA (x) [scm_vtable_index_vcell];
2866 if (vcell == 0)
2867 arg2 = SCM_CAR (x); /* struct planted in code */
2868 else
2869 arg2 = SCM_PACK (vcell);
2870 }
2871 else
2872 goto wrongnumargs;
2873 #else
2874 arg2 = EVALCAR (x, env);
2875 #endif
2876 { /* have two or more arguments */
2877 #ifdef DEVAL
2878 debug.info->a.args = scm_cons2 (t.arg1, arg2, SCM_EOL);
2879 #endif
2880 x = SCM_CDR (x);
2881 if (SCM_NULLP (x)) {
2882 ENTER_APPLY;
2883 evap2:
2884 switch (SCM_TYP7 (proc))
2885 { /* have two arguments */
2886 case scm_tc7_subr_2:
2887 case scm_tc7_subr_2o:
2888 RETURN (SCM_SUBRF (proc) (t.arg1, arg2));
2889 case scm_tc7_lsubr:
2890 #ifdef DEVAL
2891 RETURN (SCM_SUBRF (proc) (debug.info->a.args))
2892 #else
2893 RETURN (SCM_SUBRF (proc) (scm_cons2 (t.arg1, arg2, SCM_EOL)));
2894 #endif
2895 case scm_tc7_lsubr_2:
2896 RETURN (SCM_SUBRF (proc) (t.arg1, arg2, SCM_EOL));
2897 case scm_tc7_rpsubr:
2898 case scm_tc7_asubr:
2899 RETURN (SCM_SUBRF (proc) (t.arg1, arg2));
2900 case scm_tc7_smob:
2901 if (!SCM_SMOB_APPLICABLE_P (proc))
2902 goto badfun;
2903 RETURN (SCM_SMOB_APPLY_2 (proc, t.arg1, arg2));
2904 cclon:
2905 case scm_tc7_cclo:
2906 #ifdef DEVAL
2907 RETURN (SCM_APPLY (SCM_CCLO_SUBR (proc),
2908 scm_cons (proc, debug.info->a.args),
2909 SCM_EOL));
2910 #else
2911 RETURN (SCM_APPLY (SCM_CCLO_SUBR (proc),
2912 scm_cons2 (proc, t.arg1,
2913 scm_cons (arg2,
2914 scm_eval_args (x,
2915 env,
2916 proc))),
2917 SCM_EOL));
2918 #endif
2919 case scm_tcs_cons_gloc:
2920 if (SCM_OBJ_CLASS_FLAGS (proc) & SCM_CLASSF_PURE_GENERIC)
2921 {
2922 x = SCM_ENTITY_PROCEDURE (proc);
2923 #ifdef DEVAL
2924 arg2 = debug.info->a.args;
2925 #else
2926 arg2 = scm_cons2 (t.arg1, arg2, SCM_EOL);
2927 #endif
2928 goto type_dispatch;
2929 }
2930 else if (!SCM_I_OPERATORP (proc))
2931 goto badfun;
2932 else
2933 {
2934 operatorn:
2935 #ifdef DEVAL
2936 RETURN (SCM_APPLY (SCM_I_ENTITYP (proc)
2937 ? SCM_ENTITY_PROCEDURE (proc)
2938 : SCM_OPERATOR_PROCEDURE (proc),
2939 scm_cons (proc, debug.info->a.args),
2940 SCM_EOL));
2941 #else
2942 RETURN (SCM_APPLY (SCM_I_ENTITYP (proc)
2943 ? SCM_ENTITY_PROCEDURE (proc)
2944 : SCM_OPERATOR_PROCEDURE (proc),
2945 scm_cons2 (proc, t.arg1,
2946 scm_cons (arg2,
2947 scm_eval_args (x,
2948 env,
2949 proc))),
2950 SCM_EOL));
2951 #endif
2952 }
2953 case scm_tc7_subr_0:
2954 case scm_tc7_cxr:
2955 case scm_tc7_subr_1o:
2956 case scm_tc7_subr_1:
2957 case scm_tc7_subr_3:
2958 goto wrongnumargs;
2959 default:
2960 goto badfun;
2961 case scm_tc7_pws:
2962 proc = SCM_PROCEDURE (proc);
2963 #ifdef DEVAL
2964 debug.info->a.proc = proc;
2965 #endif
2966 if (!SCM_CLOSUREP (proc))
2967 goto evap2;
2968 if (scm_badformalsp (proc, 2))
2969 goto umwrongnumargs;
2970 case scm_tcs_closures:
2971 /* clos2: */
2972 #ifdef DEVAL
2973 env = EXTEND_ENV (SCM_CAR (SCM_CODE (proc)),
2974 debug.info->a.args,
2975 SCM_ENV (proc));
2976 #else
2977 env = EXTEND_ENV (SCM_CAR (SCM_CODE (proc)),
2978 scm_cons2 (t.arg1, arg2, SCM_EOL), SCM_ENV (proc));
2979 #endif
2980 x = SCM_CODE (proc);
2981 goto nontoplevel_cdrxbegin;
2982 }
2983 }
2984 #ifdef SCM_CAUTIOUS
2985 if (SCM_IMP (x) || SCM_NECONSP (x))
2986 goto wrongnumargs;
2987 #endif
2988 #ifdef DEVAL
2989 debug.info->a.args = scm_cons2 (t.arg1, arg2,
2990 scm_deval_args (x, env, proc,
2991 SCM_CDRLOC (SCM_CDR (debug.info->a.args))));
2992 #endif
2993 ENTER_APPLY;
2994 evap3:
2995 switch (SCM_TYP7 (proc))
2996 { /* have 3 or more arguments */
2997 #ifdef DEVAL
2998 case scm_tc7_subr_3:
2999 SCM_ASRTGO (SCM_NULLP (SCM_CDR (x)), wrongnumargs);
3000 RETURN (SCM_SUBRF (proc) (t.arg1, arg2,
3001 SCM_CADDR (debug.info->a.args)));
3002 case scm_tc7_asubr:
3003 #ifdef BUILTIN_RPASUBR
3004 t.arg1 = SCM_SUBRF(proc)(t.arg1, arg2);
3005 arg2 = SCM_CDR (SCM_CDR (debug.info->a.args));
3006 do
3007 {
3008 t.arg1 = SCM_SUBRF(proc)(t.arg1, SCM_CAR (arg2));
3009 arg2 = SCM_CDR (arg2);
3010 }
3011 while (SCM_NIMP (arg2));
3012 RETURN (t.arg1)
3013 #endif /* BUILTIN_RPASUBR */
3014 case scm_tc7_rpsubr:
3015 #ifdef BUILTIN_RPASUBR
3016 if (SCM_FALSEP (SCM_SUBRF (proc) (t.arg1, arg2)))
3017 RETURN (SCM_BOOL_F)
3018 t.arg1 = SCM_CDR (SCM_CDR (debug.info->a.args));
3019 do
3020 {
3021 if (SCM_FALSEP (SCM_SUBRF (proc) (arg2, SCM_CAR (t.arg1))))
3022 RETURN (SCM_BOOL_F)
3023 arg2 = SCM_CAR (t.arg1);
3024 t.arg1 = SCM_CDR (t.arg1);
3025 }
3026 while (SCM_NIMP (t.arg1));
3027 RETURN (SCM_BOOL_T)
3028 #else /* BUILTIN_RPASUBR */
3029 RETURN (SCM_APPLY (proc, t.arg1,
3030 scm_acons (arg2,
3031 SCM_CDR (SCM_CDR (debug.info->a.args)),
3032 SCM_EOL)))
3033 #endif /* BUILTIN_RPASUBR */
3034 case scm_tc7_lsubr_2:
3035 RETURN (SCM_SUBRF (proc) (t.arg1, arg2,
3036 SCM_CDR (SCM_CDR (debug.info->a.args))))
3037 case scm_tc7_lsubr:
3038 RETURN (SCM_SUBRF (proc) (debug.info->a.args))
3039 case scm_tc7_smob:
3040 if (!SCM_SMOB_APPLICABLE_P (proc))
3041 goto badfun;
3042 RETURN (SCM_SMOB_APPLY_3 (proc, t.arg1, arg2,
3043 SCM_CDDR (debug.info->a.args)));
3044 case scm_tc7_cclo:
3045 goto cclon;
3046 case scm_tc7_pws:
3047 proc = SCM_PROCEDURE (proc);
3048 debug.info->a.proc = proc;
3049 if (!SCM_CLOSUREP (proc))
3050 goto evap3;
3051 if (scm_badargsp (SCM_CAR (SCM_CODE (proc)), debug.info->a.args))
3052 goto umwrongnumargs;
3053 case scm_tcs_closures:
3054 SCM_SET_ARGSREADY (debug);
3055 env = EXTEND_ENV (SCM_CAR (SCM_CODE (proc)),
3056 debug.info->a.args,
3057 SCM_ENV (proc));
3058 x = SCM_CODE (proc);
3059 goto nontoplevel_cdrxbegin;
3060 #else /* DEVAL */
3061 case scm_tc7_subr_3:
3062 SCM_ASRTGO (SCM_NULLP (SCM_CDR (x)), wrongnumargs);
3063 RETURN (SCM_SUBRF (proc) (t.arg1, arg2, EVALCAR (x, env)));
3064 case scm_tc7_asubr:
3065 #ifdef BUILTIN_RPASUBR
3066 t.arg1 = SCM_SUBRF (proc) (t.arg1, arg2);
3067 do
3068 {
3069 t.arg1 = SCM_SUBRF(proc)(t.arg1, EVALCAR(x, env));
3070 x = SCM_CDR(x);
3071 }
3072 while (SCM_NIMP (x));
3073 RETURN (t.arg1)
3074 #endif /* BUILTIN_RPASUBR */
3075 case scm_tc7_rpsubr:
3076 #ifdef BUILTIN_RPASUBR
3077 if (SCM_FALSEP (SCM_SUBRF (proc) (t.arg1, arg2)))
3078 RETURN (SCM_BOOL_F)
3079 do
3080 {
3081 t.arg1 = EVALCAR (x, env);
3082 if (SCM_FALSEP (SCM_SUBRF (proc) (arg2, t.arg1)))
3083 RETURN (SCM_BOOL_F)
3084 arg2 = t.arg1;
3085 x = SCM_CDR (x);
3086 }
3087 while (SCM_NIMP (x));
3088 RETURN (SCM_BOOL_T)
3089 #else /* BUILTIN_RPASUBR */
3090 RETURN (SCM_APPLY (proc, t.arg1,
3091 scm_acons (arg2,
3092 scm_eval_args (x, env, proc),
3093 SCM_EOL)));
3094 #endif /* BUILTIN_RPASUBR */
3095 case scm_tc7_lsubr_2:
3096 RETURN (SCM_SUBRF (proc) (t.arg1, arg2, scm_eval_args (x, env, proc)));
3097 case scm_tc7_lsubr:
3098 RETURN (SCM_SUBRF (proc) (scm_cons2 (t.arg1,
3099 arg2,
3100 scm_eval_args (x, env, proc))));
3101 case scm_tc7_smob:
3102 if (!SCM_SMOB_APPLICABLE_P (proc))
3103 goto badfun;
3104 RETURN (SCM_SMOB_APPLY_3 (proc, t.arg1, arg2,
3105 scm_eval_args (x, env, proc)));
3106 case scm_tc7_cclo:
3107 goto cclon;
3108 case scm_tc7_pws:
3109 proc = SCM_PROCEDURE (proc);
3110 if (!SCM_CLOSUREP (proc))
3111 goto evap3;
3112 {
3113 SCM formals = SCM_CAR (SCM_CODE (proc));
3114 if (SCM_NULLP (formals)
3115 || (SCM_CONSP (formals)
3116 && (SCM_NULLP (SCM_CDR (formals))
3117 || (SCM_CONSP (SCM_CDR (formals))
3118 && scm_badargsp (SCM_CDDR (formals), x)))))
3119 goto umwrongnumargs;
3120 }
3121 case scm_tcs_closures:
3122 #ifdef DEVAL
3123 SCM_SET_ARGSREADY (debug);
3124 #endif
3125 env = EXTEND_ENV (SCM_CAR (SCM_CODE (proc)),
3126 scm_cons2 (t.arg1,
3127 arg2,
3128 scm_eval_args (x, env, proc)),
3129 SCM_ENV (proc));
3130 x = SCM_CODE (proc);
3131 goto nontoplevel_cdrxbegin;
3132 #endif /* DEVAL */
3133 case scm_tcs_cons_gloc:
3134 if (SCM_OBJ_CLASS_FLAGS (proc) & SCM_CLASSF_PURE_GENERIC)
3135 {
3136 #ifdef DEVAL
3137 arg2 = debug.info->a.args;
3138 #else
3139 arg2 = scm_cons2 (t.arg1, arg2, scm_eval_args (x, env, proc));
3140 #endif
3141 x = SCM_ENTITY_PROCEDURE (proc);
3142 goto type_dispatch;
3143 }
3144 else if (!SCM_I_OPERATORP (proc))
3145 goto badfun;
3146 else
3147 goto operatorn;
3148 case scm_tc7_subr_2:
3149 case scm_tc7_subr_1o:
3150 case scm_tc7_subr_2o:
3151 case scm_tc7_subr_0:
3152 case scm_tc7_cxr:
3153 case scm_tc7_subr_1:
3154 goto wrongnumargs;
3155 default:
3156 goto badfun;
3157 }
3158 }
3159 #ifdef DEVAL
3160 exit:
3161 if (CHECK_EXIT && SCM_TRAPS_P)
3162 if (SCM_EXIT_FRAME_P || (SCM_TRACE_P && SCM_TRACED_FRAME_P (debug)))
3163 {
3164 SCM_CLEAR_TRACED_FRAME (debug);
3165 if (SCM_CHEAPTRAPS_P)
3166 t.arg1 = scm_make_debugobj (&debug);
3167 else
3168 {
3169 int first;
3170 SCM val = scm_make_continuation (&first);
3171
3172 if (first)
3173 t.arg1 = val;
3174 else
3175 {
3176 proc = val;
3177 goto ret;
3178 }
3179 }
3180 scm_ithrow (scm_sym_exit_frame, scm_cons2 (t.arg1, proc, SCM_EOL), 0);
3181 }
3182 ret:
3183 scm_last_debug_frame = debug.prev;
3184 return proc;
3185 #endif
3186 }
3187
3188
3189 /* SECTION: This code is compiled once.
3190 */
3191
3192 #ifndef DEVAL
3193
3194 /* This code processes the arguments to apply:
3195
3196 (apply PROC ARG1 ... ARGS)
3197
3198 Given a list (ARG1 ... ARGS), this function conses the ARG1
3199 ... arguments onto the front of ARGS, and returns the resulting
3200 list. Note that ARGS is a list; thus, the argument to this
3201 function is a list whose last element is a list.
3202
3203 Apply calls this function, and applies PROC to the elements of the
3204 result. apply:nconc2last takes care of building the list of
3205 arguments, given (ARG1 ... ARGS).
3206
3207 Rather than do new consing, apply:nconc2last destroys its argument.
3208 On that topic, this code came into my care with the following
3209 beautifully cryptic comment on that topic: "This will only screw
3210 you if you do (scm_apply scm_apply '( ... ))" If you know what
3211 they're referring to, send me a patch to this comment. */
3212
3213 SCM_DEFINE (scm_nconc2last, "apply:nconc2last", 1, 0, 0,
3214 (SCM lst),
3215 "Given a list (@var{arg1} @dots{} @var{args}), this function\n"
3216 "conses the @var{arg1} @dots{} arguments onto the front of\n"
3217 "@var{args}, and returns the resulting list. Note that\n"
3218 "@var{args} is a list; thus, the argument to this function is\n"
3219 "a list whose last element is a list.\n"
3220 "Note: Rather than do new consing, @code{apply:nconc2last}\n"
3221 "destroys its argument, so use with care.")
3222 #define FUNC_NAME s_scm_nconc2last
3223 {
3224 SCM *lloc;
3225 SCM_VALIDATE_NONEMPTYLIST (1,lst);
3226 lloc = &lst;
3227 while (SCM_NNULLP (SCM_CDR (*lloc)))
3228 lloc = SCM_CDRLOC (*lloc);
3229 SCM_ASSERT (scm_ilength (SCM_CAR (*lloc)) >= 0, lst, SCM_ARG1, FUNC_NAME);
3230 *lloc = SCM_CAR (*lloc);
3231 return lst;
3232 }
3233 #undef FUNC_NAME
3234
3235 #endif /* !DEVAL */
3236
3237
3238 /* SECTION: When DEVAL is defined this code yields scm_dapply.
3239 * It is compiled twice.
3240 */
3241
3242 #if 0
3243
3244 SCM
3245 scm_apply (SCM proc, SCM arg1, SCM args)
3246 {}
3247 #endif
3248
3249 #if 0
3250
3251 SCM
3252 scm_dapply (SCM proc, SCM arg1, SCM args)
3253 { /* empty */ }
3254 #endif
3255
3256
3257 /* Apply a function to a list of arguments.
3258
3259 This function is exported to the Scheme level as taking two
3260 required arguments and a tail argument, as if it were:
3261 (lambda (proc arg1 . args) ...)
3262 Thus, if you just have a list of arguments to pass to a procedure,
3263 pass the list as ARG1, and '() for ARGS. If you have some fixed
3264 args, pass the first as ARG1, then cons any remaining fixed args
3265 onto the front of your argument list, and pass that as ARGS. */
3266
3267 SCM
3268 SCM_APPLY (SCM proc, SCM arg1, SCM args)
3269 {
3270 #ifdef DEBUG_EXTENSIONS
3271 #ifdef DEVAL
3272 scm_debug_frame debug;
3273 scm_debug_info debug_vect_body;
3274 debug.prev = scm_last_debug_frame;
3275 debug.status = SCM_APPLYFRAME;
3276 debug.vect = &debug_vect_body;
3277 debug.vect[0].a.proc = proc;
3278 debug.vect[0].a.args = SCM_EOL;
3279 scm_last_debug_frame = &debug;
3280 #else
3281 if (SCM_DEBUGGINGP)
3282 return scm_dapply (proc, arg1, args);
3283 #endif
3284 #endif
3285
3286 SCM_ASRTGO (SCM_NIMP (proc), badproc);
3287
3288 /* If ARGS is the empty list, then we're calling apply with only two
3289 arguments --- ARG1 is the list of arguments for PROC. Whatever
3290 the case, futz with things so that ARG1 is the first argument to
3291 give to PROC (or SCM_UNDEFINED if no args), and ARGS contains the
3292 rest.
3293
3294 Setting the debug apply frame args this way is pretty messy.
3295 Perhaps we should store arg1 and args directly in the frame as
3296 received, and let scm_frame_arguments unpack them, because that's
3297 a relatively rare operation. This works for now; if the Guile
3298 developer archives are still around, see Mikael's post of
3299 11-Apr-97. */
3300 if (SCM_NULLP (args))
3301 {
3302 if (SCM_NULLP (arg1))
3303 {
3304 arg1 = SCM_UNDEFINED;
3305 #ifdef DEVAL
3306 debug.vect[0].a.args = SCM_EOL;
3307 #endif
3308 }
3309 else
3310 {
3311 #ifdef DEVAL
3312 debug.vect[0].a.args = arg1;
3313 #endif
3314 args = SCM_CDR (arg1);
3315 arg1 = SCM_CAR (arg1);
3316 }
3317 }
3318 else
3319 {
3320 args = scm_nconc2last (args);
3321 #ifdef DEVAL
3322 debug.vect[0].a.args = scm_cons (arg1, args);
3323 #endif
3324 }
3325 #ifdef DEVAL
3326 if (SCM_ENTER_FRAME_P && SCM_TRAPS_P)
3327 {
3328 SCM tmp;
3329 if (SCM_CHEAPTRAPS_P)
3330 tmp = scm_make_debugobj (&debug);
3331 else
3332 {
3333 int first;
3334
3335 tmp = scm_make_continuation (&first);
3336 if (!first)
3337 goto entap;
3338 }
3339 scm_ithrow (scm_sym_enter_frame, scm_cons (tmp, SCM_EOL), 0);
3340 }
3341 entap:
3342 ENTER_APPLY;
3343 #endif
3344 tail:
3345 switch (SCM_TYP7 (proc))
3346 {
3347 case scm_tc7_subr_2o:
3348 args = SCM_NULLP (args) ? SCM_UNDEFINED : SCM_CAR (args);
3349 RETURN (SCM_SUBRF (proc) (arg1, args))
3350 case scm_tc7_subr_2:
3351 SCM_ASRTGO (SCM_NNULLP (args) && SCM_NULLP (SCM_CDR (args)),
3352 wrongnumargs);
3353 args = SCM_CAR (args);
3354 RETURN (SCM_SUBRF (proc) (arg1, args))
3355 case scm_tc7_subr_0:
3356 SCM_ASRTGO (SCM_UNBNDP (arg1), wrongnumargs);
3357 RETURN (SCM_SUBRF (proc) ())
3358 case scm_tc7_subr_1:
3359 SCM_ASRTGO (!SCM_UNBNDP (arg1), wrongnumargs);
3360 case scm_tc7_subr_1o:
3361 SCM_ASRTGO (SCM_NULLP (args), wrongnumargs);
3362 RETURN (SCM_SUBRF (proc) (arg1))
3363 case scm_tc7_cxr:
3364 SCM_ASRTGO (SCM_NULLP (args), wrongnumargs);
3365 if (SCM_SUBRF (proc))
3366 {
3367 if (SCM_INUMP (arg1))
3368 {
3369 RETURN (scm_make_real (SCM_DSUBRF (proc) ((double) SCM_INUM (arg1))));
3370 }
3371 SCM_ASRTGO (SCM_NIMP (arg1), floerr);
3372 if (SCM_REALP (arg1))
3373 {
3374 RETURN (scm_make_real (SCM_DSUBRF (proc) (SCM_REAL_VALUE (arg1))));
3375 }
3376 #ifdef SCM_BIGDIG
3377 if (SCM_BIGP (arg1))
3378 RETURN (scm_make_real (SCM_DSUBRF (proc) (scm_big2dbl (arg1))))
3379 #endif
3380 floerr:
3381 SCM_WTA_DISPATCH_1 (*SCM_SUBR_GENERIC (proc), arg1,
3382 SCM_ARG1, SCM_SYMBOL_CHARS (SCM_SNAME (proc)));
3383 }
3384 proc = SCM_SNAME (proc);
3385 {
3386 char *chrs = SCM_SYMBOL_CHARS (proc) + SCM_SYMBOL_LENGTH (proc) - 1;
3387 while ('c' != *--chrs)
3388 {
3389 SCM_ASSERT (SCM_CONSP (arg1),
3390 arg1, SCM_ARG1, SCM_SYMBOL_CHARS (proc));
3391 arg1 = ('a' == *chrs) ? SCM_CAR (arg1) : SCM_CDR (arg1);
3392 }
3393 RETURN (arg1)
3394 }
3395 case scm_tc7_subr_3:
3396 SCM_ASRTGO (SCM_NNULLP (args)
3397 && SCM_NNULLP (SCM_CDR (args))
3398 && SCM_NULLP (SCM_CDDR (args)),
3399 wrongnumargs);
3400 RETURN (SCM_SUBRF (proc) (arg1, SCM_CAR (args), SCM_CAR (SCM_CDR (args))))
3401 case scm_tc7_lsubr:
3402 #ifdef DEVAL
3403 RETURN (SCM_SUBRF (proc) (SCM_UNBNDP (arg1) ? SCM_EOL : debug.vect[0].a.args))
3404 #else
3405 RETURN (SCM_SUBRF (proc) (SCM_UNBNDP (arg1) ? SCM_EOL : scm_cons (arg1, args)))
3406 #endif
3407 case scm_tc7_lsubr_2:
3408 SCM_ASRTGO (SCM_CONSP (args), wrongnumargs);
3409 RETURN (SCM_SUBRF (proc) (arg1, SCM_CAR (args), SCM_CDR (args)))
3410 case scm_tc7_asubr:
3411 if (SCM_NULLP (args))
3412 RETURN (SCM_SUBRF (proc) (arg1, SCM_UNDEFINED))
3413 while (SCM_NIMP (args))
3414 {
3415 SCM_ASSERT (SCM_CONSP (args), args, SCM_ARG2, "apply");
3416 arg1 = SCM_SUBRF (proc) (arg1, SCM_CAR (args));
3417 args = SCM_CDR (args);
3418 }
3419 RETURN (arg1);
3420 case scm_tc7_rpsubr:
3421 if (SCM_NULLP (args))
3422 RETURN (SCM_BOOL_T);
3423 while (SCM_NIMP (args))
3424 {
3425 SCM_ASSERT (SCM_CONSP (args), args, SCM_ARG2, "apply");
3426 if (SCM_FALSEP (SCM_SUBRF (proc) (arg1, SCM_CAR (args))))
3427 RETURN (SCM_BOOL_F);
3428 arg1 = SCM_CAR (args);
3429 args = SCM_CDR (args);
3430 }
3431 RETURN (SCM_BOOL_T);
3432 case scm_tcs_closures:
3433 #ifdef DEVAL
3434 arg1 = (SCM_UNBNDP (arg1) ? SCM_EOL : debug.vect[0].a.args);
3435 #else
3436 arg1 = (SCM_UNBNDP (arg1) ? SCM_EOL : scm_cons (arg1, args));
3437 #endif
3438 #ifndef SCM_RECKLESS
3439 if (scm_badargsp (SCM_CAR (SCM_CODE (proc)), arg1))
3440 goto wrongnumargs;
3441 #endif
3442
3443 /* Copy argument list */
3444 if (SCM_IMP (arg1))
3445 args = arg1;
3446 else
3447 {
3448 SCM tl = args = scm_cons (SCM_CAR (arg1), SCM_UNSPECIFIED);
3449 while (arg1 = SCM_CDR (arg1), SCM_CONSP (arg1))
3450 {
3451 SCM_SETCDR (tl, scm_cons (SCM_CAR (arg1),
3452 SCM_UNSPECIFIED));
3453 tl = SCM_CDR (tl);
3454 }
3455 SCM_SETCDR (tl, arg1);
3456 }
3457
3458 args = EXTEND_ENV (SCM_CAR (SCM_CODE (proc)), args, SCM_ENV (proc));
3459 proc = SCM_CDR (SCM_CODE (proc));
3460 again:
3461 arg1 = proc;
3462 while (SCM_NNULLP (arg1 = SCM_CDR (arg1)))
3463 {
3464 if (SCM_IMP (SCM_CAR (proc)))
3465 {
3466 if (SCM_ISYMP (SCM_CAR (proc)))
3467 {
3468 proc = scm_m_expand_body (proc, args);
3469 goto again;
3470 }
3471 else
3472 SCM_EVALIM2 (SCM_CAR (proc));
3473 }
3474 else
3475 SCM_CEVAL (SCM_CAR (proc), args);
3476 proc = arg1;
3477 }
3478 RETURN (EVALCAR (proc, args));
3479 case scm_tc7_smob:
3480 if (!SCM_SMOB_APPLICABLE_P (proc))
3481 goto badproc;
3482 if (SCM_UNBNDP (arg1))
3483 RETURN (SCM_SMOB_APPLY_0 (proc))
3484 else if (SCM_NULLP (args))
3485 RETURN (SCM_SMOB_APPLY_1 (proc, arg1))
3486 else if (SCM_NULLP (SCM_CDR (args)))
3487 RETURN (SCM_SMOB_APPLY_2 (proc, arg1, SCM_CAR (args)))
3488 else
3489 RETURN (SCM_SMOB_APPLY_3 (proc, arg1, SCM_CAR (args), SCM_CDR (args)));
3490 case scm_tc7_cclo:
3491 #ifdef DEVAL
3492 args = (SCM_UNBNDP(arg1) ? SCM_EOL : debug.vect[0].a.args);
3493 arg1 = proc;
3494 proc = SCM_CCLO_SUBR (proc);
3495 debug.vect[0].a.proc = proc;
3496 debug.vect[0].a.args = scm_cons (arg1, args);
3497 #else
3498 args = (SCM_UNBNDP(arg1) ? SCM_EOL : scm_cons (arg1, args));
3499 arg1 = proc;
3500 proc = SCM_CCLO_SUBR (proc);
3501 #endif
3502 goto tail;
3503 case scm_tc7_pws:
3504 proc = SCM_PROCEDURE (proc);
3505 #ifdef DEVAL
3506 debug.vect[0].a.proc = proc;
3507 #endif
3508 goto tail;
3509 case scm_tcs_cons_gloc:
3510 if (SCM_OBJ_CLASS_FLAGS (proc) & SCM_CLASSF_PURE_GENERIC)
3511 {
3512 #ifdef DEVAL
3513 args = (SCM_UNBNDP(arg1) ? SCM_EOL : debug.vect[0].a.args);
3514 #else
3515 args = (SCM_UNBNDP(arg1) ? SCM_EOL : scm_cons (arg1, args));
3516 #endif
3517 RETURN (scm_apply_generic (proc, args));
3518 }
3519 else if (!SCM_I_OPERATORP (proc))
3520 goto badproc;
3521 else
3522 {
3523 #ifdef DEVAL
3524 args = (SCM_UNBNDP(arg1) ? SCM_EOL : debug.vect[0].a.args);
3525 #else
3526 args = (SCM_UNBNDP(arg1) ? SCM_EOL : scm_cons (arg1, args));
3527 #endif
3528 arg1 = proc;
3529 proc = (SCM_I_ENTITYP (proc)
3530 ? SCM_ENTITY_PROCEDURE (proc)
3531 : SCM_OPERATOR_PROCEDURE (proc));
3532 #ifdef DEVAL
3533 debug.vect[0].a.proc = proc;
3534 debug.vect[0].a.args = scm_cons (arg1, args);
3535 #endif
3536 if (SCM_NIMP (proc))
3537 goto tail;
3538 else
3539 goto badproc;
3540 }
3541 wrongnumargs:
3542 scm_wrong_num_args (proc);
3543 default:
3544 badproc:
3545 scm_wrong_type_arg ("apply", SCM_ARG1, proc);
3546 RETURN (arg1);
3547 }
3548 #ifdef DEVAL
3549 exit:
3550 if (CHECK_EXIT && SCM_TRAPS_P)
3551 if (SCM_EXIT_FRAME_P || (SCM_TRACE_P && SCM_TRACED_FRAME_P (debug)))
3552 {
3553 SCM_CLEAR_TRACED_FRAME (debug);
3554 if (SCM_CHEAPTRAPS_P)
3555 arg1 = scm_make_debugobj (&debug);
3556 else
3557 {
3558 int first;
3559 SCM val = scm_make_continuation (&first);
3560
3561 if (first)
3562 arg1 = val;
3563 else
3564 {
3565 proc = val;
3566 goto ret;
3567 }
3568 }
3569 scm_ithrow (scm_sym_exit_frame, scm_cons2 (arg1, proc, SCM_EOL), 0);
3570 }
3571 ret:
3572 scm_last_debug_frame = debug.prev;
3573 return proc;
3574 #endif
3575 }
3576
3577
3578 /* SECTION: The rest of this file is only read once.
3579 */
3580
3581 #ifndef DEVAL
3582
3583 /* Typechecking for multi-argument MAP and FOR-EACH.
3584
3585 Verify that each element of the vector ARGV, except for the first,
3586 is a proper list whose length is LEN. Attribute errors to WHO,
3587 and claim that the i'th element of ARGV is WHO's i+2'th argument. */
3588 static inline void
3589 check_map_args (SCM argv,
3590 long len,
3591 SCM gf,
3592 SCM proc,
3593 SCM args,
3594 const char *who)
3595 {
3596 SCM *ve = SCM_VELTS (argv);
3597 int i;
3598
3599 for (i = SCM_VECTOR_LENGTH (argv) - 1; i >= 1; i--)
3600 {
3601 int elt_len = scm_ilength (ve[i]);
3602
3603 if (elt_len < 0)
3604 {
3605 if (gf)
3606 scm_apply_generic (gf, scm_cons (proc, args));
3607 else
3608 scm_wrong_type_arg (who, i + 2, ve[i]);
3609 }
3610
3611 if (elt_len != len)
3612 scm_out_of_range (who, ve[i]);
3613 }
3614
3615 scm_remember_upto_here_1 (argv);
3616 }
3617
3618
3619 SCM_GPROC (s_map, "map", 2, 0, 1, scm_map, g_map);
3620
3621 /* Note: Currently, scm_map applies PROC to the argument list(s)
3622 sequentially, starting with the first element(s). This is used in
3623 evalext.c where the Scheme procedure `map-in-order', which guarantees
3624 sequential behaviour, is implemented using scm_map. If the
3625 behaviour changes, we need to update `map-in-order'.
3626 */
3627
3628 SCM
3629 scm_map (SCM proc, SCM arg1, SCM args)
3630 #define FUNC_NAME s_map
3631 {
3632 long i, len;
3633 SCM res = SCM_EOL;
3634 SCM *pres = &res;
3635 SCM *ve = &args; /* Keep args from being optimized away. */
3636
3637 len = scm_ilength (arg1);
3638 SCM_GASSERTn (len >= 0,
3639 g_map, scm_cons2 (proc, arg1, args), SCM_ARG2, s_map);
3640 SCM_VALIDATE_REST_ARGUMENT (args);
3641 if (SCM_NULLP (args))
3642 {
3643 while (SCM_NIMP (arg1))
3644 {
3645 *pres = scm_cons (scm_apply (proc, SCM_CAR (arg1), scm_listofnull),
3646 SCM_EOL);
3647 pres = SCM_CDRLOC (*pres);
3648 arg1 = SCM_CDR (arg1);
3649 }
3650 return res;
3651 }
3652 args = scm_vector (arg1 = scm_cons (arg1, args));
3653 ve = SCM_VELTS (args);
3654 #ifndef SCM_RECKLESS
3655 check_map_args (args, len, g_map, proc, arg1, s_map);
3656 #endif
3657 while (1)
3658 {
3659 arg1 = SCM_EOL;
3660 for (i = SCM_VECTOR_LENGTH (args) - 1; i >= 0; i--)
3661 {
3662 if (SCM_IMP (ve[i]))
3663 return res;
3664 arg1 = scm_cons (SCM_CAR (ve[i]), arg1);
3665 ve[i] = SCM_CDR (ve[i]);
3666 }
3667 *pres = scm_cons (scm_apply (proc, arg1, SCM_EOL), SCM_EOL);
3668 pres = SCM_CDRLOC (*pres);
3669 }
3670 }
3671 #undef FUNC_NAME
3672
3673
3674 SCM_GPROC (s_for_each, "for-each", 2, 0, 1, scm_for_each, g_for_each);
3675
3676 SCM
3677 scm_for_each (SCM proc, SCM arg1, SCM args)
3678 #define FUNC_NAME s_for_each
3679 {
3680 SCM *ve = &args; /* Keep args from being optimized away. */
3681 long i, len;
3682 len = scm_ilength (arg1);
3683 SCM_GASSERTn (len >= 0, g_for_each, scm_cons2 (proc, arg1, args),
3684 SCM_ARG2, s_for_each);
3685 SCM_VALIDATE_REST_ARGUMENT (args);
3686 if SCM_NULLP (args)
3687 {
3688 while SCM_NIMP (arg1)
3689 {
3690 scm_apply (proc, SCM_CAR (arg1), scm_listofnull);
3691 arg1 = SCM_CDR (arg1);
3692 }
3693 return SCM_UNSPECIFIED;
3694 }
3695 args = scm_vector (arg1 = scm_cons (arg1, args));
3696 ve = SCM_VELTS (args);
3697 #ifndef SCM_RECKLESS
3698 check_map_args (args, len, g_for_each, proc, arg1, s_for_each);
3699 #endif
3700 while (1)
3701 {
3702 arg1 = SCM_EOL;
3703 for (i = SCM_VECTOR_LENGTH (args) - 1; i >= 0; i--)
3704 {
3705 if SCM_IMP
3706 (ve[i]) return SCM_UNSPECIFIED;
3707 arg1 = scm_cons (SCM_CAR (ve[i]), arg1);
3708 ve[i] = SCM_CDR (ve[i]);
3709 }
3710 scm_apply (proc, arg1, SCM_EOL);
3711 }
3712 }
3713 #undef FUNC_NAME
3714
3715
3716 SCM
3717 scm_closure (SCM code, SCM env)
3718 {
3719 register SCM z;
3720 SCM_NEWCELL (z);
3721 SCM_SETCODE (z, code);
3722 SCM_SETENV (z, env);
3723 return z;
3724 }
3725
3726
3727 scm_bits_t scm_tc16_promise;
3728
3729 SCM
3730 scm_makprom (SCM code)
3731 {
3732 SCM_RETURN_NEWSMOB (scm_tc16_promise, SCM_UNPACK (code));
3733 }
3734
3735
3736
3737 static int
3738 promise_print (SCM exp, SCM port, scm_print_state *pstate)
3739 {
3740 int writingp = SCM_WRITINGP (pstate);
3741 scm_puts ("#<promise ", port);
3742 SCM_SET_WRITINGP (pstate, 1);
3743 scm_iprin1 (SCM_CDR (exp), port, pstate);
3744 SCM_SET_WRITINGP (pstate, writingp);
3745 scm_putc ('>', port);
3746 return !0;
3747 }
3748
3749
3750 SCM_DEFINE (scm_force, "force", 1, 0, 0,
3751 (SCM x),
3752 "If the promise @var{x} has not been computed yet, compute and\n"
3753 "return @var{x}, otherwise just return the previously computed\n"
3754 "value.")
3755 #define FUNC_NAME s_scm_force
3756 {
3757 SCM_VALIDATE_SMOB (1, x, promise);
3758 if (!((1L << 16) & SCM_CELL_WORD_0 (x)))
3759 {
3760 SCM ans = scm_apply (SCM_CELL_OBJECT_1 (x), SCM_EOL, SCM_EOL);
3761 if (!((1L << 16) & SCM_CELL_WORD_0 (x)))
3762 {
3763 SCM_DEFER_INTS;
3764 SCM_SET_CELL_OBJECT_1 (x, ans);
3765 SCM_SET_CELL_WORD_0 (x, SCM_CELL_WORD_0 (x) | (1L << 16));
3766 SCM_ALLOW_INTS;
3767 }
3768 }
3769 return SCM_CELL_OBJECT_1 (x);
3770 }
3771 #undef FUNC_NAME
3772
3773
3774 SCM_DEFINE (scm_promise_p, "promise?", 1, 0, 0,
3775 (SCM obj),
3776 "Return true if @var{obj} is a promise, i.e. a delayed computation\n"
3777 "(@pxref{Delayed evaluation,,,r4rs.info,The Revised^4 Report on Scheme}).")
3778 #define FUNC_NAME s_scm_promise_p
3779 {
3780 return SCM_BOOL (SCM_TYP16_PREDICATE (scm_tc16_promise, obj));
3781 }
3782 #undef FUNC_NAME
3783
3784
3785 SCM_DEFINE (scm_cons_source, "cons-source", 3, 0, 0,
3786 (SCM xorig, SCM x, SCM y),
3787 "Create and return a new pair whose car and cdr are @var{x} and @var{y}.\n"
3788 "Any source properties associated with @var{xorig} are also associated\n"
3789 "with the new pair.")
3790 #define FUNC_NAME s_scm_cons_source
3791 {
3792 SCM p, z;
3793 SCM_NEWCELL (z);
3794 SCM_SET_CELL_OBJECT_0 (z, x);
3795 SCM_SET_CELL_OBJECT_1 (z, y);
3796 /* Copy source properties possibly associated with xorig. */
3797 p = scm_whash_lookup (scm_source_whash, xorig);
3798 if (!SCM_IMP (p))
3799 scm_whash_insert (scm_source_whash, z, p);
3800 return z;
3801 }
3802 #undef FUNC_NAME
3803
3804
3805 SCM_DEFINE (scm_copy_tree, "copy-tree", 1, 0, 0,
3806 (SCM obj),
3807 "Recursively copy the data tree that is bound to @var{obj}, and return a\n"
3808 "pointer to the new data structure. @code{copy-tree} recurses down the\n"
3809 "contents of both pairs and vectors (since both cons cells and vector\n"
3810 "cells may point to arbitrary objects), and stops recursing when it hits\n"
3811 "any other object.")
3812 #define FUNC_NAME s_scm_copy_tree
3813 {
3814 SCM ans, tl;
3815 if (SCM_IMP (obj))
3816 return obj;
3817 if (SCM_VECTORP (obj))
3818 {
3819 scm_sizet i = SCM_VECTOR_LENGTH (obj);
3820 ans = scm_c_make_vector (i, SCM_UNSPECIFIED);
3821 while (i--)
3822 SCM_VELTS (ans)[i] = scm_copy_tree (SCM_VELTS (obj)[i]);
3823 return ans;
3824 }
3825 if (SCM_NCONSP (obj))
3826 return obj;
3827 ans = tl = scm_cons_source (obj,
3828 scm_copy_tree (SCM_CAR (obj)),
3829 SCM_UNSPECIFIED);
3830 while (obj = SCM_CDR (obj), SCM_CONSP (obj))
3831 {
3832 SCM_SETCDR (tl, scm_cons (scm_copy_tree (SCM_CAR (obj)),
3833 SCM_UNSPECIFIED));
3834 tl = SCM_CDR (tl);
3835 }
3836 SCM_SETCDR (tl, obj);
3837 return ans;
3838 }
3839 #undef FUNC_NAME
3840
3841
3842 /* We have three levels of EVAL here:
3843
3844 - scm_i_eval (exp, env)
3845
3846 evaluates EXP in environment ENV. ENV is a lexical environment
3847 structure as used by the actual tree code evaluator. When ENV is
3848 a top-level environment, then changes to the current module are
3849 tracked by modifying ENV so that it continues to be in sync with
3850 the current module.
3851
3852 - scm_primitive_eval (exp)
3853
3854 evaluates EXP in the top-level environment as determined by the
3855 current module. This is done by constructing a suitable
3856 environment and calling scm_i_eval. Thus, changes to the
3857 top-level module are tracked normally.
3858
3859 - scm_eval (exp, mod)
3860
3861 evaluates EXP while MOD is the current module. Thius is done by
3862 setting the current module to MOD, invoking scm_primitive_eval on
3863 EXP, and then restoring the current module to the value it had
3864 previously. That is, while EXP is evaluated, changes to the
3865 current module are tracked, but these changes do not persist when
3866 scm_eval returns.
3867
3868 For each level of evals, there are two variants, distinguished by a
3869 _x suffix: the ordinary variant does not modify EXP while the _x
3870 variant can destructively modify EXP into something completely
3871 unintelligible. A Scheme data structure passed as EXP to one of the
3872 _x variants should not ever be used again for anything. So when in
3873 doubt, use the ordinary variant.
3874
3875 */
3876
3877 SCM scm_system_transformer;
3878
3879 /* XXX - scm_i_eval is meant to be useable for evaluation in
3880 non-toplevel environments, for example when used by the debugger.
3881 Can the system transform deal with this? */
3882
3883 SCM
3884 scm_i_eval_x (SCM exp, SCM env)
3885 {
3886 SCM transformer = scm_fluid_ref (SCM_CDR (scm_system_transformer));
3887 if (SCM_NIMP (transformer))
3888 exp = scm_apply (transformer, exp, scm_listofnull);
3889 return SCM_XEVAL (exp, env);
3890 }
3891
3892 SCM
3893 scm_i_eval (SCM exp, SCM env)
3894 {
3895 SCM transformer = scm_fluid_ref (SCM_CDR (scm_system_transformer));
3896 if (SCM_NIMP (transformer))
3897 exp = scm_apply (transformer, exp, scm_listofnull);
3898 exp = scm_copy_tree (exp);
3899 return SCM_XEVAL (exp, env);
3900 }
3901
3902 SCM
3903 scm_primitive_eval_x (SCM exp)
3904 {
3905 SCM env = scm_top_level_env (scm_current_module_lookup_closure ());
3906 return scm_i_eval_x (exp, env);
3907 }
3908
3909 SCM_DEFINE (scm_primitive_eval, "primitive-eval", 1, 0, 0,
3910 (SCM exp),
3911 "Evaluate @var{exp} in the top-level environment specified by\n"
3912 "the current module.")
3913 #define FUNC_NAME s_scm_primitive_eval
3914 {
3915 SCM env = scm_top_level_env (scm_current_module_lookup_closure ());
3916 return scm_i_eval (exp, env);
3917 }
3918 #undef FUNC_NAME
3919
3920 /* Eval does not take the second arg optionally. This is intentional
3921 * in order to be R5RS compatible, and to prepare for the new module
3922 * system, where we would like to make the choice of evaluation
3923 * environment explicit. */
3924
3925 static void
3926 change_environment (void *data)
3927 {
3928 SCM pair = SCM_PACK (data);
3929 SCM new_module = SCM_CAR (pair);
3930 SCM old_module = scm_current_module ();
3931 SCM_SETCDR (pair, old_module);
3932 scm_set_current_module (new_module);
3933 }
3934
3935
3936 static void
3937 restore_environment (void *data)
3938 {
3939 SCM pair = SCM_PACK (data);
3940 SCM old_module = SCM_CDR (pair);
3941 SCM new_module = scm_current_module ();
3942 SCM_SETCAR (pair, new_module);
3943 scm_set_current_module (old_module);
3944 }
3945
3946 static SCM
3947 inner_eval_x (void *data)
3948 {
3949 return scm_primitive_eval_x (SCM_PACK(data));
3950 }
3951
3952 SCM
3953 scm_eval_x (SCM exp, SCM module)
3954 #define FUNC_NAME "eval!"
3955 {
3956 SCM_VALIDATE_MODULE (2, module);
3957
3958 return scm_internal_dynamic_wind
3959 (change_environment, inner_eval_x, restore_environment,
3960 (void *) SCM_UNPACK (exp),
3961 (void *) SCM_UNPACK (scm_cons (module, SCM_BOOL_F)));
3962 }
3963 #undef FUNC_NAME
3964
3965 static SCM
3966 inner_eval (void *data)
3967 {
3968 return scm_primitive_eval (SCM_PACK(data));
3969 }
3970
3971 SCM_DEFINE (scm_eval, "eval", 2, 0, 0,
3972 (SCM exp, SCM module),
3973 "Evaluate @var{exp}, a list representing a Scheme expression,\n"
3974 "in the top-level environment specified by @var{module}.\n"
3975 "While @var{exp} is evaluated (using @var{primitive-eval}),\n"
3976 "@var{module} is made the current module. The current module\n"
3977 "is reset to its previous value when @var{eval} returns.")
3978 #define FUNC_NAME s_scm_eval
3979 {
3980 SCM_VALIDATE_MODULE (2, module);
3981
3982 return scm_internal_dynamic_wind
3983 (change_environment, inner_eval, restore_environment,
3984 (void *) SCM_UNPACK (exp),
3985 (void *) SCM_UNPACK (scm_cons (module, SCM_BOOL_F)));
3986 }
3987 #undef FUNC_NAME
3988
3989 #if (SCM_DEBUG_DEPRECATED == 0)
3990
3991 /* Use scm_current_module () or scm_interaction_environment ()
3992 * instead. The former is the module selected during loading of code.
3993 * The latter is the module in which the user of this thread currently
3994 * types expressions.
3995 */
3996
3997 SCM scm_top_level_lookup_closure_var;
3998
3999 /* Avoid using this functionality altogether (except for implementing
4000 * libguile, where you can use scm_i_eval or scm_i_eval_x).
4001 *
4002 * Applications should use either C level scm_eval_x or Scheme
4003 * scm_eval; or scm_primitive_eval_x or scm_primitive_eval. */
4004
4005 SCM
4006 scm_eval_3 (SCM obj, int copyp, SCM env)
4007 {
4008 if (copyp)
4009 return scm_i_eval (obj, env);
4010 else
4011 return scm_i_eval_x (obj, env);
4012 }
4013
4014 SCM_DEFINE (scm_eval2, "eval2", 2, 0, 0,
4015 (SCM obj, SCM env_thunk),
4016 "Evaluate @var{exp}, a Scheme expression, in the environment\n"
4017 "designated by @var{lookup}, a symbol-lookup function."
4018 "Do not use this version of eval, it does not play well\n"
4019 "with the module system. Use @code{eval} or\n"
4020 "@code{primitive-eval} instead.")
4021 #define FUNC_NAME s_scm_eval2
4022 {
4023 return scm_i_eval (obj, scm_top_level_env (env_thunk));
4024 }
4025 #undef FUNC_NAME
4026
4027 #endif /* DEPRECATED */
4028
4029
4030 /* At this point, scm_deval and scm_dapply are generated.
4031 */
4032
4033 #ifdef DEBUG_EXTENSIONS
4034 # define DEVAL
4035 # include "eval.c"
4036 #endif
4037
4038
4039
4040 void
4041 scm_init_eval ()
4042 {
4043 scm_init_opts (scm_evaluator_traps,
4044 scm_evaluator_trap_table,
4045 SCM_N_EVALUATOR_TRAPS);
4046 scm_init_opts (scm_eval_options_interface,
4047 scm_eval_opts,
4048 SCM_N_EVAL_OPTIONS);
4049
4050 scm_tc16_promise = scm_make_smob_type ("promise", 0);
4051 scm_set_smob_mark (scm_tc16_promise, scm_markcdr);
4052 scm_set_smob_print (scm_tc16_promise, promise_print);
4053
4054 scm_f_apply = scm_make_subr ("apply", scm_tc7_lsubr_2, scm_apply);
4055 scm_system_transformer = scm_sysintern ("scm:eval-transformer",
4056 scm_make_fluid ());
4057
4058 scm_lisp_nil = scm_sysintern ("nil", SCM_UNDEFINED);
4059 SCM_SETCDR (scm_lisp_nil, SCM_CAR (scm_lisp_nil));
4060 scm_lisp_nil = SCM_CAR (scm_lisp_nil);
4061 scm_lisp_t = scm_sysintern ("t", SCM_UNDEFINED);
4062 SCM_SETCDR (scm_lisp_t, SCM_CAR (scm_lisp_t));
4063 scm_lisp_t = SCM_CAR (scm_lisp_t);
4064
4065 /* acros */
4066 /* end of acros */
4067
4068 #if SCM_DEBUG_DEPRECATED == 0
4069 scm_top_level_lookup_closure_var =
4070 scm_sysintern ("*top-level-lookup-closure*", scm_make_fluid ());
4071 #endif
4072
4073 #ifndef SCM_MAGIC_SNARFER
4074 #include "libguile/eval.x"
4075 #endif
4076
4077 scm_add_feature ("delay");
4078 }
4079
4080 #endif /* !DEVAL */
4081
4082 /*
4083 Local Variables:
4084 c-file-style: "gnu"
4085 End:
4086 */