home *** CD-ROM | disk | FTP | other *** search
- /* lisp.c -- Core of the Lisp, reading and evaluating...
- Copyright (C) 1993, 1994 John Harper <jsh@ukc.ac.uk>
-
- This file is part of Jade.
-
- Jade is free software; you can redistribute it and/or modify it
- under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 2, or (at your option)
- any later version.
-
- Jade is distributed in the hope that it will be useful, but
- WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with Jade; see the file COPYING. If not, write to
- the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
-
- #include "jade.h"
- #include "jade_protos.h"
-
- #include <string.h>
- #include <stdlib.h>
- #include <ctype.h>
-
- _PR VALUE readlispexp(VALUE, int *);
-
- _PR VALUE evallambda(VALUE, VALUE, bool);
- _PR VALUE funcall(VALUE, VALUE);
- _PR VALUE evalstring(u_char *, bool);
-
- _PR VALUE calllisp0(VALUE);
- _PR VALUE calllisp1(VALUE, VALUE);
- _PR VALUE calllisp2(VALUE, VALUE, VALUE);
-
- _PR void lisp_prin(VALUE, VALUE);
- _PR void string_princ(VALUE, VALUE);
- _PR void string_print(VALUE, VALUE);
-
- _PR VALUE findmemberbyindex(VALUE, int);
- _PR VALUE movedownlist(VALUE, int);
- _PR int listlen(VALUE);
- _PR VALUE copylist(VALUE);
- _PR VALUE handlevarint(VALUE, long *);
-
- _PR void handleerror(VALUE, VALUE);
- _PR void signalargerror(VALUE, int);
-
- _PR void lisp_init(void);
-
- _PR VALUE sym_debug_entry, sym_debug_exit, sym_debug_error_entry;
- VALUE sym_debug_entry, sym_debug_exit, sym_debug_error_entry;
-
- _PR VALUE sym_quote, sym_lambda, sym_macro, sym_autoload, sym_function;
- VALUE sym_quote, sym_lambda, sym_macro, sym_autoload, sym_function;
-
- _PR VALUE sym_standard_input, sym_standard_output, sym_defun;
- VALUE sym_standard_input, sym_standard_output, sym_defun;
-
- _PR VALUE sym_amp_optional, sym_amp_rest, sym_amp_aux;
- VALUE sym_amp_optional, sym_amp_rest, sym_amp_aux;
-
- /*
- * When a `throw' happens a function stuffs a cons-cell in here with,
- * (TAG . VALUE).
- * An error is the above with TAG=sym_error and VALUE a list of relevant
- * data.
- */
- _PR VALUE ThrowValue;
- VALUE ThrowValue;
-
- _PR VALUE sym_error, sym_error_message, sym_invalid_function;
- _PR VALUE sym_void_function, sym_void_value, sym_bad_arg, sym_invalid_read_syntax;
- _PR VALUE sym_end_of_stream, sym_invalid_lambda_list, sym_missing_arg;
- _PR VALUE sym_invalid_macro, sym_invalid_autoload, sym_no_catcher;
- _PR VALUE sym_buffer_read_only, sym_bad_event_desc, sym_file_error;
- _PR VALUE sym_invalid_stream, sym_setting_constant, sym_process_error;
- _PR VALUE sym_invalid_area;
-
- VALUE sym_error, sym_error_message, sym_invalid_function,
- sym_void_function, sym_void_value, sym_bad_arg, sym_invalid_read_syntax,
- sym_end_of_stream, sym_invalid_lambda_list, sym_missing_arg,
- sym_invalid_macro, sym_invalid_autoload, sym_no_catcher,
- sym_buffer_read_only, sym_bad_event_desc, sym_file_error,
- sym_invalid_stream, sym_setting_constant, sym_process_error,
- sym_invalid_area;
-
- #ifdef MINSTACK
- _PR VALUE sym_stack_error;
- VALUE sym_stack_error;
- #endif
-
- _PR VALUE DebugOnError, sym_error_info;
- VALUE DebugOnError, sym_error_info;
-
- /*
- * When TRUE cmd_eval() calls the "debug-entry" function
- */
- _PR bool SingleStepFlag;
- bool SingleStepFlag;
-
- _PR struct LispCall *LispCallStack;
- struct LispCall *LispCallStack;
-
- static long LispDepth, MaxLispDepth = 250;
-
- /*
- * All of the read-related functions are now stream based. This will
- * probably add some (much?) overhead but I think it's worth it?
- *
- * The `c' variable which keeps coming up is the lookahead character,
- * since each read*() routine normally has to look at the next character
- * to see if it's what it wants. If not, this char is given to someone
- * else...
- */
-
- /*
- * Steps over white space, if a semi-colon is found the rest of the line
- * is ignored.
- */
- static int
- nextlispexp(VALUE strm, int c)
- {
- while(c != EOF)
- {
- switch(c)
- {
- case ' ':
- case '\t':
- case '\n':
- case '\f':
- break;
- case ';':
- while((c = streamgetc(strm)) != EOF)
- {
- if((c == '\n') || (c == '\f'))
- break;
- }
- break;
- default:
- return(c);
- }
- c = streamgetc(strm);
- }
- return(c);
- }
-
- static VALUE
- readlisplist(VALUE strm, int *c_p)
- {
- VALUE result = sym_nil;
- VALUE last = NULL;
- int c = streamgetc(strm);
- c = nextlispexp(strm, c);
- while((c != EOF) && (c != ')') && (c != ']'))
- {
- if(c == '.')
- {
- c = streamgetc(strm);
- if(last)
- {
- if(!(VCDR(last) = readlispexp(strm, &c)))
- return(NULL);
- }
- else
- {
- cmd_signal(sym_invalid_read_syntax,
- LIST_1(MKSTR("Nothing to dot second element of cons-cell to")));
- return(NULL);
- }
- }
- else
- {
- VALUE this;
- if(!(this = cmd_cons(sym_nil, sym_nil)))
- return(NULL);
- if(last)
- VCDR(last) = this;
- else
- result = this;
- if(!(VCAR(this) = readlispexp(strm, &c)))
- return(NULL);
- last = this;
- }
- c = nextlispexp(strm, c);
- }
- if(c == EOF)
- return(cmd_signal(sym_end_of_stream, LIST_1(strm)));
- *c_p = streamgetc(strm);
- return(result);
- }
- /*
- * could be number *or* symbol
- */
- static VALUE
- readlispsymbol(VALUE strm, int *c_p)
- {
- VALUE result;
- u_char buff[256];
- u_char *buf = buff + 1;
- int c = *c_p;
- int i = 0;
- bool couldbenum = TRUE;
- buff[0] = V_StaticString;
- while(c != EOF)
- {
- switch(c)
- {
- case ' ':
- case '\t':
- case '\n':
- case '\f':
- case '(':
- case ')':
- case '[':
- case ']':
- case '\'':
- case '"':
- case ';':
- goto done;
- case '\\':
- couldbenum = FALSE;
- c = streamgetc(strm);
- if(c == EOF)
- return(cmd_signal(sym_end_of_stream, LIST_1(strm)));
- buf[i++] = c;
- break;
- case '|':
- couldbenum = FALSE;
- c = streamgetc(strm);
- while((c != EOF) && (c != '|'))
- {
- buf[i++] = c;
- c = streamgetc(strm);
- }
- if(c == EOF)
- return(cmd_signal(sym_end_of_stream, LIST_1(strm)));
- break;
- default:
- if(couldbenum)
- {
- /*
- * if c isn't a digit (decimal or hex) and c isn't a sign
- * at the start of the string then it's not a number!
- */
- if(!(isdigit(c) || ((i >= 2) && isxdigit(c)) || ((i == 1) && (toupper(c) == 'X'))))
- {
- if(!((i == 0) && ((c == '+') || (c == '-'))))
- couldbenum = FALSE;
- }
- }
- buf[i++] = c;
- }
- c = streamgetc(strm);
- }
- done:
- buf[i] = 0;
- if(couldbenum && ((i > 1) || isdigit(*buf)))
- {
- char *dummy;
- result = newnumber(strtol(buf, &dummy, 0));
- }
- else
- {
- if(!(result = cmd_find_symbol(buff, sym_nil))
- || (NILP(result) && strcmp(buf, "nil")))
- {
- VALUE name;
- if((name = valstrdup(buf)) && (result = cmd_make_symbol(name)))
- result = cmd_intern_symbol(result, sym_nil);
- else
- result = NULL;
- }
- }
- *c_p = c;
- return(result);
- }
- static VALUE
- readlispvector(VALUE strm, int *c_p)
- {
- VALUE result;
- VALUE list = readlisplist(strm, c_p);
- if(list)
- {
- VALUE cur = list;
- int len;
- for(len = 0; CONSP(cur); len++)
- cur = VCDR(cur);
- result = newvector(len);
- if(result)
- {
- int i;
- cur = list;
- for(i = 0; i < len; i++)
- {
- VALUE nxt = VCDR(cur);
- VVECT(result)->vc_Array[i] = VCAR(cur);
- #if 1
- /* I think it's okay to put the cons cells back onto their
- freelist. There can't be any references to them?? */
- cons_free(cur);
- #endif
- cur = nxt;
- }
- }
- else
- result = NULL;
- }
- else
- result = NULL;
- return(result);
- }
- static VALUE
- readlispstr(VALUE strm, int *c_p)
- {
- VALUE result;
- int buflen = 128, i = 0;
- int c = streamgetc(strm);
- u_char *buf = mystralloc(buflen);
- if(buf)
- {
- while((c != EOF) && (c != '"'))
- {
- if(i == buflen)
- {
- int newbuflen = buflen * 2;
- u_char *newbuf = mystralloc(newbuflen);
- if(newbuf)
- {
- memcpy(newbuf, buf, i);
- mystrfree(buf);
- buf = newbuf;
- buflen = newbuflen;
- }
- else
- {
- settitle(NoMemMsg);
- return(NULL);
- }
- }
- if(c == '\\')
- {
- c = streamgetc(strm);
- buf[i++] = escstreamchar(strm, &c);
- }
- else
- {
- buf[i++] = c;
- c = streamgetc(strm);
- }
- }
- if(c == EOF)
- result = cmd_signal(sym_end_of_stream, LIST_1(strm));
- else
- {
- *c_p = streamgetc(strm);
- result = valstrdupn(buf, i);
- }
- mystrfree(buf);
- return(result);
- }
- settitle(NoMemMsg);
- return(NULL);
- }
- /*
- * Using the above readlisp*() functions this classifies each type
- * of expression and translates it into a lisp object (VALUE).
- * Returns NULL in case of error.
- */
- VALUE
- readlispexp(VALUE strm, int *c_p)
- {
- VALUE result;
- int c;
- #ifdef MINSTACK
- if(STK_SIZE <= MINSTACK)
- {
- STK_WARN("read");
- return(cmd_signal(sym_stack_error, sym_nil));
- }
- #endif
- switch(c = nextlispexp(strm, *c_p))
- {
- case EOF:
- *c_p = c;
- return(sym_nil);
- case '\(':
- result = readlisplist(strm, &c);
- break;
- case '\'':
- /*
- * transmogrify 'X into (quote X)
- */
- result = cmd_cons(sym_quote, cmd_cons(sym_nil, sym_nil));
- if(result)
- {
- c = streamgetc(strm);
- if(c == EOF)
- goto eof;
- else if(!(VCAR(VCDR(result)) = readlispexp(strm, &c)))
- result = NULL;
- }
- break;
- case '[':
- result = readlispvector(strm, &c);
- break;
- case '"':
- result = readlispstr(strm, &c);
- break;
- case '?':
- switch(c = streamgetc(strm))
- {
- case EOF:
- goto eof;
- case '\\':
- if((c = streamgetc(strm)) == EOF)
- goto eof;
- else
- result = newnumber(escstreamchar(strm, &c));
- break;
- default:
- result = newnumber(c);
- c = streamgetc(strm);
- }
- break;
- case '#':
- switch(c = streamgetc(strm))
- {
- case EOF:
- goto eof;
- case '\'':
- result = cmd_cons(sym_function, cmd_cons(sym_nil, sym_nil));
- if(result)
- {
- if((c = streamgetc(strm)) == EOF)
- goto eof;
- if(!(VCAR(VCDR(result)) = readlispexp(strm, &c)))
- result = NULL;
- }
- break;
- default:
- result = cmd_signal(sym_invalid_read_syntax, LIST_1(strm));
- }
- break;
- default:
- result = readlispsymbol(strm, &c);
- }
- *c_p = c;
- return(result);
-
- eof:
- return(cmd_signal(sym_end_of_stream, LIST_1(strm)));
- }
-
- /*
- * Evaluates each element of `list' and builds them into a new list.
- */
- static VALUE
- evallist(VALUE list)
- {
- VALUE result = sym_nil;
- VALUE *last = &result;
- GCVAL gcv_result, gcv_list;
- PUSHGC(gcv_result, result);
- PUSHGC(gcv_list, list);
- while(CONSP(list))
- {
- VALUE tmp;
- if(!(tmp = cmd_eval(VCAR(list))))
- {
- result = NULL;
- break;
- }
- if(!(*last = cmd_cons(tmp, sym_nil)))
- {
- result = NULL;
- break;
- }
- list = VCDR(list);
- last = &VCDR(*last);
- }
- if(result && last && !NILP(list))
- *last = cmd_eval(list);
- POPGC; POPGC;
- return(result);
- }
-
- /*
- * format of lambda-lists is something like,
- *
- * [{required-symbols}] [&optional {optional-symbols}] [&rest symbol]
- * [&aux {auxiliary-symbols}]
- *
- * NB: auxiliary symbols are set to nil.
- */
- static VALUE
- bindlambdalist(VALUE lambdaList, VALUE argList, int evalArgs)
- {
- #define STATE_REQUIRED 1
- #define STATE_OPTIONAL 2
- #define STATE_REST 3
- #define STATE_AUX 4
- VALUE boundlist = sym_nil;
- if(CONSP(lambdaList))
- {
- GCVAL gcv_boundlist;
- char state = STATE_REQUIRED;
- PUSHGC(gcv_boundlist, boundlist);
- while(CONSP(lambdaList) && SYMBOLP(VCAR(lambdaList)))
- {
- VALUE argobj;
- VALUE argspec = VCAR(lambdaList);
- if(VSTR(VSYM(argspec)->sym_Name)[0] == '&')
- {
- if(argspec == sym_amp_optional)
- {
- if(state > STATE_OPTIONAL)
- {
- cmd_signal(sym_invalid_lambda_list, LIST_1(lambdaList));
- goto error;
- }
- state = STATE_OPTIONAL;
- lambdaList = VCDR(lambdaList);
- continue;
- }
- else if(argspec == sym_amp_rest)
- {
- if(state > STATE_REST)
- {
- cmd_signal(sym_invalid_lambda_list, LIST_1(lambdaList));
- goto error;
- }
- state = STATE_REST;
- lambdaList = VCDR(lambdaList);
- continue;
- }
- else if(argspec == sym_amp_aux)
- {
- state = STATE_AUX;
- lambdaList = VCDR(lambdaList);
- continue;
- }
- }
- switch(state)
- {
- case STATE_REQUIRED:
- if(!CONSP(argList))
- {
- cmd_signal(sym_missing_arg, LIST_1(argspec));
- goto error;
- }
- /* FALL THROUGH */
- case STATE_OPTIONAL:
- if(CONSP(argList))
- {
- if(evalArgs)
- {
- if(!(argobj = cmd_eval(VCAR(argList))))
- goto error;
- }
- else
- argobj = VCAR(argList);
- argList = VCDR(argList);
- }
- else
- argobj = sym_nil;
- boundlist = bindsymbol(boundlist, argspec, argobj);
- break;
- case STATE_REST:
- if(evalArgs)
- {
- if(!(argobj = evallist(argList)))
- goto error;
- }
- else
- argobj = argList;
- boundlist = bindsymbol(boundlist, argspec, argobj);
- state = STATE_AUX;
- break;
- case STATE_AUX:
- boundlist = bindsymbol(boundlist, argspec, sym_nil);
- }
- lambdaList = VCDR(lambdaList);
- }
- POPGC;
- }
- return(boundlist);
-
- error:
- POPGC;
- unbindsymbols(boundlist);
- return(NULL);
- }
-
- VALUE
- evallambda(VALUE lambdaExp, VALUE argList, bool evalArgs)
- {
- VALUE result = NULL;
- if(CONSP(VCDR(lambdaExp)))
- {
- VALUE boundlist;
- GCVAL gcv_lambdaExp, gcv_argList;
- PUSHGC(gcv_lambdaExp, lambdaExp);
- PUSHGC(gcv_argList, argList);
- lambdaExp = VCDR(lambdaExp);
- boundlist = bindlambdalist(VCAR(lambdaExp), argList, evalArgs);
- if(boundlist)
- {
- GCVAL gcv_boundlist;
- PUSHGC(gcv_boundlist, boundlist);
- result = cmd_progn(VCDR(lambdaExp));
- POPGC;
- unbindsymbols(boundlist);
- }
- else
- result = NULL;
- POPGC; POPGC;
- }
- return(result);
- }
-
- static VALUE
- _eval(VALUE obj)
- {
- VALUE result = NULL;
- GCVAL gcv_obj;
- #ifdef MINSTACK
- if(STK_SIZE <= MINSTACK)
- {
- STK_WARN("eval");
- return(cmd_signal(sym_stack_error, sym_nil));
- }
- #endif
- if(++LispDepth > MaxLispDepth)
- {
- cmd_signal(sym_error, LIST_1(MKSTR("max-lisp-depth exceeded, possible infite recursion?")));
- }
- else if(obj)
- {
- switch(VTYPE(obj))
- {
- VALUE funcobj, arglist;
- int type;
- case V_Symbol:
- if(!(result = cmd_symbol_value(obj)))
- cmd_signal(sym_void_value, LIST_1(obj));
- break;
- case V_Cons:
- again:
- funcobj = VCAR(obj);
- arglist = VCDR(obj);
- if(SYMBOLP(funcobj))
- {
- if(VSYM(funcobj)->sym_Flags & SF_DEBUG)
- SingleStepFlag = TRUE;
- funcobj = cmd_symbol_function(funcobj);
- if(!funcobj)
- {
- cmd_signal(sym_void_function, LIST_1(VCAR(obj)));
- goto end;
- }
- }
- switch(type = VTYPE(funcobj))
- {
- VALUE alist, car, args[5];
- GCVALN gcvn_args;
- int i, nargs;
- case V_Subr0:
- result = VSUBR0FUN(funcobj)();
- break;
- case V_SubrN:
- PUSHGC(gcv_obj, obj);
- alist = evallist(arglist);
- if(alist)
- result = VSUBRNFUN(funcobj)(alist);
- POPGC;
- break;
- case V_Subr1:
- nargs = 1;
- args[0] = sym_nil;
- goto do_subr;
- case V_Subr2:
- nargs = 2;
- args[0] = args[1] = sym_nil;
- goto do_subr;
- case V_Subr3:
- nargs = 3;
- args[0] = args[1] = args[2] = sym_nil;
- goto do_subr;
- case V_Subr4:
- nargs = 4;
- args[0] = args[1] = args[2] = args[3] = sym_nil;
- goto do_subr;
- case V_Subr5:
- nargs = 5;
- args[0] = args[1] = args[2] = args[3] = args[4] = sym_nil;
- do_subr:
- PUSHGCN(gcvn_args, args, nargs);
- PUSHGC(gcv_obj, obj);
- for(i = 0; i < nargs; i++)
- {
- if(CONSP(arglist))
- {
- if(!(args[i] = cmd_eval(VCAR(arglist))))
- {
- POPGC; POPGCN;
- goto end;
- }
- arglist = VCDR(arglist);
- }
- else
- break;
- }
- POPGC; POPGCN;
- switch(type)
- {
- case V_Subr1:
- result = VSUBR1FUN(funcobj)(args[0]);
- break;
- case V_Subr2:
- result = VSUBR2FUN(funcobj)(args[0], args[1]);
- break;
- case V_Subr3:
- result = VSUBR3FUN(funcobj)(args[0], args[1], args[2]);
- break;
- case V_Subr4:
- result = VSUBR4FUN(funcobj)(args[0], args[1],
- args[2], args[3]);
- break;
- case V_Subr5:
- result = VSUBR5FUN(funcobj)(args[0], args[1], args[2],
- args[3], args[4]);
- break;
- }
- break;
- case V_SF:
- result = VSFFUN(funcobj)(arglist);
- break;
- case V_Cons:
- car = VCAR(funcobj);
- if(car == sym_lambda)
- {
- struct LispCall lc;
- lc.lc_Next = LispCallStack;
- lc.lc_Fun = VCAR(obj);
- lc.lc_Args = arglist;
- lc.lc_ArgsEvalledP = sym_nil;
- LispCallStack = &lc;
- if(!(result = evallambda(funcobj, arglist, TRUE))
- && ThrowValue && (VCAR(ThrowValue) == sym_defun))
- {
- result = VCDR(ThrowValue);
- ThrowValue = NULL;
- }
- LispCallStack = lc.lc_Next;
- }
- else if(car == sym_macro)
- {
- funcobj = VCDR(funcobj);
- if(CONSP(funcobj) && (VCAR(funcobj) == sym_lambda))
- {
- VALUE form = evallambda(funcobj, arglist, FALSE);
- if(form)
- result = cmd_eval(form);
- }
- else
- cmd_signal(sym_invalid_macro, LIST_1(VCAR(obj)));
- }
- else if(car == sym_autoload)
- {
- if(!SYMBOLP(VCAR(obj)))
- {
- /* Unless the car of the original `obj' we're evalling
- is a symbol don't bother. (Because it wouldn't
- be possible to find the new definition.) */
- cmd_signal(sym_invalid_autoload,
- list_2(VCAR(obj),
- MKSTR("Can only autoload from symbols")));
- }
- else
- {
- VALUE autoload = VCDR(funcobj);
- if(CONSP(autoload))
- {
- PUSHGC(gcv_obj, obj);
- /* trash the autoload defn, this way I make sure
- that we don't keep trying to autoload a function
- indefinitely. */
- VCAR(funcobj) = sym_nil;
- result = cmd_load(VCAR(autoload), sym_t, sym_nil, sym_nil);
- POPGC;
- if(result && !NILP(result))
- {
- result = NULL;
- goto again;
- }
- }
- else
- cmd_signal(sym_invalid_autoload, LIST_1(VCAR(obj)));
- }
- }
- else
- cmd_signal(sym_invalid_function, LIST_1(VCAR(obj)));
- break;
- default:
- cmd_signal(sym_invalid_function, LIST_1(VCAR(obj)));
- break;
- }
- break;
- case V_Var:
- if(!(result = VVARFUN(obj)(NULL)))
- cmd_signal(sym_void_value, LIST_1(obj));
- break;
- default:
- result = obj;
- break;
- }
- }
- else
- cmd_signal(sym_error, LIST_1(MKSTR("Void object to `eval'")));
- /* In case I missed a non-local exit somewhere. */
- if(result && ThrowValue)
- result = NULL;
- end:
- LispDepth--;
- return(result);
- }
- _PR VALUE cmd_eval(VALUE);
- DEFUN("eval", cmd_eval, subr_eval, (VALUE obj), V_Subr1, DOC_eval) /*
- ::doc:eval::
- (eval FORM)
- Evaluates FORM and returns its value.
- ::end:: */
- {
- static int DbDepth;
- bool newssflag = TRUE;
- VALUE result;
-
- /*
- * Safety barrier... when the last window is closed the only safe
- * thing to do is die :(
- */
- if(!CurrVW)
- return(NULL);
-
- if((DataAfterGC >= DataBeforeGC) && !GCinhibit)
- {
- GCVAL gcv_obj;
- PUSHGC(gcv_obj, obj);
- cmd_garbage_collect(sym_t);
- POPGC;
- }
-
- if(!SingleStepFlag)
- return(_eval(obj));
-
- DbDepth++;
- result = NULL;
- if(VSYM(sym_debug_entry)->sym_Function)
- {
- VALUE dbres;
- VALUE dbargs = cmd_cons(obj, cmd_cons(newnumber(DbDepth), sym_nil));
- if(dbargs)
- {
- GCVAL gcv_dbargs;
- PUSHGC(gcv_dbargs, dbargs);
- SingleStepFlag = FALSE;
- if((dbres = funcall(sym_debug_entry, dbargs)) && CONSP(dbres))
- {
- switch(VNUM(VCAR(dbres)))
- {
- case 1:
- /* single step cdr and following stuff */
- SingleStepFlag = TRUE;
- result = _eval(VCDR(dbres));
- SingleStepFlag = FALSE;
- break;
- case 2:
- /* run through cdr and step following */
- result = _eval(VCDR(dbres));
- break;
- case 3:
- /* run cdr and following */
- result = _eval(VCDR(dbres));
- newssflag = FALSE;
- break;
- case 4:
- /* result = cdr */
- SingleStepFlag = TRUE;
- result = VCDR(dbres);
- SingleStepFlag = FALSE;
- break;
- }
- if(result)
- {
- if(VSYM(sym_debug_exit)->sym_Function)
- {
- VCAR(dbargs) = result;
- if(!(dbres = funcall(sym_debug_exit, dbargs)))
- result = NULL;
- }
- }
- }
- POPGC;
- }
- }
- else
- {
- cmd_signal(sym_error, LIST_1(MKSTR("No debugger installed")));
- newssflag = FALSE;
- result = NULL;
- }
- DbDepth--;
- SingleStepFlag = newssflag;
- return(result);
- }
-
- VALUE
- funcall(VALUE fun, VALUE arglist)
- {
- int type;
- VALUE result = NULL, origfun = fun;
- GCVAL gcv_origfun, gcv_arglist;
- #ifdef MINSTACK
- if(STK_SIZE <= MINSTACK)
- {
- STK_WARN("funcall");
- return(cmd_signal(sym_stack_error, sym_nil));
- }
- #endif
- if(++LispDepth > MaxLispDepth)
- {
- LispDepth--;
- return(cmd_signal(sym_error, LIST_1(MKSTR("max-lisp-depth exceeded, possible infite recursion?"))));
- }
- if((DataAfterGC >= DataBeforeGC) && !GCinhibit)
- {
- PUSHGC(gcv_origfun, origfun);
- PUSHGC(gcv_arglist, arglist);
- cmd_garbage_collect(sym_t);
- POPGC; POPGC;
- }
-
- again:
- if(SYMBOLP(fun))
- {
- if(VSYM(fun)->sym_Flags & SF_DEBUG)
- SingleStepFlag = TRUE;
- fun = cmd_symbol_function(fun);
- if(!fun)
- {
- cmd_signal(sym_void_function, LIST_1(origfun));
- goto end;
- }
- }
- switch(type = VTYPE(fun))
- {
- int i, nargs;
- VALUE car, argv[5];
- case V_SubrN:
- result = VSUBRNFUN(fun)(arglist);
- break;
- case V_Subr0:
- result = VSUBR0FUN(fun)();
- break;
- case V_Subr1:
- nargs = 1;
- argv[0] = sym_nil;
- goto do_subr;
- case V_Subr2:
- nargs = 2;
- argv[0] = argv[1] = sym_nil;
- goto do_subr;
- case V_Subr3:
- nargs = 3;
- argv[0] = argv[1] = argv[2] = sym_nil;
- goto do_subr;
- case V_Subr4:
- nargs = 4;
- argv[0] = argv[1] = argv[2] = argv[3] = sym_nil;
- goto do_subr;
- case V_Subr5:
- nargs = 5;
- argv[0] = argv[1] = argv[2] = argv[3] = argv[4] = sym_nil;
- do_subr:
- for(i = 0; i < nargs; i++)
- {
- if(CONSP(arglist))
- {
- argv[i] = VCAR(arglist);
- arglist = VCDR(arglist);
- }
- else
- break;
- }
- switch(type)
- {
- case V_Subr1:
- result = VSUBR1FUN(fun)(argv[0]);
- break;
- case V_Subr2:
- result = VSUBR2FUN(fun)(argv[0], argv[1]);
- break;
- case V_Subr3:
- result = VSUBR3FUN(fun)(argv[0], argv[1], argv[2]);
- break;
- case V_Subr4:
- result = VSUBR4FUN(fun)(argv[0], argv[1], argv[2], argv[3]);
- break;
- case V_Subr5:
- result = VSUBR5FUN(fun)(argv[0], argv[1], argv[2],
- argv[3], argv[4]);
- break;
- }
- break;
- case V_Cons:
- car = VCAR(fun);
- if(car == sym_lambda)
- {
- struct LispCall lc;
- lc.lc_Next = LispCallStack;
- lc.lc_Fun = origfun;
- lc.lc_Args = arglist;
- lc.lc_ArgsEvalledP = sym_t;
- LispCallStack = &lc;
- if(!(result = evallambda(fun, arglist, FALSE))
- && ThrowValue && (VCAR(ThrowValue) == sym_defun))
- {
- result = VCDR(ThrowValue);
- ThrowValue = NULL;
- }
- LispCallStack = lc.lc_Next;
- }
- else if(car == sym_autoload)
- {
- if(!SYMBOLP(origfun))
- {
- /* Unless the function we're funcall'ing is a symbol don't
- bother. */
- cmd_signal(sym_invalid_autoload, list_2(fun, MKSTR("Can only autoload from symbols")));
- }
- else
- {
- VALUE autoload = VCDR(fun);
- if(CONSP(autoload))
- {
- PUSHGC(gcv_origfun, origfun);
- PUSHGC(gcv_arglist, arglist);
- /* trash the autoload defn, this way I make sure
- that we don't keep trying to autoload a function
- indefinitely. */
- VCAR(fun) = sym_nil;
- autoload = cmd_load(VCAR(autoload), sym_t, sym_nil, sym_nil);
- POPGC; POPGC;
- if(autoload && !NILP(autoload))
- {
- fun = origfun;
- goto again;
- }
- }
- else
- cmd_signal(sym_invalid_autoload, LIST_1(fun));
- }
- }
- else
- cmd_signal(sym_invalid_function, LIST_1(fun));
- break;
- default:
- cmd_signal(sym_invalid_function, LIST_1(fun));
- }
- /* In case I missed a non-local exit somewhere. */
- if(result && ThrowValue)
- result = NULL;
- end:
- LispDepth--;
- return(result);
- }
-
- _PR VALUE cmd_funcall(VALUE);
- DEFUN("funcall", cmd_funcall, subr_funcall, (VALUE args), V_SubrN, DOC_funcall) /*
- ::doc:funcall::
- (funcall FUNCTION ARGS...)
- Calls FUNCTION with arguments ARGS... and returns its result.
- ::end:: */
- {
- if(!CONSP(args))
- return(cmd_signal(sym_bad_arg, list_2(sym_nil, newnumber(1))));
- return(funcall(VCAR(args), VCDR(args)));
- }
-
- _PR VALUE cmd_progn(VALUE);
- DEFUN("progn", cmd_progn, subr_progn, (VALUE args), V_SF, DOC_progn) /*
- ::doc:progn::
- (progn FORMS... ) <SPECIAL-FORM>
- Eval's each of the FORMS in order returning the value of the last
- one.
- ::end:: */
- {
- VALUE result = sym_nil;
- GCVAL gcv_args;
- PUSHGC(gcv_args, args);
- while(CONSP(args))
- {
- result = cmd_eval(VCAR(args));
- args = VCDR(args);
- if(!result)
- break;
- }
- if(result && !NILP(args))
- result = cmd_eval(args);
- POPGC;
- return(result);
- }
-
- VALUE
- evalstring(u_char *str, bool isValString)
- {
- VALUE res = sym_nil;
- VALUE stream = cmd_cons(newnumber(0), sym_nil);
- if(stream)
- {
- VALUE obj;
- int c;
- GCVAL gcv_stream;
- if(isValString)
- VCDR(stream) = STRING_HDR(str);
- else
- {
- if(!(VCDR(stream) = valstrdup(str)))
- return(NULL);
- }
- PUSHGC(gcv_stream, stream);
- obj = sym_nil;
- c = streamgetc(stream);
- while(res && (c != EOF) && (obj = readlispexp(stream, &c)))
- res = cmd_eval(obj);
- POPGC;
- }
- return(res);
- }
-
- VALUE
- calllisp0(VALUE function)
- {
- return(funcall(function, sym_nil));
- }
- VALUE
- calllisp1(VALUE function, VALUE arg1)
- {
- return(funcall(function, LIST_1(arg1)));
- }
- VALUE
- calllisp2(VALUE function, VALUE arg1, VALUE arg2)
- {
- return(funcall(function, LIST_2(arg1, arg2)));
- }
-
- void
- lisp_prin(VALUE strm, VALUE obj)
- {
- switch(VTYPE(obj))
- {
- u_char tbuf[40];
- int j;
- case V_Number:
- sprintf(tbuf, "%ld", VNUM(obj));
- streamputs(strm, tbuf, FALSE);
- break;
- case V_Cons:
- streamputc(strm, '\(');
- while(CONSP(VCDR(obj)))
- {
- printval(strm, VCAR(obj));
- obj = VCDR(obj);
- streamputc(strm, ' ');
- }
- printval(strm, VCAR(obj));
- if(!NILP(VCDR(obj)))
- {
- streamputs(strm, " . ", FALSE);
- printval(strm, VCDR(obj));
- }
- streamputc(strm, ')');
- break;
- case V_Vector:
- streamputc(strm, '\[');
- for(j = 0; j < VVECT(obj)->vc_Size; j++)
- {
- if(VVECT(obj)->vc_Array[j])
- printval(strm, VVECT(obj)->vc_Array[j]);
- else
- streamputs(strm, "#<void>", FALSE);
- if(j != (VVECT(obj)->vc_Size - 1))
- streamputc(strm, ' ');
- }
- streamputc(strm, ']');
- break;
- case V_Subr0:
- case V_Subr1:
- case V_Subr2:
- case V_Subr3:
- case V_Subr4:
- case V_Subr5:
- case V_SubrN:
- sprintf(tbuf, "#<subr %s>", VSTR(VXSUBR(obj)->subr_Name));
- streamputs(strm, tbuf, FALSE);
- break;
- case V_SF:
- sprintf(tbuf, "#<special-form %s>", VSTR(VXSUBR(obj)->subr_Name));
- streamputs(strm, tbuf, FALSE);
- break;
- case V_Var:
- sprintf(tbuf, "#<var %s>", VSTR(VXSUBR(obj)->subr_Name));
- streamputs(strm, tbuf, FALSE);
- break;
- #ifndef HAVE_UNIX
- case V_Process:
- streamputs(strm, "#<process>", FALSE);
- break;
- #endif
- default:
- streamputs(strm, "#<unknown object type>", FALSE);
- }
- }
-
- void
- string_princ(VALUE strm, VALUE obj)
- {
- streamputs(strm, VSTR(obj), FALSE);
- }
- void
- string_print(VALUE strm, VALUE obj)
- {
- u_char *s = VSTR(obj);
- u_char c;
- streamputc(strm, '\"');
- while((c = *s++))
- {
- switch(c)
- {
- case '\t':
- streamputs(strm, "\\t", FALSE);
- break;
- case '\n':
- streamputs(strm, "\\n", FALSE);
- break;
- case '\\':
- streamputs(strm, "\\\\", FALSE);
- break;
- case '"':
- streamputs(strm, "\\\"", FALSE);
- break;
- default:
- streamputc(strm, (int)c);
- }
- }
- streamputc(strm, '\"');
- }
-
- VALUE
- findmemberbyindex(VALUE list, int index)
- {
- while((--index) && CONSP(list))
- list = VCDR(list);
- if(CONSP(list))
- return(VCAR(list));
- return(sym_nil);
- }
- VALUE
- movedownlist(VALUE list, int nodes)
- {
- while((nodes--) && CONSP(list))
- list = VCDR(list);
- return(list);
- }
- int
- listlen(VALUE list)
- {
- int i = 0;
- while(CONSP(list))
- {
- i++;
- list = VCDR(list);
- }
- return(i);
- }
- VALUE
- copylist(VALUE list)
- {
- VALUE result;
- VALUE *last = &result;
- while(CONSP(list))
- {
- if(!(*last = cmd_cons(VCAR(list), sym_nil)))
- return(NULL);
- list = VCDR(list);
- last = &VCDR(*last);
- }
- *last = list;
- return(result);
- }
-
- /*
- * Used for easy handling of `var' objects
- */
- VALUE
- handlevarint(VALUE val, long *data)
- {
- if(val)
- {
- if(NUMBERP(val))
- *data = VNUM(val);
- return(NULL);
- }
- return(newnumber(*data));
- }
-
- _PR VALUE cmd_break(void);
- DEFUN("break", cmd_break, subr_break, (void), V_Subr0, DOC_break) /*
- ::doc:break::
- (break)
- The next form to be evaluated will be done so through the Lisp debugger.
- ::end:: */
- {
- SingleStepFlag = TRUE;
- return(sym_t);
- }
-
- _PR VALUE cmd_step(VALUE);
- DEFUN("step", cmd_step, subr_step, (VALUE form), V_Subr1, DOC_step) /*
- ::doc:step::
- (step FORM)
- Use the Lisp debugger to evaluate FORM.
- ::end:: */
- {
- VALUE res;
- bool oldssf = SingleStepFlag;
- SingleStepFlag = TRUE;
- res = cmd_eval(form);
- SingleStepFlag = oldssf;
- return(res);
- }
-
- _PR VALUE cmd_macroexpand(VALUE, VALUE);
- DEFUN("macroexpand", cmd_macroexpand, subr_macroexpand, (VALUE form, VALUE env), V_Subr2, DOC_macroexpand) /*
- ::doc:macroexpand::
- (macroexpand FORM [ENVIRONMENT])
- If FORM is a macro call, expand it until it isn't. If ENVIRONMENT is
- specified it is an alist of `(MACRO-NAME . DEFINITION)'.
- ::end:: */
- {
- VALUE car;
- GCVAL gcv_form, gcv_env, gcv_car;
- PUSHGC(gcv_form, form);
- PUSHGC(gcv_env, env);
- PUSHGC(gcv_car, car);
- top:
- if(CONSP(form))
- {
- car = VCAR(form);
- if(SYMBOLP(car))
- {
- VALUE tmp;
- if(!NILP(env) && (tmp = cmd_assq(car, env)) && CONSP(tmp))
- {
- car = VCDR(tmp);
- form = evallambda(car, VCDR(form), FALSE);
- if(form)
- goto top;
- }
- else
- {
- car = cmd_symbol_function(car);
- if(!car || NILP(car))
- goto end;
- if(CONSP(car) && (VCAR(car) == sym_macro) && (VCAR(VCDR(car)) == sym_lambda))
- {
- form = evallambda(VCDR(car), VCDR(form), FALSE);
- if(form)
- goto top;
- }
- }
- }
- }
- end:
- POPGC; POPGC; POPGC;
- return(form);
- }
-
- _PR VALUE cmd_get_doc_string(VALUE idx);
- DEFUN("get-doc-string", cmd_get_doc_string, subr_get_doc_string, (VALUE idx), V_Subr1, DOC_get_doc_string) /*
- ::doc:get_doc_string::
- (get-doc-string INDEX)
- Returns the document-string number INDEX.
- ::end:: */
- {
- DECLARE1(idx, NUMBERP);
- return(cmd_read_file_from_to(MKSTR(DOC_FILE), idx, newnumber((int)'\f')));
- }
-
- _PR VALUE cmd_add_doc_string(VALUE str);
- DEFUN("add-doc-string", cmd_add_doc_string, subr_add_doc_string, (VALUE str), V_Subr1, DOC_add_doc_string) /*
- ::doc:add_doc_string::
- (add-doc-string STRING)
- Appends STRING to the end of the doc-file and returns the index position of
- it's first character (a number).
- ::end:: */
- {
- FILE *docs;
- DECLARE1(str, STRINGP);
- docs = fopen(DOC_FILE, "a");
- if(docs)
- {
- int len = strlen(VSTR(str));
- VALUE idx = newnumber(ftell(docs));
- if(fwrite(VSTR(str), 1, len, docs) != len)
- {
- return(cmd_signal(sym_file_error,
- LIST_1(MKSTR("Can't append to doc-file"))));
- }
- putc('\f', docs);
- fclose(docs);
- return(idx);
- }
- return(cmd_signal(sym_file_error,
- list_2(MKSTR("Can't open doc-file"), MKSTR(DOC_FILE))));
- }
-
- _PR VALUE var_debug_on_error(VALUE val);
- DEFUN("debug-on-error", var_debug_on_error, subr_debug_on_error, (VALUE val), V_Var, DOC_debug_on_error) /*
- ::doc:debug_on_error::
- When an error is signalled this variable controls whether or not to enter the
- Lisp debugger immediately. If the variable's value is t or a list of symbols
- - one of which is the signalled error symbol - the debugger is entered.
- See `signal'.
- ::end:: */
- {
- if(val)
- DebugOnError = val;
- return(DebugOnError);
- }
-
- _PR VALUE cmd_signal(VALUE error, VALUE data);
- DEFUN("signal", cmd_signal, subr_signal, (VALUE error, VALUE data), V_Subr2, DOC_signal) /*
- ::doc:signal::
- (signal ERROR-SYMBOL DATA)
- Signal that an error has happened. ERROR-SYMBOL is the name of a symbol
- classifying the type of error, it should have a property `error-message' (a
- string) with a short description of the error message.
- DATA is a list of objects which are relevant to the error -- they will
- be made available to any error-handler or printed by the default error
- -handler.
- ::end:: */
- {
- VALUE tmp, errlist;
- /* Can only have one error at once. */
- if(ThrowValue)
- return(NULL);
- DECLARE1(error, SYMBOLP);
-
- errlist = cmd_cons(error, data);
-
- if(((DebugOnError == sym_t)
- || (CONSP(DebugOnError) && (tmp = cmd_memq(error, DebugOnError))
- && !NILP(tmp)))
- && VSYM(sym_debug_error_entry)->sym_Function)
- {
- /* Enter debugger. */
- VALUE oldDebugOnError = DebugOnError;
- GCVAL gcv_odoe;
- bool oldssflag = SingleStepFlag;
- DebugOnError = sym_nil;
- SingleStepFlag = FALSE;
- PUSHGC(gcv_odoe, oldDebugOnError);
- tmp = funcall(sym_debug_error_entry, cmd_cons(errlist, sym_nil));
- POPGC;
- DebugOnError = oldDebugOnError;
- if(tmp && (tmp == sym_t))
- SingleStepFlag = TRUE;
- else
- SingleStepFlag = oldssflag;
- }
- ThrowValue = cmd_cons(sym_error, errlist);
- return(NULL);
- }
-
- _PR VALUE cmd_error_protect(VALUE args);
- DEFUN("error-protect", cmd_error_protect, subr_error_protect, (VALUE args), V_SF, DOC_error_protect) /*
- ::doc:error_protect::
- (error-protect FORM HANDLERS...) <SPECIAL-FORM>
- Evaluates FORM with error-handlers in place, if no errors occur return the
- value returned by FORM, else the value of whichever handler's body was
- evaluated.
- Each HANDLER is a list looking like `(ERROR-SYMBOL BODY...)'. If an error
- of type ERROR-SYMBOL occurs BODY is evaluated with the symbol `error-info'
- temporarily set to `(ERROR-SYMBOL . DATA)' (these were the arguments given to
- the `signal' which caused the error).
- ::end:: */
- {
- VALUE res;
- GCVAL gcv_args;
- if(!CONSP(args))
- return(cmd_signal(sym_bad_arg, list_2(sym_nil, newnumber(1))));
- PUSHGC(gcv_args, args);
- if(!(res = cmd_eval(VCAR(args))) && ThrowValue
- && (VCAR(ThrowValue) == sym_error))
- {
- /* an error. */
- VALUE errorsym = VCAR(VCDR(ThrowValue)), handlers = VCDR(args);
- while(CONSP(handlers) && CONSP(VCAR(handlers)))
- {
- VALUE handler = VCAR(handlers);
- if((VCAR(handler) == errorsym) || (VCAR(handler) == sym_error))
- {
- VALUE bindlist = sym_nil;
- GCVAL gcv_bindlist;
- bindlist = bindsymbol(sym_nil, sym_error_info, VCDR(ThrowValue));
- ThrowValue = NULL;
- PUSHGC(gcv_bindlist, bindlist);
- res = cmd_progn(VCDR(handler));
- POPGC;
- unbindsymbols(bindlist);
- break;
- }
- handlers = VCDR(handlers);
- }
- }
- POPGC;
- return(res);
- }
-
- void
- handleerror(VALUE error, VALUE data)
- {
- VALUE errstr;
- cmd_beep();
- if(!(errstr = cmd_get(error, sym_error_message)) || !STRINGP(errstr))
- errstr = MKSTR("Unknown error");
- switch(listlen(data))
- {
- case 0:
- cmd_format(list_3(sym_t, MKSTR("%s"), errstr));
- break;
- case 1:
- cmd_format(list_4(sym_t, MKSTR("%s: %s"), errstr, VCAR(data)));
- break;
- case 2:
- cmd_format(list_5(sym_t, MKSTR("%s: %s, %s"), errstr,
- VCAR(data), VCAR(VCDR(data))));
- break;
- case 3:
- cmd_format(cmd_cons(sym_t, list_5(MKSTR("%s: %s, %s, %s"), errstr,
- VCAR(data), VCAR(VCDR(data)), VCAR(VCDR(VCDR(data))))));
- break;
- default:
- cmd_format(list_3(sym_t, MKSTR("%s: ..."), errstr));
- }
- }
-
- void
- signalargerror(VALUE obj, int argNum)
- {
- cmd_signal(sym_bad_arg, list_2(obj, newnumber(argNum)));
- }
-
- _PR VALUE cmd_backtrace(VALUE strm);
- DEFUN("backtrace", cmd_backtrace, subr_backtrace, (VALUE strm), V_Subr1, DOC_backtrace) /*
- ::doc:backtrace::
- (backtrace [STREAM])
- Prints a backtrace of the current Lisp call stack to STREAM (or to
- `standard-output').
- The format is something like:
- FUNCTION (ARGLIST) ARGS-EVALLED-P
- where ARGS-EVALLED-P is either `t' or `nil', depending on whether or not
- ARGLIST had been evaluated or not before being put into the stack.
- ::end:: */
- {
- struct LispCall *lc;
- if(NILP(strm) && !(strm = cmd_symbol_value(sym_standard_output)))
- return(cmd_signal(sym_bad_arg, list_2(strm, newnumber(1))));
- lc = LispCallStack;
- while(lc)
- {
- streamputc(strm, '\n');
- printval(strm, lc->lc_Fun);
- streamputc(strm, ' ');
- printval(strm, lc->lc_Args);
- streamputc(strm, ' ');
- printval(strm, lc->lc_ArgsEvalledP);
- lc = lc->lc_Next;
- }
- return(sym_t);
- }
-
- _PR VALUE var_max_lisp_depth(VALUE val);
- DEFUN("max-lisp-depth", var_max_lisp_depth, subr_max_lisp_depth, (VALUE val), V_Var, DOC_max_lisp_depth) /*
- ::doc:max_lisp_depth::
- The maximum number of times that eval and funcall can be called recursively.
- This is intended to stop infinite recursion, if the default value of 250 is
- too small (you get errors in normal use) set it to something larger.
- ::end:: */
- {
- return(handlevarint(val, &MaxLispDepth));
- }
-
- void
- lisp_init(void)
- {
- INTERN(sym_quote, "quote");
- INTERN(sym_lambda, "lambda");
- INTERN(sym_macro, "macro");
- INTERN(sym_autoload, "autoload");
- INTERN(sym_function, "function");
- INTERN(sym_standard_input, "standard-input");
- INTERN(sym_standard_output, "standard-output");
- INTERN(sym_defun, "defun");
- INTERN(sym_debug_entry, "debug-entry");
- INTERN(sym_debug_exit, "debug-exit");
- INTERN(sym_debug_error_entry, "debug-error-entry");
- INTERN(sym_amp_optional, "&optional");
- INTERN(sym_amp_rest, "&rest");
- INTERN(sym_amp_aux, "&aux");
- markstatic(&ThrowValue);
- ADD_SUBR(subr_eval);
- ADD_SUBR(subr_funcall);
- ADD_SUBR(subr_progn);
- ADD_SUBR(subr_break);
- ADD_SUBR(subr_step);
- ADD_SUBR(subr_macroexpand);
- ADD_SUBR(subr_get_doc_string);
- ADD_SUBR(subr_add_doc_string);
- ADD_SUBR(subr_debug_on_error);
- ADD_SUBR(subr_signal);
- ADD_SUBR(subr_error_protect);
- ADD_SUBR(subr_backtrace);
- ADD_SUBR(subr_max_lisp_depth);
-
- /* Stuff for error-handling */
- DebugOnError = sym_nil;
- INTERN(sym_error_message, "error-message");
- INTERN(sym_error, "error");
- cmd_put(sym_error, sym_error_message, MKSTR("Error"));
- INTERN(sym_invalid_function, "invalid-function");
- cmd_put(sym_invalid_function, sym_error_message, MKSTR("Invalid function"));
- INTERN(sym_void_function, "void-function");
- cmd_put(sym_void_function, sym_error_message, MKSTR("Function value is void"));
- INTERN(sym_void_value, "void-value");
- cmd_put(sym_void_value, sym_error_message, MKSTR("Value as variable is void"));
- INTERN(sym_bad_arg, "bad-arg");
- cmd_put(sym_bad_arg, sym_error_message, MKSTR("Bad argument"));
- INTERN(sym_invalid_read_syntax, "invalid-read-syntax");
- cmd_put(sym_invalid_read_syntax, sym_error_message, MKSTR("Invalid read syntax"));
- INTERN(sym_end_of_stream, "end-of-stream");
- cmd_put(sym_end_of_stream, sym_error_message, MKSTR("Premature end of stream"));
- INTERN(sym_invalid_lambda_list, "invalid-lambda-list");
- cmd_put(sym_invalid_lambda_list, sym_error_message, MKSTR("Invalid lambda-list"));
- INTERN(sym_missing_arg, "missing-arg");
- cmd_put(sym_missing_arg, sym_error_message, MKSTR("Required argument missing"));
- INTERN(sym_invalid_macro, "invalid-macro");
- cmd_put(sym_invalid_macro, sym_error_message, MKSTR("Invalid macro definition"));
- INTERN(sym_invalid_autoload, "invalid-autoload");
- cmd_put(sym_invalid_autoload, sym_error_message, MKSTR("Invalid autoload definition"));
- INTERN(sym_no_catcher, "no-catcher");
- cmd_put(sym_no_catcher, sym_error_message, MKSTR("No catch'er for throw"));
- INTERN(sym_buffer_read_only, "buffer-read-only");
- cmd_put(sym_buffer_read_only, sym_error_message, MKSTR("Buffer is read-only"));
- INTERN(sym_bad_event_desc, "bad_event_desc");
- cmd_put(sym_bad_event_desc, sym_error_message, MKSTR("Invalid event description"));
- INTERN(sym_file_error, "file-error");
- cmd_put(sym_file_error, sym_error_message, MKSTR("File error"));
- INTERN(sym_invalid_stream, "invalid-stream");
- cmd_put(sym_invalid_stream, sym_error_message, MKSTR("Invalid stream"));
- INTERN(sym_setting_constant, "setting-constant");
- cmd_put(sym_setting_constant, sym_error_message, MKSTR("Attempt to set value of constant"));
- INTERN(sym_process_error, "process-error");
- cmd_put(sym_process_error, sym_error_message, MKSTR("Process error"));
- INTERN(sym_invalid_area, "invalid-area");
- cmd_put(sym_invalid_area, sym_error_message, MKSTR("Invalid area"));
- #ifdef MINSTACK
- INTERN(sym_stack_error, "stack-error");
- cmd_put(sym_stack_error, sym_error_message, MKSTR("Stack overflow"));
- #endif
- INTERN(sym_error_info, "error-info");
- }
-