* debug.c, debug.h: Removed obsolete code.
[bpt/guile.git] / libguile / eval.c
CommitLineData
0f2d19dd
JB
1/* Copyright (C) 1995,1996 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, 675 Mass Ave, Cambridge, MA 02139, USA.
16 *
17 * As a special exception, the Free Software Foundation gives permission
18 * for additional uses of the text contained in its release of GUILE.
19 *
20 * The exception is that, if you link the GUILE library with other files
21 * to produce an executable, this does not by itself cause the
22 * resulting executable to be covered by the GNU General Public License.
23 * Your use of that executable is in no way restricted on account of
24 * linking the GUILE library code into it.
25 *
26 * This exception does not however invalidate any other reasons why
27 * the executable file might be covered by the GNU General Public License.
28 *
29 * This exception applies only to the code released by the
30 * Free Software Foundation under the name GUILE. If you copy
31 * code from other Free Software Foundation releases into a copy of
32 * GUILE, as the General Public License permits, the exception does
33 * not apply to the code that you add in this way. To avoid misleading
34 * anyone as to the status of such modified files, you must delete
35 * this exception notice from them.
36 *
37 * If you write modifications of your own for GUILE, it is your choice
38 * whether to permit this exception to apply to your modifications.
39 * If you do not wish that, delete this exception notice.
40 */
41\f
42
6dbd0af5
MD
43/* This file is read twice in order to produce debugging versions of
44 * scm_ceval and scm_apply. These functions, scm_deval and
45 * scm_dapply, are produced when we define the preprocessor macro
46 * DEVAL. The file is divided into sections which are treated
47 * differently with respect to DEVAL. The heads of these sections are
48 * marked with the string "SECTION:".
49 */
50
51
52/* SECTION: This code is compiled once.
0f2d19dd
JB
53 */
54
55#ifndef DEVAL
56
57#include <stdio.h>
58#include "_scm.h"
20e6290e
JB
59#include "debug.h"
60#include "append.h"
61#include "alist.h"
62#include "sequences.h"
63#include "eq.h"
64#include "continuations.h"
65#include "throw.h"
66#include "smob.h"
67#include "markers.h"
68#include "procprop.h"
69#include "hashtab.h"
ac46ab16 70#include "hash.h"
0f2d19dd 71
20e6290e
JB
72#ifdef DEBUG_EXTENSIONS
73#include "debug.h"
74#endif /* DEBUG_EXTENSIONS */
75
76#include "srcprop.h"
77#include "stackchk.h"
78
79#include "eval.h"
0f2d19dd
JB
80\f
81
6dbd0af5
MD
82/* The evaluator contains a plethora of EVAL symbols.
83 * This is an attempt at explanation.
84 *
85 * The following macros should be used in code which is read twice
86 * (where the choice of evaluator is hard soldered):
87 *
88 * SCM_CEVAL is the symbol used within one evaluator to call itself.
89 * Originally, it is defined to scm_ceval, but is redefined to
90 * scm_deval during the second pass.
91 *
92 * SIDEVAL corresponds to SCM_CEVAL, but is used in situations where
93 * only side effects of expressions matter. All immediates are
94 * ignored.
95 *
96 * EVALIM is used when it is known that the expression is an
97 * immediate. (This macro never calls an evaluator.)
98 *
99 * EVALCAR evaluates the car of an expression.
100 *
101 * EVALCELLCAR is like EVALCAR, but is used when it is known that the
102 * car is a lisp cell.
103 *
104 * The following macros should be used in code which is read once
105 * (where the choice of evaluator is dynamic):
106 *
107 * XEVAL takes care of immediates without calling an evaluator. It
108 * then calls scm_ceval *or* scm_deval, depending on the debugging
109 * mode.
110 *
111 * XEVALCAR corresponds to EVALCAR, but uses scm_ceval *or* scm_deval
112 * depending on the debugging mode.
113 *
114 * The main motivation for keeping this plethora is efficiency
115 * together with maintainability (=> locality of code).
116 */
117
0f2d19dd
JB
118#define EVALCELLCAR(x, env) (SCM_SYMBOLP (SCM_CAR(x)) \
119 ? *scm_lookupcar(x, env) \
120 : SCM_CEVAL(SCM_CAR(x), env))
121
122#ifdef MEMOIZE_LOCALS
6dbd0af5 123#define EVALIM(x, env) (SCM_ILOCP(x)?*scm_ilookup((x), env):x)
0f2d19dd 124#else
6dbd0af5 125#define EVALIM(x, env) x
0f2d19dd
JB
126#endif
127#define EVALCAR(x, env) (SCM_NCELLP(SCM_CAR(x))\
128 ? (SCM_IMP(SCM_CAR(x)) \
6dbd0af5 129 ? EVALIM(SCM_CAR(x), env) \
0f2d19dd
JB
130 : SCM_GLOC_VAL(SCM_CAR(x))) \
131 : EVALCELLCAR(x, env))
132#ifdef DEBUG_EXTENSIONS
133#define XEVALCAR(x, env) (SCM_NCELLP(SCM_CAR(x)) \
134 ? (SCM_IMP(SCM_CAR(x)) \
6dbd0af5 135 ? EVALIM(SCM_CAR(x), env) \
0f2d19dd
JB
136 : SCM_GLOC_VAL(SCM_CAR(x))) \
137 : (SCM_SYMBOLP(SCM_CAR(x)) \
138 ? *scm_lookupcar(x, env) \
139 : (*scm_ceval_ptr) (SCM_CAR(x), env)))
140#else
141#define XEVALCAR(x, env) EVALCAR(x, env)
142#endif
143
e2806c10 144#define EXTEND_ENV SCM_EXTEND_ENV
0f2d19dd
JB
145
146#ifdef MEMOIZE_LOCALS
1cc91f1b 147
0f2d19dd
JB
148SCM *
149scm_ilookup (iloc, env)
150 SCM iloc;
151 SCM env;
0f2d19dd
JB
152{
153 register int ir = SCM_IFRAME (iloc);
154 register SCM er = env;
155 for (; 0 != ir; --ir)
156 er = SCM_CDR (er);
157 er = SCM_CAR (er);
158 for (ir = SCM_IDIST (iloc); 0 != ir; --ir)
159 er = SCM_CDR (er);
160 if (SCM_ICDRP (iloc))
161 return &SCM_CDR (er);
162 return &SCM_CAR (SCM_CDR (er));
163}
164#endif
165
1cc91f1b 166
0f2d19dd
JB
167SCM *
168scm_lookupcar (vloc, genv)
169 SCM vloc;
170 SCM genv;
0f2d19dd
JB
171{
172 SCM env = genv;
173 register SCM *al, fl, var = SCM_CAR (vloc);
174#ifdef MEMOIZE_LOCALS
175 register SCM iloc = SCM_ILOC00;
176#endif
177 for (; SCM_NIMP (env); env = SCM_CDR (env))
178 {
179 if (SCM_BOOL_T == scm_procedure_p (SCM_CAR (env)))
180 break;
181 al = &SCM_CAR (env);
182 for (fl = SCM_CAR (*al); SCM_NIMP (fl); fl = SCM_CDR (fl))
183 {
184 if (SCM_NCONSP (fl))
185 if (fl == var)
186 {
187#ifdef MEMOIZE_LOCALS
188 SCM_CAR (vloc) = iloc + SCM_ICDR;
189#endif
190 return &SCM_CDR (*al);
191 }
192 else
193 break;
194 al = &SCM_CDR (*al);
195 if (SCM_CAR (fl) == var)
196 {
197#ifdef MEMOIZE_LOCALS
198#ifndef RECKLESS /* letrec inits to SCM_UNDEFINED */
199 if (SCM_UNBNDP (SCM_CAR (*al)))
200 {
201 env = SCM_EOL;
202 goto errout;
203 }
204#endif
205 SCM_CAR (vloc) = iloc;
206#endif
207 return &SCM_CAR (*al);
208 }
209#ifdef MEMOIZE_LOCALS
210 iloc += SCM_IDINC;
211#endif
212 }
213#ifdef MEMOIZE_LOCALS
214 iloc = (~SCM_IDSTMSK) & (iloc + SCM_IFRINC);
215#endif
216 }
217 {
218 SCM top_thunk, vcell;
219 if (SCM_NIMP(env))
220 {
221 top_thunk = SCM_CAR(env); /* env now refers to a top level env thunk */
222 env = SCM_CDR (env);
223 }
224 else
225 top_thunk = SCM_BOOL_F;
226 vcell = scm_sym2vcell (var, top_thunk, SCM_BOOL_F);
227 if (vcell == SCM_BOOL_F)
228 goto errout;
229 else
230 var = vcell;
231 }
232#ifndef RECKLESS
233 if (SCM_NNULLP (env) || SCM_UNBNDP (SCM_CDR (var)))
234 {
235 var = SCM_CAR (var);
236 errout:
f5bf2977 237 /* scm_everr (vloc, genv,...) */
01f61221 238 scm_error (scm_misc_error_key,
f5bf2977
GH
239 NULL,
240 SCM_NULLP (env)
241 ? "Unbound variable: %S"
242 : "Damaged environment: %S",
243 scm_listify (var, SCM_UNDEFINED),
244 SCM_BOOL_F);
0f2d19dd
JB
245 }
246#endif
247 SCM_CAR (vloc) = var + 1;
248 /* Except wait...what if the var is not a vcell,
249 * but syntax or something....
250 */
251 return &SCM_CDR (var);
252}
253
254#define unmemocar scm_unmemocar
1cc91f1b 255
0f2d19dd
JB
256SCM
257scm_unmemocar (form, env)
258 SCM form;
259 SCM env;
0f2d19dd 260{
6dbd0af5 261#ifdef DEBUG_EXTENSIONS
0f2d19dd 262 register int ir;
6dbd0af5 263#endif
0f2d19dd
JB
264 SCM c;
265
266 if (SCM_IMP (form))
267 return form;
268 c = SCM_CAR (form);
269 if (1 == (c & 7))
270 SCM_CAR (form) = SCM_CAR (c - 1);
271#ifdef MEMOIZE_LOCALS
6dbd0af5 272#ifdef DEBUG_EXTENSIONS
0f2d19dd
JB
273 else if (SCM_ILOCP (c))
274 {
275 for (ir = SCM_IFRAME (c); ir != 0; --ir)
276 env = SCM_CDR (env);
277 env = SCM_CAR (SCM_CAR (env));
278 for (ir = SCM_IDIST (c); ir != 0; --ir)
279 env = SCM_CDR (env);
280 SCM_CAR (form) = SCM_ICDRP (c) ? env : SCM_CAR (env);
281 }
6dbd0af5 282#endif
0f2d19dd
JB
283#endif
284 return form;
285}
286
1cc91f1b 287
0f2d19dd
JB
288SCM
289scm_eval_car (pair, env)
290 SCM pair;
291 SCM env;
0f2d19dd 292{
6dbd0af5 293 return XEVALCAR (pair, env);
0f2d19dd
JB
294}
295
296\f
297/*
298 * The following rewrite expressions and
299 * some memoized forms have different syntax
300 */
301
302static char s_expression[] = "missing or extra expression";
303static char s_test[] = "bad test";
304static char s_body[] = "bad body";
305static char s_bindings[] = "bad bindings";
306static char s_variable[] = "bad variable";
307static char s_clauses[] = "bad or missing clauses";
308static char s_formals[] = "bad formals";
309#define ASSYNT(_cond, _arg, _pos, _subr) if(!(_cond))scm_wta(_arg, (char *)_pos, _subr);
310
311SCM scm_i_dot, scm_i_quote, scm_i_quasiquote, scm_i_lambda, scm_i_let,
312 scm_i_arrow, scm_i_else, scm_i_unquote, scm_i_uq_splicing, scm_i_apply;
313SCM scm_i_name;
6dbd0af5
MD
314SCM scm_i_define, scm_i_and, scm_i_begin, scm_i_case, scm_i_cond,
315 scm_i_do, scm_i_if, scm_i_let, scm_i_letrec, scm_i_letstar,
316 scm_i_or, scm_i_set, scm_i_atapply, scm_i_atcall_cc;
0f2d19dd
JB
317static char s_quasiquote[] = "quasiquote";
318static char s_delay[] = "delay";
6dbd0af5
MD
319static char s_undefine[] = "undefine";
320#ifdef DEBUG_EXTENSIONS
321SCM scm_i_enter_frame, scm_i_apply_frame, scm_i_exit_frame;
322SCM scm_i_trace;
323#endif
0f2d19dd
JB
324
325#define ASRTSYNTAX(cond_, msg_) if(!(cond_))scm_wta(xorig, (msg_), what);
326
327
1cc91f1b
JB
328
329static void bodycheck SCM_P ((SCM xorig, SCM *bodyloc, char *what));
330
0f2d19dd
JB
331static void
332bodycheck (xorig, bodyloc, what)
333 SCM xorig;
334 SCM *bodyloc;
335 char *what;
0f2d19dd
JB
336{
337 ASRTSYNTAX (scm_ilength (*bodyloc) >= 1, s_expression);
338}
339
340
1cc91f1b 341
0f2d19dd
JB
342SCM
343scm_m_quote (xorig, env)
344 SCM xorig;
345 SCM env;
0f2d19dd
JB
346{
347 ASSYNT (scm_ilength (SCM_CDR (xorig)) == 1, xorig, s_expression, "quote");
348 return scm_cons (SCM_IM_QUOTE, SCM_CDR (xorig));
349}
350
351
1cc91f1b 352
0f2d19dd
JB
353SCM
354scm_m_begin (xorig, env)
355 SCM xorig;
356 SCM env;
0f2d19dd
JB
357{
358 ASSYNT (scm_ilength (SCM_CDR (xorig)) >= 1, xorig, s_expression, "begin");
359 return scm_cons (SCM_IM_BEGIN, SCM_CDR (xorig));
360}
361
362
1cc91f1b 363
0f2d19dd
JB
364SCM
365scm_m_if (xorig, env)
366 SCM xorig;
367 SCM env;
0f2d19dd
JB
368{
369 int len = scm_ilength (SCM_CDR (xorig));
370 ASSYNT (len >= 2 && len <= 3, xorig, s_expression, "if");
371 return scm_cons (SCM_IM_IF, SCM_CDR (xorig));
372}
373
374
1cc91f1b 375
0f2d19dd
JB
376SCM
377scm_m_set (xorig, env)
378 SCM xorig;
379 SCM env;
0f2d19dd 380{
6dbd0af5
MD
381 SCM x = SCM_CDR (xorig);
382 ASSYNT (2 == scm_ilength (x), xorig, s_expression, "set!");
383 ASSYNT (SCM_NIMP (SCM_CAR (x)) && SCM_SYMBOLP (SCM_CAR (x)),
384 xorig, s_variable, "set!");
0f2d19dd
JB
385 return scm_cons (SCM_IM_SET, x);
386}
387
388
389#if 0
1cc91f1b 390
0f2d19dd
JB
391SCM
392scm_m_vref (xorig, env)
393 SCM xorig;
394 SCM env;
0f2d19dd
JB
395{
396 SCM x = SCM_CDR (xorig);
397 ASSYNT (1 == scm_ilength (x), xorig, s_expression, s_vref);
398 if (SCM_NIMP(x) && UDSCM_VARIABLEP (SCM_CAR (x)))
399 {
f5bf2977 400 /* scm_everr (SCM_UNDEFINED, env,..., "global variable reference") */
01f61221 401 scm_error (scm_misc_error_key,
f5bf2977
GH
402 NULL,
403 "Bad variable: %S",
404 scm_listify (SCM_CAR (SCM_CDR (x)), SCM_UNDEFINED),
405 SCM_BOOL_F);
0f2d19dd
JB
406 }
407 ASSYNT (SCM_NIMP(x) && DEFSCM_VARIABLEP (SCM_CAR (x)),
408 xorig, s_variable, s_vref);
409 return
410 return scm_cons (IM_VREF, x);
411}
412
413
1cc91f1b 414
0f2d19dd
JB
415SCM
416scm_m_vset (xorig, env)
417 SCM xorig;
418 SCM env;
0f2d19dd
JB
419{
420 SCM x = SCM_CDR (xorig);
421 ASSYNT (3 == scm_ilength (x), xorig, s_expression, s_vset);
422 ASSYNT (( DEFSCM_VARIABLEP (SCM_CAR (x))
423 || UDSCM_VARIABLEP (SCM_CAR (x))),
424 xorig, s_variable, s_vset);
425 return scm_cons (IM_VSET, x);
426}
427#endif
428
429
1cc91f1b 430
0f2d19dd
JB
431SCM
432scm_m_and (xorig, env)
433 SCM xorig;
434 SCM env;
0f2d19dd
JB
435{
436 int len = scm_ilength (SCM_CDR (xorig));
437 ASSYNT (len >= 0, xorig, s_test, "and");
438 if (len >= 1)
439 return scm_cons (SCM_IM_AND, SCM_CDR (xorig));
440 else
441 return SCM_BOOL_T;
442}
443
444
1cc91f1b 445
0f2d19dd
JB
446SCM
447scm_m_or (xorig, env)
448 SCM xorig;
449 SCM env;
0f2d19dd
JB
450{
451 int len = scm_ilength (SCM_CDR (xorig));
452 ASSYNT (len >= 0, xorig, s_test, "or");
453 if (len >= 1)
454 return scm_cons (SCM_IM_OR, SCM_CDR (xorig));
455 else
456 return SCM_BOOL_F;
457}
458
459
1cc91f1b 460
0f2d19dd
JB
461SCM
462scm_m_case (xorig, env)
463 SCM xorig;
464 SCM env;
0f2d19dd
JB
465{
466 SCM proc, x = SCM_CDR (xorig);
467 ASSYNT (scm_ilength (x) >= 2, xorig, s_clauses, "case");
468 while (SCM_NIMP (x = SCM_CDR (x)))
469 {
470 proc = SCM_CAR (x);
471 ASSYNT (scm_ilength (proc) >= 2, xorig, s_clauses, "case");
472 ASSYNT (scm_ilength (SCM_CAR (proc)) >= 0 || scm_i_else == SCM_CAR (proc),
473 xorig, s_clauses, "case");
474 }
475 return scm_cons (SCM_IM_CASE, SCM_CDR (xorig));
476}
477
478
1cc91f1b 479
0f2d19dd
JB
480SCM
481scm_m_cond (xorig, env)
482 SCM xorig;
483 SCM env;
0f2d19dd
JB
484{
485 SCM arg1, x = SCM_CDR (xorig);
486 int len = scm_ilength (x);
487 ASSYNT (len >= 1, xorig, s_clauses, "cond");
488 while (SCM_NIMP (x))
489 {
490 arg1 = SCM_CAR (x);
491 len = scm_ilength (arg1);
492 ASSYNT (len >= 1, xorig, s_clauses, "cond");
493 if (scm_i_else == SCM_CAR (arg1))
494 {
495 ASSYNT (SCM_NULLP (SCM_CDR (x)) && len >= 2, xorig, "bad ELSE clause", "cond");
496 SCM_CAR (arg1) = SCM_BOOL_T;
497 }
498 if (len >= 2 && scm_i_arrow == SCM_CAR (SCM_CDR (arg1)))
499 ASSYNT (3 == len && SCM_NIMP (SCM_CAR (SCM_CDR (SCM_CDR (arg1)))),
500 xorig, "bad recipient", "cond");
501 x = SCM_CDR (x);
502 }
503 return scm_cons (SCM_IM_COND, SCM_CDR (xorig));
504}
505
506
1cc91f1b 507
0f2d19dd
JB
508SCM
509scm_m_lambda (xorig, env)
510 SCM xorig;
511 SCM env;
0f2d19dd
JB
512{
513 SCM proc, x = SCM_CDR (xorig);
514 if (scm_ilength (x) < 2)
515 goto badforms;
516 proc = SCM_CAR (x);
517 if SCM_NULLP
518 (proc) goto memlambda;
519 if SCM_IMP
520 (proc) goto badforms;
521 if SCM_SYMBOLP
522 (proc) goto memlambda;
523 if SCM_NCONSP
524 (proc) goto badforms;
525 while SCM_NIMP
526 (proc)
527 {
528 if SCM_NCONSP
529 (proc)
530 if (!SCM_SYMBOLP (proc))
531 goto badforms;
532 else
533 goto memlambda;
534 if (!(SCM_NIMP (SCM_CAR (proc)) && SCM_SYMBOLP (SCM_CAR (proc))))
535 goto badforms;
536 proc = SCM_CDR (proc);
537 }
538 if SCM_NNULLP
539 (proc)
540 badforms:scm_wta (xorig, s_formals, "lambda");
541memlambda:
542 bodycheck (xorig, &SCM_CDR (x), "lambda");
543 return scm_cons (SCM_IM_LAMBDA, SCM_CDR (xorig));
544}
545
546
1cc91f1b 547
0f2d19dd
JB
548SCM
549scm_m_letstar (xorig, env)
550 SCM xorig;
551 SCM env;
0f2d19dd
JB
552{
553 SCM x = SCM_CDR (xorig), arg1, proc, vars = SCM_EOL, *varloc = &vars;
554 int len = scm_ilength (x);
555 ASSYNT (len >= 2, xorig, s_body, "let*");
556 proc = SCM_CAR (x);
557 ASSYNT (scm_ilength (proc) >= 0, xorig, s_bindings, "let*");
6dbd0af5 558 while SCM_NIMP (proc)
0f2d19dd
JB
559 {
560 arg1 = SCM_CAR (proc);
561 ASSYNT (2 == scm_ilength (arg1), xorig, s_bindings, "let*");
562 ASSYNT (SCM_NIMP (SCM_CAR (arg1)) && SCM_SYMBOLP (SCM_CAR (arg1)), xorig, s_variable, "let*");
563 *varloc = scm_cons2 (SCM_CAR (arg1), SCM_CAR (SCM_CDR (arg1)), SCM_EOL);
564 varloc = &SCM_CDR (SCM_CDR (*varloc));
565 proc = SCM_CDR (proc);
566 }
567 x = scm_cons (vars, SCM_CDR (x));
568 bodycheck (xorig, &SCM_CDR (x), "let*");
569 return scm_cons (SCM_IM_LETSTAR, x);
570}
571
572/* DO gets the most radically altered syntax
573 (do ((<var1> <init1> <step1>)
574 (<var2> <init2>)
575 ... )
576 (<test> <return>)
577 <body>)
578 ;; becomes
579 (do_mem (varn ... var2 var1)
580 (<init1> <init2> ... <initn>)
581 (<test> <return>)
582 (<body>)
583 <step1> <step2> ... <stepn>) ;; missing steps replaced by var
584 */
585
586
1cc91f1b 587
0f2d19dd
JB
588SCM
589scm_m_do (xorig, env)
590 SCM xorig;
591 SCM env;
0f2d19dd
JB
592{
593 SCM x = SCM_CDR (xorig), arg1, proc;
594 SCM vars = SCM_EOL, inits = SCM_EOL, steps = SCM_EOL;
595 SCM *initloc = &inits, *steploc = &steps;
596 int len = scm_ilength (x);
597 ASSYNT (len >= 2, xorig, s_test, "do");
598 proc = SCM_CAR (x);
599 ASSYNT (scm_ilength (proc) >= 0, xorig, s_bindings, "do");
600 while SCM_NIMP
601 (proc)
602 {
603 arg1 = SCM_CAR (proc);
604 len = scm_ilength (arg1);
605 ASSYNT (2 == len || 3 == len, xorig, s_bindings, "do");
606 ASSYNT (SCM_NIMP (SCM_CAR (arg1)) && SCM_SYMBOLP (SCM_CAR (arg1)), xorig, s_variable, "do");
607 /* vars reversed here, inits and steps reversed at evaluation */
608 vars = scm_cons (SCM_CAR (arg1), vars); /* variable */
609 arg1 = SCM_CDR (arg1);
610 *initloc = scm_cons (SCM_CAR (arg1), SCM_EOL); /* init */
611 initloc = &SCM_CDR (*initloc);
612 arg1 = SCM_CDR (arg1);
613 *steploc = scm_cons (SCM_IMP (arg1) ? SCM_CAR (vars) : SCM_CAR (arg1), SCM_EOL); /* step */
614 steploc = &SCM_CDR (*steploc);
615 proc = SCM_CDR (proc);
616 }
617 x = SCM_CDR (x);
618 ASSYNT (scm_ilength (SCM_CAR (x)) >= 1, xorig, s_test, "do");
619 x = scm_cons2 (SCM_CAR (x), SCM_CDR (x), steps);
620 x = scm_cons2 (vars, inits, x);
621 bodycheck (xorig, &SCM_CAR (SCM_CDR (SCM_CDR (x))), "do");
622 return scm_cons (SCM_IM_DO, x);
623}
624
6dbd0af5
MD
625/* evalcar is small version of inline EVALCAR when we don't care about
626 * speed
627 */
628#define evalcar scm_eval_car
0f2d19dd 629
1cc91f1b
JB
630
631static SCM iqq SCM_P ((SCM form, SCM env, int depth));
632
0f2d19dd
JB
633static SCM
634iqq (form, env, depth)
635 SCM form;
636 SCM env;
637 int depth;
0f2d19dd
JB
638{
639 SCM tmp;
640 int edepth = depth;
641 if SCM_IMP
642 (form) return form;
643 if (SCM_VECTORP (form))
644 {
645 long i = SCM_LENGTH (form);
646 SCM *data = SCM_VELTS (form);
647 tmp = SCM_EOL;
648 for (; --i >= 0;)
649 tmp = scm_cons (data[i], tmp);
650 return scm_vector (iqq (tmp, env, depth));
651 }
652 if SCM_NCONSP
653 (form) return form;
654 tmp = SCM_CAR (form);
655 if (scm_i_quasiquote == tmp)
656 {
657 depth++;
658 goto label;
659 }
660 if (scm_i_unquote == tmp)
661 {
662 --depth;
663 label:
664 form = SCM_CDR (form);
665 /* !!! might need a check here to be sure that form isn't a struct. */
666 SCM_ASSERT (SCM_NIMP (form) && SCM_ECONSP (form) && SCM_NULLP (SCM_CDR (form)),
667 form, SCM_ARG1, s_quasiquote);
668 if (0 == depth)
669 return evalcar (form, env);
670 return scm_cons2 (tmp, iqq (SCM_CAR (form), env, depth), SCM_EOL);
671 }
672 if (SCM_NIMP (tmp) && (scm_i_uq_splicing == SCM_CAR (tmp)))
673 {
674 tmp = SCM_CDR (tmp);
675 if (0 == --edepth)
676 return scm_append (scm_cons2 (evalcar (tmp, env), iqq (SCM_CDR (form), env, depth), SCM_EOL));
677 }
678 return scm_cons (iqq (SCM_CAR (form), env, edepth), iqq (SCM_CDR (form), env, depth));
679}
680
681/* Here are acros which return values rather than code. */
682
1cc91f1b 683
0f2d19dd
JB
684SCM
685scm_m_quasiquote (xorig, env)
686 SCM xorig;
687 SCM env;
0f2d19dd
JB
688{
689 SCM x = SCM_CDR (xorig);
690 ASSYNT (scm_ilength (x) == 1, xorig, s_expression, s_quasiquote);
691 return iqq (SCM_CAR (x), env, 1);
692}
693
1cc91f1b 694
0f2d19dd
JB
695SCM
696scm_m_delay (xorig, env)
697 SCM xorig;
698 SCM env;
0f2d19dd
JB
699{
700 ASSYNT (scm_ilength (xorig) == 2, xorig, s_expression, s_delay);
701 xorig = SCM_CDR (xorig);
702 return scm_makprom (scm_closure (scm_cons2 (SCM_EOL, SCM_CAR (xorig), SCM_CDR (xorig)),
703 env));
704}
705
1cc91f1b
JB
706
707static SCM env_top_level SCM_P ((SCM env));
708
0f2d19dd
JB
709static SCM
710env_top_level (env)
711 SCM env;
0f2d19dd
JB
712{
713 while (SCM_NIMP(env))
714 {
715 if (SCM_BOOL_T == scm_procedure_p (SCM_CAR(env)))
716 return SCM_CAR(env);
717 env = SCM_CDR (env);
718 }
719 return SCM_BOOL_F;
720}
721
1cc91f1b 722
0f2d19dd
JB
723SCM
724scm_m_define (x, env)
725 SCM x;
726 SCM env;
0f2d19dd
JB
727{
728 SCM proc, arg1 = x;
729 x = SCM_CDR (x);
730 /* ASSYNT(SCM_NULLP(env), x, "bad placement", s_define);*/
731 ASSYNT (scm_ilength (x) >= 2, arg1, s_expression, "define");
732 proc = SCM_CAR (x);
733 x = SCM_CDR (x);
734 while (SCM_NIMP (proc) && SCM_CONSP (proc))
735 { /* nested define syntax */
736 x = scm_cons (scm_cons2 (scm_i_lambda, SCM_CDR (proc), x), SCM_EOL);
737 proc = SCM_CAR (proc);
738 }
739 ASSYNT (SCM_NIMP (proc) && SCM_SYMBOLP (proc), arg1, s_variable, "define");
740 ASSYNT (1 == scm_ilength (x), arg1, s_expression, "define");
741 if (SCM_TOP_LEVEL (env))
742 {
743 x = evalcar (x, env);
6dbd0af5 744#ifdef DEBUG_EXTENSIONS
b7ff98dd 745 if (SCM_REC_PROCNAMES_P && SCM_NIMP (x) && SCM_CLOSUREP (x))
6dbd0af5
MD
746 scm_set_procedure_property_x (x, scm_i_name, proc);
747#endif
0f2d19dd
JB
748 arg1 = scm_sym2vcell (proc, env_top_level (env), SCM_BOOL_T);
749#if 0
750#ifndef RECKLESS
751 if (SCM_NIMP (SCM_CDR (arg1)) && ((SCM) SCM_SNAME (SCM_CDR (arg1)) == proc)
752 && (SCM_CDR (arg1) != x))
753 scm_warn ("redefining built-in ", SCM_CHARS (proc));
754 else
755#endif
756 if (5 <= scm_verbose && SCM_UNDEFINED != SCM_CDR (arg1))
757 scm_warn ("redefining ", SCM_CHARS (proc));
0f2d19dd
JB
758#endif
759 SCM_CDR (arg1) = x;
760#ifdef SICP
761 return scm_cons2 (scm_i_quote, SCM_CAR (arg1), SCM_EOL);
762#else
763 return SCM_UNSPECIFIED;
764#endif
765 }
766 return scm_cons2 (SCM_IM_DEFINE, proc, x);
767}
6dbd0af5
MD
768
769SCM
770scm_m_undefine (x, env)
771 SCM x, env;
772{
773 SCM arg1 = x;
774 x = SCM_CDR (x);
775 ASSYNT (SCM_TOP_LEVEL (env), arg1, "bad placement ", s_undefine);
776 ASSYNT (SCM_NIMP (x) && SCM_CONSP (x) && SCM_CDR (x) == SCM_EOL,
777 arg1, s_expression, s_undefine);
778 x = SCM_CAR (x);
779 ASSYNT (SCM_NIMP (x) && SCM_SYMBOLP (x), arg1, s_variable, s_undefine);
780 arg1 = scm_sym2vcell (x, env_top_level (env), SCM_BOOL_F);
781 ASSYNT (SCM_NFALSEP (arg1) && !SCM_UNBNDP (SCM_CDR (arg1)),
782 x, "variable already unbound ", s_undefine);
783#if 0
784#ifndef RECKLESS
785 if (SCM_NIMP (SCM_CDR (arg1)) && ((SCM) SCM_SNAME (SCM_CDR (arg1)) == x))
786 scm_warn ("undefining built-in ", SCM_CHARS (x));
787 else
788#endif
789 if (5 <= scm_verbose && SCM_UNDEFINED != SCM_CDR (arg1))
790 scm_warn ("redefining ", SCM_CHARS (x));
791#endif
792 SCM_CDR (arg1) = SCM_UNDEFINED;
793#ifdef SICP
794 return SCM_CAR (arg1);
795#else
796 return SCM_UNSPECIFIED;
797#endif
798}
799
0f2d19dd
JB
800/* end of acros */
801
1cc91f1b 802
0f2d19dd
JB
803SCM
804scm_m_letrec (xorig, env)
805 SCM xorig;
806 SCM env;
0f2d19dd
JB
807{
808 SCM cdrx = SCM_CDR (xorig); /* locally mutable version of form */
809 char *what = SCM_CHARS (SCM_CAR (xorig));
810 SCM x = cdrx, proc, arg1; /* structure traversers */
811 SCM vars = SCM_EOL, inits = SCM_EOL, *initloc = &inits;
812
813 ASRTSYNTAX (scm_ilength (x) >= 2, s_body);
814 proc = SCM_CAR (x);
815 if SCM_NULLP
816 (proc) return scm_m_letstar (xorig, env); /* null binding, let* faster */
817 ASRTSYNTAX (scm_ilength (proc) >= 1, s_bindings);
818 do
819 {
820 /* vars scm_list reversed here, inits reversed at evaluation */
821 arg1 = SCM_CAR (proc);
822 ASRTSYNTAX (2 == scm_ilength (arg1), s_bindings);
823 ASRTSYNTAX (SCM_NIMP (SCM_CAR (arg1)) && SCM_SYMBOLP (SCM_CAR (arg1)), s_variable);
824 vars = scm_cons (SCM_CAR (arg1), vars);
825 *initloc = scm_cons (SCM_CAR (SCM_CDR (arg1)), SCM_EOL);
826 initloc = &SCM_CDR (*initloc);
827 }
828 while SCM_NIMP
829 (proc = SCM_CDR (proc));
830 cdrx = scm_cons2 (vars, inits, SCM_CDR (x));
831 bodycheck (xorig, &SCM_CDR (SCM_CDR (cdrx)), what);
832 return scm_cons (SCM_IM_LETREC, cdrx);
833}
834
1cc91f1b 835
0f2d19dd
JB
836SCM
837scm_m_let (xorig, env)
838 SCM xorig;
839 SCM env;
0f2d19dd
JB
840{
841 SCM cdrx = SCM_CDR (xorig); /* locally mutable version of form */
842 SCM x = cdrx, proc, arg1, name; /* structure traversers */
843 SCM vars = SCM_EOL, inits = SCM_EOL, *varloc = &vars, *initloc = &inits;
844
845 ASSYNT (scm_ilength (x) >= 2, xorig, s_body, "let");
846 proc = SCM_CAR (x);
847 if (SCM_NULLP (proc)
848 || (SCM_NIMP (proc) && SCM_CONSP (proc)
849 && SCM_NIMP (SCM_CAR (proc)) && SCM_CONSP (SCM_CAR (proc)) && SCM_NULLP (SCM_CDR (proc))))
850 return scm_m_letstar (xorig, env); /* null or single binding, let* is faster */
851 ASSYNT (SCM_NIMP (proc), xorig, s_bindings, "let");
852 if (SCM_CONSP (proc)) /* plain let, proc is <bindings> */
853 return scm_cons (SCM_IM_LET, SCM_CDR (scm_m_letrec (xorig, env)));
854 if (!SCM_SYMBOLP (proc))
855 scm_wta (xorig, s_bindings, "let"); /* bad let */
856 name = proc; /* named let, build equiv letrec */
857 x = SCM_CDR (x);
858 ASSYNT (scm_ilength (x) >= 2, xorig, s_body, "let");
859 proc = SCM_CAR (x); /* bindings scm_list */
860 ASSYNT (scm_ilength (proc) >= 0, xorig, s_bindings, "let");
861 while SCM_NIMP
862 (proc)
863 { /* vars and inits both in order */
864 arg1 = SCM_CAR (proc);
865 ASSYNT (2 == scm_ilength (arg1), xorig, s_bindings, "let");
866 ASSYNT (SCM_NIMP (SCM_CAR (arg1)) && SCM_SYMBOLP (SCM_CAR (arg1)), xorig, s_variable, "let");
867 *varloc = scm_cons (SCM_CAR (arg1), SCM_EOL);
868 varloc = &SCM_CDR (*varloc);
869 *initloc = scm_cons (SCM_CAR (SCM_CDR (arg1)), SCM_EOL);
870 initloc = &SCM_CDR (*initloc);
871 proc = SCM_CDR (proc);
872 }
873 return
874 scm_m_letrec (scm_cons2 (scm_i_let,
875 scm_cons (scm_cons2 (name, scm_cons2 (scm_i_lambda, vars, SCM_CDR (x)), SCM_EOL), SCM_EOL),
876 scm_acons (name, inits, SCM_EOL)), /* body */
877 env);
878}
879
880
1cc91f1b 881
0f2d19dd
JB
882SCM
883scm_m_apply (xorig, env)
884 SCM xorig;
885 SCM env;
0f2d19dd
JB
886{
887 ASSYNT (scm_ilength (SCM_CDR (xorig)) == 2, xorig, s_expression, "@apply");
888 return scm_cons (SCM_IM_APPLY, SCM_CDR (xorig));
889}
890
e2806c10 891#define s_atcall_cc (SCM_ISYMCHARS(SCM_IM_CONT)+1)
0f2d19dd 892
1cc91f1b 893
0f2d19dd
JB
894SCM
895scm_m_cont (xorig, env)
896 SCM xorig;
897 SCM env;
0f2d19dd
JB
898{
899 ASSYNT (scm_ilength (SCM_CDR (xorig)) == 1, xorig, s_expression, "@call-with-current-continuation");
900 return scm_cons (SCM_IM_CONT, SCM_CDR (xorig));
901}
902
6dbd0af5
MD
903/* scm_unmemocopy takes a memoized expression together with its
904 * environment and rewrites it to its original form. Thus, it is the
905 * inversion of the rewrite rules above. The procedure is not
906 * optimized for speed. It's used in scm_iprin1 when printing the
907 * code of a closure, in scm_procedure_source and in scm_expr_stack
908 * when generating the source for a stackframe.
909 */
910
1cc91f1b
JB
911
912static SCM unmemocopy SCM_P ((SCM x, SCM env));
913
6dbd0af5
MD
914static SCM
915unmemocopy (x, env)
916 SCM x;
917 SCM env;
6dbd0af5
MD
918{
919 SCM ls, z;
920#ifdef DEBUG_EXTENSIONS
921 SCM p;
922#endif
923 if (SCM_NCELLP (x) || SCM_NECONSP (x))
924 return x;
925#ifdef DEBUG_EXTENSIONS
926 p = scm_whash_lookup (scm_source_whash, x);
927#endif
928 switch (SCM_TYP7 (x))
929 {
930 case (127 & SCM_IM_AND):
931 ls = z = scm_cons (scm_i_and, SCM_UNSPECIFIED);
932 break;
933 case (127 & SCM_IM_BEGIN):
934 ls = z = scm_cons (scm_i_begin, SCM_UNSPECIFIED);
935 break;
936 case (127 & SCM_IM_CASE):
937 ls = z = scm_cons (scm_i_case, SCM_UNSPECIFIED);
938 break;
939 case (127 & SCM_IM_COND):
940 ls = z = scm_cons (scm_i_cond, SCM_UNSPECIFIED);
941 break;
942 case (127 & SCM_IM_DO):
943 ls = scm_cons (scm_i_do, SCM_UNSPECIFIED);
944 goto transform;
945 case (127 & SCM_IM_IF):
946 ls = z = scm_cons (scm_i_if, SCM_UNSPECIFIED);
947 break;
948 case (127 & SCM_IM_LET):
949 ls = scm_cons (scm_i_let, SCM_UNSPECIFIED);
950 goto transform;
951 case (127 & SCM_IM_LETREC):
952 {
953 SCM f, v, e, s;
954 ls = scm_cons (scm_i_letrec, SCM_UNSPECIFIED);
955 transform:
956 x = SCM_CDR (x);
957 f = v = SCM_CAR (x);
958 x = SCM_CDR (x);
e2806c10 959 z = EXTEND_ENV (f, SCM_EOL, env);
6dbd0af5
MD
960 e = scm_reverse (unmemocopy (SCM_CAR (x),
961 SCM_CAR (ls) == scm_i_letrec ? z : env));
962 env = z;
963 s = SCM_CAR (ls) == scm_i_do
964 ? scm_reverse (unmemocopy (SCM_CDR (SCM_CDR (SCM_CDR (x))), env))
965 : f;
966 z = SCM_EOL;
967 do
968 {
969 z = scm_acons (SCM_CAR (v),
970 scm_cons (SCM_CAR (e),
971 SCM_CAR (s) == SCM_CAR (v)
972 ? SCM_EOL
973 : scm_cons (SCM_CAR (s), SCM_EOL)),
974 z);
975 v = SCM_CDR (v);
976 e = SCM_CDR (e);
977 s = SCM_CDR (s);
978 }
979 while SCM_NIMP (v);
980 SCM_CDR (ls) = z = scm_cons (z, SCM_UNSPECIFIED);
981 if (SCM_CAR (ls) == scm_i_do)
982 {
983 x = SCM_CDR (x);
984 z = (SCM_CDR (z) = scm_cons (unmemocopy (SCM_CAR (x), env),
985 SCM_UNSPECIFIED));
986 x = (SCM) (&SCM_CAR (SCM_CDR (x)) - 1);
987 }
988 break;
989 }
990 case (127 & SCM_IM_LETSTAR):
991 {
992 SCM b, y;
993 x = SCM_CDR (x);
994 b = SCM_CAR (x);
995 y = SCM_EOL;
996 if SCM_IMP (b)
997 {
e2806c10 998 env = EXTEND_ENV (SCM_EOL, SCM_EOL, env);
6dbd0af5
MD
999 goto letstar;
1000 }
1001 y = z = scm_acons (SCM_CAR (b),
1002 unmemocar (
1003 scm_cons (unmemocopy (SCM_CAR (SCM_CDR (b)), env), SCM_EOL), env),
1004 SCM_UNSPECIFIED);
e2806c10 1005 env = EXTEND_ENV (SCM_CAR (b), SCM_BOOL_F, env);
6dbd0af5
MD
1006 b = SCM_CDR (SCM_CDR (b));
1007 if (SCM_IMP (b))
1008 {
1009 SCM_SETCDR (y, SCM_EOL);
1010 ls = scm_cons (scm_i_let, z = scm_cons (y, SCM_UNSPECIFIED));
1011 break;
1012 }
1013 do
1014 {
1015 z = (SCM_CDR (z) = scm_acons (SCM_CAR (b),
1016 unmemocar (
1017 scm_cons (unmemocopy (SCM_CAR (SCM_CDR (b)), env), SCM_EOL), env),
1018 SCM_UNSPECIFIED));
e2806c10 1019 env = EXTEND_ENV (SCM_CAR (b), SCM_BOOL_F, env);
6dbd0af5
MD
1020 b = SCM_CDR (SCM_CDR (b));
1021 }
1022 while SCM_NIMP (b);
1023 SCM_CDR (z) = SCM_EOL;
1024 letstar:
1025 ls = scm_cons (scm_i_letstar, z = scm_cons (y, SCM_UNSPECIFIED));
1026 break;
1027 }
1028 case (127 & SCM_IM_OR):
1029 ls = z = scm_cons (scm_i_or, SCM_UNSPECIFIED);
1030 break;
1031 case (127 & SCM_IM_LAMBDA):
1032 x = SCM_CDR (x);
1033 ls = scm_cons (scm_i_lambda,
1034 z = scm_cons (SCM_CAR (x), SCM_UNSPECIFIED));
e2806c10 1035 env = EXTEND_ENV (SCM_CAR (x), SCM_EOL, env);
6dbd0af5
MD
1036 break;
1037 case (127 & SCM_IM_QUOTE):
1038 ls = z = scm_cons (scm_i_quote, SCM_UNSPECIFIED);
1039 break;
1040 case (127 & SCM_IM_SET):
1041 ls = z = scm_cons (scm_i_set, SCM_UNSPECIFIED);
1042 break;
1043 case (127 & SCM_IM_DEFINE):
1044 {
1045 SCM n;
1046 x = SCM_CDR (x);
1047 ls = scm_cons (scm_i_define,
1048 z = scm_cons (n = SCM_CAR (x), SCM_UNSPECIFIED));
1049 if (SCM_NNULLP (env))
1050 SCM_CAR (SCM_CAR (env)) = scm_cons (n, SCM_CAR (SCM_CAR (env)));
1051 break;
1052 }
1053 case (127 & SCM_MAKISYM (0)):
1054 z = SCM_CAR (x);
1055 if (!SCM_ISYMP (z))
1056 goto unmemo;
1057 switch SCM_ISYMNUM (z)
1058 {
1059 case (SCM_ISYMNUM (SCM_IM_APPLY)):
1060 ls = z = scm_cons (scm_i_atapply, SCM_UNSPECIFIED);
1061 goto loop;
1062 case (SCM_ISYMNUM (SCM_IM_CONT)):
1063 ls = z = scm_cons (scm_i_atcall_cc, SCM_UNSPECIFIED);
1064 goto loop;
1065 default:
1066 }
1067 unmemo:
1068 default:
1069 ls = z = unmemocar (scm_cons (unmemocopy (SCM_CAR (x), env),
1070 SCM_UNSPECIFIED),
1071 env);
1072 }
1073loop:
1074 while (SCM_CELLP (x = SCM_CDR (x)) && SCM_ECONSP (x))
1075 z = (SCM_CDR (z) = unmemocar (scm_cons (unmemocopy (SCM_CAR (x), env),
1076 SCM_UNSPECIFIED),
1077 env));
1078 SCM_CDR (z) = x;
1079#ifdef DEBUG_EXTENSIONS
1080 if (SCM_NFALSEP (p))
1081 scm_whash_insert (scm_source_whash, ls, p);
1082#endif
1083 return ls;
1084}
1085
1cc91f1b 1086
6dbd0af5
MD
1087SCM
1088scm_unmemocopy (x, env)
1089 SCM x;
1090 SCM env;
6dbd0af5
MD
1091{
1092 if (SCM_NNULLP (env))
1093 /* Make a copy of the lowest frame to protect it from
1094 modifications by SCM_IM_DEFINE */
1095 return unmemocopy (x, scm_cons (SCM_CAR (env), SCM_CDR (env)));
1096 else
1097 return unmemocopy (x, env);
1098}
1099
0f2d19dd 1100#ifndef RECKLESS
1cc91f1b 1101
0f2d19dd
JB
1102int
1103scm_badargsp (formals, args)
1104 SCM formals;
1105 SCM args;
0f2d19dd
JB
1106{
1107 while SCM_NIMP
1108 (formals)
1109 {
1110 if SCM_NCONSP
1111 (formals) return 0;
1112 if SCM_IMP
1113 (args) return 1;
1114 formals = SCM_CDR (formals);
1115 args = SCM_CDR (args);
1116 }
1117 return SCM_NNULLP (args) ? 1 : 0;
1118}
1119#endif
1120
1121
1122\f
1123long scm_tc16_macro;
1124
1cc91f1b 1125
6dbd0af5
MD
1126SCM
1127scm_eval_args (l, env)
1128 SCM l;
1129 SCM env;
6dbd0af5
MD
1130{
1131 SCM res = SCM_EOL, *lloc = &res;
1132 while (SCM_NIMP (l))
1133 {
1134 *lloc = scm_cons (EVALCAR (l, env), SCM_EOL);
1135 lloc = &SCM_CDR (*lloc);
1136 l = SCM_CDR (l);
1137 }
1138 return res;
1139}
0f2d19dd
JB
1140#endif /* !DEVAL */
1141
6dbd0af5
MD
1142
1143/* SECTION: This code is specific for the debugging support. One
1144 * branch is read when DEVAL isn't defined, the other when DEVAL is
1145 * defined.
1146 */
1147
1148#ifndef DEVAL
1149
1150#define SCM_APPLY scm_apply
1151#define PREP_APPLY(proc, args)
1152#define ENTER_APPLY
1153#define RETURN(x) return x;
b7ff98dd
MD
1154#ifdef STACK_CHECKING
1155#ifndef NO_CEVAL_STACK_CHECKING
1156#define EVAL_STACK_CHECKING
1157#endif
6dbd0af5
MD
1158#endif
1159
1160#else /* !DEVAL */
1161
0f2d19dd
JB
1162#undef SCM_CEVAL
1163#define SCM_CEVAL scm_deval /* Substitute all uses of scm_ceval */
1164#undef SCM_APPLY
1165#define SCM_APPLY scm_dapply
6dbd0af5
MD
1166#undef PREP_APPLY
1167#define PREP_APPLY(p, l) \
1168{ ++debug.info; debug.info->a.proc = p; debug.info->a.args = l; }
1169#undef ENTER_APPLY
1170#define ENTER_APPLY \
1171{\
b7ff98dd 1172 SCM_SET_ARGSREADY (debug);\
6dbd0af5 1173 if (CHECK_APPLY)\
b7ff98dd 1174 if (SCM_APPLY_FRAME_P || (SCM_TRACE_P && PROCTRACEP (proc)))\
6dbd0af5 1175 {\
b7ff98dd
MD
1176 SCM tmp, tail = SCM_TRACED_FRAME_P (debug) ? SCM_BOOL_T : SCM_BOOL_F;\
1177 SCM_SET_TRACED_FRAME (debug);\
1178 if (SCM_CHEAPTRAPS_P)\
6dbd0af5
MD
1179 {\
1180 tmp = scm_make_debugobj ((scm_debug_frame *) &debug);\
1181 scm_ithrow (scm_i_apply_frame, scm_cons2 (tmp, tail, SCM_EOL), 0);\
1182 }\
1183 else\
1184 {\
1185 scm_make_cont (&tmp);\
1186 if (!setjmp (SCM_JMPBUF (tmp)))\
1187 scm_ithrow (scm_i_apply_frame, scm_cons2 (tmp, tail, SCM_EOL), 0);\
1188 }\
1189 }\
1190}
0f2d19dd
JB
1191#undef RETURN
1192#define RETURN(e) {proc = (e); goto exit;}
b7ff98dd
MD
1193#ifdef STACK_CHECKING
1194#ifndef EVAL_STACK_CHECKING
1195#define EVAL_STACK_CHECKING
1196#endif
6dbd0af5
MD
1197#endif
1198
1199/* scm_ceval_ptr points to the currently selected evaluator.
1200 * *fixme*: Although efficiency is important here, this state variable
1201 * should probably not be a global. It should be related to the
1202 * current repl.
1203 */
1204
1cc91f1b
JB
1205
1206SCM (*scm_ceval_ptr) SCM_P ((SCM x, SCM env));
0f2d19dd 1207
1646d37b 1208/* scm_last_debug_frame contains a pointer to the last debugging
6dbd0af5
MD
1209 * information stack frame. It is accessed very often from the
1210 * debugging evaluator, so it should probably not be indirectly
1211 * addressed. Better to save and restore it from the current root at
1212 * any stack swaps.
1213 */
1214
1646d37b
MD
1215#ifndef USE_THREADS
1216scm_debug_frame *scm_last_debug_frame;
1217#endif
6dbd0af5
MD
1218
1219/* scm_debug_eframe_size is the number of slots available for pseudo
1220 * stack frames at each real stack frame.
1221 */
1222
1223int scm_debug_eframe_size;
1224
b7ff98dd 1225int scm_debug_mode, scm_check_entry_p, scm_check_apply_p, scm_check_exit_p;
6dbd0af5
MD
1226
1227scm_option scm_debug_opts[] = {
b7ff98dd
MD
1228 { SCM_OPTION_BOOLEAN, "cheap", 1,
1229 "*Flyweight representation of the stack at traps." },
1230 { SCM_OPTION_BOOLEAN, "breakpoints", 0, "*Check for breakpoints." },
1231 { SCM_OPTION_BOOLEAN, "trace", 0, "*Trace mode." },
1232 { SCM_OPTION_BOOLEAN, "procnames", 1,
1233 "Record procedure names at definition." },
1234 { SCM_OPTION_BOOLEAN, "backwards", 0,
1235 "Display backtrace in anti-chronological order." },
1236 { SCM_OPTION_INTEGER, "frames", 2,
1237 "Maximum number of tail-recursive frames in backtrace." },
1238 { SCM_OPTION_INTEGER, "depth", 80, "Maximal length of backtrace." },
1239 { SCM_OPTION_BOOLEAN, "backtrace", 0,
1240 "Show backtrace on error (use debugging evaluator)." },
1241 { SCM_OPTION_BOOLEAN, "deval", 0, "Use the debugging evaluator." },
1242 { SCM_OPTION_INTEGER, "stack", 20000, "Stack size limit (0 = no check)." }
6dbd0af5
MD
1243};
1244
1245scm_option scm_evaluator_trap_table[] = {
b7ff98dd
MD
1246 { SCM_OPTION_BOOLEAN, "enter-frame", 0, "Trap when eval enters new frame." },
1247 { SCM_OPTION_BOOLEAN, "apply-frame", 0, "Trap when entering apply." },
1248 { SCM_OPTION_BOOLEAN, "exit-frame", 0, "Trap when exiting eval or apply." }
6dbd0af5
MD
1249};
1250
1251SCM
1252scm_deval_args (l, env, lloc)
1253 SCM l, env, *lloc;
0f2d19dd 1254{
6dbd0af5 1255 SCM *res = lloc;
0f2d19dd
JB
1256 while (SCM_NIMP (l))
1257 {
1258 *lloc = scm_cons (EVALCAR (l, env), SCM_EOL);
1259 lloc = &SCM_CDR (*lloc);
1260 l = SCM_CDR (l);
1261 }
6dbd0af5 1262 return *res;
0f2d19dd
JB
1263}
1264
6dbd0af5
MD
1265#endif /* !DEVAL */
1266
1267
1268/* SECTION: Some local definitions for the evaluator.
1269 */
1270
1271#ifndef DEVAL
1272#ifdef SCM_FLOATS
1273#define CHECK_EQVISH(A,B) (((A) == (B)) || (SCM_NFALSEP (scm_eqv_p ((A), (B)))))
1274#else
1275#define CHECK_EQVISH(A,B) ((A) == (B))
1276#endif
1277#endif /* DEVAL */
1278
1279
1280/* SECTION: This is the evaluator. Like any real monster, it has
1281 * three heads. This code is compiled twice.
1282 */
1283
0f2d19dd 1284#if 0
1cc91f1b 1285
0f2d19dd
JB
1286SCM
1287scm_ceval (x, env)
1288 SCM x;
1289 SCM env;
0f2d19dd
JB
1290{}
1291#endif
1292#if 0
1cc91f1b 1293
0f2d19dd
JB
1294SCM
1295scm_deval (x, env)
1296 SCM x;
1297 SCM env;
0f2d19dd
JB
1298{}
1299#endif
1300
1cc91f1b 1301
6dbd0af5 1302SCM
0f2d19dd
JB
1303SCM_CEVAL (x, env)
1304 SCM x;
1305 SCM env;
1306{
1307 union
1308 {
1309 SCM *lloc;
1310 SCM arg1;
1311 } t;
6dbd0af5
MD
1312 SCM proc, arg2;
1313#ifdef DEVAL
1314 struct
1315 {
1316 scm_debug_frame *prev;
1317 long status;
1318 scm_debug_info vect[scm_debug_eframe_size];
1319 scm_debug_info *info;
1320 } debug;
1646d37b 1321 debug.prev = scm_last_debug_frame;
6dbd0af5
MD
1322 debug.status = scm_debug_eframe_size;
1323 debug.info = &debug.vect[0];
1646d37b 1324 scm_last_debug_frame = (scm_debug_frame *) &debug;
6dbd0af5 1325#endif
b7ff98dd
MD
1326#ifdef EVAL_STACK_CHECKING
1327 if (SCM_STACK_OVERFLOW_P ((SCM_STACKITEM *) &proc)
1328 && scm_stack_checking_enabled_p)
6dbd0af5 1329 {
b7ff98dd 1330#ifdef DEVAL
6dbd0af5
MD
1331 debug.info->e.exp = x;
1332 debug.info->e.env = env;
b7ff98dd 1333#endif
6dbd0af5
MD
1334 scm_report_stack_overflow ();
1335 }
1336#endif
1337#ifdef DEVAL
1338 goto start;
1339#endif
1340loopnoap:
1341 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
1342loop:
1343#ifdef DEVAL
1344#if 0 /* This will probably never have any practical use ... */
1345 if (CHECK_EXIT)
1346 {
b7ff98dd 1347 if (SINGLE_STEP || (SCM_TRACE_P && SCM_TRACED_FRAME_P (debug)))
6dbd0af5
MD
1348 {
1349 SINGLE_STEP = 0;
b7ff98dd
MD
1350 SCM_RESET_DEBUG_MODE;
1351 SCM_CLEAR_TRACED_FRAME (debug);
6dbd0af5
MD
1352 scm_make_cont (&t.arg1);
1353 if (!setjmp (SCM_JMPBUF (t.arg1)))
1354 scm_ithrow (scm_i_exit_tail, scm_cons (t.arg1, SCM_EOL), 0);
1355 }
1356 }
1357nextframe:
1358#endif
b7ff98dd
MD
1359 SCM_CLEAR_ARGSREADY (debug);
1360 if (SCM_OVERFLOWP (debug))
6dbd0af5
MD
1361 --debug.info;
1362 else if (++debug.info == (scm_debug_info *) &debug.info)
1363 {
b7ff98dd 1364 SCM_SET_OVERFLOW (debug);
6dbd0af5
MD
1365 debug.info -= 2;
1366 }
1367start:
1368 debug.info->e.exp = x;
1369 debug.info->e.env = env;
1370 if (CHECK_ENTRY)
b7ff98dd 1371 if (SCM_ENTER_FRAME_P || (SCM_BREAKPOINTS_P && SRCBRKP (x)))
6dbd0af5 1372 {
b7ff98dd
MD
1373 SCM tail = SCM_TAILRECP (debug) ? SCM_BOOL_T : SCM_BOOL_F;
1374 SCM_SET_TAILREC (debug);
1375 SCM_ENTER_FRAME_P = 0;
1376 SCM_RESET_DEBUG_MODE;
1377 if (SCM_CHEAPTRAPS_P)
6dbd0af5
MD
1378 t.arg1 = scm_make_debugobj ((scm_debug_frame *) &debug);
1379 else
1380 {
1381 scm_make_cont (&t.arg1);
1382 if (setjmp (SCM_JMPBUF (t.arg1)))
1383 {
1384 x = SCM_THROW_VALUE (t.arg1);
1385 if (SCM_IMP (x))
1386 {
1387 RETURN (x);
1388 }
1389 else
1390 /* This gives the possibility for the debugger to
1391 modify the source expression before evaluation. */
1392 goto dispatch;
1393 }
1394 }
1395 scm_ithrow (scm_i_enter_frame,
1396 scm_cons2 (t.arg1, tail,
1397 scm_cons (scm_unmemocopy (x, env), SCM_EOL)),
1398 0);
1399 }
1400dispatch:
1401#endif
0f2d19dd 1402 SCM_ASYNC_TICK;
0f2d19dd
JB
1403 switch (SCM_TYP7 (x))
1404 {
1405 case scm_tcs_symbols:
1406 /* Only happens when called at top level.
1407 */
1408 x = scm_cons (x, SCM_UNDEFINED);
1409 goto retval;
1410
1411 case (127 & SCM_IM_AND):
1412 x = SCM_CDR (x);
1413 t.arg1 = x;
1414 while (SCM_NNULLP (t.arg1 = SCM_CDR (t.arg1)))
1415 if (SCM_FALSEP (EVALCAR (x, env)))
1416 {
1417 RETURN (SCM_BOOL_F);
1418 }
1419 else
1420 x = t.arg1;
6dbd0af5 1421 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
0f2d19dd
JB
1422 goto carloop;
1423
1424 case (127 & SCM_IM_BEGIN):
6dbd0af5
MD
1425 cdrxnoap:
1426 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
0f2d19dd
JB
1427 cdrxbegin:
1428 x = SCM_CDR (x);
1429
1430 begin:
1431 t.arg1 = x;
1432 while (SCM_NNULLP (t.arg1 = SCM_CDR (t.arg1)))
1433 {
1434 SIDEVAL (SCM_CAR (x), env);
1435 x = t.arg1;
1436 }
1437
1438 carloop: /* scm_eval car of last form in list */
1439 if (SCM_NCELLP (SCM_CAR (x)))
1440 {
1441 x = SCM_CAR (x);
6dbd0af5 1442 RETURN (SCM_IMP (x) ? EVALIM (x, env) : SCM_GLOC_VAL (x))
0f2d19dd
JB
1443 }
1444
1445 if (SCM_SYMBOLP (SCM_CAR (x)))
1446 {
1447 retval:
6dbd0af5 1448 RETURN (*scm_lookupcar (x, env))
0f2d19dd
JB
1449 }
1450
1451 x = SCM_CAR (x);
1452 goto loop; /* tail recurse */
1453
1454
1455 case (127 & SCM_IM_CASE):
1456 x = SCM_CDR (x);
1457 t.arg1 = EVALCAR (x, env);
1458 while (SCM_NIMP (x = SCM_CDR (x)))
1459 {
1460 proc = SCM_CAR (x);
1461 if (scm_i_else == SCM_CAR (proc))
1462 {
1463 x = SCM_CDR (proc);
6dbd0af5 1464 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
0f2d19dd
JB
1465 goto begin;
1466 }
1467 proc = SCM_CAR (proc);
1468 while (SCM_NIMP (proc))
1469 {
1470 if (CHECK_EQVISH (SCM_CAR (proc), t.arg1))
1471 {
1472 x = SCM_CDR (SCM_CAR (x));
6dbd0af5 1473 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
0f2d19dd
JB
1474 goto begin;
1475 }
1476 proc = SCM_CDR (proc);
1477 }
1478 }
6dbd0af5 1479 RETURN (SCM_UNSPECIFIED)
0f2d19dd
JB
1480
1481
1482 case (127 & SCM_IM_COND):
1483 while (SCM_NIMP (x = SCM_CDR (x)))
1484 {
1485 proc = SCM_CAR (x);
1486 t.arg1 = EVALCAR (proc, env);
1487 if (SCM_NFALSEP (t.arg1))
1488 {
1489 x = SCM_CDR (proc);
6dbd0af5 1490 if SCM_NULLP (x)
0f2d19dd 1491 {
6dbd0af5 1492 RETURN (t.arg1)
0f2d19dd
JB
1493 }
1494 if (scm_i_arrow != SCM_CAR (x))
6dbd0af5
MD
1495 {
1496 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
1497 goto begin;
1498 }
0f2d19dd
JB
1499 proc = SCM_CDR (x);
1500 proc = EVALCAR (proc, env);
1501 SCM_ASRTGO (SCM_NIMP (proc), badfun);
6dbd0af5
MD
1502 PREP_APPLY (proc, scm_cons (t.arg1, SCM_EOL));
1503 ENTER_APPLY;
0f2d19dd
JB
1504 goto evap1;
1505 }
1506 }
6dbd0af5 1507 RETURN (SCM_UNSPECIFIED)
0f2d19dd
JB
1508
1509
1510 case (127 & SCM_IM_DO):
1511 x = SCM_CDR (x);
1512 proc = SCM_CAR (SCM_CDR (x)); /* inits */
1513 t.arg1 = SCM_EOL; /* values */
1514 while (SCM_NIMP (proc))
1515 {
1516 t.arg1 = scm_cons (EVALCAR (proc, env), t.arg1);
1517 proc = SCM_CDR (proc);
1518 }
e2806c10 1519 env = EXTEND_ENV (SCM_CAR (x), t.arg1, env);
0f2d19dd
JB
1520 x = SCM_CDR (SCM_CDR (x));
1521 while (proc = SCM_CAR (x), SCM_FALSEP (EVALCAR (proc, env)))
1522 {
1523 for (proc = SCM_CAR (SCM_CDR (x)); SCM_NIMP (proc); proc = SCM_CDR (proc))
1524 {
1525 t.arg1 = SCM_CAR (proc); /* body */
1526 SIDEVAL (t.arg1, env);
1527 }
1528 for (t.arg1 = SCM_EOL, proc = SCM_CDR (SCM_CDR (x)); SCM_NIMP (proc); proc = SCM_CDR (proc))
1529 t.arg1 = scm_cons (EVALCAR (proc, env), t.arg1); /* steps */
e2806c10 1530 env = EXTEND_ENV (SCM_CAR (SCM_CAR (env)), t.arg1, SCM_CDR (env));
0f2d19dd
JB
1531 }
1532 x = SCM_CDR (proc);
1533 if (SCM_NULLP (x))
6dbd0af5
MD
1534 RETURN (SCM_UNSPECIFIED);
1535 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
0f2d19dd
JB
1536 goto begin;
1537
1538
1539 case (127 & SCM_IM_IF):
1540 x = SCM_CDR (x);
1541 if (SCM_NFALSEP (EVALCAR (x, env)))
1542 x = SCM_CDR (x);
1543 else if (SCM_IMP (x = SCM_CDR (SCM_CDR (x))))
1544 {
1545 RETURN (SCM_UNSPECIFIED);
1546 }
6dbd0af5 1547 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
0f2d19dd
JB
1548 goto carloop;
1549
1550
1551 case (127 & SCM_IM_LET):
1552 x = SCM_CDR (x);
1553 proc = SCM_CAR (SCM_CDR (x));
1554 t.arg1 = SCM_EOL;
1555 do
1556 {
1557 t.arg1 = scm_cons (EVALCAR (proc, env), t.arg1);
1558 }
1559 while (SCM_NIMP (proc = SCM_CDR (proc)));
e2806c10 1560 env = EXTEND_ENV (SCM_CAR (x), t.arg1, env);
0f2d19dd 1561 x = SCM_CDR (x);
6dbd0af5 1562 goto cdrxnoap;
0f2d19dd
JB
1563
1564
1565 case (127 & SCM_IM_LETREC):
1566 x = SCM_CDR (x);
e2806c10 1567 env = EXTEND_ENV (SCM_CAR (x), scm_undefineds, env);
0f2d19dd
JB
1568 x = SCM_CDR (x);
1569 proc = SCM_CAR (x);
1570 t.arg1 = SCM_EOL;
1571 do
1572 {
1573 t.arg1 = scm_cons (EVALCAR (proc, env), t.arg1);
1574 }
1575 while (SCM_NIMP (proc = SCM_CDR (proc)));
1576 SCM_CDR (SCM_CAR (env)) = t.arg1;
6dbd0af5 1577 goto cdrxnoap;
0f2d19dd
JB
1578
1579
1580 case (127 & SCM_IM_LETSTAR):
1581 x = SCM_CDR (x);
1582 proc = SCM_CAR (x);
1583 if (SCM_IMP (proc))
1584 {
e2806c10 1585 env = EXTEND_ENV (SCM_EOL, SCM_EOL, env);
6dbd0af5 1586 goto cdrxnoap;
0f2d19dd
JB
1587 }
1588 do
1589 {
1590 t.arg1 = SCM_CAR (proc);
1591 proc = SCM_CDR (proc);
e2806c10 1592 env = EXTEND_ENV (t.arg1, EVALCAR (proc, env), env);
0f2d19dd
JB
1593 }
1594 while (SCM_NIMP (proc = SCM_CDR (proc)));
6dbd0af5 1595 goto cdrxnoap;
0f2d19dd
JB
1596
1597 case (127 & SCM_IM_OR):
1598 x = SCM_CDR (x);
1599 t.arg1 = x;
1600 while (SCM_NNULLP (t.arg1 = SCM_CDR (t.arg1)))
1601 {
1602 x = EVALCAR (x, env);
1603 if (SCM_NFALSEP (x))
1604 {
1605 RETURN (x);
1606 }
1607 x = t.arg1;
1608 }
6dbd0af5 1609 PREP_APPLY (SCM_UNDEFINED, SCM_EOL);
0f2d19dd
JB
1610 goto carloop;
1611
1612
1613 case (127 & SCM_IM_LAMBDA):
1614 RETURN (scm_closure (SCM_CDR (x), env));
1615
1616
1617 case (127 & SCM_IM_QUOTE):
1618 RETURN (SCM_CAR (SCM_CDR (x)));
1619
1620
1621 case (127 & SCM_IM_SET):
0f2d19dd
JB
1622 x = SCM_CDR (x);
1623 proc = SCM_CAR (x);
6dbd0af5 1624 switch (7 & (int) proc)
0f2d19dd
JB
1625 {
1626 case 0:
1627 t.lloc = scm_lookupcar (x, env);
1628 break;
1629 case 1:
1630 t.lloc = &SCM_GLOC_VAL (proc);
1631 break;
1632#ifdef MEMOIZE_LOCALS
1633 case 4:
1634 t.lloc = scm_ilookup (proc, env);
1635 break;
1636#endif
1637 }
1638 x = SCM_CDR (x);
1639 *t.lloc = EVALCAR (x, env);
0f2d19dd
JB
1640#ifdef SICP
1641 RETURN (*t.lloc);
1642#else
1643 RETURN (SCM_UNSPECIFIED);
1644#endif
1645
1646
1647 case (127 & SCM_IM_DEFINE): /* only for internal defines */
1648 x = SCM_CDR (x);
1649 proc = SCM_CAR (x);
1650 x = SCM_CDR (x);
1651 x = evalcar (x, env);
6dbd0af5 1652#ifdef DEBUG_EXTENSIONS
b7ff98dd 1653 if (SCM_REC_PROCNAMES_P && SCM_NIMP (x) && SCM_CLOSUREP (x))
6dbd0af5
MD
1654 scm_set_procedure_property_x (x, scm_i_name, proc);
1655#endif
0f2d19dd
JB
1656 env = SCM_CAR (env);
1657 SCM_DEFER_INTS;
1658 SCM_CAR (env) = scm_cons (proc, SCM_CAR (env));
1659 SCM_CDR (env) = scm_cons (x, SCM_CDR (env));
1660 SCM_ALLOW_INTS;
1661 RETURN (SCM_UNSPECIFIED);
1662
1663
1664
1665 /* new syntactic forms go here. */
1666 case (127 & SCM_MAKISYM (0)):
1667 proc = SCM_CAR (x);
1668 SCM_ASRTGO (SCM_ISYMP (proc), badfun);
1669 switch SCM_ISYMNUM (proc)
1670 {
1671#if 0
1672 case (SCM_ISYMNUM (IM_VREF)):
1673 {
1674 SCM var;
1675 var = SCM_CAR (SCM_CDR (x));
1676 RETURN (SCM_CDR(var));
1677 }
1678 case (SCM_ISYMNUM (IM_VSET)):
1679 SCM_CDR (SCM_CAR ( SCM_CDR (x))) = EVALCAR( SCM_CDR ( SCM_CDR (x)), env);
1680 SCM_CAR (SCM_CAR ( SCM_CDR (x))) = scm_tc16_variable;
6dbd0af5 1681 RETURN (SCM_UNSPECIFIED)
0f2d19dd
JB
1682#endif
1683
1684 case (SCM_ISYMNUM (SCM_IM_APPLY)):
1685 proc = SCM_CDR (x);
1686 proc = EVALCAR (proc, env);
1687 SCM_ASRTGO (SCM_NIMP (proc), badfun);
1688 if (SCM_CLOSUREP (proc))
1689 {
6dbd0af5 1690 PREP_APPLY (proc, SCM_EOL);
0f2d19dd
JB
1691 t.arg1 = SCM_CDR (SCM_CDR (x));
1692 t.arg1 = EVALCAR (t.arg1, env);
6dbd0af5
MD
1693#ifdef DEVAL
1694 debug.info->a.args = t.arg1;
1695#endif
0f2d19dd
JB
1696#ifndef RECKLESS
1697 if (scm_badargsp (SCM_CAR (SCM_CODE (proc)), t.arg1))
1698 goto wrongnumargs;
1699#endif
e2806c10 1700 env = EXTEND_ENV (SCM_CAR (SCM_CODE (proc)), t.arg1, SCM_ENV (proc));
0f2d19dd
JB
1701 x = SCM_CODE (proc);
1702 goto cdrxbegin;
1703 }
1704 proc = scm_i_apply;
1705 goto evapply;
1706
1707 case (SCM_ISYMNUM (SCM_IM_CONT)):
1708 scm_make_cont (&t.arg1);
1709 if (setjmp (SCM_JMPBUF (t.arg1)))
1710 {
1711 SCM val;
1712 val = SCM_THROW_VALUE (t.arg1);
6dbd0af5 1713 RETURN (val);
0f2d19dd
JB
1714 }
1715 proc = SCM_CDR (x);
1716 proc = evalcar (proc, env);
1717 SCM_ASRTGO (SCM_NIMP (proc), badfun);
6dbd0af5
MD
1718 PREP_APPLY (proc, scm_cons (t.arg1, SCM_EOL));
1719 ENTER_APPLY;
0f2d19dd
JB
1720 goto evap1;
1721
1722 default:
1723 goto badfun;
1724 }
1725
1726 default:
1727 proc = x;
1728 badfun:
f5bf2977 1729 /* scm_everr (x, env,...) */
01f61221 1730 scm_error (scm_misc_error_key,
f5bf2977
GH
1731 NULL,
1732 "Wrong type to apply: %S",
1733 scm_listify (proc, SCM_UNDEFINED),
1734 SCM_BOOL_F);
0f2d19dd
JB
1735 case scm_tc7_vector:
1736 case scm_tc7_wvect:
1737 case scm_tc7_bvect:
1738 case scm_tc7_byvect:
1739 case scm_tc7_svect:
1740 case scm_tc7_ivect:
1741 case scm_tc7_uvect:
1742 case scm_tc7_fvect:
1743 case scm_tc7_dvect:
1744 case scm_tc7_cvect:
1745#ifdef LONGLONGS
1746 case scm_tc7_llvect:
1747#endif
1748 case scm_tc7_string:
1749 case scm_tc7_mb_string:
1750 case scm_tc7_substring:
1751 case scm_tc7_mb_substring:
1752 case scm_tc7_smob:
1753 case scm_tcs_closures:
1754 case scm_tcs_subrs:
1755 RETURN (x);
1756
1757#ifdef MEMOIZE_LOCALS
1758 case (127 & SCM_ILOC00):
1759 proc = *scm_ilookup (SCM_CAR (x), env);
1760 SCM_ASRTGO (SCM_NIMP (proc), badfun);
1761#ifndef RECKLESS
1762#ifdef CAUTIOUS
1763 goto checkargs;
1764#endif
1765#endif
1766 break;
1767#endif /* ifdef MEMOIZE_LOCALS */
1768
1769
1770 case scm_tcs_cons_gloc:
1771 proc = SCM_GLOC_VAL (SCM_CAR (x));
1772 SCM_ASRTGO (SCM_NIMP (proc), badfun);
1773#ifndef RECKLESS
1774#ifdef CAUTIOUS
1775 goto checkargs;
1776#endif
1777#endif
1778 break;
1779
1780
1781 case scm_tcs_cons_nimcar:
1782 if (SCM_SYMBOLP (SCM_CAR (x)))
1783 {
1784 proc = *scm_lookupcar (x, env);
1785 if (SCM_IMP (proc))
1786 {
1787 unmemocar (x, env);
1788 goto badfun;
1789 }
1790 if (scm_tc16_macro == SCM_TYP16 (proc))
1791 {
1792 unmemocar (x, env);
1793
1794 handle_a_macro:
1795 t.arg1 = SCM_APPLY (SCM_CDR (proc), x, scm_cons (env, scm_listofnull));
1796 switch ((int) (SCM_CAR (proc) >> 16))
1797 {
1798 case 2:
1799 if (scm_ilength (t.arg1) <= 0)
1800 t.arg1 = scm_cons2 (SCM_IM_BEGIN, t.arg1, SCM_EOL);
6dbd0af5
MD
1801#ifdef DEVAL
1802 if (!SCM_CLOSUREP (SCM_CDR (proc)))
1803 {
1804#if 0 /* Top-level defines doesn't very often occur in backtraces */
1805 if (scm_m_define == SCM_SUBRF (SCM_CDR (proc)) && SCM_TOP_LEVEL (env))
1806 /* Prevent memoizing result of define macro */
1807 {
1808 debug.info->e.exp = scm_cons (SCM_CAR (x), SCM_CDR (x));
1809 scm_set_source_properties_x (debug.info->e.exp,
1810 scm_source_properties (x));
1811 }
1812#endif
1813 SCM_DEFER_INTS;
1814 SCM_CAR (x) = SCM_CAR (t.arg1);
1815 SCM_CDR (x) = SCM_CDR (t.arg1);
1816 SCM_ALLOW_INTS;
1817 goto dispatch;
1818 }
1819 /* Prevent memoizing of debug info expression. */
1820 debug.info->e.exp = scm_cons (SCM_CAR (x), SCM_CDR (x));
1821 scm_set_source_properties_x (debug.info->e.exp,
1822 scm_source_properties (x));
1823#endif
0f2d19dd
JB
1824 SCM_DEFER_INTS;
1825 SCM_CAR (x) = SCM_CAR (t.arg1);
1826 SCM_CDR (x) = SCM_CDR (t.arg1);
1827 SCM_ALLOW_INTS;
6dbd0af5 1828 goto loopnoap;
0f2d19dd
JB
1829 case 1:
1830 if (SCM_NIMP (x = t.arg1))
6dbd0af5 1831 goto loopnoap;
0f2d19dd
JB
1832 case 0:
1833 RETURN (t.arg1);
1834 }
1835 }
1836 }
1837 else
1838 proc = SCM_CEVAL (SCM_CAR (x), env);
1839 SCM_ASRTGO (SCM_NIMP (proc), badfun);
1840#ifndef RECKLESS
1841#ifdef CAUTIOUS
1842 checkargs:
1843#endif
1844 if (SCM_CLOSUREP (proc))
1845 {
1846 arg2 = SCM_CAR (SCM_CODE (proc));
1847 t.arg1 = SCM_CDR (x);
1848 while (SCM_NIMP (arg2))
1849 {
1850 if (SCM_NCONSP (arg2))
1851 goto evapply;
1852 if (SCM_IMP (t.arg1))
1853 goto umwrongnumargs;
1854 arg2 = SCM_CDR (arg2);
1855 t.arg1 = SCM_CDR (t.arg1);
1856 }
1857 if (SCM_NNULLP (t.arg1))
1858 goto umwrongnumargs;
1859 }
1860 else if (scm_tc16_macro == SCM_TYP16 (proc))
1861 goto handle_a_macro;
1862#endif
1863 }
1864
1865
6dbd0af5
MD
1866evapply:
1867 PREP_APPLY (proc, SCM_EOL);
1868 if (SCM_NULLP (SCM_CDR (x))) {
1869 ENTER_APPLY;
0f2d19dd
JB
1870 switch (SCM_TYP7 (proc))
1871 { /* no arguments given */
1872 case scm_tc7_subr_0:
1873 RETURN (SCM_SUBRF (proc) ());
1874 case scm_tc7_subr_1o:
1875 RETURN (SCM_SUBRF (proc) (SCM_UNDEFINED));
1876 case scm_tc7_lsubr:
1877 RETURN (SCM_SUBRF (proc) (SCM_EOL));
1878 case scm_tc7_rpsubr:
1879 RETURN (SCM_BOOL_T);
1880 case scm_tc7_asubr:
1881 RETURN (SCM_SUBRF (proc) (SCM_UNDEFINED, SCM_UNDEFINED));
6dbd0af5 1882#ifdef CCLO
0f2d19dd
JB
1883 case scm_tc7_cclo:
1884 t.arg1 = proc;
1885 proc = SCM_CCLO_SUBR (proc);
6dbd0af5
MD
1886#ifdef DEVAL
1887 debug.info->a.proc = proc;
1888 debug.info->a.args = scm_cons (t.arg1, SCM_EOL);
1889#endif
0f2d19dd 1890 goto evap1;
6dbd0af5 1891#endif
0f2d19dd
JB
1892 case scm_tcs_closures:
1893 x = SCM_CODE (proc);
e2806c10 1894 env = EXTEND_ENV (SCM_CAR (x), SCM_EOL, SCM_ENV (proc));
0f2d19dd
JB
1895 goto cdrxbegin;
1896 case scm_tc7_contin:
1897 case scm_tc7_subr_1:
1898 case scm_tc7_subr_2:
1899 case scm_tc7_subr_2o:
1900 case scm_tc7_cxr:
1901 case scm_tc7_subr_3:
1902 case scm_tc7_lsubr_2:
1903 umwrongnumargs:
1904 unmemocar (x, env);
1905 wrongnumargs:
f5bf2977
GH
1906 /* scm_everr (x, env,...) */
1907 scm_wrong_num_args (proc);
0f2d19dd
JB
1908 default:
1909 /* handle macros here */
1910 goto badfun;
1911 }
6dbd0af5 1912 }
0f2d19dd
JB
1913
1914 /* must handle macros by here */
1915 x = SCM_CDR (x);
1916#ifdef CAUTIOUS
1917 if (SCM_IMP (x))
1918 goto wrongnumargs;
1919#endif
1920 t.arg1 = EVALCAR (x, env);
6dbd0af5
MD
1921#ifdef DEVAL
1922 debug.info->a.args = scm_cons (t.arg1, SCM_EOL);
1923#endif
0f2d19dd
JB
1924 x = SCM_CDR (x);
1925 if (SCM_NULLP (x))
1926 {
6dbd0af5 1927 ENTER_APPLY;
0f2d19dd
JB
1928 evap1:
1929 switch (SCM_TYP7 (proc))
6dbd0af5 1930 { /* have one argument in t.arg1 */
0f2d19dd
JB
1931 case scm_tc7_subr_2o:
1932 RETURN (SCM_SUBRF (proc) (t.arg1, SCM_UNDEFINED));
1933 case scm_tc7_subr_1:
1934 case scm_tc7_subr_1o:
1935 RETURN (SCM_SUBRF (proc) (t.arg1));
1936 case scm_tc7_cxr:
1937#ifdef SCM_FLOATS
1938 if (SCM_SUBRF (proc))
1939 {
1940 if (SCM_INUMP (t.arg1))
1941 {
1942 RETURN (scm_makdbl (SCM_DSUBRF (proc) ((double) SCM_INUM (t.arg1)),
1943 0.0));
1944 }
1945 SCM_ASRTGO (SCM_NIMP (t.arg1), floerr);
1946 if (SCM_REALP (t.arg1))
1947 {
1948 RETURN (scm_makdbl (SCM_DSUBRF (proc) (SCM_REALPART (t.arg1)), 0.0));
1949 }
1950#ifdef SCM_BIGDIG
1951 if (SCM_BIGP (t.arg1))
1952 {
1953 RETURN (scm_makdbl (SCM_DSUBRF (proc) (scm_big2dbl (t.arg1)), 0.0));
1954 }
1955#endif
1956 floerr:
1957 scm_wta (t.arg1, (char *) SCM_ARG1, SCM_CHARS (SCM_SNAME (proc)));
1958 }
1959#endif
1960 proc = (SCM) SCM_SNAME (proc);
1961 {
1962 char *chrs = SCM_CHARS (proc) + SCM_LENGTH (proc) - 1;
1963 while ('c' != *--chrs)
1964 {
1965 SCM_ASSERT (SCM_NIMP (t.arg1) && SCM_CONSP (t.arg1),
1966 t.arg1, SCM_ARG1, SCM_CHARS (proc));
1967 t.arg1 = ('a' == *chrs) ? SCM_CAR (t.arg1) : SCM_CDR (t.arg1);
1968 }
1969 RETURN (t.arg1);
1970 }
1971 case scm_tc7_rpsubr:
1972 RETURN (SCM_BOOL_T);
1973 case scm_tc7_asubr:
1974 RETURN (SCM_SUBRF (proc) (t.arg1, SCM_UNDEFINED));
1975 case scm_tc7_lsubr:
1976#ifdef DEVAL
6dbd0af5 1977 RETURN (SCM_SUBRF (proc) (debug.info->a.args))
0f2d19dd
JB
1978#else
1979 RETURN (SCM_SUBRF (proc) (scm_cons (t.arg1, SCM_EOL)));
1980#endif
6dbd0af5 1981#ifdef CCLO
0f2d19dd
JB
1982 case scm_tc7_cclo:
1983 arg2 = t.arg1;
1984 t.arg1 = proc;
1985 proc = SCM_CCLO_SUBR (proc);
6dbd0af5
MD
1986#ifdef DEVAL
1987 debug.info->a.args = scm_cons (t.arg1, debug.info->a.args);
1988 debug.info->a.proc = proc;
1989#endif
0f2d19dd 1990 goto evap2;
6dbd0af5 1991#endif
0f2d19dd
JB
1992 case scm_tcs_closures:
1993 x = SCM_CODE (proc);
1994#ifdef DEVAL
e2806c10 1995 env = EXTEND_ENV (SCM_CAR (x), debug.info->a.args, SCM_ENV (proc));
0f2d19dd 1996#else
e2806c10 1997 env = EXTEND_ENV (SCM_CAR (x), scm_cons (t.arg1, SCM_EOL), SCM_ENV (proc));
0f2d19dd
JB
1998#endif
1999 goto cdrxbegin;
2000 case scm_tc7_contin:
2001 scm_call_continuation (proc, t.arg1);
2002 case scm_tc7_subr_2:
2003 case scm_tc7_subr_0:
2004 case scm_tc7_subr_3:
2005 case scm_tc7_lsubr_2:
2006 goto wrongnumargs;
2007 default:
2008 goto badfun;
2009 }
2010 }
2011#ifdef CAUTIOUS
2012 if (SCM_IMP (x))
2013 goto wrongnumargs;
2014#endif
2015 { /* have two or more arguments */
2016 arg2 = EVALCAR (x, env);
6dbd0af5
MD
2017#ifdef DEVAL
2018 debug.info->a.args = scm_cons2 (t.arg1, arg2, SCM_EOL);
2019#endif
0f2d19dd
JB
2020 x = SCM_CDR (x);
2021 if (SCM_NULLP (x)) {
6dbd0af5 2022 ENTER_APPLY;
0f2d19dd
JB
2023#ifdef CCLO
2024 evap2:
2025#endif
6dbd0af5
MD
2026 switch (SCM_TYP7 (proc))
2027 { /* have two arguments */
2028 case scm_tc7_subr_2:
2029 case scm_tc7_subr_2o:
2030 RETURN (SCM_SUBRF (proc) (t.arg1, arg2));
2031 case scm_tc7_lsubr:
0f2d19dd 2032#ifdef DEVAL
6dbd0af5
MD
2033 RETURN (SCM_SUBRF (proc) (debug.info->a.args))
2034#else
2035 RETURN (SCM_SUBRF (proc) (scm_cons2 (t.arg1, arg2, SCM_EOL)));
0f2d19dd 2036#endif
6dbd0af5
MD
2037 case scm_tc7_lsubr_2:
2038 RETURN (SCM_SUBRF (proc) (t.arg1, arg2, SCM_EOL));
2039 case scm_tc7_rpsubr:
2040 case scm_tc7_asubr:
2041 RETURN (SCM_SUBRF (proc) (t.arg1, arg2));
2042#ifdef CCLO
2043 cclon:
2044 case scm_tc7_cclo:
0f2d19dd 2045#ifdef DEVAL
6dbd0af5
MD
2046 RETURN (SCM_APPLY (SCM_CCLO_SUBR (proc), proc,
2047 scm_cons (debug.info->a.args, SCM_EOL)));
0f2d19dd 2048#else
6dbd0af5
MD
2049 RETURN (SCM_APPLY (SCM_CCLO_SUBR (proc), proc,
2050 scm_cons2 (t.arg1, arg2,
2051 scm_cons (scm_eval_args (x, env), SCM_EOL))));
0f2d19dd 2052#endif
6dbd0af5
MD
2053 /* case scm_tc7_cclo:
2054 x = scm_cons(arg2, scm_eval_args(x, env));
2055 arg2 = t.arg1;
2056 t.arg1 = proc;
2057 proc = SCM_CCLO_SUBR(proc);
2058 goto evap3; */
2059#endif
2060 case scm_tc7_subr_0:
2061 case scm_tc7_cxr:
2062 case scm_tc7_subr_1o:
2063 case scm_tc7_subr_1:
2064 case scm_tc7_subr_3:
2065 case scm_tc7_contin:
2066 goto wrongnumargs;
2067 default:
2068 goto badfun;
2069 case scm_tcs_closures:
0f2d19dd 2070#ifdef DEVAL
e2806c10 2071 env = EXTEND_ENV (SCM_CAR (SCM_CODE (proc)), debug.info->a.args, SCM_ENV (proc));
0f2d19dd 2072#else
e2806c10 2073 env = EXTEND_ENV (SCM_CAR (SCM_CODE (proc)), scm_cons2 (t.arg1, arg2, SCM_EOL), SCM_ENV (proc));
0f2d19dd 2074#endif
6dbd0af5
MD
2075 x = SCM_CODE (proc);
2076 goto cdrxbegin;
2077 }
0f2d19dd
JB
2078 }
2079#ifdef DEVAL
6dbd0af5
MD
2080 debug.info->a.args = scm_cons2 (t.arg1, arg2,
2081 scm_deval_args (x, env, &SCM_CDR (SCM_CDR (debug.info->a.args))));
0f2d19dd 2082#endif
6dbd0af5
MD
2083 ENTER_APPLY;
2084 switch (SCM_TYP7 (proc))
2085 { /* have 3 or more arguments */
0f2d19dd 2086#ifdef DEVAL
6dbd0af5
MD
2087 case scm_tc7_subr_3:
2088 SCM_ASRTGO (SCM_NULLP (SCM_CDR (x)), wrongnumargs);
2089 RETURN (SCM_SUBRF (proc) (t.arg1, arg2, SCM_CAR (SCM_CDR (SCM_CDR (debug.info->a.args)))));
2090 case scm_tc7_asubr:
2091 /* t.arg1 = SCM_SUBRF(proc)(t.arg1, arg2);
2092 while SCM_NIMP(x) {
2093 t.arg1 = SCM_SUBRF(proc)(t.arg1, EVALCAR(x, env));
2094 x = SCM_CDR(x);
2095 }
2096 RETURN (t.arg1) */
2097 case scm_tc7_rpsubr:
2098 RETURN (SCM_APPLY (proc, t.arg1, scm_acons (arg2, SCM_CDR (SCM_CDR (debug.info->a.args)), SCM_EOL)))
2099 case scm_tc7_lsubr_2:
2100 RETURN (SCM_SUBRF (proc) (t.arg1, arg2, SCM_CDR (SCM_CDR (debug.info->a.args))))
2101 case scm_tc7_lsubr:
2102 RETURN (SCM_SUBRF (proc) (debug.info->a.args))
0f2d19dd 2103#ifdef CCLO
6dbd0af5
MD
2104 case scm_tc7_cclo:
2105 goto cclon;
0f2d19dd 2106#endif
6dbd0af5 2107 case scm_tcs_closures:
b7ff98dd 2108 SCM_SET_ARGSREADY (debug);
e2806c10 2109 env = EXTEND_ENV (SCM_CAR (SCM_CODE (proc)),
6dbd0af5
MD
2110 debug.info->a.args,
2111 SCM_ENV (proc));
2112 x = SCM_CODE (proc);
2113 goto cdrxbegin;
2114#else /* DEVAL */
2115 case scm_tc7_subr_3:
2116 SCM_ASRTGO (SCM_NULLP (SCM_CDR (x)), wrongnumargs);
2117 RETURN (SCM_SUBRF (proc) (t.arg1, arg2, EVALCAR (x, env)));
2118 case scm_tc7_asubr:
2119 /* t.arg1 = SCM_SUBRF(proc)(t.arg1, arg2);
2120 while SCM_NIMP(x) {
2121 t.arg1 = SCM_SUBRF(proc)(t.arg1, EVALCAR(x, env));
2122 x = SCM_CDR(x);
2123 }
2124 RETURN (t.arg1) */
2125 case scm_tc7_rpsubr:
2126 RETURN (SCM_APPLY (proc, t.arg1, scm_acons (arg2, scm_eval_args (x, env), SCM_EOL)));
2127 case scm_tc7_lsubr_2:
2128 RETURN (SCM_SUBRF (proc) (t.arg1, arg2, scm_eval_args (x, env)));
2129 case scm_tc7_lsubr:
2130 RETURN (SCM_SUBRF (proc) (scm_cons2 (t.arg1, arg2, scm_eval_args (x, env))));
0f2d19dd 2131#ifdef CCLO
6dbd0af5
MD
2132 case scm_tc7_cclo:
2133 goto cclon;
0f2d19dd 2134#endif
6dbd0af5
MD
2135 case scm_tcs_closures:
2136#ifdef DEVAL
b7ff98dd 2137 SCM_SET_ARGSREADY (debug);
6dbd0af5 2138#endif
e2806c10 2139 env = EXTEND_ENV (SCM_CAR (SCM_CODE (proc)),
6dbd0af5
MD
2140 scm_cons2 (t.arg1, arg2, scm_eval_args (x, env)),
2141 SCM_ENV (proc));
2142 x = SCM_CODE (proc);
2143 goto cdrxbegin;
0f2d19dd 2144#endif /* DEVAL */
6dbd0af5
MD
2145 case scm_tc7_subr_2:
2146 case scm_tc7_subr_1o:
2147 case scm_tc7_subr_2o:
2148 case scm_tc7_subr_0:
2149 case scm_tc7_cxr:
2150 case scm_tc7_subr_1:
2151 case scm_tc7_contin:
2152 goto wrongnumargs;
2153 default:
2154 goto badfun;
2155 }
0f2d19dd
JB
2156 }
2157#ifdef DEVAL
6dbd0af5
MD
2158exit:
2159 if (CHECK_EXIT)
b7ff98dd 2160 if (SCM_EXIT_FRAME_P || (SCM_TRACE_P && SCM_TRACED_FRAME_P (debug)))
6dbd0af5 2161 {
b7ff98dd
MD
2162 SCM_EXIT_FRAME_P = 0;
2163 SCM_RESET_DEBUG_MODE;
2164 SCM_CLEAR_TRACED_FRAME (debug);
2165 if (SCM_CHEAPTRAPS_P)
6dbd0af5
MD
2166 t.arg1 = scm_make_debugobj ((scm_debug_frame *) &debug);
2167 else
2168 {
2169 scm_make_cont (&t.arg1);
2170 if (setjmp (SCM_JMPBUF (t.arg1)))
2171 {
2172 proc = SCM_THROW_VALUE (t.arg1);
2173 goto ret;
2174 }
2175 }
2176 scm_ithrow (scm_i_exit_frame, scm_cons2 (t.arg1, proc, SCM_EOL), 0);
2177 }
2178ret:
1646d37b 2179 scm_last_debug_frame = debug.prev;
0f2d19dd
JB
2180 return proc;
2181#endif
2182}
2183
6dbd0af5
MD
2184
2185/* SECTION: This code is compiled once.
2186 */
2187
0f2d19dd
JB
2188#ifndef DEVAL
2189
2190SCM_PROC(s_procedure_documentation, "procedure-documentation", 1, 0, 0, scm_procedure_documentation);
1cc91f1b 2191
0f2d19dd
JB
2192SCM
2193scm_procedure_documentation (proc)
2194 SCM proc;
0f2d19dd
JB
2195{
2196 SCM code;
2197 SCM_ASSERT (SCM_BOOL_T == scm_procedure_p (proc) && SCM_NIMP (proc) && SCM_TYP7 (proc) != scm_tc7_contin,
2198 proc, SCM_ARG1, s_procedure_documentation);
2199 switch (SCM_TYP7 (proc))
2200 {
2201 case scm_tcs_closures:
2202 code = SCM_CDR (SCM_CODE (proc));
2203 if (SCM_IMP (SCM_CDR (code)))
2204 return SCM_BOOL_F;
2205 code = SCM_CAR (code);
2206 if (SCM_IMP (code))
2207 return SCM_BOOL_F;
2208 if (SCM_STRINGP (code))
2209 return code;
2210 default:
2211 return SCM_BOOL_F;
2212/*
2213 case scm_tcs_subrs:
2214#ifdef CCLO
2215 case scm_tc7_cclo:
2216#endif
2217*/
2218 }
2219}
2220
b145c172
JB
2221/* This code processes the 'arg ...' parameters to apply.
2222
2223 (apply PROC ARG1 ... ARGS)
2224
2225 The ARG1 ... arguments are consed on to the front of ARGS (which
2226 must be a list), and then PROC is applied to the elements of the
2227 result. apply:nconc2last takes care of building the list of
2228 arguments, given (ARG1 ... ARGS).
2229
2230 apply:nconc2last destroys its argument. On that topic, this code
2231 came into my care with the following beautifully cryptic comment on
2232 that topic: "This will only screw you if you do (scm_apply
2233 scm_apply '( ... ))" If you know what they're referring to, send
2234 me a patch to this comment. */
2235
0f2d19dd 2236SCM_PROC(s_nconc2last, "apply:nconc2last", 1, 0, 0, scm_nconc2last);
1cc91f1b 2237
0f2d19dd
JB
2238SCM
2239scm_nconc2last (lst)
2240 SCM lst;
0f2d19dd
JB
2241{
2242 SCM *lloc;
b145c172 2243 SCM_ASSERT (scm_ilength (lst) > 0, lst, SCM_ARG1, s_nconc2last);
0f2d19dd
JB
2244 lloc = &lst;
2245 while (SCM_NNULLP (SCM_CDR (*lloc)))
b145c172
JB
2246 lloc = &SCM_CDR (*lloc);
2247 SCM_ASSERT (scm_ilength (SCM_CAR (*lloc)) >= 0, lst, SCM_ARG1, s_nconc2last);
0f2d19dd
JB
2248 *lloc = SCM_CAR (*lloc);
2249 return lst;
2250}
2251
2252#endif /* !DEVAL */
2253
6dbd0af5
MD
2254
2255/* SECTION: When DEVAL is defined this code yields scm_dapply.
2256 * It is compiled twice.
2257 */
2258
0f2d19dd 2259#if 0
1cc91f1b 2260
0f2d19dd
JB
2261SCM
2262scm_apply (proc, arg1, args)
2263 SCM proc;
2264 SCM arg1;
2265 SCM args;
0f2d19dd
JB
2266{}
2267#endif
2268
2269#if 0
1cc91f1b 2270
0f2d19dd
JB
2271SCM
2272scm_dapply (proc, arg1, args)
2273 SCM proc;
2274 SCM arg1;
2275 SCM args;
0f2d19dd
JB
2276{}
2277#endif
2278
1cc91f1b 2279
0f2d19dd
JB
2280SCM
2281SCM_APPLY (proc, arg1, args)
2282 SCM proc;
2283 SCM arg1;
2284 SCM args;
0f2d19dd
JB
2285{
2286#ifdef DEBUG_EXTENSIONS
2287#ifdef DEVAL
6dbd0af5 2288 scm_debug_frame debug;
1646d37b 2289 debug.prev = scm_last_debug_frame;
b7ff98dd 2290 debug.status = SCM_APPLYFRAME;
6dbd0af5
MD
2291 debug.vect[0].a.proc = proc;
2292 debug.vect[0].a.args = SCM_EOL;
1646d37b 2293 scm_last_debug_frame = &debug;
0f2d19dd 2294#else
b7ff98dd 2295 if (SCM_DEBUGGINGP)
0f2d19dd
JB
2296 return scm_dapply (proc, arg1, args);
2297#endif
2298#endif
2299
2300 SCM_ASRTGO (SCM_NIMP (proc), badproc);
2301 if (SCM_NULLP (args))
2302 {
2303 if (SCM_NULLP (arg1))
2304 arg1 = SCM_UNDEFINED;
2305 else
2306 {
2307 args = SCM_CDR (arg1);
2308 arg1 = SCM_CAR (arg1);
2309 }
2310 }
2311 else
2312 {
2313 /* SCM_ASRTGO(SCM_NIMP(args) && SCM_CONSP(args), wrongnumargs); */
2314 args = scm_nconc2last (args);
2315 }
0f2d19dd 2316#ifdef DEVAL
6dbd0af5 2317 debug.vect[0].a.args = scm_cons (arg1, args);
b7ff98dd 2318 if (SCM_ENTER_FRAME_P)
6dbd0af5
MD
2319 {
2320 SCM tmp;
b7ff98dd
MD
2321 SCM_ENTER_FRAME_P = 0;
2322 SCM_RESET_DEBUG_MODE;
2323 if (SCM_CHEAPTRAPS_P)
6dbd0af5
MD
2324 tmp = scm_make_debugobj ((scm_debug_frame *) &debug);
2325 else
2326 {
2327 scm_make_cont (&tmp);
2328 if (setjmp (SCM_JMPBUF (tmp)))
2329 goto entap;
2330 }
2331 scm_ithrow (scm_i_enter_frame, scm_cons (tmp, SCM_EOL), 0);
2332 }
2333entap:
2334 ENTER_APPLY;
2335#endif
2336#ifdef CCLO
2337tail:
0f2d19dd
JB
2338#endif
2339 switch (SCM_TYP7 (proc))
2340 {
2341 case scm_tc7_subr_2o:
2342 args = SCM_NULLP (args) ? SCM_UNDEFINED : SCM_CAR (args);
2343 RETURN (SCM_SUBRF (proc) (arg1, args))
2344 case scm_tc7_subr_2:
2345 SCM_ASRTGO (SCM_NULLP (SCM_CDR (args)), wrongnumargs);
2346 args = SCM_CAR (args);
2347 RETURN (SCM_SUBRF (proc) (arg1, args))
2348 case scm_tc7_subr_0:
2349 SCM_ASRTGO (SCM_UNBNDP (arg1), wrongnumargs);
2350 RETURN (SCM_SUBRF (proc) ())
2351 case scm_tc7_subr_1:
2352 case scm_tc7_subr_1o:
2353 SCM_ASRTGO (SCM_NULLP (args), wrongnumargs);
2354 RETURN (SCM_SUBRF (proc) (arg1))
2355 case scm_tc7_cxr:
2356 SCM_ASRTGO (SCM_NULLP (args), wrongnumargs);
2357#ifdef SCM_FLOATS
2358 if (SCM_SUBRF (proc))
2359 {
6dbd0af5
MD
2360 if (SCM_INUMP (arg1))
2361 {
2362 RETURN (scm_makdbl (SCM_DSUBRF (proc) ((double) SCM_INUM (arg1)), 0.0));
2363 }
0f2d19dd 2364 SCM_ASRTGO (SCM_NIMP (arg1), floerr);
6dbd0af5
MD
2365 if (SCM_REALP (arg1))
2366 {
2367 RETURN (scm_makdbl (SCM_DSUBRF (proc) (SCM_REALPART (arg1)), 0.0));
2368 }
0f2d19dd
JB
2369#ifdef SCM_BIGDIG
2370 if SCM_BIGP
2371 (arg1)
2372 RETURN (scm_makdbl (SCM_DSUBRF (proc) (scm_big2dbl (arg1)), 0.0))
2373#endif
2374 floerr:
2375 scm_wta (arg1, (char *) SCM_ARG1, SCM_CHARS (SCM_SNAME (proc)));
2376 }
2377#endif
2378 proc = (SCM) SCM_SNAME (proc);
2379 {
2380 char *chrs = SCM_CHARS (proc) + SCM_LENGTH (proc) - 1;
2381 while ('c' != *--chrs)
2382 {
2383 SCM_ASSERT (SCM_NIMP (arg1) && SCM_CONSP (arg1),
2384 arg1, SCM_ARG1, SCM_CHARS (proc));
2385 arg1 = ('a' == *chrs) ? SCM_CAR (arg1) : SCM_CDR (arg1);
2386 }
2387 RETURN (arg1)
2388 }
2389 case scm_tc7_subr_3:
2390 RETURN (SCM_SUBRF (proc) (arg1, SCM_CAR (args), SCM_CAR (SCM_CDR (args))))
2391 case scm_tc7_lsubr:
2392#ifdef DEVAL
6dbd0af5 2393 RETURN (SCM_SUBRF (proc) (SCM_UNBNDP (arg1) ? SCM_EOL : debug.vect[0].a.args))
0f2d19dd
JB
2394#else
2395 RETURN (SCM_SUBRF (proc) (SCM_UNBNDP (arg1) ? SCM_EOL : scm_cons (arg1, args)))
2396#endif
2397 case scm_tc7_lsubr_2:
2398 SCM_ASRTGO (SCM_NIMP (args) && SCM_CONSP (args), wrongnumargs);
2399 RETURN (SCM_SUBRF (proc) (arg1, SCM_CAR (args), SCM_CDR (args)))
2400 case scm_tc7_asubr:
2401 if (SCM_NULLP (args))
2402 RETURN (SCM_SUBRF (proc) (arg1, SCM_UNDEFINED))
2403 while (SCM_NIMP (args))
2404 {
2405 SCM_ASSERT (SCM_CONSP (args), args, SCM_ARG2, "apply");
2406 arg1 = SCM_SUBRF (proc) (arg1, SCM_CAR (args));
2407 args = SCM_CDR (args);
2408 }
2409 RETURN (arg1);
2410 case scm_tc7_rpsubr:
2411 if (SCM_NULLP (args))
2412 RETURN (SCM_BOOL_T);
2413 while (SCM_NIMP (args))
2414 {
2415 SCM_ASSERT (SCM_CONSP (args), args, SCM_ARG2, "apply");
2416 if (SCM_FALSEP (SCM_SUBRF (proc) (arg1, SCM_CAR (args))))
2417 RETURN (SCM_BOOL_F);
2418 arg1 = SCM_CAR (args);
2419 args = SCM_CDR (args);
2420 }
2421 RETURN (SCM_BOOL_T);
2422 case scm_tcs_closures:
2423#ifdef DEVAL
6dbd0af5 2424 arg1 = (SCM_UNBNDP (arg1) ? SCM_EOL : debug.vect[0].a.args);
0f2d19dd
JB
2425#else
2426 arg1 = (SCM_UNBNDP (arg1) ? SCM_EOL : scm_cons (arg1, args));
2427#endif
2428#ifndef RECKLESS
2429 if (scm_badargsp (SCM_CAR (SCM_CODE (proc)), arg1))
2430 goto wrongnumargs;
2431#endif
e2806c10 2432 args = EXTEND_ENV (SCM_CAR (SCM_CODE (proc)), arg1, SCM_ENV (proc));
0f2d19dd
JB
2433 proc = SCM_CODE (proc);
2434 while (SCM_NNULLP (proc = SCM_CDR (proc)))
2435 arg1 = EVALCAR (proc, args);
2436 RETURN (arg1);
2437 case scm_tc7_contin:
2438 SCM_ASRTGO (SCM_NULLP (args), wrongnumargs);
2439 scm_call_continuation (proc, arg1);
2440#ifdef CCLO
2441 case scm_tc7_cclo:
2442#ifdef DEVAL
6dbd0af5
MD
2443 args = (SCM_UNBNDP(arg1) ? SCM_EOL : debug.vect[0].a.args);
2444 arg1 = proc;
2445 proc = SCM_CCLO_SUBR (proc);
2446 debug.vect[0].a.proc = proc;
2447 debug.vect[0].a.args = scm_cons (arg1, args);
0f2d19dd
JB
2448#else
2449 args = (SCM_UNBNDP(arg1) ? SCM_EOL : scm_cons (arg1, args));
0f2d19dd
JB
2450 arg1 = proc;
2451 proc = SCM_CCLO_SUBR (proc);
6dbd0af5 2452#endif
0f2d19dd
JB
2453 goto tail;
2454#endif
2455 wrongnumargs:
f5bf2977 2456 scm_wrong_num_args (proc);
0f2d19dd
JB
2457 default:
2458 badproc:
2459 scm_wta (proc, (char *) SCM_ARG1, "apply");
2460 RETURN (arg1);
2461 }
2462#ifdef DEVAL
6dbd0af5
MD
2463exit:
2464 if (CHECK_EXIT)
b7ff98dd 2465 if (SCM_EXIT_FRAME_P || (SCM_TRACE_P && SCM_TRACED_FRAME_P (debug)))
6dbd0af5 2466 {
b7ff98dd
MD
2467 SCM_EXIT_FRAME_P = 0;
2468 SCM_RESET_DEBUG_MODE;
2469 SCM_CLEAR_TRACED_FRAME (debug);
2470 if (SCM_CHEAPTRAPS_P)
6dbd0af5
MD
2471 arg1 = scm_make_debugobj ((scm_debug_frame *) &debug);
2472 else
2473 {
2474 scm_make_cont (&arg1);
2475 if (setjmp (SCM_JMPBUF (arg1)))
2476 {
2477 proc = SCM_THROW_VALUE (arg1);
2478 goto ret;
2479 }
2480 }
2481 scm_ithrow (scm_i_exit_frame, scm_cons2 (arg1, proc, SCM_EOL), 0);
2482 }
2483ret:
1646d37b 2484 scm_last_debug_frame = debug.prev;
0f2d19dd
JB
2485 return proc;
2486#endif
2487}
2488
6dbd0af5
MD
2489
2490/* SECTION: The rest of this file is only read once.
2491 */
2492
0f2d19dd
JB
2493#ifndef DEVAL
2494
2495SCM_PROC(s_map, "map", 2, 0, 1, scm_map);
1cc91f1b 2496
0f2d19dd
JB
2497SCM
2498scm_map (proc, arg1, args)
2499 SCM proc;
2500 SCM arg1;
2501 SCM args;
0f2d19dd
JB
2502{
2503 long i;
2504 SCM res = SCM_EOL;
2505 SCM *pres = &res;
2506 SCM *ve = &args; /* Keep args from being optimized away. */
2507
2508 if (SCM_NULLP (arg1))
2509 return res;
2510 SCM_ASSERT (SCM_NIMP (arg1), arg1, SCM_ARG2, s_map);
2511 if (SCM_NULLP (args))
2512 {
2513 while (SCM_NIMP (arg1))
2514 {
2515 SCM_ASSERT (SCM_CONSP (arg1), arg1, SCM_ARG2, s_map);
2516 *pres = scm_cons (scm_apply (proc, SCM_CAR (arg1), scm_listofnull), SCM_EOL);
2517 pres = &SCM_CDR (*pres);
2518 arg1 = SCM_CDR (arg1);
2519 }
2520 return res;
2521 }
2522 args = scm_vector (scm_cons (arg1, args));
2523 ve = SCM_VELTS (args);
2524#ifndef RECKLESS
2525 for (i = SCM_LENGTH (args) - 1; i >= 0; i--)
2526 SCM_ASSERT (SCM_NIMP (ve[i]) && SCM_CONSP (ve[i]), args, SCM_ARG2, s_map);
2527#endif
2528 while (1)
2529 {
2530 arg1 = SCM_EOL;
2531 for (i = SCM_LENGTH (args) - 1; i >= 0; i--)
2532 {
2533 if SCM_IMP
2534 (ve[i]) return res;
2535 arg1 = scm_cons (SCM_CAR (ve[i]), arg1);
2536 ve[i] = SCM_CDR (ve[i]);
2537 }
2538 *pres = scm_cons (scm_apply (proc, arg1, SCM_EOL), SCM_EOL);
2539 pres = &SCM_CDR (*pres);
2540 }
2541}
2542
2543
2544SCM_PROC(s_for_each, "for-each", 2, 0, 1, scm_for_each);
1cc91f1b 2545
0f2d19dd
JB
2546SCM
2547scm_for_each (proc, arg1, args)
2548 SCM proc;
2549 SCM arg1;
2550 SCM args;
0f2d19dd
JB
2551{
2552 SCM *ve = &args; /* Keep args from being optimized away. */
2553 long i;
2554 if SCM_NULLP (arg1)
2555 return SCM_UNSPECIFIED;
2556 SCM_ASSERT (SCM_NIMP (arg1), arg1, SCM_ARG2, s_for_each);
2557 if SCM_NULLP (args)
2558 {
2559 while SCM_NIMP (arg1)
2560 {
2561 SCM_ASSERT (SCM_CONSP (arg1), arg1, SCM_ARG2, s_for_each);
2562 scm_apply (proc, SCM_CAR (arg1), scm_listofnull);
2563 arg1 = SCM_CDR (arg1);
2564 }
2565 return SCM_UNSPECIFIED;
2566 }
2567 args = scm_vector (scm_cons (arg1, args));
2568 ve = SCM_VELTS (args);
2569#ifndef RECKLESS
2570 for (i = SCM_LENGTH (args) - 1; i >= 0; i--)
2571 SCM_ASSERT (SCM_NIMP (ve[i]) && SCM_CONSP (ve[i]), args, SCM_ARG2, s_for_each);
2572#endif
2573 while (1)
2574 {
2575 arg1 = SCM_EOL;
2576 for (i = SCM_LENGTH (args) - 1; i >= 0; i--)
2577 {
2578 if SCM_IMP
2579 (ve[i]) return SCM_UNSPECIFIED;
2580 arg1 = scm_cons (SCM_CAR (ve[i]), arg1);
2581 ve[i] = SCM_CDR (ve[i]);
2582 }
2583 scm_apply (proc, arg1, SCM_EOL);
2584 }
2585}
2586
2587
1cc91f1b 2588
0f2d19dd
JB
2589SCM
2590scm_closure (code, env)
2591 SCM code;
2592 SCM env;
0f2d19dd
JB
2593{
2594 register SCM z;
2595 SCM_NEWCELL (z);
2596 SCM_SETCODE (z, code);
2597 SCM_ENV (z) = env;
2598 return z;
2599}
2600
2601
2602long scm_tc16_promise;
1cc91f1b 2603
0f2d19dd
JB
2604SCM
2605scm_makprom (code)
2606 SCM code;
0f2d19dd
JB
2607{
2608 register SCM z;
2609 SCM_NEWCELL (z);
2610 SCM_CDR (z) = code;
2611 SCM_CAR (z) = scm_tc16_promise;
2612 return z;
2613}
2614
2615
1cc91f1b
JB
2616
2617static int prinprom SCM_P ((SCM exp, SCM port, scm_print_state *pstate));
2618
0f2d19dd 2619static int
19402679 2620prinprom (exp, port, pstate)
0f2d19dd
JB
2621 SCM exp;
2622 SCM port;
19402679 2623 scm_print_state *pstate;
0f2d19dd 2624{
19402679 2625 int writingp = SCM_WRITINGP (pstate);
0f2d19dd 2626 scm_gen_puts (scm_regular_string, "#<promise ", port);
19402679
MD
2627 SCM_SET_WRITINGP (pstate, 1);
2628 scm_iprin1 (SCM_CDR (exp), port, pstate);
2629 SCM_SET_WRITINGP (pstate, writingp);
0f2d19dd
JB
2630 scm_gen_putc ('>', port);
2631 return !0;
2632}
2633
2634
2635SCM_PROC(s_makacro, "procedure->syntax", 1, 0, 0, scm_makacro);
1cc91f1b 2636
0f2d19dd
JB
2637SCM
2638scm_makacro (code)
2639 SCM code;
0f2d19dd
JB
2640{
2641 register SCM z;
2642 SCM_NEWCELL (z);
2643 SCM_CDR (z) = code;
2644 SCM_CAR (z) = scm_tc16_macro;
2645 return z;
2646}
2647
2648
2649SCM_PROC(s_makmacro, "procedure->macro", 1, 0, 0, scm_makmacro);
1cc91f1b 2650
0f2d19dd
JB
2651SCM
2652scm_makmacro (code)
2653 SCM code;
0f2d19dd
JB
2654{
2655 register SCM z;
2656 SCM_NEWCELL (z);
2657 SCM_CDR (z) = code;
2658 SCM_CAR (z) = scm_tc16_macro | (1L << 16);
2659 return z;
2660}
2661
2662
2663SCM_PROC(s_makmmacro, "procedure->memoizing-macro", 1, 0, 0, scm_makmmacro);
1cc91f1b 2664
0f2d19dd
JB
2665SCM
2666scm_makmmacro (code)
2667 SCM code;
0f2d19dd
JB
2668{
2669 register SCM z;
2670 SCM_NEWCELL (z);
2671 SCM_CDR (z) = code;
2672 SCM_CAR (z) = scm_tc16_macro | (2L << 16);
2673 return z;
2674}
2675
2676
1cc91f1b
JB
2677
2678static int prinmacro SCM_P ((SCM exp, SCM port, scm_print_state *pstate));
2679
0f2d19dd 2680static int
19402679 2681prinmacro (exp, port, pstate)
0f2d19dd
JB
2682 SCM exp;
2683 SCM port;
19402679 2684 scm_print_state *pstate;
0f2d19dd 2685{
19402679 2686 int writingp = SCM_WRITINGP (pstate);
0f2d19dd
JB
2687 if (SCM_CAR (exp) & (3L << 16))
2688 scm_gen_puts (scm_regular_string, "#<macro", port);
2689 else
2690 scm_gen_puts (scm_regular_string, "#<syntax", port);
2691 if (SCM_CAR (exp) & (2L << 16))
2692 scm_gen_putc ('!', port);
2693 scm_gen_putc (' ', port);
19402679
MD
2694 SCM_SET_WRITINGP (pstate, 1);
2695 scm_iprin1 (SCM_CDR (exp), port, pstate);
2696 SCM_SET_WRITINGP (pstate, writingp);
0f2d19dd
JB
2697 scm_gen_putc ('>', port);
2698 return !0;
2699}
2700
2701SCM_PROC(s_force, "force", 1, 0, 0, scm_force);
1cc91f1b 2702
0f2d19dd
JB
2703SCM
2704scm_force (x)
2705 SCM x;
0f2d19dd
JB
2706{
2707 SCM_ASSERT ((SCM_TYP16 (x) == scm_tc16_promise), x, SCM_ARG1, s_force);
2708 if (!((1L << 16) & SCM_CAR (x)))
2709 {
2710 SCM ans = scm_apply (SCM_CDR (x), SCM_EOL, SCM_EOL);
2711 if (!((1L << 16) & SCM_CAR (x)))
2712 {
2713 SCM_DEFER_INTS;
2714 SCM_CDR (x) = ans;
2715 SCM_CAR (x) |= (1L << 16);
2716 SCM_ALLOW_INTS;
2717 }
2718 }
2719 return SCM_CDR (x);
2720}
2721
2722SCM_PROC (s_promise_p, "promise?", 1, 0, 0, scm_promise_p);
1cc91f1b 2723
0f2d19dd
JB
2724SCM
2725scm_promise_p (x)
2726 SCM x;
0f2d19dd
JB
2727{
2728 return ((SCM_NIMP (x) && (SCM_TYP16 (x) == scm_tc16_promise))
2729 ? SCM_BOOL_T
2730 : SCM_BOOL_F);
2731}
2732
2733SCM_PROC(s_copy_tree, "copy-tree", 1, 0, 0, scm_copy_tree);
1cc91f1b 2734
0f2d19dd
JB
2735SCM
2736scm_copy_tree (obj)
2737 SCM obj;
0f2d19dd
JB
2738{
2739 SCM ans, tl;
2740 if SCM_IMP
2741 (obj) return obj;
2742 if (SCM_VECTORP (obj))
2743 {
2744 scm_sizet i = SCM_LENGTH (obj);
2745 ans = scm_make_vector (SCM_MAKINUM (i), SCM_UNSPECIFIED, SCM_UNDEFINED);
2746 while (i--)
2747 SCM_VELTS (ans)[i] = scm_copy_tree (SCM_VELTS (obj)[i]);
2748 return ans;
2749 }
2750 if SCM_NCONSP (obj)
2751 return obj;
2752/* return scm_cons(scm_copy_tree(SCM_CAR(obj)), scm_copy_tree(SCM_CDR(obj))); */
2753 ans = tl = scm_cons (scm_copy_tree (SCM_CAR (obj)), SCM_UNSPECIFIED);
2754 while (SCM_NIMP (obj = SCM_CDR (obj)) && SCM_CONSP (obj))
2755 tl = (SCM_CDR (tl) = scm_cons (scm_copy_tree (SCM_CAR (obj)), SCM_UNSPECIFIED));
2756 SCM_CDR (tl) = obj;
2757 return ans;
2758}
2759
1cc91f1b 2760
0f2d19dd
JB
2761SCM
2762scm_eval_3 (obj, copyp, env)
2763 SCM obj;
2764 int copyp;
2765 SCM env;
0f2d19dd
JB
2766{
2767 if (SCM_NIMP (SCM_CDR (scm_system_transformer)))
2768 obj = scm_apply (SCM_CDR (scm_system_transformer), obj, scm_listofnull);
2769 else if (copyp)
2770 obj = scm_copy_tree (obj);
6dbd0af5 2771 return XEVAL (obj, env);
0f2d19dd
JB
2772}
2773
1cc91f1b 2774
0f2d19dd
JB
2775SCM
2776scm_top_level_env (thunk)
2777 SCM thunk;
0f2d19dd
JB
2778{
2779 if (SCM_IMP(thunk))
2780 return SCM_EOL;
2781 else
2782 return scm_cons(thunk, (SCM)SCM_EOL);
2783}
2784
2785SCM_PROC(s_eval2, "eval2", 2, 0, 0, scm_eval2);
1cc91f1b 2786
0f2d19dd
JB
2787SCM
2788scm_eval2 (obj, env_thunk)
2789 SCM obj;
2790 SCM env_thunk;
0f2d19dd
JB
2791{
2792 return scm_eval_3 (obj, 1, scm_top_level_env(env_thunk));
2793}
2794
2795SCM_PROC(s_eval, "eval", 1, 0, 0, scm_eval);
1cc91f1b 2796
0f2d19dd
JB
2797SCM
2798scm_eval (obj)
2799 SCM obj;
0f2d19dd
JB
2800{
2801 return
2802 scm_eval_3(obj, 1, scm_top_level_env(SCM_CDR(scm_top_level_lookup_thunk_var)));
2803}
2804
2805SCM_PROC(s_eval_x, "eval!", 1, 0, 0, scm_eval_x);
1cc91f1b 2806
0f2d19dd
JB
2807SCM
2808scm_eval_x (obj)
2809 SCM obj;
0f2d19dd
JB
2810{
2811 return
2812 scm_eval_3(obj,
2813 0,
2814 scm_top_level_env (SCM_CDR (scm_top_level_lookup_thunk_var)));
2815}
2816
2817SCM_PROC (s_macro_eval_x, "macro-eval!", 2, 0, 0, scm_macro_eval_x);
1cc91f1b 2818
0f2d19dd
JB
2819SCM
2820scm_macro_eval_x (exp, env)
2821 SCM exp;
2822 SCM env;
0f2d19dd
JB
2823{
2824 return scm_eval_3 (exp, 0, env);
2825}
2826
1cc91f1b 2827
0f2d19dd
JB
2828SCM
2829scm_definedp (x, env)
2830 SCM x;
2831 SCM env;
0f2d19dd
JB
2832{
2833 SCM proc = SCM_CAR (x = SCM_CDR (x));
2834 if (SCM_ISYMP (proc))
2835 return SCM_BOOL_T;
2836 else if(SCM_IMP(proc) || !SCM_SYMBOLP(proc))
2837 return SCM_BOOL_F;
2838 else
2839 {
2840 SCM vcell = scm_sym2vcell(proc, env_top_level(env), SCM_BOOL_F);
2841 return (vcell == SCM_BOOL_F || SCM_UNBNDP(SCM_CDR(vcell))) ? SCM_BOOL_F : SCM_BOOL_T;
2842 }
2843}
2844
2845static scm_smobfuns promsmob =
2846{scm_markcdr, scm_free0, prinprom};
2847
2848static scm_smobfuns macrosmob =
2849{scm_markcdr, scm_free0, prinmacro};
2850
1cc91f1b 2851
0f2d19dd
JB
2852SCM
2853scm_make_synt (name, macroizer, fcn)
2854 char *name;
2855 SCM (*macroizer) ();
2856 SCM (*fcn) ();
0f2d19dd
JB
2857{
2858 SCM symcell = scm_sysintern (name, SCM_UNDEFINED);
2859 long tmp = ((((SCM_CELLPTR) (SCM_CAR (symcell))) - scm_heap_org) << 8);
2860 register SCM z;
2861 if ((tmp >> 8) != ((SCM_CELLPTR) (SCM_CAR (symcell)) - scm_heap_org))
2862 tmp = 0;
2863 SCM_NEWCELL (z);
2864 SCM_SUBRF (z) = fcn;
2865 SCM_CAR (z) = tmp + scm_tc7_subr_2;
2866 SCM_CDR (symcell) = macroizer (z);
2867 return SCM_CAR (symcell);
2868}
2869
6dbd0af5
MD
2870
2871/* At this point, scm_deval and scm_dapply are generated.
2872 */
2873
0f2d19dd 2874#ifdef DEBUG_EXTENSIONS
6dbd0af5
MD
2875# define DEVAL
2876# include "eval.c"
0f2d19dd
JB
2877#endif
2878
2879
1cc91f1b 2880
0f2d19dd
JB
2881void
2882scm_init_eval ()
0f2d19dd 2883{
0f2d19dd
JB
2884 scm_tc16_promise = scm_newsmob (&promsmob);
2885 scm_tc16_macro = scm_newsmob (&macrosmob);
2886 scm_i_apply = scm_make_subr ("apply", scm_tc7_lsubr_2, scm_apply);
2887 scm_system_transformer = scm_sysintern ("scm:eval-transformer", SCM_UNDEFINED);
2888 scm_i_dot = SCM_CAR (scm_sysintern (".", SCM_UNDEFINED));
2889 scm_i_arrow = SCM_CAR (scm_sysintern ("=>", SCM_UNDEFINED));
2890 scm_i_else = SCM_CAR (scm_sysintern ("else", SCM_UNDEFINED));
2891 scm_i_unquote = SCM_CAR (scm_sysintern ("unquote", SCM_UNDEFINED));
2892 scm_i_uq_splicing = SCM_CAR (scm_sysintern ("unquote-splicing", SCM_UNDEFINED));
2893
2894 /* acros */
2895 scm_i_quasiquote = scm_make_synt (s_quasiquote, scm_makacro, scm_m_quasiquote);
6dbd0af5 2896 scm_make_synt (s_undefine, scm_makacro, scm_m_undefine);
0f2d19dd
JB
2897 scm_make_synt (s_delay, scm_makacro, scm_m_delay);
2898 /* end of acros */
2899
2900 scm_top_level_lookup_thunk_var =
2901 scm_sysintern("*top-level-lookup-thunk*", SCM_BOOL_F);
2902
6dbd0af5
MD
2903 scm_i_and = scm_make_synt ("and", scm_makmmacro, scm_m_and);
2904 scm_i_begin = scm_make_synt ("begin", scm_makmmacro, scm_m_begin);
2905 scm_i_case = scm_make_synt ("case", scm_makmmacro, scm_m_case);
2906 scm_i_cond = scm_make_synt ("cond", scm_makmmacro, scm_m_cond);
2907 scm_i_define = scm_make_synt ("define", scm_makmmacro, scm_m_define);
2908 scm_i_do = scm_make_synt ("do", scm_makmmacro, scm_m_do);
2909 scm_i_if = scm_make_synt ("if", scm_makmmacro, scm_m_if);
0f2d19dd
JB
2910 scm_i_lambda = scm_make_synt ("lambda", scm_makmmacro, scm_m_lambda);
2911 scm_i_let = scm_make_synt ("let", scm_makmmacro, scm_m_let);
6dbd0af5
MD
2912 scm_i_letrec = scm_make_synt ("letrec", scm_makmmacro, scm_m_letrec);
2913 scm_i_letstar = scm_make_synt ("let*", scm_makmmacro, scm_m_letstar);
2914 scm_i_or = scm_make_synt ("or", scm_makmmacro, scm_m_or);
0f2d19dd 2915 scm_i_quote = scm_make_synt ("quote", scm_makmmacro, scm_m_quote);
6dbd0af5
MD
2916 scm_i_set = scm_make_synt ("set!", scm_makmmacro, scm_m_set);
2917 scm_i_atapply = scm_make_synt ("@apply", scm_makmmacro, scm_m_apply);
2918 scm_i_atcall_cc = scm_make_synt ("@call-with-current-continuation",
2919 scm_makmmacro, scm_m_cont);
2920
0f2d19dd
JB
2921 scm_make_synt ("defined?", scm_makmmacro, scm_definedp);
2922 scm_i_name = SCM_CAR (scm_sysintern ("name", SCM_UNDEFINED));
2923 scm_permanent_object (scm_i_name);
6dbd0af5
MD
2924
2925#ifdef DEBUG_EXTENSIONS
2926 scm_i_enter_frame = SCM_CAR (scm_sysintern ("enter-frame", SCM_UNDEFINED));
2927 scm_i_apply_frame = SCM_CAR (scm_sysintern ("apply-frame", SCM_UNDEFINED));
2928 scm_i_exit_frame = SCM_CAR (scm_sysintern ("exit-frame", SCM_UNDEFINED));
2929 scm_i_trace = SCM_CAR (scm_sysintern ("trace", SCM_UNDEFINED));
2930#endif
2931
0f2d19dd
JB
2932#include "eval.x"
2933}
0f2d19dd 2934
6dbd0af5 2935#endif /* !DEVAL */