perm filename MACLSP.DBA[UP,DOC] blob sn#239461 filedate 1976-10-03 generic text, type C, neo UTF8
COMMENT ⊗   VALID 00157 PAGES
C REC  PAGE   DESCRIPTION
C00001 00001
C00017 00002
C00019 00003			                         General Information
C00023 00004			                    LISP/MACLISP Reference Manual
C00028 00005			                         General Information
C00031 00006			                    LISP/MACLISP Reference Manual
C00032 00007			                                 Data
C00037 00008			                    LISP/MACLISP Reference Manual
C00043 00009			                                 Data
C00047 00010			                    LISP/MACLISP Reference Manual
C00050 00011			                                 Data
C00053 00012			                    LISP/MACLISP Reference Manual
C00055 00013			                     The Basic Processes of LISP
C00057 00014			                    LISP/MACLISP Reference Manual
C00060 00015			                     The Basic Processes of LISP
C00065 00016			                    LISP/MACLISP Reference Manual
C00070 00017			                     The Basic Processes of LISP
C00072 00018			                    LISP/MACLISP Reference Manual
C00075 00019			                     The Basic Processes of LISP
C00078 00020			                    LISP/MACLISP Reference Manual
C00082 00021			                     The Basic Processes of LISP
C00086 00022			                    LISP/MACLISP Reference Manual
C00090 00023			                     The Basic Processes of LISP
C00092 00024			                    LISP/MACLISP Reference Manual
C00093 00025			              Functions for Manipulating List Structure
C00095 00026			                    LISP/MACLISP Reference Manual
C00098 00027			              Functions for Manipulating List Structure
C00102 00028			                    LISP/MACLISP Reference Manual
C00105 00029			              Functions for Manipulating List Structure
C00108 00030			                    LISP/MACLISP Reference Manual
C00109 00031			              Functions for Manipulating List Structure
C00111 00032			                    LISP/MACLISP Reference Manual
C00114 00033			              Functions for Manipulating List Structure
C00117 00034			                    LISP/MACLISP Reference Manual
C00120 00035			              Functions for Manipulating List Structure
C00124 00036			                    LISP/MACLISP Reference Manual
C00125 00037			                           Flow of Control
C00129 00038			                    LISP/MACLISP Reference Manual
C00133 00039			                           Flow of Control
C00137 00040			                    LISP/MACLISP Reference Manual
C00141 00041			                           Flow of Control
C00145 00042			                    LISP/MACLISP Reference Manual
C00149 00043			                           Flow of Control
C00150 00044			                    LISP/MACLISP Reference Manual
C00154 00045			                           Flow of Control
C00158 00046			                    LISP/MACLISP Reference Manual
C00161 00047			           Manipulating the Constituents of Atomic Symbols
C00165 00048			                    LISP/MACLISP Reference Manual
C00167 00049			           Manipulating the Constituents of Atomic Symbols
C00171 00050			                    LISP/MACLISP Reference Manual
C00174 00051			           Manipulating the Constituents of Atomic Symbols
C00177 00052			                    LISP/MACLISP Reference Manual
C00181 00053			           Manipulating the Constituents of Atomic Symbols
C00182 00054			                    LISP/MACLISP Reference Manual
C00186 00055			           Manipulating the Constituents of Atomic Symbols
C00187 00056			                    LISP/MACLISP Reference Manual
C00188 00057			                         Functions on Numbers
C00190 00058			                    LISP/MACLISP Reference Manual
C00193 00059			                         Functions on Numbers
C00196 00060			                    LISP/MACLISP Reference Manual
C00197 00061			                         Functions on Numbers
C00200 00062			                    LISP/MACLISP Reference Manual
C00201 00063			                         Functions on Numbers
C00204 00064			                    LISP/MACLISP Reference Manual
C00206 00065			                         Functions on Numbers
C00207 00066			                    LISP/MACLISP Reference Manual
C00209 00067			                         Functions on Numbers
C00212 00068			                    LISP/MACLISP Reference Manual
C00214 00069			                         Functions on Numbers
C00216 00070			                    LISP/MACLISP Reference Manual
C00218 00071			                         Functions on Numbers
C00219 00072			                    LISP/MACLISP Reference Manual
C00222 00073			                        Character Manipulation
C00225 00074			                    LISP/MACLISP Reference Manual
C00229 00075			                        Character Manipulation
C00230 00076			                    LISP/MACLISP Reference Manual
C00233 00077			                        Character Manipulation
C00236 00078			                    LISP/MACLISP Reference Manual
C00237 00079			                     Functions Concerning Arrays
C00241 00080			                    LISP/MACLISP Reference Manual
C00244 00081			                     Functions Concerning Arrays
C00248 00082			                    LISP/MACLISP Reference Manual
C00250 00083			                         "Mapping" Functions
C00254 00084			                    LISP/MACLISP Reference Manual
C00258 00085			                         "Mapping" Functions
C00261 00086			                    LISP/MACLISP Reference Manual
C00262 00087			                          Sorting Functions
C00266 00088			                    LISP/MACLISP Reference Manual
C00268 00089			              Functions for Controlling the Interpreter
C00271 00090			                    LISP/MACLISP Reference Manual
C00273 00091			              Functions for Controlling the Interpreter
C00276 00092			                    LISP/MACLISP Reference Manual
C00280 00093			              Functions for Controlling the Interpreter
C00285 00094			                    LISP/MACLISP Reference Manual
C00286 00095			              Functions for Controlling the Interpreter
C00290 00096			                    LISP/MACLISP Reference Manual
C00293 00097			              Functions for Controlling the Interpreter
C00296 00098			                    LISP/MACLISP Reference Manual
C00301 00099			              Functions for Controlling the Interpreter
C00304 00100			                    LISP/MACLISP Reference Manual
C00309 00101			              Functions for Controlling the Interpreter
C00312 00102			                    LISP/MACLISP Reference Manual
C00317 00103			              Functions for Controlling the Interpreter
C00319 00104			                    LISP/MACLISP Reference Manual
C00323 00105			              Functions for Controlling the Interpreter
C00326 00106			                    LISP/MACLISP Reference Manual
C00329 00107			              Functions for Controlling the Interpreter
C00332 00108			                    LISP/MACLISP Reference Manual
C00335 00109			              Functions for Controlling the Interpreter
C00339 00110			                    LISP/MACLISP Reference Manual
C00342 00111			              Functions for Controlling the Interpreter
C00343 00112			                    LISP/MACLISP Reference Manual
C00345 00113			              Functions for Controlling the Interpreter
C00349 00114			                    LISP/MACLISP Reference Manual
C00350 00115			              Functions for Controlling the Interpreter
C00354 00116			                    LISP/MACLISP Reference Manual
C00358 00117			              Functions for Controlling the Interpreter
C00362 00118			                    LISP/MACLISP Reference Manual
C00367 00119			              Functions for Controlling the Interpreter
C00371 00120			                    LISP/MACLISP Reference Manual
C00375 00121			              Functions for Controlling the Interpreter
C00378 00122			                    LISP/MACLISP Reference Manual
C00379 00123			              Functions for Controlling the Interpreter
C00381 00124			                    LISP/MACLISP Reference Manual
C00385 00125			              Functions for Controlling the Interpreter
C00388 00126			                    LISP/MACLISP Reference Manual
C00391 00127			              Functions for Controlling the Interpreter
C00395 00128			                    LISP/MACLISP Reference Manual
C00396 00129			              Functions for Controlling the Interpreter
C00399 00130			                    LISP/MACLISP Reference Manual
C00400 00131			                           Input and Output
C00404 00132			                    LISP/MACLISP Reference Manual
C00406 00133			                           Input and Output
C00411 00134			                    LISP/MACLISP Reference Manual
C00417 00135			                           Input and Output
C00421 00136	
C00422 00137	.in +%undent%
C00423 00138			                    LISP/MACLISP Reference Manual
C00427 00139			                           Input and Output
C00429 00140			                    LISP/MACLISP Reference Manual
C00432 00141			                           Input and Output
C00436 00142			                    LISP/MACLISP Reference Manual
C00439 00143			                           Input and Output
C00442 00144			                    LISP/MACLISP Reference Manual
C00445 00145			                           Input and Output
C00448 00146			                    LISP/MACLISP Reference Manual
C00453 00147			                           Input and Output
C00455 00148			                    LISP/MACLISP Reference Manual
C00459 00149			                           Input and Output
C00463 00150			                    LISP/MACLISP Reference Manual
C00466 00151			                           Input and Output
C00470 00152			                    LISP/MACLISP Reference Manual
C00472 00153			                           Input and Output
C00476 00154			                    LISP/MACLISP Reference Manual
C00479 00155			                           Input and Output
C00480 00156			                    LISP/MACLISP Reference Manual
C00484 00157			                           Input and Output
C00486 ENDMK
C⊗;

                           ***************
                           ***************
                           *             *
                           * ROUGH DRAFT *
                           *             *
                           ***************
                           ***************
                    LISP/MACLISP Reference Manual
                              Dialect:  MACLISP
                              Authors:
                              David A. Moon
                              David P. Reed
                              and
                              Ira Goldstein
                              Guy L. Steele
                              Alexander Sunguroff
              **************DO NOT BELIEVE**************
              *************DO NOT DUPLICATE*************
c   Copyright, 1973, Massachusetts Institute of Technology
    All rights reserved
		                         General Information
                    ***** ROUGH DRAFT #9905 *****
 1.         General Information
 1.1       The MACLISP Language
   MACLISP is a dialect of LISP developed at M.I.T.'s Project MAC  for
use  in  artificial intelligence research and related fields.  MACLISP
is descended from the commonly-known LISP 1.5  dialect,  however  many
features of the language have been changed or added.
   This  document  is  intended  both  as  a  reference source for the
language and as a user's guide to three implementations.   These  are,
in  chronological  order,  the  M.I.T.  Artifical  Intelligence  Lab's
implentation on the DEC pdp-10 computer under their  operating  system
ITS,  hereafter referred to as "the ITS implementation," Project MAC's
implementation on Honeywell's version of the Multics system, hereafter
referred to as "the Multics implementation," and the version that runs
on the DEC pdp-10 under  DEC's  TOPS-10  operating  system,  hereafter
called  "the  DEC-10  implementation."  The DEC-10 implementation also
runs under TENEX by means of a TOPS-10 emulator.  Since  the  ITS  and
DEC-10   implementations  are  closely  related,  they  are  sometimes
referred to collectively as the pdp-10 implementation.
   These  implementations  are  mostly   compatible;   however,   some
implementations  have  extra  features  designed  to  exploit peculiar
features of the system on which they run, and some implementations are
temporarily missing some features.  Most programs  will  work  on  any
implementation,  although  it  is  possible to write machine-dependent
code if you try hard enough.
 1.2       Structure of the Manual
   This manual is not specifically designed  for  LISP  users  of  any
particular  level  of  ability,  though it does make assumptions as to
what an "average" user of LISP will require of a manual.  Since it  is
intended for a general class of users it must satisfy some constraints
of  design  in  order  to  be  of benefit to a user of some particular
ability.  The manual must provide as much information as a user  might
need,  yet  provide  it  in a manner such that a less experienced user
might still have access to some of that information.
11/18/73                        1. 1.2                          Page 1
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
   The general structuring of the manual is  by  meaning;   things  of
similar  meaning will be found grouped together.  Explanatory text and
function definitions are interspersed.  Usually text will be found  at
the  beginnings of chapters, sections, or subsections with definitions
following.  Complexity tends to increase across  each  subdivision  of
the  manual  while  usefulness  to  a new user tends to decrease.  The
chapters in the beginning of the manual are of more use to a new user,
the later ones contain either more complex or less useful information.
If a chapter is undivided then it will become more complex toward  the
end.   If  a  chapter  is  subdivided, then each section or subsection
again follows the same criteria.
   Accessing information in the manual is dependant on both the user's
level of ability and the purpose for which she  or  he  is  using  the
manual.   Though cover to cover reading is not recommended (though not
excluded), it is suggested that someone who has never previously  seen
this  manual  browse  through  it,  touching  the  beginning  of  each
subdivision that is listed in the  Table  of  Contents,  in  order  to
familiarize himself or herself with the material that it contains.  To
find  an  answer  to some particular question, one must use one of the
provided access methods.  Since the manual is  structured  by  meaning
one  can  use  the Table of Contents that is found at the beginning of
the manual, to find where information  of  a  general  class  will  be
found.   Entry  into  the manual by meaning is also facilitated by the
Glossary and the Concept Index which are found at the  end.   Also  at
the  end  of  the  manual  is  a Function Index which is probably most
useful to a regular and  repeated  user  of  the  dialect,  or  to  an
experienced user of another dialect, who wishes to find out the answer
to  a question about a specific function.  However since the manual is
structured by meaning, it is useful to examine other functions in  the
vicinity of the first, for usefulness.
   It  is  again  suggested  that  a  new reader of this manual should
familiarize himself or herself with its contents.
 1.3       Notational Conventions
   There are some conventions of notation that must  be  mentioned  at
this time, due to their being used in examples.
   A  combination  of  the  characters,  equal  sign  and greater then
symbol, " => ," will  be  used  in  examples  of  LISP  code  to  mean
evaluation (that is the application of the function, eval.).
   All  uses  of  the phrase, "LISP reader," unless further qualified,
refer to that part of the LISP system which does  input,  and  not  to
some person.
Page 2                          1. 1.3                        11/18/73
		                         General Information
                    ***** ROUGH DRAFT #9905 *****
   The two characters, accent acute, " ' ," and semi-colon, " ; ," are
examples  of  what  are  called  macro  characters.   Though the macro
character facility, which is defined in the chapter  on  Input/Output,
is  ot  of  immediate interest to a new user of the dialect, these two
come preset by the LISP system and are useful.  When the  LISP  reader
encounters  an  accent  accute,  it reads in the next S-expression and
encloses it in a call to the function, quote.  That is:
                              'some-atom
turns into:
                          (quote some-atom)
and
                            '(cons 'a 'b)
turns into
                  (quote (cons (quote a) (quote b)))
The semi-colon is used a commenting feature.   When  the  LISP  reader
encounters it, it discards the rest of that line of input.
   All  LISP  examples  in  this  manual  are written according to the
conventions of the Multics implementation, which uses both  upper  and
lower  case  letters  and spells the names of most system functions in
lower case.  Some implementations  of  MACLISP  only  use  upper  case
letters  because  they  run  on  systems  which  are not equipped with
terminals  capable  of  generating  and  displaying  the  full   ascii
character set.  Howeverm these systems will accept input in lower case
and translate it to upper case.
11/18/73                        1. 1.3                          Page 3
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
                    This page intentionally left blank.
Page 4                          1. 1.3                        11/18/73
		                                 Data
                    ***** ROUGH DRAFT #9905 *****
 2.         Data
 2.1       Data Types
   LISP works with pieces of data called "objects" or "S-expressions."
These can be simple "atomic" objects or complex objects compounded out
of  other  objects.  Functions, the basic units of a LISP program, are
also objects and may be manipulated as data.
   Objects come in several types.  All types are self-evident, that is
it is possible for the system to tell what type an object is  just  by
looking  at  it,  so  it  is  not  necessary  to  declare the types of
variables as in some other languages.  It should be  noted  that  LISP
represents  objects  as  pointers,  so that any object will fit in the
same cell, and the same object may have several  different  usages  --
for  example  the  same  identical  object  may  be a component of two
different compound objects.
   The data-types are divided into three broad  classes:   the  atomic
types,  the  non-atomic  types,  and the composite types.  Objects are
divided into the same three classes according to their  type.   Atomic
objects  are  basic  units  which  cannot  be  broken down by ordinary
chemical means, while non-atomic objects  are  structures  constructed
out  of  other objects, and composite objects are indivisible entities
which have subcomponents which may be extracted and modified  but  not
removed.
   The  atomic  data  types  are numbers, atomic symbols, strings, and
subr-objects.
   In LISP numbers  can  be  represented  by  three  types  of  atomic
objects:   fixnums,  flonums,  and bignums.  A fixnum is a fixed-point
binary integer whose range of values is  limited  by  the  size  of  a
machine word.  A flonum is a floating-point number whose precision and
range   of   values   are   machine-dependent.    A   bignum   is   an
arbitrary-precision integer.  It is impossible to  get  "overflow"  in
bignum  arithmetic,  as  any  finite  integer  can be represented as a
bignum.  However, fixnum and flonum arithmetic is faster  than  bignum
arithmetic  and  bignums  require  more  memory.   Sometimes  the word
"fixnum" is used to include both fixnums and bignums; in this  manual,
however,  the  word "fixnum" will never include bignums unless that is
explicitly stated.
   The external representations for numbers are as follows:  a  fixnum
is  represented  as  a sequence of digits in a specified base, usually
octal.  A trailing decimal point indicates a decimal base.   A  flonum
11/18/73                        2. 2.1                          Page 5
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
is  represented  as  a set of digits containing an embedded or leading
decimal point and/or a trailing exponent.  The exponent is  introduced
by  an  upper  or lower case "e".  A bignum looks like a fixnum except
that it has enough digits that  it  will  not  fit  within  the  range
available  to  fixnums.   Any number may be preceded by a + or - sign.
Some examples of fixnums are 4, -1232, -191., +46.  An  example  of  a
bignum   is   1565656565656565656565656565656565.   Some  examples  of
flonums are:  4.0, .01, -6e5, 4.2e-1.
   Another LISP data type is the string.  This is a sequence of  0  or
more  characters.   Strings  are used to hold messages to be typed out
and to  manipulate  text  when  the  structure  of  the  text  is  not
appropriate   for   the   use  of  "list  processing."   The  external
representation of a string is a sequence  of  characters  enclosed  in
double-quotes, e.g. "foo".  If a " is to be included in the string, it
is written twice, e.g. "foo""bar" is foo"bar.
   One of the most important LISP data types is the atomic symbol.  In
fact,  the  word "atom" is often used to mean just atomic symbols, and
not the other atomic types.  An atomic symbol has a name, a value, and
possibly a list of "properties".  The name is used  to  refer  to  the
symbol  in input and output.  The external representation of an atomic
symbol is just its name.  This name is often called  the  "pname,"  or
"print-name,"  as it is a sequence of characters that are printed out.
For example, an atomic symbol with a pname of foo would be represented
externally as foo; internally as a structure containing the value, the
pname "foo", and the properties.
   There are two special atomic symbols, t and nil.  These always have
themselves as values and their values may not be changed.  nil is used
as a "marker" is many contexts; it is essential to the maintenance  of
data  structures  such as lists.  t is usually used when an antithesis
to nil is required for some purpose.
   The value of an atomic symbol is any object of any type.  There are
functions to set and get  the  value  of  a  symbol.   Because  atomic
symbols  have  values  associated  with  them,  they  can  be  used as
variables in programs and as "dummy arguments" in  functions.   It  is
also  possible for an atomic symbol to have no value, in which case it
is said to be "undefined" or "unbound."
   The property list of an atomic symbol will be explained in  section
6.2.   It  is  used  for  such  things  as  recording  the fact that a
particular atomic symbol is the name of a function.
   An atomic symbol with less than two  characters  in  its  pname  is
often  called  a  "character  object"  and  used to represent an ascii
character.  The atomic symbol with a zero-length pname represents  the
ascii   null  character,  and  the  symbols  with  1-character  pnames
represent the character which is their pname.   Functions  which  take
character  objects as input usually also accept a string one character
long or a fixnum equal to the  ascii-code  value  for  the  character.
Page 6                          2. 2.1                        11/18/73
		                                 Data
                    ***** ROUGH DRAFT #9905 *****
Character  objects  are  always  interned  on the obarray (see section
6.3).
   A "subr-object" is a special atomic data-type whose use is normally
hidden in the implementation.   A  subr-object  represents  executable
machine   code.    The  functions  built  into  the  LISP  system  are
subr-object, as  are  user  functions  that  have  been  compiled.   A
subr-object  cannot  be named directly, so each system function has an
atomic  symbol  which  serves  as  its  name.   The  symbol  has   the
subr-object as a "property."
   One  composite  data  type  is  the  array.  An array consists of a
number of cells, each of which may contain any LISP object.  The cells
of an array are accessed by subscripting.  An array may  have  one  or
more  dimensions;  the  upper  limit  on  the  number of dimensions is
implementation-defined.  An array is always associated with an  atomic
symbol which is its name.  This atomic symbol has on its property list
a  property  with  the  indicator  'array'  and  a  value,  called  an
array-object or sometimes a "special array cell,"  which  permits  the
implementation  to access the array.  See chapter 9 for an explanation
of how to create, use, and delete arrays.
   Another composite data type is the file-object, which is  described
in chapter 13.
   The  non-atomic  data  type  is  the "cons."  A cons is a structure
containing  two  components,  called  the  "car"  and  the  "cdr"  for
historical reasons.  These two components may be any LISP object, even
another cons (in fact, they could even be the same cons).  In this way
complex structures can be built up out of simple conses.  Internally a
cons is represented in a form similar to:
     
     |                 |                 |
     |     car         |      cdr        |
     |||
where  the  boxes  represent  cells  of  memory large enough to hold a
pointer, and "car"  and  "cdr"  are  two  pointers  to  objects.   The
external representation of a cons is the "dotted-pair" notation
(A . B) where A is the car and B is the cdr.
   Another  way  to write the internal representation of a cons, which
is more convenient for large structures, is:
 ---> o -----> cdr
     |
     |
     V
    car
11/18/73                        2. 2.1                          Page 7
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
   There  are  three  LISP  functions  associated  with  conses.   The
function  cons  combines its two arguments into a cons; (A . B) can be
generated by (cons A B).  The function car  returns  the  car  of  its
argument, and the function cdr returns the cdr of its argument.
   One  type  of  structure,  built  out of conses, that is used quite
often, is the "list."  A list is a row of objects of arbitrary length.
A list of 3 things A, B, and C is constructed as (cons A (cons B (cons
C nil)));  nil is a special atom that is used to mark  the  end  of  a
list.  The structure of a list can be diagrammed as:
 ---> o ----> o ----> o ----> nil
     |       |       |
     |       |       |
     V       V       V
     A       B       C
From  this it can be seen that the car of a list is its first element,
that the cdr of a list is the list of  its  elements  other  than  the
first, and that the list of no elements is the same as nil.
   This  list  of A, B, and C could be represented in the dot-notation
used for conses as  (A . (B . (C . nil))), however a  more  convenient
notation  for  the  external representation of lists has been defined:
the "list-notation" (A B C).  It is also possible to have a hybrid  of
the two notations which is used for structures which are almost a list
except that they end in an atom other than nil.  For example,
(A . (B . (C . D))) can be represented as (A B C . D).
   A   list  not  containing  any  elements  is  perfectly  legal  and
frequently used.  This zero-length list is the atom nil.   It  may  be
typed in as either nil or ().
Page 8                          2. 2.1                        11/18/73
		                                 Data
                    ***** ROUGH DRAFT #9905 *****
 2.2          Predicates for Checking Types
        A  predicate  is  a  function  which  tests for some condition
     involving its argument and returns t if that  condition  is  true
     and  nil  if  it is not true.  These predicates return t if their
     argument is of the type specified by the name  of  the  function,
     nil  if  it  is  of  some other type.  Note that the name of most
     predicates ends in the letter p, by convention.
atom		SUBR 1 arg
     The atom predicate is nil if its argument is a dotted-pair  or  a
     list,  and t if it is any kind of atomic object such as a number,
     a character string, or an atomic symbol.
fixp		SUBR 1 arg
     The fixp predicate returns t if its argument is  a  fixnum  or  a
     bignum, otherwise nil.
floatp		SUBR 1 arg
     The  floatp  predicate returns t if its argument is a flonum, nil
     if it is not.
numberp		SUBR 1 arg
     The numberp predicate returns t if its argument is a number,  nil
     if it is not.
typep		SUBR 1 arg
     typep  is  a general type-predicate.  It returns an atomic symbol
     describing the type of its argument, chosen from the list
               (fixnum flonum bignum list symbol string random)
     symbol means atomic symbol.  Random is for all types  that  don't
     fit  in any other category.  Thus numberp could have been defined
     by:
11/18/73                          2.2                           Page 9
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
     (defun numberp (x)
        (and (memq (typep x) '(fixnum flonum bignum))
               x))
These two functions only exist in the Multics implementation.
stringp		SUBR 1 arg
     The stringp predicate returns its argument if that argument is  a
     string, otherwise nil.
subrp		SUBR 1 arg
     The subrp predicate returns t if its argument is a "subr" object,
     i.e.  a  pointer  to  the  machine  code for a compiled or system
     function.  Example:
         (subrp (get 'car 'subr)) => t
Page 10                           2.2                         11/18/73
		                     The Basic Processes of LISP
                    ***** ROUGH DRAFT #9905 *****
 3.         The Basic Processes of LISP
 3.1       Binding
        The way "local variables" are implemented  in  LISP  is  by  a
     procedure   known  as  "binding."   Local  variables  and  global
     variables are all the value of the one  atomic  symbol  with  the
     pname  of the name of the variable. [??what is this cruft??] When
     the scope of a "local variable" is entered, the old value of  the
     variable  is  saved  and  it  is  reset to the value it will have
     locally.  This  is  "binding."   When  the  scope  of  the  local
     variable  is exited, for whatever reason, whether it is a "normal
     exit" or an "abnormal exit," the variable is restored to its  old
     value.  This is "unbinding."
        Binding  is  used  for temporary variables in prog`s and do`s,
     and for  binding  lambda-variables  ("dummy  arguments")  to  the
     values  of  the  arguments  to  a  function or lambda-expression.
     [??how can anyone understand this??]
11/18/73                        3. 3.1                         Page 11
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
 3.2       Evaluation
   Evaluation is a transformation which takes  one  object,  called  a
form, and produces another, called the value of that form.  Evaluation
is   used  internally  by  LISP  in  processing  typed  input  and  in
(recursively)  evaluating  portions  of  a  form  in  the  process  of
evaluating that form.  Evaluation is available for explicit use as the
function eval.
   Evaluation  is  performed  by  the  LISP interpreter, following the
rules set forth below.
   Numbers and strings always evaluate to themselves.
   Atomic symbols evaluate to the 'value' associated with them.  It is
possible for an atomic symbol to have no  value,  in  which  case  the
process  of  evaluation  encounters  an  error,  which  is  handled as
described in section 12.4.  The  special  atomic  symbols  t  and  nil
always  have  themselves  as  values,  consequently they evaluate like
numbers rather than like atomic symbols.
   Random objects, such  as  subr-objects,  files,  and  array-objects
evaluate   to  something  random;  often  themselves.   Note  that  an
array-object is different from an atomic symbol which is the  name  of
an  array;  such  an  atomic symbol is evaluated the same as any other
atomic symbol.
   The evaluation of non-atomic forms is more complex.  The  evaluator
regards  a  non-atomic  form as a list, whose first element (car) is a
function and whose remaining elements (cdr) are arguments.  The  value
of  the  form  is  the  result  of  the function when applied to those
arguments, according to the "application" procedure described below.
Page 12                         3. 3.2                        11/18/73
		                     The Basic Processes of LISP
                    ***** ROUGH DRAFT #9905 *****
 3.3       Application
   "Application" is the procedure by which a function is invoked  with
specified arguments to produce a value (and possibly side effects.)
   The  first  step  in application is an examination of the function.
If it is atomic, then it is required to  be  an  atomic  symbol.   The
atomic  symbol's  property  list  is searched for one of the following
properties, called "functional properties":
       expr, fexpr, macro, subr, fsubr, lsubr, array, autoload
If none of these is found, then the atomic symbol is evaluated and its
value is taken to be the function  being  called  and  application  is
restarted at the beginning.
   If  an array property is found, there is a subscripted reference to
the array.  The arguments are evaluated from left to right,  and  used
as  subscripts  to  the  array.  Consequently they must be fixnums and
there must be the same number of them as there are dimensions  in  the
array and they must lie within the bounds of the array.  The result is
the contents of the array cell specified by the subscripts.
   If  a  subr,  lsubr,  or  fsubr property is found, the value of the
property  must  be  a  subr-object.   The  subr-object  represents   a
machine-code  subroutine,  which  may  be  a  function built in to the
interpreter, a compiled LISP function, or a function written  in  some
other  language made known to LISP by some facility such as defsubr or
lap, depending  on  the  implementation.   The  evaluator  calls  this
subroutine,  giving  it the specified arguments, and the result is the
LISP object returned by the subroutine.  If the subr-object was in  an
fsubr  property,  the  subroutine is called with one argument which is
the cdr of the list being  evaluated.   Thus  the  arguments  are  not
evaluated.   If  it  was  a  subr or lsubr property, the arguments are
evaluated from left to right before they are passed to the subroutine.
A subr requires a certain fixed number of arguments, but an lsubr  can
take  a  variable number of arguments, between two bounds which depend
on the particular lsubr.  (See the args function).
   If a fexpr property is found, the value of the property must  be  a
list  whose  car is the atom lambda and whose cadr is a list of one or
two atomic symbols, referred to as lambda-variables.  The  cddr  is  a
list  of  zero  or  more  objects, referred to as the body.  The first
lambda-variable is bound to the cdr of the form being evaluated,  i.e.
to  the  list  of  unevaluated  arguments.  Of course, the body of the
fexpr may evaluate  the  arguments  itself  by  explicitly  using  the
function eval.  The second lambda-variable, if present, is bound to an
"a-list pointer" which represents the binding state which existed just
before   the   fexpr's   lambda-variables   were   bound.   After  the
lambda-variables have been bound, the body of the fexpr  is  evaluated
from  left  to  right.   The  result  is  the  value  of the last form
evaluated.
11/18/73                        3. 3.3                         Page 13
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
   If an expr property is found, there are three cases:   1)   If  the
value of the property is an atomic symbol, that atomic symbol is taken
as  the  function and application is restarted from the beginning.  2)
If the value of the property is a list whose car is  the  atom  lambda
and  whose  cadr  is  a  list  of  zero or more atomic symbols, called
lambda-variables,  then  the  evaluation  is  the  invocation  of   an
interpreted  function  called an 'expr.' There must be the same number
of arguments as lambda-variables.  The arguments  are  evaluated  from
left to right and then the lambda-variables are bound to the values of
the arguments.  Next the body of the expr is evaluated in the same way
as  for a fexpr.  3)  If the value of the property is a list whose car
is the atom lambda and whose cadr is an atomic symbol other than  nil,
the  evaluation  is  an invocation of an interpreted function called a
'lexpr,' which is the interpreted version of lsubr.  The arguments are
evaluated from left to right and saved in a place where the  functions
arg  and  setarg  can  find  them.  Then the single lambda-variable is
bound to the number of arguments, and the body  is  evaluated  in  the
same way as for an expr.
   If a macro property is found, its value must look like the value of
a  fexpr  property.   The  difference  between  a macro and a fexpr is
twofold.  One, the first lambda-variable is bound to the  whole  form,
instead of just the cdr of the form (the list of arguments).  Two, the
object returned by the macro is treated as a form and re-evaluated and
its value becomes the result of the application.
   If an autoload property is found, the definition of the function is
loaded in from an external file and then used.  See section 12.4.4 for
details.
   If  the  function  is not an atom, it is what is sometimes called a
"functional form."  Note that actually a functional form  is  anything
that  can be applied, including atoms.  One kind of functional form is
a list whose car is the atomic symbol lambda.  This is often called  a
"lambda"  expression.   It  is  applied exactly the same way as if the
function had been an atomic symbol which had an  expr  property  whose
value was the lambda-expression.
   Another  kind  of  functional  form is a list of the atom label, an
atomic symbol, and a functional form.  The atomic symbol is  bound  to
the  functional  form,  and then the functional form is applied to the
arguments.   This  is  used  for   strange   things   like   recursive
lambda-expressions.    Generally  a  permanently-defined  function  is
better than a label.
   The third kind of functional form  is  a  "funarg,"  which  can  be
produced  by  the  *function  function.  The funarg contains an a-list
pointer.  The binding context  is  temporarily  set  to  the  previous
context indicated by this a-list pointer, and then the functional form
contained in the funarg is applied.
Page 14                         3. 3.3                        11/18/73
		                     The Basic Processes of LISP
                    ***** ROUGH DRAFT #9905 *****
   If  the  functional form does not fall into any of the above cases,
it is evaluated and the value is  then  used  as  the  function  being
applied and application starts over again at the beginning.
   In  addition  to  the  variety  of  application which has just been
described, which is used internally by the evaluation procedure, there
is a similar but not identical application procedure available through
the function apply.  The main difference is that the function and  the
arguments are passed to apply seperately.  They are not consed up into
a  form.   Consequently  macros  are  not  accepted by this version of
application.  In addition, the  arguments  to  exprs,  lexprs,  subrs,
lsubrs,  arrays, etc.  are not evaluated, since the caller of apply is
presumed to have prepared the arguments.
11/18/73                        3. 3.3                         Page 15
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
 3.4       A-list Pointers
   There is a special type of object called an "a-list pointer"  which
can  be  used  to  refer  to  a  binding  context.   Due  to the stack
implementation of MACLISP, an  a-list  pointer  is  only  valid  while
control  is  nested  within  the  binding context it names.  It is not
possible to exit from within a binding context but keep it  around  by
keeping an a-list pointer to it.
   An  a-list  pointer  is either a negative fixnum or nil.  nil means
the "global" or "top level" binding context.  The negative fixnum is a
special value of implementation  dependent  meaning  which  should  be
obtained  only  from one of the three following sources:  the function
evalframe, the function errframe, or the second lambda-variable  of  a
fexpr.
   The  only  use for a-list pointers is to pass them to the functions
eval and apply to specify the binding context in which  variables  are
to  be  evaluated  during  that  evaluation  or  application.   A-list
pointers are also used internally by *function.  When it  generates  a
funarg,  it puts in the funarg the functional form it was given and an
a-list pointer designating the binding environment current at the time
*function was called.
Page 16                         3. 3.4                        11/18/73
		                     The Basic Processes of LISP
                    ***** ROUGH DRAFT #9905 *****
 3.5   Functions to Perform These Processes
eval		LSUBR 1 or 2 args
     (eval x) evaluates x, just as if it had  been  typed  in  at  top
     level, and returns the result.  Note that since eval is an lsubr,
     its argument actually will be evaluated twice.
     (eval  x  y)  evaluates x in the binding context specified by the
     a-list pointer y.
apply		LSUBR 2 or 3 args
     (apply f y) applies the function f to the list  of  arguments  y.
     Unless  f  is  an  fsubr  or  fexpr such as 'cond' or 'and' which
     evaluates its arguments in a funny way, the arguments in the list
     y are used without being evaluated.
     Examples:
         (setq f '+) (apply f '(1 2 3)) => 6
         (setq f '-) (apply f '(1 2 3)) => -4
          (apply 'cons '((+ 2 3)  4))  =>
               ((+ 2 3) .  4) not (5 . 4)
     (apply f y p) works like apply with 2 arguments except  that  the
     application  is  done in the binding environment specified by the
     "a-list" pointer p.
quote		FSUBR
     Quote returns its unevaluated argument.  Quote is used to include
     constants in a form.  For convenience, the read function normally
     converts any  S-expression  preceded  by  the  apostrophe  (acute
     accent)  character  into  the  form  (quote <s-expression>).  For
     example, the form:
          (setq x '(some list))
     is converted by the reader to:
          (setq x (quote (some list)))
     which causes the variable x to be set to the constant list  value
     shown upon evaluation.  For more information on input syntax, see
     the detailed discussion in chapter 13.
11/18/73                        3. 3.5                         Page 17
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
function		FSUBR
     Function  is  like  quote except that its argument is a function.
     It is used when passing a functional argument.  Example:
     (f00 x (function (lambda (p q)
                         (cond ((numberp q) p)
                               ((numberp p) q)
                         ;or any other random function in here
                               (t (cons p q)) )))
               y)
     calls f00 with 3 arguments, the second of which is  the  function
     defined by the lambda-expression.
     Note:  quote  and  function  are  completely  equivalent  in  the
     interpreter.  The compiler sometimes needs function  to  tell  it
     that a lambda-expression is a function to be compiled rather than
     a constant.
     Function   makes  no  attempt  to  solve  the  "funarg  problem."
     *function should be used for this purpose.
*function		FSUBR
     The value of (*function f) is a "funarg" of the  function  f.   A
     funarg  can  be  used  like  a  function.   It has the additional
     property that it contains an a-list pointer so that the values of
     variables are bound the same during the application of the funarg
     as at  the  time  it  was  created,  provided  that  the  binding
     environment  in  which the funarg was created still exists on the
     stack. Hence if foo is  a  function  that  accepts  a  functional
     argument, such as
     (defun foo (f)
         (append one-value (f the-other-value) ))
     then
     (foo (*function bar))
     works, but
     (foo (prog (x y z)
               (do something)
               (return (*function bar)) ))
     does  not if bar  intends  to reference the prog  variables x, y,
     and  z.  *function  is   intended  to   help  solve  the  "funarg
     problem,"   however  it  only  works  in  some  easy  cases.   In
Page 18                         3. 3.5                        11/18/73
		                     The Basic Processes of LISP
                    ***** ROUGH DRAFT #9905 *****
     particular, two general cases  of  the  funarg  problem  are  not
     solved.   funarg's generated by *function are intended for use as
     functional  arguments,  and  cannot  be  returned  as  values  of
     functional  applications.  Also, due to the implementation, which
     essentially generates a copy  of  the  environment  at  the  time
     *function  is  applied,  assignments  to variables in this copied
     environment do not affect the values of those  variables  in  the
     environment which exists at the time *function is applied.  Thus,
     the  user  should be careful in his use of *function to make sure
     that his use does  not  exceed  the  limitations  of  the  funarg
     mechanism.
        A funarg has the form
          (funarg <function> . <pdl-ptr>)
comment             FSUBR
     comment  ignores  its  arguments  and  returns  the atomic symbol
     comment.  Example:
     (defun foo (x)
         (cond ((null x) 0)
               (t (comment x has something in it)
                  (1+ (foo (cdr x))))))
     Usually  it   is   preferable   to   comment   code   using   the
     semicolon-macro  feature  of  the  standard  input  syntax.  This
     allows the user to add comments to his code which are ignored  by
     the input package. Example:
     (defun foo (x)
         (cond ((null x) 0)
               (t (1+ (foo (cdr x))))        ;x has something in it
               ))
prog2		LSUBR 2 or more args
     Prog2  evaluates  its  arguments  from  left  to  right, like any
     lsubr, and returns the value of its second argument.
     Examples:
         (prog2 (do-this) (do-that))         ;get 2  things evaluated
         (setq x (prog2 nil y
                         (setq y x)))        ;parallel assignment.
                                             ;exchanges x and  y.
11/18/73                        3. 3.5                         Page 19
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
progn		LSUBR 1 or more args
     progn essentially evaluates all of its arguments and returns  the
     value  of the last one.  Although lambda-expressions, prog-forms,
     do-forms, cond-forms and  iog-forms  all  use  progn  implicitly,
     there  are occasions upon which one needs to evaluate a number of
     forms for side-effects when not in these forms. progn serves this
     purpose. Example:
          (progn (setq a 1) (cons a '(stuff))) => (1 stuff)
arg		SUBR 1 arg
     (arg nil), when evaluated inside a lexpr,  gives  the  number  of
     arguments supplied to that lexpr.
     (arg  i),  when  evaluated inside a lexpr, gives the value of the
     i'th argument to the lexpr.  i must be a fixnum in this case.  It
     is  an  error  if  i is less than 1 or greater than the number of
     arguments supplied to the lexpr.  Example:
     (defun foo nargs            ; define a lexpr foo.
         (print (arg nil))       ; print the number of args supplied.
         (print (arg 2))         ; print the second argument.
         (+ (arg 1) (arg 3)))    ; return the sum of 1st and 3rd args.
setarg		SUBR 2 args
     Setarg is used only inside  a  lexpr.   (setarg  i  x)  sets  the
     lexpr's  i'th argument to x.  i must be greater than zero and not
     greater than the number of arguments passed to the lexpr.   After
     (setarg i x) has been done, (arg i) will return x.
listify		SUBR 1 arg
     listify  is a function which efficiently manufactures a list of n
     of the arguments of a lexpr.  With  a  positive  argument  n,  it
     returns  a  list  of  the first n arguments of the lexpr.  With a
     negative argment n, it  returns  a  list  of  the  last  (abs  n)
     arguments  of  the  lexpr.   Basically, it works as if defined as
     follows:
         (defun listify (n)
              (cond ((minusp n)
                     (*listify (arg nil) (+ (arg nil) n 1)))
                    (t
                     (*listify n 1)) ))
Page 20                         3. 3.5                        11/18/73
		                     The Basic Processes of LISP
                    ***** ROUGH DRAFT #9905 *****
         (defun *listify (n m)      ; auxiliary function.
              (do ((i n (1- i))
                   (l nil (cons (arg i) l)))
                  ((< i m) l) ))
funcall		LSUBR 1 or more args
     (funcall f a1 a2 ... an) calls the function f with the  arguments
     a1, a2, ..., an.  It is similar to apply except that the seperate
     arguments  are given to funcall, rather than a list of arguments.
     If f is an expr, a lexpr, a subr, or an lsubr, the arguments  are
     not  re-evaluated.   If  f  is  a fexpr or an fsubr there must be
     exactly one argument.  f may not be a macro.
     Example:
     (setq cons 'plus)
     (cons 1 2) => (1 . 2)
     (funcall cons 1 2) => 3
11/18/73                        3. 3.5                         Page 21
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
                    This page intentionally left blank.
Page 22                         3. 3.5                        11/18/73
		              Functions for Manipulating List Structure
                    ***** ROUGH DRAFT #9905 *****
 4.         Functions for Manipulating List Structure
 4.1        Functions that Examine Existing List Structure
car		SUBR 1 arg
     Takes the first part of a cons.
     Examples:
               (car '(a b)) => a
               (car '(1 . 2)) => 1
cdr		SUBR 1 arg
     Takes the second part of a cons.
     Example:  (cdr '(a b c)) => (b c)
     Note: the cdr of an atomic symbol is its property list.
c...r		SUBR 1 arg
     All the compositions of up to four cars and cdrs are  defined  as
     functions  in  their  own  right.  The names begin with c and end
     with  r,  and  in  between  is  the  sequence  of  a's  and   d's
     corresponding to the composition performed by the function.
     For example,
                  (cddadr x) = (cdr (cdr (car (cdr x))))
     Some  of  the  most commonly used ones are:  cadr, which gets the
     second element of a list.  caddr, which gets the third element of
     a list.  cadddr, which gets the fourth element of a list.
11/18/73                          4.1                          Page 23
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
assoc		SUBR 2 args
     (assoc x y) looks up x in the association list  (list  of  dotted
     pairs)  y.  The value is the first dotted pair whose car is equal
     to x, or nil if there is none such.
     Examples:
          (assoc 'r '((a . b) (c . d) (r . x) (s . y) (r . z)))
               =>  (r . x)
          (assoc 'fooo '((foo . bar) (zoo . goo))) => nil
     It is  okay to rplacd the result of assoc as long as  it is   not
     nil.  Example:
         (setq values '((x .  100) (y  . 200) (z .  50)))
         (assoc 'y values) => (y . 200)
         (rplacd (assoc 'y values)  201)
         (assoc 'y values)  => (y . 201) now
     (One should always be careful about using rplacd however)
     Assoc could have been defined by:
     (defun assoc (x y)
         (cond ((null y) nil)
               ((equal x (caar y)) (car y))
               ((assoc x (cdr y))) ))
assq		SUBR 2 args
     Assq  is like assoc except that the comparison uses eq instead of
     equal.  Assq could have been defined by:
     (defun assq (x y)
         (cond ((null y) nil)
               ((eq x (caar y)) (car y))
               ((assq x (cdr y))) ))
sassoc		SUBR 3 args
     (sassoc x y z) is like (assoc x y) except that if x is not  found
     in  y,  instead of returning nil sassoc calls the function z with
     no arguments.  Sassoc could have been defined by:
     (defun sassoc (x y z)
         (or (assoc x y)
             (apply z nil)))
Page 24                           4.1                         11/18/73
		              Functions for Manipulating List Structure
                    ***** ROUGH DRAFT #9905 *****
sassq		SUBR 3 args
     (sassq x y z) is like (assq x y) except that if x is not found in
     y, instead of returning nil sassq calls the function  z  with  no
     arguments.  Sassq could have been defined by:
     (defun sassq (x y z)
         (or (assq x y)
             (apply z nil)))
eq		SUBR 2 args
     Eq is a predicate.  (eq x y) is t if x and y are exactly the same
     object,  nil  otherwise.   (cf.  equal).  It should be noted that
     things that print the same are not necessarily eq to each  other.
     In  particular,  numbers  with the same value need not be eq.  In
     general, two symbols with the same print-name are eq, but  it  is
     possible  with  maknam  or  varible  obarrays to generate symbols
     which have the same print-name but are not eq.
     Examples:
               (eq 'a 'b) => nil
               (eq 'a 'a) => t
               (eq '(a b) '(a b)) => nil (usually)
               (setq x '(a b)) (eq x x) => t since it is the same
                                             '(a b) in both arguments.
               (eq 1 1) => t or nil depending on the implementation.
equal		SUBR 2 args
     The equal predicate returns  t  if  its  arguments  have  similar
     structure.  (cf.  eq) Two numbers are equal if they have the same
     value (flonums are never equal to fixnums though).   Two  strings
     are  equal if they have the same length, and the contents are the
     same.  All other atomic objects are equal if and only if they are
     eq.  For dotted pairs and lists, equal is defined recursively as:
               (equal x y) = (or (eq x y)
                                 (and (equal (car x) (car y))
                                      (equal (cdr x) (cdr y))))
     As a consequence of this definition, it may be  seen  that  equal
     need  not  terminate  when  applied to looped list structure.  In
     addition, eq always implies equal.  An  intuitive  definition  of
     equal  (which is not quite correct) is that two objects are equal
     if they look the same when printed out.
11/18/73                          4.1                          Page 25
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
last		SUBR 1 arg
     Last returns the last dotted  pair  of  the  list  which  is  its
     argument.  Example:
               (setq x '(a b c d))
               (last x) => (d)
               (rplacd (last x) '(e f))
               x => (a b c d e f)
     Last could have been defined by:
     (defun last (x)
         (cond ((null x) x)
               ((null (cdr x)) x)
               ((last (cdr x))) ))
     In  some implementations, the null check above may be replaced by
     an atom check, which will catch dotted lists.  Code which depends
     on  this  fact  should  not  be  written  though,   because   all
     implementations are subject to change on this point.
length		SUBR 1 arg
     Length  returns the length of its argument, which must be a list.
     The length of a list is the number of  top-level  conses  in  it.
     Examples:
               (length nil) => 0
               (length '(a b c d)) => 4
               (length '(a (b c) d)) => 3
     Length could have been defined by:
     (defun length (x)
         (cond ((null x) 0)
               ((1+ (length (cdr x)))) ))
     The  warning  about dotted lists given under last applies also to
     length.
Page 26                           4.1                         11/18/73
		              Functions for Manipulating List Structure
                    ***** ROUGH DRAFT #9905 *****
member		SUBR 2 args
     (member x y) returns nil if x is not a  member  of  the  list  y.
     Otherwise,  it  returns the portion of y beginning with the first
     occurrence of x.  The comparison is made by equal.  y is searched
     on the top level only.  Example:
               (member 'x '(1 2 3 4)) => nil
               (member 'x '(a (x y) c x d e x f)) => (x d e x f)
     Note that the value returned by member is eq to  the  portion  of
     the  list  beginning with x.  Thus rplaca on the result of member
     may be used, if you first check  to  make  sure  member  did  not
     return nil.  Member could have been defined by:
     (defun member (x y)
         (cond ((null y) nil)
               ((equal x (car y)) y)
               ((member x (cdr y))) ))
memq		SUBR 2 args
     Memq  is like member, except eq is used for the comparison.  Memq
     could have been defined by:
     (defun memq (x y)
         (cond ((null y) nil)
               ((eq x (car y)) y)
               ((memq x (cdr y))) ))
not		SUBR 1 arg
     Not returns t if its argument is nil, otherwise it returns nil.
null		SUBR 1 arg
     This is the same as not.
sxhash		SUBR 1 arg
     Sxhash computes a hash code of an S-expression, and returns it as
     a fixnum which may be positive or negative.  A property of sxhash
     is that (equal x y) implies  (=  (sxhash  x)  (sxhash  y)).   The
     number  returned  by  sxhash is some possibly large number in the
11/18/73                          4.1                          Page 27
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
     range allowed by fixnums.  It is guaranteed that:
     1) sxhash for an atomic symbol will always be positive.
     2) sxhash of any particular expression  will  be  constant  in  a
     particular implementation for all time.
     3)  Two  different  implementations  may hash the same expression
     into different values.
     4) sxhash of any object of type random will be zero.
     5) sxhash of a fixnum will = that fixnum.
Page 28                           4.1                         11/18/73
		              Functions for Manipulating List Structure
                    ***** ROUGH DRAFT #9905 *****
 4.2        Functions that Create New List Structure
cons		SUBR 2 args
        This is a primitive function to construct a  new  dotted  pair
     whose  car  is  the  first argument to cons, and whose cdr is the
     second argument to cons.  Thus the following identities hold:
         (eq (car (cons x y)) x) => t
         (eq (cdr (cons x y)) y) => t
     Examples:
         (cons 'a 'b) => (a . b)
         (cons 'a (cons 'b (cons 'c nil))) => (a b c)
         (cons 'a '(b c d e f)) => (a b c d e f)
ncons		SUBR 1 arg
     (ncons x) = (cons x nil) = (list x)
xcons		SUBR 2 args
     xcons ("exchange cons") is like cons except  that  the  order  of
     arguments is reversed.
     Example:
         (xcons 'a 'b) => (b . a)
     xcons could have been defined by:  (defun xcons (x y) (cons y x))
list		LSUBR 0 or more args
     list  constructs  and  returns  a  list  of  the  values  of  its
     arguments.
     Example:
        (list 3 4 'a (car '(b . c)) (+ 6 -2)) => (3 4 a b 4)
11/18/73                          4.2                          Page 29
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
append		LSUBR 0 or more args
     The arguments to append are lists.  The result is a list which is
     the concatenation  of  the  arguments.   The  arguments  are  not
     changed (cf nconc).  For example,
          (append '(a b c) '(d e f) nil '(g)) => (a b c d e f g)
     A  version  of append which only accepts two arguments could have
     been defined by:
     (defun append (x y)
         (cond ((null x) y)
               ((cons (car x) (append (cdr x) y)) )))
     The generalization to any number of arguments could then be  made
     using a lexpr:
     (defun full-append argcount
       (and (> argcount 0)
         (do ((i (1- argcount) (1- i))
              (val (arg argcount)))
             ((< i 1)
              val)
           (setq val (append (arg i) val)))))
reverse		SUBR 1 arg
     Given  a  list  as  argument,  reverse  creates  a new list whose
     elements are the elements of its argument taken in reverse order.
     Reverse does not modify its argument, unlike  nreverse  which  is
     faster but does modify its argument.  Example:
                     (reverse '(a b c d)) => (d c b a)
     Reverse could have been defined by:
     (defun reverse (x)
         (do ((l x (cdr l))         ; scan down argument,
              (r nil
                 (cons (car l) r))) ; putting each element into list
             ((null l) r)))         ; until no more elements.
Page 30                           4.2                         11/18/73
		              Functions for Manipulating List Structure
                    ***** ROUGH DRAFT #9905 *****
subst		SUBR 3 args
     (subst  x  y  z) substitutes x for all occurrences of y in z, and
     returns the modified z.  The original z is  unchanged,  as  subst
     recursively  copies  all  of  z  replacing elements eq to y as it
     goes.  If x and y are nil, z is completely  copied,  which  is  a
     convenient way to copy arbitrary list structure.
     Example:
        (subst 'Tempest 'Hurricane
               '(Shakespeare wrote (The Hurricane)))
          => (Shakespeare wrote (The Tempest))
     Subst could have been defined by:
     (defun subst (x y z)
         (cond ((equal y z) x)    ;if item equals y, replace.
               ((atom z) z)       ;if no substructure, return arg.
               ((cons (subst x y (car z))
                      (subst x y (cdr z))))))
sublis		SUBR 2 args
     sublis makes substitutions for atomic symbols in an S-expression.
     The  first  argument  to  sublis  is a list of dotted pairs.  The
     second argument is an S-expression.   The  return  value  is  the
     S-expression  with  atoms  that  are  the  car  of  a dotted pair
     replaced by the cdr of that dotted pair.   The  argument  is  not
     modified  - new conses are created where necessary and only where
     necessary, so the newly created structure shares as much  of  its
     substructure  as  possible  with  the  old.   For  example, if no
     successful substitutions are made, the result is eq  to  sublis's
     second argument.
     Example:
         (sublis '((x . 100) (z . zprime))
                 '(plus x (minus g z x p) 4))
            => (plus 100 (minus g zprime 100 p) 4)
11/18/73                          4.2                          Page 31
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
 4.3        Functions that Modify Existing List Structure
rplaca		SUBR 2 args
     (rplaca x y) changes the car of x to y and returns (the modified)
     x.  Example:
         (setq x '(a b c))
         (rplaca x 'd) => (d b c)
        Now x => (d b c)
rplacd		SUBR 2 args
     (rplacd x y) changes the cdr of x to y and returns (the modified)
     x.  Example:
         (setq x '(a b c))
         (rplacd x 'd) => (a . d)
        Now x => (a . d)
nconc		LSUBR 0 or more args
     nconc  takes  lists as arguments.  It returns a list which is the
     arguments concatenated  together.   The  arguments  are  changed,
     rather than copied. (cf. append)
     Example:
               (nconc '(a b c) '(d e f)) => (a b c d e f)
     Note that the constant (a b c) has been changed to (a b c d e f).
     If  this  form is evaluated again, it will yield (a b c d e f d e
     f).
     nconc could have been defined by:
     (defun nconc (x y)            ;for simplicity, this definition
         (cond ((null x) y)        ;only works for 2 arguments.
               (t
                (rplacd (last x) y);hook y onto x
                x)))               ;and return the modified x.
nreverse		SUBR 1 arg
     nreverse reverses its argument, which  should  be  a  list.   The
     argument  is  destroyed  by  rplacd's  all  through the list (cf.
     reverse).
     Example:
Page 32                           4.3                         11/18/73
		              Functions for Manipulating List Structure
                    ***** ROUGH DRAFT #9905 *****
               (nreverse '(a b c)) => (c b a)
     nreverse could have been defined by:
     (defun nreverse  (x)
         (cond ((null x) nil)
               ((*nrev x nil))))
     (defun *nrev (x y)            ;auxiliary function
         (cond ((null (cdr x)) (rplacd x y))
               ((*nrev (cdr x) (rplacd x y)))))
               ;;  this  last  call  depends  on  order  of   argument
     evaluation.
delete		LSUBR 2 or 3 args
     (delete x y) returns the list y with all top-level occurrences of
     x  removed.  Equal is used for the comparison.  The argument y is
     actually modified (rplacd'ed) when instances  of  x  are  spliced
     out.
     (delete  x  y  n)  is  like  (delete x y) except only the first n
     instances of x are deleted.  n is allowed to be zero.   If  n  is
     greater  than  the  number  of  occurences  of x in the list, all
     occurrences of x in the list will be deleted.
     Example:  (delete 'a '(b a c (a b) d a e)) => (b c (a b) d e)
     delete could have been defined by:
     (defun delete nargs        ; lexpr definition for 2 or 3 args
         (*delete (arg 1)       ; pass along arguments...
                  (arg 2)
                  (cond ((= nargs 3) (arg 3))
                        (123456789)))) ; infinity
     (defun *delete (x y n)        ;auxiliary function
         (cond ((or (null y) (zerop n)) y)
               ((equal x (car y)) (*delete x
                                           (cdr y)
                                           (1- n)))
               ((rplacd y (*delete x (cdr y) n)))))
delq		LSUBR 2 or 3 args
     delq is the same as  delete  except  that  eq  is  used  for  the
     comparison instead of equal.  See delete.
11/18/73                          4.3                          Page 33
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
                    This page intentionally left blank.
Page 34                           4.3                         11/18/73
		                           Flow of Control
                    ***** ROUGH DRAFT #9905 *****
 5.         Flow of Control
        MACLISP  provides a variety of structures for flow of control.
     Conditionals allow control to branch depending on the value of  a
     predicate.   "and"  and  "or" are basically one-arg conditionals,
     while cond is a very generalized multi-armed conditional.
        Recursion consists of doing part of the work  that  is  to  be
     done  oneself,  and  handing off the rest to someone else to take
     care of, when that someone else happens to be (another invocation
     of) oneself.
        Iteration is a control structure present  in  most  languages.
     It  is  similar  to recursion but sometimes more useful.  MACLISP
     contains  a  generalized  iteration  facility.    The   iteration
     facility also permits those who like "gotos" to use them.
        Nonlocal exits are similar to a return, except that the return
     is  from several levels of function calling rather than just one,
     and is determined  at  run  time.   These  are  mostly  used  for
     applications  like  escaping from the middle of an algorithm when
     it is discovered that the algorithm is not applicable.
        Errors  are  a  type  of  non-local  exit  used  by  the  lisp
     interpreter  when it discovers a condition that it does not like.
     Errors have  the  additional  feature  of  correctability,  which
     allows  a  user-specified  function (most often a break loop), to
     get a chance to come in and correct the error or at least inspect
     what was happening and  determine  what  caused  it,  before  the
     nonlocal  exit  occurs.   This  is explained in detail in section
     12.4.
 5.1        Conditionals
and		FSUBR
     'and' evaluates its arguments one at a time, from left to  right.
     If  any  argument evaluates to nil, 'and' immediately returns nil
     without evaluating the remaining arguments.  If all the arguments
     evaluate non-nil, 'and' returns the value of its  last  argument.
     'and'  can  be used both for logical operations, where nil stands
     for False and t stands for True, and as a conditional expression.
     Examples:
          (and x y)
11/18/73                          5.1                          Page 35
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
          (and (setq temp (assq x y))
               (rplacd temp z))
          (and (null (errset (something)))
               (princ "There was an error."))
     Note: (and) => t, which is the identity for this operation.
or		FSUBR
     'or' evaluates its arguments one by one from left to  right.   If
     an  argument evaluates to nil, 'or' proceeds to evaluate the next
     argument.  If there are no more arguments, 'or' returns nil.  But
     if an argument evaluates non-nil, 'or' immediately  returns  that
     value  without  evaluating  any remaining arguments.  'or' can be
     used both for logical operations, where nil stands for False  and
     t for True, and as a conditional expression.
     Note:  (or) => nil, the identity for this operation.
cond		FSUBR
     cond  processes  its  arguments,  called  "clauses," from left to
     right.  The car of  each  clause,  called  the  "antecedent,"  is
     evaluated.   If  it  is  nil,  cond  advances to the next clause.
     Otherwise, the cdr of the clause is treated as a list  of  forms,
     called  "consequents,"  which  are  evaluated from left to right.
     After evaluating the consequents, cond returns without inspecting
     any remaining clauses.  The  value  is  the  value  of  the  last
     consequent  evaluated,  or  the  value of the antecedent if there
     were no consequents in the clause.  If cond runs out  of  clauses
     (i.e. if every antecedent is nil), the value of the cond is nil.
     Example:
         (cond ((zerop x) (+ x 3)) ;first clause.
                                   ;(zerop x) is antecedent.
                                   ;(plus x 3) is consequent.
               ((null y)
                (setq x 4)
                (cons x z))        ;a clause with 2 consequents
               (z)                 ;a clause with no consequents.
                                   ;the antecedent is just z.
               )                   ;this is the end of the cond.
     This  is like the traditional LISP 1.5 cond except that it is not
     necessary to have exactly one consequent in each clause,  and  it
     is permissible to run out of clauses.
Page 36                           5.1                         11/18/73
		                           Flow of Control
                    ***** ROUGH DRAFT #9905 *****
 5.2        Iteration
prog		FSUBR
     prog is the "program"  function.  It provides temporary variables
     and the ability to do "go-tos."  The form of a prog is:
                                              
                          |       <tag>         |
        (prog (<var>...) <                       > ...)
                          |   <statement>     |
        The  first  thing  in  a prog is a list of temporary variables
     <var>.  Each variable has  its  value  saved  when  the  prog  is
     entered  and  restored  when the prog is left.  The variables are
     initialized to nil when the prog is entered, thus they  are  said
     to be "bound to nil" by the prog.
        The rest of a prog is the body.  An item in the body may be an
     atomic symbol which is a <tag> or a non-atomic <statement>.
        prog,  after  binding  the  temporary variables, evaluates its
     body sequentially.  <tag>s are skipped  over;   <statement>s  are
     evaluated but the values are ignored.  If  the end of the body is
     reached,   prog  returns  nil.   If (return x) is evaluated, prog
     stops evaluating its body and returns the value  of  x.   If  (go
     tag)  is  seen, prog  jumps to the part of the body labelled with
     the tag.  The argument to 'go' is  not  evaluated  unless  it  is
     non-atomic.
        It  should  be noted that the prog function is an extension of
     the LISP 1.5 prog function, in that go's and return's  may  occur
     in  more  places  than  LISP  1.5  allowed.   However,  the  LISP
     compilers implemented on ITS, Multics, and the DECsystem  10  for
     MACLISP  require  that  go's and return's be lexically within the
     scope of the prog. This makes a function which does not contain a
     prog, but which contains a go or return uncompilable.
        See also the 'do' function,  which uses  a  body  similar   to
     prog.   The  do  function  and  the catch and throw functions are
     included  in  MACLISP  as  an  attempt  to  encourage   goto-less
     programming  style,  which  leads  to  more readable, more easily
     maintained code.  The programmer  is  recommended  to  use  these
     functions instead of prog wherever possible.
11/18/73                          5.2                          Page 37
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
     Example:
     (prog (x y z)       ;x, y, z are prog variables  - temporaries.
        (setq  y  (car w) z (cdr w))           ;w is a free  variable.
     loop
        (cond ((null y) (return x))
              ((null z) (go err)))
     rejoin
        (setq x (cons (cons (car y) (car z))
                         x))
        (setq y (cdr y)
              z (cdr z))
        (go loop)
     err
        (break are-you-sure? t)
        (setq z  y)
        (go rejoin))
do	FSUBR
     do provides a generalized "do loop" facility, with  an  arbitrary
     number of "control variables" whose values are saved  when the do
     is entered and restored when it is left.  It comes in two forms.
        The newer form of do is:
     (do ((<var> <init> <repeat>)...)
         (<end-test> <exit-form>...)
         <body>...)
     The  first  argument  of  do  is  a  list of zero or more control
     variable specifiers.  Each control variable specifier has as  its
     car  the name of a variable, as its cadr an initial value <init>,
     which defaults to nil if it is omitted, and as its caddr a repeat
     value <repeat>.  If <repeat> is omitted, the <var> is not changed
     between loops.  All assignment to the control variables  is  done
     in  parallel.   At  the beginning of the first iteration, all the
     <init>s are evaluated, then the <var>s are saved, then the <var>s
     are setq'ed to the <init>s.  Note that the <init>s are  evaluated
     before the <var>s are bound.  At the beginning of each succeeding
     iteration  those  <var>s that have <repeat>s get setq'ed to their
     respective <repeat>s.  Note that all the <repeat>s are  evaluated
     before any of the <var>s are changed.
     The  second  argument of do is a list of an end testing predicate
     <end-test> and zero or more  forms,  the  <exit-form>s.   At  the
     beginning  of  each iteration, after processing of the <repeat>s,
     the <end-test> is evaluated.  If the  result  is  nil,  execution
     proceeds  with the body of the do.  If the result is not nil, the
     <exit-forms> are  evaluated  from  left  to  right  and  then  do
     returns.   The  value  of  the  do  is  the  value  of  the  last
Page 38                           5.2                         11/18/73
		                           Flow of Control
                    ***** ROUGH DRAFT #9905 *****
     <exit-form>, or nil if there were no <exit-form>s.  Note that the
     second argument to do is similar to a cond clause.  If the second
     argument to do is nil, there is no  <end-test>  or  <exit-form>s,
     and  the  the body of the do is executed only once.  In this type
     of do it is an error to have <repeat-val>s.  This type of do is a
     "prog with initial values."
     The remaining arguments to do constitute a prog body.   When  the
     end  of the body is reached, the next iteration of the do begins.
     If return is used, do returns the indicated  value  and  no  more
     iterations occur.
        The older form is:
     (do <var> <init-val> <repeat-val> <end-test> <body>...)
     The  first  time  through  the  loop  <var>  gets  the  value  of
     <init-val>;  the remaining times through the  loop  it  gets  the
     value  of  <repeat-val>,  which  is re-evaluated each time.  Note
     that <init-val> is evaluated before the value of <var> is  saved.
     After  <var>  is set, <end-test> is evaluated.  If it is non-nil,
     the do finishes and returns nil.  If the <end-test> is  nil,  the
     <body>  of the loop is executed.  The <body> is like a prog body.
     Go may be used.  If return is used, its argument is the value  of
     the  do.   If  the  end of the prog body is reached, another loop
     begins.
     Examples of the old form of do:
     (do i 0 (1+ i) (> i (cadr (arraydims x)))
               (store (x i) 0))              ;zeroes out the array x
     (do zz x (cdr zz) (or (null zz) (zerop (f (car zz)))))
                        ; this applies f to each element of x
                        ; continuously until f returns zero.
     Examples of the new form of do:
          (do ((x) (y) (z)) (nil) <body>)
     is like
          (prog (x y z) <body>)
     except that when it runs off the end  of the <body>, do loops but
     prog returns nil.
     (do ((x y (f x))) ((p x)) <body>)
     is like
     (do x y (f x) (p x) <body>)
     (do ((x x (cdr x))
          (y y (cdr y))
          (z nil (cons (f x y) z))) ; exploits parallel assignment
         ((or (null x) (null y))
11/18/73                          5.2                          Page 39
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
          (nreverse z)))            ; typical use of nreverse
                                    ; body has been omitted
     is like (maplist 'f x y).
     (do ((x e (cdr x)) (oldx x x)) ((null x)) <body>)
     This exploits the parallel assignment to control  variables.   On
     the  first  iteration,  the value of oldx is whatever value x had
     before the  do  was  entered.   On  succeeding  iterations,  oldx
     contains the value that x had on the previous iteration.
     In either form of do, the <body> may contain no forms at all.
go		FSUBR
     The  go  function is used to do a "go-to" within the body of a do
     or a prog.  If the argument is an  atom,  it  is  not  evaluated.
     Otherwise  it  is repeatedly evaluated until it is an atom.  Then
     'go' transfers control to the point in the prog labelled by a tag
     eq to the argument.  If there is no such tag in the prog,  it  is
     an unseen-go-tag error.  Example:
     (prog (x y z)
       (setq x something)
     loop
       <do something>
       (and <some predicate> (go loop))      ;regular go
       <do something more>
       (go (cond ((minusp x) 'loop)          ;"computed go"
                 (t 'endtag)))
     endtag
       (return z))
return		SUBR 1 arg
     return  is  used  to  return  from  a prog or a do.  The value of
     return's argument is returned by prog or do  as  its  value.   In
     addition,  break  recognizes  the top level form (return <value>)
     specially.  If this form is entered at  top  level  in  a  break,
     <value>  will  be  returned  as  the  value  of break.  If not at
     top-level in a break, and not in a prog or do, return will  cause
     a fail-act error if invoked.
     Example:
        (prog (x)
               (setq x (reverse y))
               (or (cddr x) (return (cadr x)))
               (return (caddr x)))
Page 40                           5.2                         11/18/73
		                           Flow of Control
                    ***** ROUGH DRAFT #9905 *****
     If y is '(z y x w y u t s), this returns u.  If y is '(a b), this
     returns a.
11/18/73                          5.2                          Page 41
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
 5.3        Nonlocal Exits
catch		FSUBR
     Catch  is the LISP function for doing structured non-local exits.
     (catch x) evaluates x and  returns  its  value,  except  that  if
     during  the  evaluation of x (throw y) should be evaluated, catch
     immediately returns y without further evaluating x.
     Catch may also be used with a  second  argument,  not  evaluated,
     which is used as a tag.  (catch x b) will catch a (throw y b) but
     not a (throw y z).  Throw with only one argument always throws to
     the  nearest  catch.   Catch  with  only one argument catches any
     throw.  It is an error if throw is done when there is no suitable
     catch.  Example:
        (catch
          (mapcar (function (lambda (x)
                             (cond ((minusp x) (throw x negative))
                                   (t (f x)) )))
               y)
          negative)
     which returns a list of f of each  element  of  y  if  y  is  all
     positive, otherwise the first negative member of y.
     The  user  of  catch  and  throw is recommended to stick to the 2
     argument version, which is no less efficient, and tends to reduce
     the  likelihood  of  bugs.   The  one  argument  versions   exist
     primarily  as  an  easy  way  to  fix old LISP programs which use
     errset and err for non-local  exits.   This  latter  practice  is
     rather  confusing, because err and errset are supposed to be used
     for error handling, not general program control.
throw		FSUBR
     Throw is used with catch as a structured nonlocal exit mechanism.
     (throw x) evaluates x and throws  the  value  back  to  the  most
     recent catch.
     (throw  x  <tag>)  throws  the value of x back to the most recent
     catch labelled with <tag> or unlabelled.  Catches with  tags  not
     eq to <tag> are skipped over.  x is evaluated but <tag> is not.
     See the description of catch for further details.
Page 42                           5.3                         11/18/73
		                           Flow of Control
                    ***** ROUGH DRAFT #9905 *****
 5.4        Causing and Controlling Errors
err		FSUBR
     (err)  causes  an error which is handled the same as a LISP error
     except that there is no preliminary user interrupt.
     (err x) is like (err)  except  that  if  control  returns  to  an
     errset,  the value of the errset will be the result of evaluating
     x, instead of nil.
     (err x nil) is the same as (err x).  (err x y), where  y  is  not
     nil,  is  like  (err x) except that x is not evaluated until just
     before the errset returns it.  That  is,  x  is  evaluated  after
     unwinding   the  pdl  and  restoring  the  bindings.   y  is  not
     evaluated.
     Note: some people use err and errset where catch  and  throw  are
     indicated.   This  is  a  very  poor  programming  practice.  See
     writeups of catch and throw for details.
error		LSUBR 0 to 3 args
     This is a function which allows user functions  to  signal  their
     own errors using the LISP error system.
     (error) is the same as (err).
     (error  <message>)  signals  a simple error - no datum is printed
     and no user interrupt is signalled.  The error message typed  out
     is <message>.
     (error  <message> <datum>) signals an error with <message> as the
     message to be typed out, <datum> as the LISP object to be printed
     in the error message.  No user interrupt is signalled.
     (error <message> <datum> <uint-chn>) signals an error  but  first
     signals  a  user  interrupt  on channel <uint-chn>, provided that
     there is such a channel and it has a  non-nil  service  function.
     <uint-chn>  may  be the channel number or the atomic symbol whose
     value is the interrupt service function for the  channel  --  see
     section  11.4.2.   If the service function returns an atom, error
     goes ahead and signals a regular error.  If the service  function
     returns  a list, error returns as its value the car of that list.
     In this case it was a "correctable" error.
11/18/73                          5.4                          Page 43
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
errset		FSUBR
     Errset evaluates its first argument.  If  no  errors  occur,  the
     result  is  consed  with  nil  and  returned.  If an error occurs
     during the  evaluation  of  the  first  argument,  the  error  is
     prevented from escaping from inside the errset and errset returns
     nil.   Errset  may  also be made to return any arbitrary value by
     use of the err function.
     If a second argument is given to errset, it is not evaluated.  If
     it is nil, no error message will be printed if  an  error  occurs
     during  the evaluation of errset's first argument.  If the second
     argument is not nil, or if errset is used with only one argument,
     any error messages generated will be printed.
     Examples:
     If you are not sure x is a number:
                        (errset (setq x (add1 x)))
     This last example may not work in compiled code if  the  compiler
     chooses  to  open-code  the  add1  rather  than  calling the add1
     subroutine.  The user of such code must be extremely  careful  if
     he wishes to use it compiled.
     To suppress message if the value of a is not an atomic symbol:
                          (errset (set a b) nil)
     To do the same but generate one's own message:
           (or (errset (set a b) nil)
               (print (list a 'is 'not 'a 'variable)))
Page 44                           5.4                         11/18/73
		           Manipulating the Constituents of Atomic Symbols
                    ***** ROUGH DRAFT #9905 *****
 6.         Manipulating the Constituents of Atomic Symbols
 6.1        The Value Cell
   Each  atomic symbol has associated with it a "value cell," which is
a piece of storage that can hold a LISP object.  Initially this  value
cell is "unbound" or "undefined," i.e. empty.  An object can be placed
into  an atomic symbol's value cell by setq'ing or binding.  Once this
has been done, this object will be returned when the atomic symbol  is
evaluated.  The atomic symbol is said to have a value of the object.
setq		FSUBR
     setq  is  used  to  assign  values to variables (atomic symbols.)
     setq  takes  its  arguments  in   pairs,   and   processes   them
     sequentially,  left  to  right.  The first member of each pair is
     the variable, the second is the value.  The  value  is  evaluated
     but the variable is not.  The value of the variable is set to the
     value  specified.   You  must  not setq the special atomic-symbol
     constants t and nil.  The value returned  by  setq  is  the  last
     value assigned, i.e. the value of its last argument.
     Example:  (setq x (+ 1 2 3) y (cons x nil))
        returns (6) and gives x a value of 6 and y a value of (6).
     Note  that  the  first  assignment is processed before the second
     assignment is done, resulting in the second use of x getting  the
     value assigned in the first pair of the setq.
set		SUBR 2 args
     Set  is  like  setq  except that the first argument is evaluated;
     also set only takes one pair of arguments.   The  first  argument
     must  evaluate to an atomic symbol, whose value is changed to the
     value of the second argument.   Set  returns  the  value  of  its
     second argument.  Example:
         (set (cond ((predicate) 'atom1) (t 'atom2))
               'stba)
11/18/73                          6.1                          Page 45
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
     evaluates  to  stba  and  gives  either atom1 or atom2 a value of
     stba.
     Set could have been defined by:
     (defun set (x y)
         (apply 'setq (list x (list 'quote y)) ))
boundp		SUBR 1 arg
     The argument to boundp must be an atomic symbol.   If  it  has  a
     value, cons of nil with that value is returned.  Otherwise nil is
     returned.  Example:
        (boundp 't) => (nil . t)   ;since the value of t is t
definedp		SUBR 1 arg
     This  predicate returns t if its argument (a symbol) has a value,
     and nil otherwise.
makunbound	SUBR 1 arg
     The argument to makunbound must be an atomic symbol.   Its  value
     is  removed  and it becomes undefined, which is the initial state
     for atomic symbols.
     Example:
               (setq a 1)
               a => 1
               (makunbound 'a)
               a => unbnd-vrbl error.
     Makunbound returns its argument.
Page 46                           6.1                         11/18/73
		           Manipulating the Constituents of Atomic Symbols
                    ***** ROUGH DRAFT #9905 *****
 6.2        The Property List
   A property-list is a list with an even number  of  elements.   Each
pair  of elements constitutes a property:  the first element is called
the "indicator" and the second is called the "value."   The  indicator
is  generally  an  atomic  symbol  which  serves  as  the  name of the
property.  For example, one type of functional property uses the  atom
expr as its indicator.  The value is a LISP object.  In the case of an
expr-property,  the value is a list beginning with lambda.  An example
of a property list with two properties on it is:
     (expr (lambda (x) (plus 14 x)) foobar t)
The first property has indicator expr and value (lambda (x)  (plus  14
x)), the second property has indicator foobar and value t.
   Each  atomic symbol has associated with it a property-list which is
kept on its cdr.  It is also possible to have  "disembodied"  property
lists  which  are  not  associated with any atom.  These also keep the
property list on their cdr, as the form of a disembodied property list
is (<anything> . plist).  The way to  create  a  disembodied  property
list is (ncons nil).
   The user familiar with LISP 1.5 will want to note that the property
list "flags" which are allowed on LISP 1.5 property lists do not exist
in MACLISP.
get		SUBR 2 args
     (get  x  y)  gets x's y-property.  x can be an atomic symbol or a
     disembodied property list.   The  value  of  x's  y  property  is
     returned,  unless  x  has  no  y-property  in  which  case nil is
     returned.  Example:
     (get 'foo 'bar)
       nil                         ;foo has no bar property
     (putprop 'foo 'zoo 'bar)      ;give foo a bar property
       zoo
     (get 'foo 'bar)
       zoo
     (cdr 'foo)                    ;look at foo's property list.
       (bar zoo ...other properties...)
11/18/73                          6.2                          Page 47
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
getl		SUBR 2 args
     (getl x  y) is like get except that y is  a  list  of  properties
     rather  than just a single property.   Getl searches x's property
     list until a property in the list y is found.  The portion of x's
     property list beginning with this property is returned.  The  car
     of  this is the property name and the cadr is what get would have
     returned.  Getl returns nil if none of the properties in y appear
     on the property list of x.  Getl could have been defined by:
     (defun getl (x pl)
        (do ((q (cdr x) (cddr q)))       ; scan down cdr of x
            ((or (null q) (memq (car q) pl)) q)))
putprop		SUBR 3 args
     (putprop x y z) gives x a  z-property of  y and  returns  y.    x
     may  an  atomic  symbol  or a disembodied property list.  This is
     like defprop except that  the  arguments  are  evaluated.   After
     somebody does (putprop x y z), (get x z) will return  y.
     Example:  (putprop 'foo 'bar 'often-with)
defprop		FSUBR
     (defprop x y z) gives x a z-property of y.  The arguments are not
     evaluated.  Example:
         (defprop foo bar often-with)
remprop		SUBR 2 args
     (remprop  x  y) removes x's y-property, by splicing it out of x's
     property list.  The value is t if x had a y-property, nil  if  it
     didn't.   x  may  be  an  atomic symbol or a disembodied property
     list.  Example:
         (remprop 'foo 'expr) undefines the function  foo  if  it  was
     defined
     by (defun foo (x) ... )
Page 48                           6.2                         11/18/73
		           Manipulating the Constituents of Atomic Symbols
                    ***** ROUGH DRAFT #9905 *****
 6.3        The Print-Name
   Each  atomic  symbol  has an associated character string called its
"print-name," or "pname" for short.  This character string is used  as
the external representation of the symbol.  If the string is typed in,
it is read as a reference to the symbol.  If the symbol is asked to be
"print"ed,  the  string  is  typed out.  Generally pnames are unique -
there is only one atomic symbol whose pname is a particular string  of
characters.  However, by using multiple obarrays (see section 12.4) or
"uninterned"  atomic  symbols (ones whose pnames are not "interned" or
registered in an obarray), it is possible to get two  atoms  with  the
same pname.
samepnamep	SUBR 2 args
     The arguments to samepnamep must evaluate to atomic symbols or to
     character  strings.  The result is t if they have the same pname,
     nil otherwise.  The pname of a character string is considered  to
     be the string itself.
     Examples:
         (samepnamep 'xyz (maknam '(x y z))) => t
         (samepnamep 'xyz (maknam '(w x y))) => nil
         (samepnamep 'x "x") => t
alphalessp	SUBR 2 args
     (alphalessp  x  y),  where x and y evaluate to atomic symbols  or
     character strings, returns t if the pname of x occurs earlier  in
     alphabetical  order  than  the  pname  of  y.   The   pname  of a
     character  string   is  considered  to  be   the  string  itself.
     Examples:
               (alphalessp 'x 'x1) => t
               (alphalessp 'z 'q) => nil
               (alphalessp "x" 'y) => t
11/18/73                          6.3                          Page 49
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
 6.4          Miscellaneous Functions
getchar		SUBR 2 args
     (getchar  x  n),  where  x is an atomic symbol and n is a number,
     returns the nth character of x's pname, where n = 1  selects  the
     first  character.   The  character  is  returned  as  a character
     object.  nil is returned if n is out of bounds.
intern		SUBR 1 arg
     (intern x), where x is an atomic symbol, puts x  on  the  current
     obarray and returns x.  Note that it puts x itself on the obarray
     and not a copy, thus if there is already an atomic symbol on that
     obarray with the same pname, it will automatically get remobed.
remob		SUBR The argument to remob must  be  an  atomic  symbol.   It  is
     removed  from  the  current  obarray  if  it  is interned on that
     obarray.  This  makes  the  atomic  symbol  inaccessible  to  any
     S-expressions that may be read in or loaded in the future.  remob
     returns nil.
maknam		SUBR 1 arg
     Maknam takes as its argument a list of characters, like readlist,
     and  returns  an uninterned atom whose pname is determined by the
     list of characters.  Example:
               (maknam '(a b 60 d)) => ab0d
gensym		LSUBR 0 or more args
     gensym creates and returns a new  atomic  symbol,  which  is  not
     interned  on the obarray (is not recognized by read.)  The atomic
     symbol's pname is of the form <prefix><number>, e.g. g0001.   The
     <number> is incremented each time.
     If  gensym  is given arguments, a numeric argument is used to set
     the <number>.  The pname of an atomic-symbol argument is used  to
     set the <prefix>.  E.g. (gensym 'foo 40) => f0032
     Note  that the <number> is in decimal and always four digits, and
Page 50                           6.4                         11/18/73
		           Manipulating the Constituents of Atomic Symbols
                    ***** ROUGH DRAFT #9905 *****
     the <prefix> is always one character.
11/18/73                          6.4                          Page 51
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
 6.5        Use of Atomic Symbols as Functions
   Atomic symbols may be used as names for functions.  This is done by
putting the actual function (a subr-object or a lambda-expression)  on
the  property  list  of  the atomic symbol as a "functional property,"
i.e. under one of the indicators expr, fexpr, macro, subr,  lsubr,  or
fsubr.
   Array  properties  (see  chapter  9)  are  also  considered  to  be
functional properties, so an atomic symbol which is  the  name  of  an
array is also the name of a function.
   When  an  atomic  symbol which is the name of a function appears in
function position in a list being  evaluated,  or  is  "applied,"  the
function which it names is used.
args		LSUBR 1 or 2 args
     (args 'f) determines the number of arguments expected by f.  If f
     wants  n arguments, args returns (nil . n).  If f can take from m
     to n arguments, args returns (m . n).  If f  is  an  fsubr  or  a
     lexpr, expr, or fexpr, the results are meaningless.
     (args  'f x), where x is (nil . n) or (m . n), sets the number of
     arguments desired by f.  This only works for compiled, non-system
     functions.
defun		FSUBR
     defun is used for defining functions.  The general form is:
               (defun <name> <optional-type>
                      ( <lambda-variable>...)
                      <body>...)
     however, <name> and <type> may be interchanged.   <type>  may  be
     expr,  fexpr,  or  macro.   If  it  is  omitted, expr is assumed.
     Examples:
     (defun addone (x) (1+ x))     ;defines an expr
     (defun quot fexpr (x) (car x))          ;defines a fexpr
     (defun fexpr quot (x) (car x))          ;is the same
     (defun zzz expr x
         (foo (arg 1)(arg 2)))     ;this is how you define a lexpr.
Page 52                           6.5                         11/18/73
		           Manipulating the Constituents of Atomic Symbols
                    ***** ROUGH DRAFT #9905 *****
     Note:  the functions defprop and putprop may  also  be  used  for
     defining functions.
11/18/73                          6.5                          Page 53
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
                    This page intentionally left blank.
Page 54                           6.5                         11/18/73
		                         Functions on Numbers
                    ***** ROUGH DRAFT #9905 *****
 7.         Functions on Numbers
     For  a  description  of  the  various  types  of  numbers used in
     MACLISP, see chapter 2.
 7.1        Arithmetic Functions
 7.1.1          Arithmetic Predicates
bigp		SUBR 1 arg
     The predicate bigp returns its argument if  that  argument  is  a
     bignum, and nil otherwise.
smallnump		SUBR 1 arg
     The  smallnump  predicate  returns its argument if it is a fixnum
     (as opposed to a bignum or a flonum), nil otherwise.
zerop		SUBR 1 arg
     The zerop predicate returns t if its argument is fixnum  zero  or
     flonum  zero.   (There  is no bignum zero.)  Otherwise it returns
     nil.
plusp		SUBR 1 arg
     The plusp predicate returns t if its argument is strictly greater
     than zero, nil if it is zero or  negative.  It is  an   error  if
     the argument is  not a number.
11/18/73                         7.1.1                         Page 55
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
minusp		SUBR 1 arg
     The  minusp  predicate  returns  t  if its argument is a negative
     number, nil if it is a non-negative number.  It is  an  error  if
     the argument is not a number.
oddp		SUBR 1 arg
     The  oddp  predicate  returns t if its argument is an odd number,
     otherwise nil.  The argument must be a fixnum or a bignum.
signp		FSUBR
     The signp predicate is used to test the sign of a number.  (signp
     c x) returns t if x's sign satisfies the test c, nil if  it  does
     not.   x is evaluated but c is not.  It is an error if x is not a
     number.  c can be one of the following:
               l         means     x<0
               le          "       x<0
               e           "       x=0
               n           "       x/=0
               ge          "       x>0
               g           "       x>0
     Examples:
         (signp le -1) => t
         (signp n 0) => nil
haulong		SUBR 1 arg
     (haulong x) returns the number of significant bits in x.   x  can
     be  a  fixnum  or  a bignum.  The result is the least integer not
     less than the base-2 logarithm of |x|+1.  Examples:
         (haulong 0) => 0
         (haulong 3) => 2
         (haulong -7) => 3
         (haulong 12345671234567) => 40.
Page 56                          7.1.1                        11/18/73
		                         Functions on Numbers
                    ***** ROUGH DRAFT #9905 *****
 7.1.2      Comparison
=		SUBR 2 args
     (= x y) is t if x and y are numerically equal.  x and y  must  be
     both fixnums or both flonums.
greaterp		LSUBR 2 or more args
     Greaterp compares its arguments, which must be numbers, from left
     to right.  If any argument is not greater than the next, greaterp
     returns  nil.   But  if  the  arguments  to greaterp are strictly
     decreasing, the result is t.  Example:
               (greaterp 4 3) => t
               (greaterp 1 1) => nil
               (greaterp 4.0 3.6 -2) => t
               (greaterp 4 3 1 2 0) => nil
>		SUBR 2 args
     (> x y) is t if x is strictly greater than y, and nil  otherwise.
     x and y must be both fixnums or both flonums.
lessp		LSUBR 2 or more args
     Lessp compares its arguments, which must be numbers, from left to
     right.   If any argument is not less than the next, lessp returns
     nil.  But if the arguments to lessp are strictly increasing,  the
     result is t.  Example:
               (lessp 3 4) => t
               (lessp 1 1) => nil
               (lessp -2 3.6 4) => t
               (lessp 0 2 1 3 4) => nil
11/18/73                         7.1.2                         Page 57
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
<		SUBR 2 args
     (<  x y) is t if x is strictly less than y, and nil otherwise.  x
     and y must be both fixnums or both flonums.
max		LSUBR 1 or more args
     Max returns the largest of its arguments, which must be numbers.
min		LSUBR 1 or more args
     Min returns the smallest of its arguments, which must be numbers.
Page 58                          7.1.2                        11/18/73
		                         Functions on Numbers
                    ***** ROUGH DRAFT #9905 *****
 7.1.3      Conversion
fix		SUBR 1 arg
     (fix x) converts x to a fixnum  or  a  bignum  depending  on  its
     magnitude.  Examples:
               (fix 7.3) => 7
               (fix -1.2) => -2
float		SUBR 1 arg
     (float x) converts x to a flonum.  Example:
               (float 4) => 4.0
abs		SUBR 1 arg
     (abs  x)  =>  |x|, the absolute value of the number x.  Abs could
     have been defined by:
     (defun abs (x) (cond ((minusp x) (minus x))
                          (x) ))
minus		SUBR 1 arg
     Minus returns the negative of its argument, which can be any kind
     of number.  Examples:
               (minus 1) => -1
               (minus -3.6) => 3.6
haipart		SUBR 2 args
     (haipart x n) extracts  n  leading  or  trailing  bits  from  the
     internal  representation of x.  x may be a fixnum or a bignum.  n
     must be a fixnum.  The value is returned as a fixnum or a bignum.
     If n is positive, the result contains the n  high-order  bits  of
     abs(x).   If  n  is  negative,  the  result  contains  the abs(n)
     low-order bits of abs(x).  If abs(n) is bigger than the number of
     significant bits in x, abs(x) is returned.
11/18/73                         7.1.3                         Page 59
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
     Examples:
         (haipart 34567 7) => 162
         (haipart 34567 -5) => 27
         (haipart -34567 -5) => 27
Page 60                          7.1.3                        11/18/73
		                         Functions on Numbers
                    ***** ROUGH DRAFT #9905 *****
 7.1.4      Addition
plus		LSUBR 0 or more args
     Plus returns the sum of its arguments, which may be any  kind  of
     numbers.
+		LSUBR 0 or more args
     +  returns  the  sum  of  its  arguments.   The arguments must be
     fixnums, and the result is always a fixnum.  Overflow is ignored.
     Examples:
               (+  2 6 -1) => 7
               (+ 3) => 3          ;trivial case
               (+) => 0            ;identity element
+$		LSUBR 0 or more args
     +$ returns the sum of  its  arguments.   The  arguments  must  be
     flonums and the result is always a flonum.  Examples:
               (+$ 4.1 3.14) => 7.24
               (+$  2.0 1.5  -3.6)  => -0.1
               (+$ 2.6) => 2.6               ;trivial case
               (+$)  => 0.0                  ;identity element
add1		SUBR 1 arg
     (add1 x) => x + 1.  x may be any kind of number.
1+		SUBR 1 arg
     (1+  x)  =>  x+1.   x  must  be a fixnum.  The result is always a
     fixnum.  Overflow is ignored.
1+$		SUBR 1 arg
     (1+$ x) => x+1.0.  x must be a flonum.  The result  is  always  a
     flonum.
11/18/73                         7.1.4                         Page 61
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
 7.1.5      Subtraction
difference	LSUBR 1 or more args
     difference  returns  its  first  argument  minus  the rest of its
     arguments.  It works for any kind of numbers.
-		LSUBR 0 or more args
     This is the fixnum-only subtraction function.  It does not detect
     overflows.
     (-) => 0, the identity element
     (- x) =>  the negative of x.
     (- x y) =>  x  -  y.
     (- x y z) => x - y - z
     etc.
-$		LSUBR 0 or more args
     This is the flonum-only subtraction function.
     (-$) =>  0.0, the identity element
     (-$ x)  => the negation  of x.
     (-$ x y) => x - y.
     (-$ x y z) => x - y  -  z.
     etc.
*dif		SUBR 2 args
     This is an obsolete arithmetic difference function.
     (*dif x y) => x - y.
sub1		SUBR 1 arg
     (sub1 x) => x-1.  X may be any kind of number.
1-		SUBR 1 arg
     (1- x) => x-1.  x must be a  fixnum.   The  result  is  always  a
     fixnum and overflow is not detected.
Page 62                          7.1.5                        11/18/73
		                         Functions on Numbers
                    ***** ROUGH DRAFT #9905 *****
1-$		SUBR 1 arg
     (1-$ x) => x-1.0.  x must be a flonum.
11/18/73                         7.1.5                         Page 63
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
 7.1.6      Multiplication
times		LSUBR 0 or more args
     Times  returns  the  product  of its arguments.  It works for any
     kind of numbers.
*		LSUBR 0 or more args
     * returns the product of its arguments.  The  arguments  must  be
     fixnums.   Th  result  is  always  a  fixnum.   Overflow  is  not
     detected.  Examples:
               (* 4 5 -6) => -120.
               (* 3) => 3          ;trivial case
               (*) => 1            ;identity element
*$		LSUBR 0 or more args
     *$ returns the product of its arguments.  The arguments  must  be
     flonums and the result is always a flonum.  Examples:
               (*$ 3.0 2.0 4.0) => 24.0
               (*$ 6.1) => 6.1     ;trivial case
               (*$) => 1.0         ;identity element
Page 64                          7.1.6                        11/18/73
		                         Functions on Numbers
                    ***** ROUGH DRAFT #9905 *****
 7.1.7      Division
quotient		LSUBR 1 or more args
     Quotient  returns its first argument divided by  the  rest of its
     arguments.  The arguments may any kind of number.    (cf.  /  and
     /$) Examples:
         (quotient 3 2)  => 1      ;fixnum division truncates
         (quotient 3 2.0) =>  1.5  ;but flonum division does not..
         (quotient 6.0 1.5  2.0) => 2.0
*quo		SUBR 2 args
     This is an obsolete arithmetic quotient function.
     (*quo x y) => x / y.
/		LSUBR 0 or more args
     This is the fixnum-only division function.  The arguments must be
     fixnums  and  the  result  of  the  division  is  truncated to an
     integer and returned  as a fixnum.  Note that the  name  of  this
     function  must  be   typed   in  as  //, since LISP uses /  as an
     escape character.
     (//) => 1, the identity element.
     (//  x) => the fixnum reciprocal of x, which
               is 0 if  |x| >  1.
     (// x  y) => x/y.
     (// x  y z) =>  (x/y)/z.
     etc.
/$		LSUBR 0 or more args
     This is the flonum-only division function.   Note  that the  name
     of  this  function must be typed in as  //$, since LISP uses / as
     an escape  character.
     (//$) => 1.0, the identity element
     (//$ x) => the  reciprocal of x.
     (//$ x y) => x/y
     (//$ x y z) => (x/y)/z.
     etc.
11/18/73                         7.1.7                         Page 65
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
remainder		SUBR 2 args
     (remainder x y) => the remainder of the division of x by y.   The
     sign  of  the  remainder is the same as the sign of the dividend.
     The arguments must be fixnums or bignums.
\		SUBR 2 args
     (\ x y) returns the remainder of x divided by y, with the sign of
     x.  x and y must be fixnums.  Examples:
               (\ 5 2) => 1
               (\ 65. -9.) => 2
               (\ -65. 9.) => -2
gcd		SUBR 2 args
     (gcd x y) => the  greatest  common  divisor  of  x  and  y.   The
     arguments must be fixnums or bignums.
Page 66                          7.1.7                        11/18/73
		                         Functions on Numbers
                    ***** ROUGH DRAFT #9905 *****
 7.1.8      Exponentiation and Log Functions
expt		SUBR 2 args
                   y
     (expt x y) = x
     The  exponent  y  may  be  a bignum if the base x is 0, 1, or -1;
     otherwise y must be a fixnum.  x may be any kind of number.
sqrt		SUBR 1 arg
     (sqrt x) => a flonum which is the square root of the number x.
isqrt		SUBR 1 arg
     (isqrt x) => a fixnum which is the square root of x, truncated to
     an integer.
exp		SUBR 1 arg
                x
     (exp x) = e
log		SUBR 1 arg
     (log x) = ln x, the natural log of x.
11/18/73                         7.1.8                         Page 67
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
 7.1.9      Trigonometric Functions
sin		SUBR 1 arg
     (sin x) gives the trigonometric sine of x.  x is in  radians.   x
     may be a fixnum or a flonum.
cos		SUBR 1 arg
     (cos  x)  returns  the cosine of x.  x is in radians.  x may be a
     fixnum or a flonum.
atan		LSUBR 1 or 2 args
     (atan x) returns the arctangent of x, in radians.  x and y may be
     fixnums or flonums.  (atan x y) returns the arctangent of x/y, in
     radians.  y may be 0 as long as x is not also 0.
Page 68                          7.1.9                        11/18/73
		                         Functions on Numbers
                    ***** ROUGH DRAFT #9905 *****
 7.1.10     Random Functions
random		LSUBR 0 or 1 arg
     (random) returns a random fixnum.
     (random nil) restarts the random sequence at its beginning.
     (random x), where x is a fixnum, returns a random fixnum  between
     0 and x-1 inclusive.
11/18/73                        7.1.10                         Page 69
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
 7.2        Logical Operations on Numbers
boole		LSUBR 3 or more args
     (boole  k  x  y)  produces  a bitwise Boolean function of x and y
     under the control of k.  k must be a fixnum between 0 and 17.  If
     the binary representation of k is abcd, then the truth table  for
     the Boolean operation is:
           y
     |01
       0| a  c
     x  |
       1| b  d
     If  boole  has  more  than  three arguments, it goes from left to
     right; thus
               (boole k x y z) = (boole k (boole k x y) z)
     The most common values for k are 1 (and), 7 (or), 6  (xor).   You
     can  get the complement, or logical negation,  of x by (boole 6 x
     -1).
lsh		SUBR 2 args
     (lsh x y), where x and y are fixnums, returns x  shifted  left  y
     bits  if  y  is  positive,  or  x  shifted right |y| bits if y is
     negative.  0 bits are shifted in to fill unused  positions.   The
     result is undefined if |y| > 36.  Examples:
               (lsh 4 1) => 10     (octal)
               (lsh 14 -2) => 3
               (lsh -1 1) => -2
rot		SUBR 2 args
     (rot  x  y)  returns  as a fixnum the 36-bit representation of x,
     rotated left y bits if y is positive, or rotated right  |y|  bits
     if  y  is  negative.   X  and y must be fixnums.  The results are
     undefined if |y| > 36.  Examples:
         (rot 1 2) => 4
         (rot -1 7) => -1
         (rot 601234 36.) => 601234
         (rot 1 -2) => 200000000000 (octal)
Page 70                           7.2                         11/18/73
		                        Character Manipulation
                    ***** ROUGH DRAFT #9905 *****
 8.         Character Manipulation
 8.1          Character Objects
        An atomic symbol with less than two characters in its pname is
     often called a "character object" and used to represent an  ascii
     character.  The atomic symbol with a zero-length pname represents
     the ascii null character, and the symbols with 1-character pnames
     represent  the  character  which is their pname.  Functions which
     take character objects as input usually also accept a string  one
     character  long or a fixnum equal to the ascii-code value for the
     character.  Character objects are always interned on the  obarray
     (see section 6.3).
ascii		SUBR 1 arg
     (ascii  x), where x is a number, returns the character object for
     the ascii code x.
     Examples:
        (ascii 101) => A
        (ascii 56) => /.
explode		SUBR 1 arg
     (explode  x)  returns  a  list  of  characters,  which  are   the
     characters  that would have been typed out if (prin1 x) was done,
     including slashes for special characters but not including  extra
     newlines  inserted  to  prevent  characters  from running off the
     right margin.  Each  character  is  represented  by  a  character
     object.
     Example:
          (explode '(+ 1x 3)) => ( /( + /  // /1  x /  /3 /) )
               ;;Note the presence of slashified spaces in this list.
11/18/73                          8.1                          Page 71
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
explodec		SUBR 1 arg
     (explodec   x)  returns  a  list  of  characters  which  are  the
     characters that would have been typed out if (princ x) was  done,
     not  including extra newlines inserted to prevent characters from
     running  off  the  right  margin.   Special  characters  are  not
     slashified.  Each character is represented by a character object.
     Example:
         (explodec '(+  1x 3)) => ( /( + /  /1 x /  /3 /) )
exploden		SUBR 1 arg
     (exploden   x)  returns  a  list  of  characters  which  are  the
     characters that would have been typed out if (princ x) was  done,
     not including extra newlines inserted to prevent lines characters
     from  running  off  the right margin.  Special characters are not
     slashified.  Each character is represented by a number  which  is
     the ascii code for that character.  cf. explodec.  Example:
         (exploden '(+ 1x 3)) => (50 53 40 61 170 40 63 51)
flatc		SUBR 1 arg
     Flatc returns the length of its argument in characters, if it was
     printed out without slashifying special characters.  (flatc x) is
     the same as (length (explodec x)).
flatsize		SUBR 1 arg
     Flatsize  returns the length of its argument in characters, if it
     was printed out with special characters slashified.  (flatsize x)
     is the same as (length (explode x)).
readlist		SUBR 1 arg
     The argument to readlist is a list of characters.  The characters
     may  be  represented  either  as  numbers  (ascii  codes)  or  as
     character objects.  The characters in the list are assembled into
     an  S-expression as if they had been typed into read (See chapter
     12 for a description of read.)  If macro characters are used, any
     calls to read, readch, tyi, or tyipeek  in  the  macro  character
     functions  take their input from readlists's argument rather than
     from an I/O device or a file.
     Examples:
         (readlist '(a b c)) => abc
Page 72                           8.1                         11/18/73
		                        Character Manipulation
                    ***** ROUGH DRAFT #9905 *****
         (readlist '( /( p r 151 n t /  /' f o o /) ))
               => (print (quote foo))
     ;;Note the use of the slashified special characters  left  paren,
     space, quote, right paren in the argument to readlist.
11/18/73                          8.1                          Page 73
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
 8.2          Functions on Strings
   These  character  string  functions  only  exist  at present in the
Multics implementation of MACLISP.  They all accept atomic symbols  in
place  of  strings as arguments;  in this case the pname of the atomic
symbol is used as  the  string.   When  the  value  of  one  of  these
functions is described as a string, it is always a string and never an
atomic symbol.
getpname		SUBR 1 arg
     (getpname  x)  returns  the pname of x as a character string.  x
     must be an atomic symbol.
makeatom		SUBR 1 arg
     Makeatom returns an atomic symbol, uninterned,  whose  pname  is
     given as a character string argument.  Example:
               (makeatom "foo") => foo      ;which is not eq to a
                                             ;foo that is read in.
CtoI		SUBR 1 arg
     CtoI  returns  as a fixnum the ascii code for the first character
     of its argument, which must be a string.
     Example:  (CtoI "z") => 172
ItoC		SUBR 1 arg
     ItoC returns a string  one  character  long,  consisting  of  the
     character whose ascii code is the argument.
     Example:  (ItoC 101) => A
catenate		LSUBR 0 or more args
     The  arguments  to  catenate  must  be  strings.  The result is a
     string  which  is  all  the  arguments   concatenated   together.
     Example:
Page 74                           8.2                         11/18/73
		                        Character Manipulation
                    ***** ROUGH DRAFT #9905 *****
               (catenate "abc" "-" "bar") => "abc-bar"
index		SUBR 2 args
     Index  is  the  PL/I  builtin  function index.  The arguments are
     character strings.  The position of the first occurrence  of  the
     second  argument in the first is returned, or 0 if there is none.
     Examples:
               (index "foobar" "ba") => 4
               (index "foobar" "baz") => 0
               (index "goobababa" "bab") => 4
stringlength	SUBR 1 arg
     The argument to stringlength must be  a  character  string.   The
     number of characters in it is returned.  Examples:
         (stringlength "foo") => 3
         (stringlength "") => 0
substr		LSUBR 2 or 3 args
     This is the PL/I substr builtin.  (substr x m n) returns a string
     n  characters  long, which is a portion of the string x beginning
     with its m'th character and proceeding for n characters.  m and n
     must be fixnums, x must be a string.
     (substr x m) returns the portion of the string x  beginning  with
     its m'th character and continuing until the end of the string.
     Examples:
         (substr "foobar" 3 2) => "ob"
         (substr "resultmunger" 6) => "tmunger"
11/18/73                          8.2                          Page 75
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
                    This page intentionally left blank.
Page 76                           8.2                         11/18/73
		                     Functions Concerning Arrays
                    ***** ROUGH DRAFT #9905 *****
 9.         Functions Concerning Arrays
   LISP  provides arrays of any number of dimensions.  The contents of
the arrays can be any LISP objects.   The  different  elements  of  an
array need not be of the same type.
   An array is implemented as a space in which to keep the contents of
the  array  and  a function to access it.  The name of the function is
the name of  the  array.   The  arguments  to  the  function  are  the
subscripts.   LISP  arrays  are  always 0-origin indexed, that is, the
subscript values start at 0.  The subscripts  must  be  fixnums.   The
array-accessing  function  returns  as  its  value the contents of the
selected array cell and as a side-effect saves a pointer to this  cell
for  the  use  of  the  store  function  (see  below).  The functional
property of an array is kept under the indicator array.
   There is a special type of array called an "un  garbage  collected"
array.   If  an  object other than an atomic symbol is only referenced
from an element of a normal array, that object will stay  around,  but
if  an  object  is  only  referenced  by  an  element  of an ungarbage
collected array then the object will be  taken  away  by  the  garbage
collector  and  the  element of the ungarbage- collected array will be
changed to something random.   In  other  words,  ungarbage  collected
arrays do not protect the objects they contain.
   Some  implementations of MACLISP also have number arrays, which can
only hold either fixnums or flonums (bot not both), but which are more
efficient for  this  purpose  than  regular  arrays.   These  are  not
described here.
   Here is an example of a use of arrays:
          (array x t 500.)
          (array y t 500.)              ;define 2 arrays
          (do i 0 (1+ i) (= i (cadr (arraydims 'x)))
            (store (x i) (//$ (float i) 100.0))   ;x(i):=...
            (store (y i) (sin (x i)))             ;y(i):=...
           )        ;end loop
          (plot 'x 'y)        ;call some random plotting routine
11/18/73                          9.                           Page 77
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
*array		LSUBR 3 or more args
     (*array x y b1 b2 ... bn) defines x to be an n-dimensional array.
     The  first  subscript may range from 0 to b1-1, the second from 0
     to b2-1, etc.  If y is t a normal array is created; if y  is  nil
     an "ungarbage-collected" array is created.
array		FSUBR
     (array x y b1 b2 ... bn) is like (*array x y b1 b2 ... bn) except
     that x is not evaluated.  The other arguments are evaluated.
*rearray		LSUBR 1 or more args
     *rearray is used to redefine the dimensions of an array.
     (*rearray  x)  gets rid of the array x.  x is evaluated - it must
     evaluate to an atomic symbol.  The value is t if it was an array,
     nil if it was not.
     (*rearray x type dim1 dim2 ... dimn) is like (*array x type  dim1
     dim2  ...  dimn)  except  that  the  contents  of  the previously
     existing array named x are copied into the new array named x.
store		FSUBR
     The first argument to store must be a subscripted reference to an
     array.  The second argument is  evaluated  and  stored  into  the
     referenced  cell  of  the  array.   Store  evaluates  its  second
     argument before its first argument.
     Examples:
         (store (data i j) (plus i j))
        (store (sine-values (fix (*$ x 100.0)))
               (sin x))
arraydims		SUBR 1 arg
     (arraydims 'x), where x is an array, returns a list of  the  type
     and  bounds  of  x.   Thus if x was defined by (array x t 10 20),
     (arraydims 'x) => (t 10 20)
Page 78                           9.                          11/18/73
		                     Functions Concerning Arrays
                    ***** ROUGH DRAFT #9905 *****
bltarray		SUBR 2 args
     Bltarray is used to copy one array into another.
     (bltarray x y) moves  the  contents  of  the  array  x  into  the
     contents of the array y.  If x is bigger than y, it is truncated.
     If x is smaller than y, the rest of y is unchanged.  x and y must
     evaluate to atomic symbols which have array properties.
fillarray		subr 2 args
     (fillarray <array> <list>) fills the array with consecutive items
     from the list; thus fillarray could have been defined by:
     (defun fillarray (a x)
         (do ((x x (cdr x)) ((n 0 (1+ n)))
             ((null x))
               (store (a n) (car x))
          ))
     If  the  array is too short to contain all the items in the list,
     the extra items are ignored.  (This is not reflected in the  LISP
     definition  above.)   If  the  list  is  too short to fill up the
     array, the last element of the list is used to fill each  of  the
     remaining  slots  in  the  array.  An additional flaw in the LISP
     definition is that fillarray will work with arrays of  more  than
     one  dimension,  filling the array in row-major order.  fillarray
     returns its first argument.
listarray		SUBR 1 arg
     (listarray  <array-name>)  takes  the  elements  of   the   array
     specified  by  <array-name> and returns them as the elements of a
     list.  The length of the list is the size of the  array  and  the
     elements  are  present  in the list in the same order as they are
     stored in the array, starting with the zeroth element.
*********************************************************************
*********************************************************************
*********                                                   *********
*********                TO BE SUPPLIED                     *********
*********               loadarrays.runoff              *********
*********                                                   *********
*********************************************************************
*********************************************************************
11/18/73                          9.                           Page 79
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
*********************************************************************
*********************************************************************
*********                                                   *********
*********                TO BE SUPPLIED                     *********
*********               dumparrays.runoff              *********
*********                                                   *********
*********************************************************************
*********************************************************************
Page 80                           9.                          11/18/73
		                         "Mapping" Functions
                    ***** ROUGH DRAFT #9905 *****
10.         "Mapping" Functions
   Mapping is a type of iteration in which a function is  successively
applied to pieces of a list.  There are several options for the way in
which  the pieces of the list are chosen and for what is done with the
results returned by the applications of the function.
   For example, mapcar operates on successive elements  of  the  list.
As  it  goes down the list, it calls the function giving it an element
of the list as its one argument:  first the car of the list, then  the
cadr,  then  the  caddr, etc.; continuing until the end of the list is
reached.  The value returned by mapcar is a list of the results of the
successive calls to the function.
   An example of the use of mapcar would be  mapcar'ing  the  function
abs  on  the  list  (1  -2  -4.5 6.0e15 -4.2).  The result is (1 2 4.5
6.0e15 4.2).
   The form of a call to mapcar is
                             (mapcar f x)
where f is the function to be mapped and x is the list over  which  it
is to be mapped.  Thus the example given above would be written as
          (mapcar 'abs
                  '(1 -2 -4.5 6.0e15 -4.2))
This has been generalized to allow a form such as
                       (mapcar f x1 x2 ... xn)
In this case f must be a function of n arguments.  Mapcar will proceed
down  the  lists x1, x2, ..., xn in parallel.  The first argument to f
will come from x1, the second from x2, etc.  The  iteration  stops  as
soon as any of the lists becomes exhausted.
   There  are five other mapping functions besides mapcar.  Maplist is
like mapcar except that the  function  is  applied  to  the  list  and
successive  cdr's  of  that list rather than to successive elements of
the list.  Map and mapc  are  like  maplist  and  mapcar  respectively
except  that  the  return value is the first of the lists being mapped
over and the results of the function are ignored.  Mapcan  and  mapcon
are  like mapcar and maplist respectively except that they combine the
results of the function using nconc instead of list.
   Sometimes a do or a straight recursion  is  preferable  to  a  map;
however,  the mapping functions should be used wherever they naturally
apply because this increases the clarity of the code.
   Often  f  will  be  a  lambda-type   function   rather   than   the
atomic-symbol name of a function.  For example,
11/18/73                         10.                           Page 81
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
         (mapcar '(lambda (x) (cons x something)) some-list)
   The functional argument to a mapping function must be acceptable to
apply:  it  cannot  be a macro.  A fexpr or an fsubr may be acceptable
however the results will be bizarre.  For instance, mapping set  works
better than mapping setq, and mapping cond is unlikely to be useful.
   It  is  permissible (and often useful) to break out of a map by use
of a go, return, or throw in  a  lambda-type  function  being  mapped.
Consider  this  function which is similar to and, except that it works
on a list.
(defun andl (x)
    (prog nil       ;prog just used so return will work
          (mapc (function (lambda (y)
                              (or y (return nil)) ))
                x)
          (return t)
             ))
   Here  is  a  table  showing  the  relations  between  the  six  map
functions.
                                applies function to
                         |  successive  |   successive  |
                         |   sublists   |    elements   |
          ---------------+--------------+---------------+
              its own    |              |               |
              second     |     map      |     mapc      |
             argument    |              |               |
          ---------------+--------------+---------------+
            list of the  |              |               |
returns      function    |    maplist   |    mapcar     |
              results    |              |               |
          ---------------+--------------+---------------+
            nconc of the |              |               |
              function   |    mapcon    |    mapcan     |
              results    |              |               |
          ---------------+--------------+---------------+
map                 LSUBR 2 or more args
     The  first  argument  to  map  is  a  function, and the remaining
     arguments are lists.  Map "goes down"  the  lists,  applying  the
     function  to  the  lists each time.  The value returned by map is
     its second argument.  Map stops as soon as one of  the  lists  is
     exhausted.  Example:
     (map '(lambda (x y z) (print (list x y z)))
Page 82                          10.                          11/18/73
		                         "Mapping" Functions
                    ***** ROUGH DRAFT #9905 *****
          '(1 2 3 4) '(a b c d e) '(+ - * |))
     prints
     ((1 2 3 4) (a b c d e) (+ - * |))
     ((2 3 4) (b c d e) (- * |))
     ((3 4) (c d e) (* |))
     ((4) (d e) (|))
     and returns (1 2 3 4).
mapc		LSUBR 2 or more args
     Mapc  is  just  like  map  except that the function is applied to
     successive elements  of  the  lists  rather  than  to  the  lists
     themselves.  Thus the example given under map would print
     (1 a +)
     (2 b -)
     (3 c *)
     (4 d |)
     and return (1 2 3 4)
mapcar		LSUBR 2 or more args
     Mapcar is like mapc except that the return value is a list of the
     results  of  each  application of the function.  Thus the example
     given with mapc would return, not (1 2 3 4), but
     ((1 a +) (2 b -) (3 c *) (4 d |))
maplist		LSUBR 2 or more args
     Maplist is like map except that the return value is a list of the
     results of each application of the function.   Thus  the  example
     given with map would return, not (1 2 3 4), but
     (((1 2 3 4) (a b c d e) (+ - * |)) ((2 3 4) (b c d e) (- * |))
      ((3 4) (c d e) (* |)) ((4) (d e) (|)))
mapcan		LSUBR 2 or more args
     Mapcan  is  like  mapcar  except  that the values returned by the
     function are nconc'ed together instead of being listed  together.
     Thus the example would return
     (1 a + 2 b - 3 c * 4 d |)
11/18/73                         10.                           Page 83
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
mapcon		LSUBR 2 or more args
     Mapcon  is  like  maplist  except that the values returned by the
     function are nconc'ed together instead of being listed  together.
     This  can  have  disastrous effects on the arguments to mapcon if
     one is not careful.  The example would return
     ((1 2 3 4) (a b c d e) (+ - * |) (2 3 4) (b c d e) (- * |)
      (3 4) (c d e) (* |) (4) (d e) (|))
Page 84                          10.                          11/18/73
		                          Sorting Functions
                    ***** ROUGH DRAFT #9905 *****
11.         Sorting Functions
   Several functions are provided for sorting arrays and lists.  These
functions use algorithms which always terminate no matter what sorting
predicate is used, provided only that the predicate always terminates.
These sorts are not necessarily stable, that is equal  items  may  not
stay in their original order.
   After  sorting,  the  argument  (be it list or array) is rearranged
internally so as to be in complete order.  In the  case  of  an  array
argument, this is accomplished by permuting the elements of the array,
while  in the list case, the list is reordered by rplacd's in the same
manner as nreverse.  Thus if the argument should not be clobbered, the
user should sort a copy of the argument,  obtainable  by  bltarray  or
subst, as needed.
   Should  the  comparison  predicate  cause an error, such as a wrong
argument type error, the result of the sort up to that  point  is  not
guaranteed, unless the appropriate replacement for the bad argument is
supplied by the user interrupt handler.
   Both  sort  and  sortcar  handle  the  case  in  which their second
argument is the function alphalessp in a more  efficient  manner  than
usual.   This  efficiency  is primarily due to elimination of argument
checks at comparison time.
sort		SUBR 2 args
        The first argument to  sort  is  an  S-expression  array,  the
     second a predicate of two arguments.  The domain of the predicate
     must include all objects in the array; thus if the array contains
     only  atomic  symbols,  the  predicate  need only apply to atomic
     symbols, but  if  the  array  also  contains  S-expressions,  the
     predicate must apply to them also.  The predicate should take two
     arguments,  and  return non-nil if and only if the first argument
     is strictly less than the second  (in  some  appropriate  sense).
     The  sort  function  proceeds  to  sort the contents of the array
     under the ordering imposed by  the  predicate,  and  returns  its
     first   argument.    Note   that   since  sorting  requires  many
     comparisons, and thus many calls to the predicate,  sorting  will
     be  much  faster  if  the predicate is a compiled function rather
     than interpreted.
11/18/73                         11.                           Page 85
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
     Example:  (defun mostcar (x)
         (cond ((atom x) x)
               ((mostcar (car x)))))
     (sort fooarray
           (function (lambda (x y)
               (alphalessp (mostcar x) (mostcar y)))))
     If fooarray contained these items before the sort:
     (tokens (the lion sleeps tonight))
     (carpenters (close to you))
     ((rolling stones) (brown sugar))
     ((beach boys) (i get around))
     (beatles (i want to hold your hand))
     then after the sort fooarray would contain:
     ((beach boys) (i get around))
     (beatles (i want to hold your hand))
     (carpenters (close to you))
     ((rolling stones) (brown sugar))
     (tokens (the lion sleeps tonight))
sortcar		SUBR 2 args
        sortcar is exactly like sort,  but  the  items  in  the  array
     should  all  be  non-atomic.   sortcar takes the car of each item
     before handing two items to the predicate.  Thus  sortcar  is  to
     sort as mapcar is to maplist.
Page 86                          11.                          11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
12.         Functions for Controlling the Interpreter
12.1        The Top Level Function
   When  LISP  is  at  its  "top level," it continually evaluates some
form.  Normally this form is
                    (setq * (print (eval (read))))
which causes a "read-eval-print loop," i.e. each S-expression that  is
typed  in  gets  evaluated  and  the  value  is printed, then the next
S-expression is read.  It is possible for the user to change  the  top
level form to perform some other action at top level.  See the sstatus
function (section 12.7).
   When  the  LISP  subsystem is entered, it is at top level.  At this
time, a * is typed out and LISP begins continually evaluating the  top
level  form.   LISP  can return to top level from the middle of one of
these evaluations when an  error  occurs.   Generally  errors  do  not
immediately  return  to  top  level; rather they give the programmer a
chance to debug the error.  However, if an error is not  corrected  it
will  eventually  get to top level unless there is an errset (page 44)
in the way.  When LISP returns to its top level, it again  types  a  *
and begins continuously evaluating the top level form.
errlist		VARIABLE
     The  value of errlist is a list of forms which are evaluated when
     control returns to top level either because of an error  or  when
     an  environment  is  initially  started.  This feature is used to
     provide self-starting LISP environments and  to  provide  special
     error handling for subsystems written in LISP.
11/18/73                         12.1                          Page 87
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
*		VARIABLE
     The  value of * is the result of the last evaluation performed at
     top level or in a break loop.  When the lisp environment is first
     entered and when control is returned to top level from an  error,
     the value of * is * itself.
        Example of use:
               (Lines  preceded  with a >>> are user input, others are
               system typeout)
          ;bkpt some-kind-of-lossage
      >>> (evalframe nil)                    ;get uppermost evalframe
          (-46573536345 (foo x y) -53635473537)
      >>> (evalframe (car *))                ;get preceding evalframe
          (-46573536214 (barf (quote lose!!) 2) -53635473422)
Page 88                          12.1                         11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
12.2        Break Points
break		FSUBR
     (break <tag> <pred>) evaluates <pred>, but  not  <tag>.   If  the
     value of <pred> is not nil, the state of the I/O system is saved,
     ";bkpt  <tag>" is typed out, and control returns to the terminal.
     We say that a "break loop" has been entered.  <tag>  may  be  any
     object.   It  is used only as a message typed out to identify the
     break.  It is not evaluated.
        S-expressions may be typed in and evaluated as at  top  level.
     Break  does  an  errset  so  that errors cannot cause an abnormal
     return from the break.
        If $p is typed in, break returns nil.  This "$p" is <dollar> p
     <newline> in the Multics implementation, but <altmode> P  <space>
     in the pdp-10 implementations.
        If  (return x) is typed in, break evaluates x and returns that
     value.  When break returns,  the  state  of  the  I/O  system  is
     restored.
        Break can be used to allow user intervention in a program when
     something unexpected happens.  It is used in this way by the LISP
     error system.
     (break  <tag>  <pred> <form>) is the same as (break <tag> <pred>)
     except that if $p is typed, the <form> is evaluated and  used  as
     the value of the break instead of nil.
11/18/73                         12.2                          Page 89
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
12.3         Control Characters
   LISP  can  be directed to take certain actions by entering "control
characters."  The difference between  control  characters  and  normal
input  is  that  control  characters  take  effect as soon as they are
entered while normal input only takes effect when LISP asks for it, by
use of  functions  such  as  read,  or  by  being  in  the  top  level
read-eval-print loop or in a break loop.
   Control  characters  can be typed in from the terminal according to
some procedure that depends on the implementation.  They can  also  by
"typed in" by a program using the function ioc.
   Although  control  characters are usually processed as soon as they
are typed, they will be delayed if there is a  garbage  collection  in
progress  or  LISP  is  in  (nointerrupt t) mode - see the nointerrupt
function.
               Entering Control Characters in ITS LISP
   In the pdp-10/ITS implementation of MACLISP, control characters are
entered by means of the "CTRL" key  on  the  terminal.   For  example,
CTRL/G  is  entered  by  holding down "CTRL" and striking the "G" key.
Control characters echo as an uparrow or circumflex  followed  by  the
character.  Numbers may not be used as control characters.
              Entering Control Characters in DEC-10 LISP
Control  characters  may  be entered in the same way as in ITS LISP if
LISP is currently (read)'ing from the terminal.  If a LISP program  is
actively  running,  it  is  necessary  to  first gain its attention by
striking ctrl/C.  LISP rings the bell and types a ? and  an  upparrow,
prompting  for  the  entry  of  a character to be treated as a control
character.  If you type a second ctrlC  control  will  return  to  the
monitor.
Page 90                          12.3                         11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
             Entering Control Characters in Multics LISP
   In  the Multics implementation of MACLISP, one signals one's desire
to enter a "control" character by hitting the "attention" key  on  the
terminal.   This  is  called  "break,"  "interrupt,"  "quit,"  etc. on
different terminals.  This causes lisp to type out "CTRL/"  After this
has been typed, you may type one control character, which is a  letter
from  the list in section 12.3.3 which will be interpreted to have its
"control" meaning.
   You may also enter a number, which will be interpreted in  decimal.
A  user  interrupt  will  be  issued  on  the  user  interrupt channel
indicated by the number you typed in.  If there is no such  interrupt,
or  the interrupt service function for that channel is nil, no warning
will be issued.  The argument passed to the interrupt service function
is the atom ioc.   The most useful interrupt channel  numbers  are  0,
which  is  the  same as CTRL/\@; 1, which is the same as CTRL/h, and 2
which is the same as CTRL/a (exactly).
   Note: any input that has been typed in but has not yet been read by
lisp when the attention button is pushed will be lost.   Usually  this
is the current line unless Multics happens to be running slow.
   It  is  also  possible  to enter "control" characters from an input
character stream, which may have its source at the terminal  or  in  a
file,  without  the  use  of the "attention" key.  The desired control
character is prefixed by  a  \036  character,  also  known  as  \r  or
"control up-arrow."  If two of these prefix characters occur together,
one  \036  character  is  read  and  no "control" action is performed.
Otherwise, the character following the \036 is processed as a  control
character,  then  reading  continues.  This method only works with the
letter and special-symbol control characters, but not with the  number
control characters.
NB:  Control  characters will be accepted in upper or lower case.  All
characters other than those with defined meanings are rejected with an
error message.  Only one control character may be entered at  a  time.
When  a  "user  interrupt"  is caused, if the interrupt is not enabled
nothing happens.  If the interrupt is enabled, then  a  user-specified
function  is  called.   The  interrupt  may  be  enabled  by using the
function sstatus.  E.g.:  (sstatus interrupt 2 'f00) causes f00 to  be
called with one argument when interrupt 2 occurs.
Example:
          (system output is underlined, user input is not)
          (defun loop (x) (loop (add1 x)))
          loop
          (loop 0)
                              function runs for a long time,
          <ATTN>               then user hits attention button.
          CTRL/B
          ;bkpt↑b            system enters break loop
11/18/73                         12.3                          Page 91
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
          x                   user looks at value of x
          4067
          <ATTN>               user hits attention button again
          CTRL/G              and returns to top level
          Quit
          *
Page 92                          12.3                         11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
12..3          Control Characters That Have Been Defined
     These are the control characters that have defined meanings
  A       increments  the  value  of  the  atom  ↑a  and  causes  user
          interrupt 2.
  B       causes user interrupt number 1, which (usually)  enters  the
          "bkpt ↑b" breakpoint.
  C       sets the atom ↑d  to  nil,  turning  off  garbage  collector
          messages
  D       sets the atom ↑d to t, turning on garbage collector messages
  G       quits back to top level of lisp, unwinding all bindings
  Q       sets the atom ↑q  to  t,  enabling  input  from  the  source
          selected  by  the value of infile, or by use of the function
          uread.
  R       sets the atom ↑r to t, enabling output to  the  destinations
          selected  by  the value of outfiles, or by use of the uwrite
          function.
  U       causes the current call to (read) to be restarted  from  the
          beginning.
  S       sets the atom ↑q to nil, enabling input from the terminal
  T       sets  the  atom  ↑r  to  nil,  disabling   output   to   the
          destinations that CTRL/r enables.
  V       sets the atom ↑w to nil, enabling output to the terminal
  W       sets the atom ↑w to t, disabling output to the terminal
  X       causes an error which can be caught by errset
  Z       On the pdp-10 returns to DDT.  On Multics returns to Multics
          command level. (start re-enters lisp) This control character
          is  handled immediately even when LISP is garbage collecting
          or running in (nointerrupt  t)  mode,  unlike  most  of  the
          others.
  @       causes user interrupt 0. Note that on Multics an escape must
          be used to type @ sign.
  \       causes user interrupt 14.  Note that on  Multics  an  escape
          must be used to type this backslash character.
11/18/73                        12..3                          Page 93
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
  ]       causes user interrupt 15.
  ↑       causes user interrupt 16.
  The   following   control  characters  only  exist  in  the  Multics
  implementation.
  .       does nothing, used to speed up slow process  by  causing  an
          interaction.   This control character is handled immediately
          even  when  LISP  is  garbage  collecting  or   running   in
          (nointerrupt t) mode, unlike most of the others.
  ?       asks the LISP subsystem what it is doing:  running,  waiting
          for    input,    collecting   garbage,   or   running   with
          user-interrupts  masked  off.   This  control  character  is
          handled  immediately even when LISP is garbage collecting or
          running in (nointerrupt t) mode, unlike most of the others.
  The   following   control   characters   only   exist   in    pdp-10
  implementations with the "moby I/O" capability.
  F       cause display slave to seize a display.
  N       turn on display.
  O       turn off display.
  Y       interrogate display slave.
  The   following   control   characters   only  work  in  the  pdp-10
  implementation.
  K       redisplay the current input.  allows you to get a clean copy
          of your input after rubouts have been used.
  L       erases the screen if using a display terminal, then  does  a
          control k.
  U       if using a display terminal, and in  (sstatus  pagepause  t)
          mode,  and  the  end  of the screen has been reached, typing
          control u will erase the screen and allow lisp  to  continue
          typing out.
Page 94                         12..3                         11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
12..4          Control-Character Functions
ioc		FSUBR
     The  argument  to  ioc  is  processed  as  if  it were a "control
     character" that had been typed in.  Numbers are taken as a whole,
     pname  atoms  (atomic  symbols)  are   processed   character   by
     character, except that nil causes an immediate return.  Examples:
               (ioc 1) causes user interrupt 1.
               (ioc vt) switches output to the terminal.
               (ioc q) switches input to a file.
               (ioc g) quits back to the top level of lisp.
     If ioc returns, its value is t.
iog		FSUBR
     iog saves the values of the I/O switches ↑q, ↑r, and ↑w.  Then it
     processes its first argument the same as ioc.  Next the remaining
     arguments  to  iog are evaluated, from left to right.  The values
     of the variables ↑q, ↑r, and ↑w are restored, and  the  value  of
     the last argument is returned.  Example:
               (iog vt (princ "A Message."))
     gets  a  message  to the console no matter what the I/O system is
     doing.  It evaluates to "A Message."
↑a		VARIABLE
     When a CTRL/a is done, the value of the atom  ↑a  is  incremented
     (user  interrupt 2 is also signalled.)  If ↑a is not a number, it
     is set to 0.
11/18/73                        12..4                          Page 95
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
12.4        Errors and User Interrupts
12.4.1      The LISP Error System
   The errors detected by the LISP  subsystem  are  divided  into  two
types:   correctable and uncorrectable.  The uncorrectable errors will
be explained first since they are simpler.
   An uncorrectable error is an error that causes the  destruction  of
the  evaluation  in  which  it occurs.  An example of an uncorrectable
error is illegal format  in  a  'do'.   When  an  uncorrectable  error
occurs,  the  first  thing  that  happens  is the printing of an error
message.  The error message goes to the terminal and nowhere else,  no
matter  how  the  I/O  switches  and  variables  are set.  (The CTRL/B
feature is an exception  to  this.   See  section  12.3.3)  The  error
message  consists  of some explanatory text and (sometimes) the object
that caused the error.
   After the error message has been printed, control  is  returned  to
the  most  recent  error-catcher.   There  is  an error-catcher at top
level, and error-catchers are set  up  by  the  functions  errset  and
break.   All variable bindings between the error-catcher and the point
where the  error  occurred  are  restored.   Thus  all  variables  are
restored to the values they had at top level or at the time the errset
was done, unless they were setq'ed without being bound.
   What  happens next depends on how the error-catcher was set up.  At
top level, (mapc 'eval errlist)  is  done,  a  *  is  typed,  and  the
read-eval-print   loop  (or  a  user  specified  top  level  form)  is
re-entered.  If an error returns to break,  it  simply  re-enters  its
read-eval-print  loop.   In  the  Multics implementation the fact that
break has caught an error is  signalled  by  doing  something  to  the
terminal  such as blinking a light or spinning the typeball, depending
on the type of terminal.   If  an  error  returns  to  errset,  errset
returns nil and evaluation proceeds.
   The above description is slightly simplified.  It is possible for a
user  interrupt  to  occur  between  the typing of the message and the
unwinding of bindings and return of control to an error-catcher.  This
user interrupt is normally a break  loop  which  allows  the  user  to
examine  the  values of variables before the bindings are restored, in
hope of finding the cause of the error.  If  the  error  is  going  to
return  to  top  level,  the *rset-trap user interrupt (number 19.) is
signalled.  In (*rset t) mode a break loop is entered, but  in  (*rset
nil)  mode  the  user  interrupt  is  ignored  by  the system supplied
handler.  If the error is going to return to a break or an errset, the
errset  user  interrupt  (number  4)  is   signalled.    The   initial
environment  contains  a null handler for this interrupt, but the user
may supply a break loop or other handler.
   Correctable errors are  errors  which  may  be  corrected  by  user
Page 96                         12.4.1                        11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
intervention.   If  such  an  error is correctly corrected, evaluation
will proceed as if no error had occurred.  If the  option  to  correct
the  error  is  not  exercised, this type of error will be handled the
same as an uncorrectable error.
   When a correctable error occurs, a  user  interrupt  is  signalled.
See  section  11.4.2  for user interrupt channel assignments for these
errors.  The initial environment contains handlers  for  these  errors
which  print  an  error  message similar to the message printed for an
uncorrectable error and then enter a break loop.
   The argument passed to the user interrupt handler is usually a list
describing the error.  See section 11.4.2 for details.   If  the  user
interrupt  handler  is  nil, or if it returns a non-list, the error is
treated like an uncorrectable error.  But if  the  handler  returns  a
list, the car of that list is used to correct the error in a way which
depends on the particular error which occurred.
   If  the  most  recent  error-catcher  is  an  errset  or  a  break,
correctable errors will be  treated  as  uncorrectable  errors  unless
there  is  a  non-null  handler  for  user  interrupt  4,  the  errset
interrupt.  This is to  prevent  confusing  "recursive"  error  breaks
unless  the  user  indicates  that he is sophisticated by setting up a
handler for the errset interrupt.
11/18/73                        12.4.1                         Page 97
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
12.4.2      User Interrupts
   LISP provides a number of "user interrupts," which are a  mechanism
by  which  a  user  procedure  may  temporarily  gain  control when an
exceptional condition happens.  The exceptional  conditions  that  use
the  user  interrupt  system  include  certain control characters, the
alarmclock timers, the garbage collector, and many of the errors  that
are detected by the interpreter or by the system functions.
   The  user  interrupts  are  divided up into several channels.  Each
channel is designated by a number.  Each channel has  associated  with
it  a  "service function."  If the service function is nil, interrupts
on that channel will be ignored.  If the service function is not  nil,
it  is  a  function  which  is  called  with  one  argument  when  the
user-interrupt occurs.  The nature of the argument  depends  on  which
channel  the  interrupt is on; usually it is an S-expression which can
be used to localize the cause of the interrupt.  Some user  interrupts
use  the  value  returned by the service function to decide what to do
about the cause of the interrupt.
   The service function for user interrupt channel n can  be  obtained
by  (status  interrupt  n).  It can be set by (sstatus interrupt n f).
The initial values for the service functions of the various interrupts
are provided by the system as break loops for some interrupt  channels
and nil for others.
   Some  user  interrupt  channels keep their service functions as the
values of variables accessible to the user; this  allows  them  to  be
lambda-bound.  See 12.4.3.
   The  interrupt  channels with entries in the return value column of
the table of  user  interrupts  included  in  this  section  are  user
interrupts signalled by correctable error conditions.  The argument to
the  service function is a description of the error in the form shown.
If the service function returns nil (or any atom),  the  normal  error
procedure  occurs  --  control returns to the most recent errset or to
top level if there was no errset.  If the service function  returns  a
list,  it is interpreted as the form shown in the return value column.
The car of the list is used to attempt recovery  from  the  error.  If
recovery  is  successful  execution  proceeds from the point where the
error  occurred.   If  recovery  is  unsuccessful  another  error   is
signalled.   If  a  quote  (') is shown in the return value column, it
means that the car of the list returned by the service  function  will
be evaluated before it is used.
Page 98                         12.4.2                        11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
                   Table of User Interrupt Channels
Chn  Serv. Fcn.      Reason          Arg to       Return
Num  Val. Atom      for intr       Serv. Fcn.     Value
---  ---------      --------       ---------      -----
0      none         ctrl @            nil           -
1      ↑b           ctrl b            nil           -
2      none         ctrl a            nil           -
3    alarmclock     timer went     'time  or
                    off.           'runtime         -
4     errset        error was caught   nil          -
                    by errset.
5    undf-fnctn     undefined fcn    (fcn)        (new-fcn)
6    unbnd-vrbl     undefined atom   (atom)       ('new-value)
7   wrng-type-arg   a fcn didn't   (bad-val)      (new-val)
                    like its arg.
8.  unseen-go-tag   go or throw lost (bad-tag)    (new-tag)
9.  wrng-no-args    wrong num of arg (form args-prop) or
                                     (form lambda-list) or
                                     nil          ('new-form)
10.  gc-lossage     no more core        ?             ?
11.   fail-act      misc. error.    see below     see below
14.    none         ctrl \            nil           -
15.    none         ctrl ]            nil           -
16.    none         ctrl ↑            nil           -
18.    none         autoload      (fcn . prop)      -
19.  *rset-trap     error return      nil           -
                    to top level
20.   gc-daemon     a garbage          ?            -
                    collection
                    occurred.
11/18/73                        12.4.2                         Page 99
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
   The  fail-act  interrupt,  number  11.,  is  used  for a variety of
miscellaneous error conditions.  Here is a table giving the  types  of
arguments  that  may  be passed to the fail-act service function.  For
each type the cause of the interrupt and the return value  to  correct
the error are given.
(arrayindex (name indices...)) An out-of-bounds array access  occurred
     on the array name.  Sometimes it is not possible to determine the
     name  of  the  array, in which case name will be ?.  For example,
     this can happen if the array has been remob'ed.  The return  form
     is  ((name  subs....))  which  will retry the access with the new
     subscripts subs....  name is ignored.
(go return) go or return was used outside of a prog.  The return value
     does not matter; this error is not correctable.
(arg (n)) The arg function was called with argument n,  but  this  was
     not done inside a lexpr.
(setarg (n value)) The function setarg was called with arguments n and
     value and an error similar to the preceding occurred.
(ibase) The reader variable ibase had a bad value:  not  a  fixnum  or
     not  between  2  and  36.   It  is  reset  to  8. before the user
     interrupt  occurs.   Returning  (t)  will  cause  the  reader  to
     continue reading.
(base) The printer variable base had a bad value:  not a fixnum or not
     between  2  and  36.  It is reset to 8. before the user interrupt
     occurs.  Returning (t) will cause the printer to continue.
(infile x) The input file x is invalid for one reason or another.   ↑q
     has  been  reset  to  nil.   If  (t)  is  returned by the service
     function, ↑q will be set back to t and  the  function  that  lost
     trying to input from x will proceed, taking input from infile.
(setq (nil)) You aren't allowed to change the value of nil.
(read-eof) The reader found an end of file in the middle of an object.
     Usually   this  indicates  mismatched  parentheses.   If  (t)  is
     returned, it will go on reading the broken object  from  whatever
     input source is now selected.
(outfile x) The output file x is invalid for one  reason  or  another.
     ↑r  is  reset to nil before the user interrupt occurs.  If (t) is
     returned, ↑r will be set back to t and  the  function  that  lost
     trying to output to x will go on its way.
(filepos x) The filepos function was used on the file x, but this file
     is  not  equipped  for random access.  If ('new-val) is returned,
     filepos returns new-val to its caller without further ado.
Page 100                        12.4.2                        11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
(filepos x n) The filepos function was used in the form (filepos x n),
     but n is not a position inside the  file  x.   If  ('new-val)  is
     returned,  filepos  returns new-val to its caller without further
     ado.
(openi x), (openo x), (opena x), (rename x y), (deletef  x)  The  file
     system  complained  in  some way:  e.g. file not found, incorrect
     access.  The argument passed to the service  function  represents
     the  form which was evaluated to cause the error, except that the
     values of the arguments are the  values  they  have  after  being
     mergef'ed over the defaults, i.e. they are precise namelists.  If
     ('new-val) is returned, the function that lost returns new-val as
     its value without further ado.
11/18/73                        12.4.2                        Page 101
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
12.4.3          User Interrupt Functions and Variables
alarmclock	SUBR 2 args
     alarmclock  is  a  function for controlling timers.  It can start
     and stop two seperate timers; one is a real-time  timer  and  the
     other  is  a  cpu-time  timer.   The first argument to alarmclock
     indicates which timer is being referred to:  it may be  the  atom
     time  to  indicate  the  real-time  timer  or the atom runtime to
     indicate the cpu-time timer.
     The second argument to alarmclock controls what is  done  to  the
     selected  timer.   If it is a positive (non-big) number the timer
     is  started.   Thus  if  n  is  a  positive  fixnum  or   flonum,
     (alarmclock  'time  n)  sets  the  real-time timer to go off in n
     seconds, and (alarmclock 'runtime n) sets the cpu-time  timer  to
     go  off  in n microseconds.  If the timer was already running the
     old setting is lost.  Thus at any given time each timer can  only
     be   running   for   one  alarm,  but  the  two  timers  can  run
     simultaneously.
     If the second argument to alarmclock is not  a  positive  number,
     the timer is shut off, so (alarmclock x nil) or (alarmclock x -1)
     shuts off the timer.
     alarmclock  returns  t  if  it starts a timer, nil if it shuts it
     off.
     When a timer goes off, user  interrupt  3  occurs.   The  service
     function  is  run  in  (nointerrupt t) mode so that it can not be
     interrupted until it has done its thing.  If it  wants  to  allow
     interrupts,  other  timers, etc. it can go (nointerrupt nil).  In
     any case the status of the nointerrupt flag will be restored when
     the service function returns.  The argument passed  to  the  user
     interrupt  service  function  is  a list of one element, the atom
     time or the atom runtime, depending on the first argument in  the
     call  to alarmclock that set up the timer.  See also the function
     nointerrupt.
alarmclock	VARIABLE
     The  value  of  alarmclock  is  the  service  function  for  user
     interrupt  number 3, which is the user interrupt signalled when a
     timer set up by the alarmclock function goes off.
Page 102                        12.4.3                        11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
nointerrupt	SUBR 1 arg
     (nointerrupt  t)  shuts  off  LISP  interrupts.   This   prevents
     alarmclock  timers from going off and prevents the use of control
     characters such as CTRL/g and CTRL/h.  Any  of  these  interrupts
     that  occur  are  simply  saved.  (nointerrupt t) mode is used to
     protect critical code in large subsystems written in LISP.  It is
     also used  by  the  LISP  subsystem  itself  to  protect  against
     interrupts in the garbage collector.
     (nointerrupt  nil) turns interrupts back on. Any interrupts which
     were saved will now get processed.
     Nointerrupt returns the previous state of  the  interruptdisable
     switch, t or nil.  The normal, initial state is nil.
errset		VARIABLE
     The  value  of  the  atom errset is the service function for user
     interrupt number 4, which is signalled when an error is caught by
     an errset.
fail-act		VARIABLE
     The value of fail-act is the service function for user  interrupt
     number  11.,  which  is  signalled when any of a large variety of
     miscellaneous error conditions occurs.
gc-daemon		VARIABLE
     The value of gc-daemon is the service function for user interrupt
     20., which is signalled after each garbage collection.
gc-lossage	VARIABLE
     The  value  of  gc-lossage  is  the  service  function  for  user
     interrupt  number  10.,  which is signalled when there is no more
     memory.  In the Multics implementation, there  is  always  enough
     memory, so this user interrupt never occurs.
11/18/73                        12.4.3                        Page 103
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
unbnd-vrbl	VARIABLE
     The  value  of  unbnd-vrbl  is  the  service  function  for  user
     interrupt number 6, which is signalled when an attempt is made to
     evaluate an atomic symbol which does not have a value (an unbound
     variable.)
undf-fnctn	VARIABLE
     The  value  of  undf-fnctn  is  the  service  function  for  user
     interrupt number 5, which is signalled when an attempt is made to
     call an undefined function.
unseen-go-tag	VARIABLE
     The  value  of  unseen-go-tag  is  the  service function for user
     interrupt 8., which is signalled when go or throw is used with  a
     tag  which  does  not  exist  in  the current prog body or in any
     catch, respectively.
wrng-no-args	VARIABLE
     The value of  wrng-no-args  is  the  service  function  for  user
     interrupt  channel  9.,  which  is  signalled  when a function is
     called with the wrong number of arguments.
wrng-type-arg	VARIABLE
     The value of wrng-type-arg  is  the  service  function  for  user
     interrupt number 7, which is signalled when an argument is passed
     to a system function which is not acceptable to that function.
*rset-trap	VARIABLE
     The  value  of  *rset-trap  is  the  service  function  for  user
     interrupt 19., which is signalled when an error  returns  control
     to top level, just before the bindings are restored.
Page 104                        12.4.3                        11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
12.4.4          Autoload
   The  "autoload"  feature  provides  the  ability for a function not
present in the environment to be automatically loaded in from  a  file
the  first  time  it  is  called.   When  eval, apply, funcall, or the
version of apply used by compiled LISP searches the property  list  of
an  atom  looking  for  a functional property, if the first functional
property found is under the indicator autoload, automatic loading will
occur.
   Automatic loading is performed by means of user-interrupt 18.; thus
the user may assert any desired degree of control over it.   When  the
autoload  property  is  encountered, the user-interrupt 18. handler is
called with one argument, which is a dotted  pair  whose  car  is  the
atomic  symbol  which is the function being autoload'ed, and whose cdr
is the value of the autoload property.   The  system-supplied  handler
for user interrupt 18. could have been defined by:
   (sstatus interrupt 18.
     '(lambda (x)
          (apply (function fasload) (cdr x))))
   When  the  interrupt  handler  returns,  it  had  better have put a
functional property  on  the  property  list  of  the  function  being
autoloaded.   If  not,  an  undf-fnctn error will occur with a message
such as
                 "function undefined after autoload"
Note that the functional property must be placed on the property  list
before the autoload property.  This is normally the case.
Examples of setting up functions to be autoloaded:
In the Multics implementation:
(putprop 'foo ">udd>AutoProg>Library>foo-function" 'autoload)
In the ITS implementation:
(putprop 'foo '(foo fasl dsk me) 'autoload)
11/18/73                        12.4.4                        Page 105
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
12.5        Debugging
12.5.1          Binding, Pdl Pointers, and the Evaluator
   The  Maclisp  evaluator  is  conceptually based on a push down list
(pdl), or stack, which holds bindings, evaluation frames,  and  sundry
internal  data.  Bindings are values of atomic symbols which are saved
when the symbols are used as lambda variables, prog variables,  or  do
variables.   Evaluation  frames are constructed when a non-atomic form
is evaluated or when apply  is  used.   They  correspond  to  function
calls.
   As  the  evaluator  recursively  evaluates  a  form, information is
pushed onto the pdl and later popped off.  When the *rset, nouuo,  and
noret  flags  are t this information is sufficiently detailed to be of
use in debugging.  (See the functions *rset,  nouuo,  and  noret.)   A
position  within  the  pdl  may  be named by means of a "pdl pointer,"
which is a negative fixnum whose value has meaning to  the  evaluator.
Pdl  pointers  may be used as arguments to several debugging functions
decsribed in the next section.
   There are several ways to obtain a pdl pointer.  Since  the  fixnum
value  of  a  pdl  pointer  has only internal meaning, generally a pdl
pointer cannot be obtained from user input.  Several of the  debugging
functions described in the next section generate pdl pointers.
   An  important  thing  to  note  about pdl pointers is their limited
scope of validity.  If the information on the pdl which is named by  a
pdl pointer has been popped off since the pdl pointer was created, the
pdl pointer no longer has valid meaning.
Page 106                        12.5.1                        11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
12.5.2          Functions for Debugging
*rset		SUBR 1 arg
     (*rset  x)  sets  the *rset flag to nil if x is nil, to t if x is
     non-nil, and returns the value it set it to.  If the  *rset  flag
     is  t,  extra information is kept by the interpreter to allow the
     debugging functions, such as baktrace and evalframe, to work.
baktrace		LSUBR 0 to 2 args
     baktrace displays the stack of pending function calls.   It  only
     works in (*rset t) mode.  The first argument is a pdl pointer, as
     with  evalframe.   If  it is omitted, nil is assumed, which means
     start from the top of  the  pdl.   The  second  argument  is  the
     maximum  number of lines to be typed; if it is omitted the entire
     stack is displayed.
errframe		SUBR 1 arg
     Errframe returns a  list  describing  an  error  which  has  been
     stacked  up  because  of a user interrupt.  The list has the form
     (pdlptr message alist), where pdlptr is a number which  describes
     the  location  in  the  pdl  of the error, message is a character
     string which can be printed out as a description  of  the  error,
     and  alist  is a number which can be used as a second argument to
     eval or a third argument to apply to cause evaluation  using  the
     bindings in effect just before the error occurred.
     The  argument  to  errframe  can  be nil, which means to find the
     error at the top of the stack; i.e. the most  recent  error.   It
     can  also  be  a  pdl  ptr,  in  which case the stack is searched
     downward from the  indicated  position.   Thus  the  second  most
     recent error may be found by:
               (errframe (car (errframe nil)))
     The  argument to errframe may also be a positive number, which is
     the negative of a pdl ptr.  This means start from the position in
     the stack marked by the pdl ptr and search upwards.
     If no error is found, errframe returns nil.
11/18/73                        12.5.2                        Page 107
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
errprint		SUBR 1 arg
     Errprint treats its argument the same as errframe.   The  message
     portion  of the error frame is princ'ed.  Errprint returns t if a
     message was typed out and nil if no error frame was found.
evalframe		SUBR 1 arg
     The argument to evalframe is a pdl ptr, as  with  errframe.   The
     pdl  is  searched for an evaluation of a function call, using the
     same rules about starting point and direction as  errframe  uses.
     Evalframe  always skips over any calls to itself that it finds in
     the pdl.
     The value is a list (pdlptr form alist), where pdlptr  is  a  pdl
     pointer  to  the  evaluation in the stack, suitable for use as an
     argument to evalframe or errframe or baktrace, form is  the  form
     being  evaluated  or  the name of the function being applied, and
     alist is an a-list  pointer  which  can  be  used  with  eval  to
     evaluate  something  in  the  binding  context  just  before  the
     evaluation found by evalframe.
     Evalframe returns nil if no evaluation can be found.
     Evalframe only works in (*rset t) mode.
freturn		SUBR 2 args
     (freturn p x) returns control to the evaluation designated by the
     pdl pointer p, and forces it to return x.  This  "non-local-goto"
     function can be used to do fancy recovery from errors.
See also Chapter 14, on the trace package.
The following functions only exist in the Multics implementation.
baktrace1		LSUBR 0 to 2 args
     Baktrace1  is  the  same  as  baktrace  except  that  a-list ptrs
     suitable for use with eval and apply are displayed along with the
     function names.
Page 108                        12.5.2                        11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
baktrace2		LSUBR 0 to 2 args
     Baktrace2 is the same as  baktrace1  except  that  pdl  pointers,
     suitable for use with baktrace and evalframe, are displayed along
     with the function names and a-list pointers.
11/18/73                        12.5.2                        Page 109
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
12.5.3          An Example of Debugging in Maclisp
*********************************************************************
*********************************************************************
*********                                                   *********
*********                TO BE SUPPLIED                     *********
*********               debuggingexample.runoff              *********
*********                                                   *********
*********************************************************************
*********************************************************************
Page 110                        12.5.3                        11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
12.6        Garbage Collection
   Garbage  collection  is  the  mechanism  which LISP uses to control
storage allocation.  Whenever LISP feels  that  too  much  storage  is
being  used, a garbage collection is initiated.  The garbage collector
traces through all the S-expressions which can be reached  by  car'ing
and cdr'ing from atomic symbols' values and property lists, from forms
and temporary results currently being used by the evaluator, from data
used  by  compiled code, and from the saved values of bound variables.
All the data which it finds in this way is "good" data, in that it  is
possible  for  it to be used again.  Everything else is garbage, which
can never again be used for anything because it cannot be accessed, so
the storage used by it is reclaimed and reused.
gc		FSUBR
     (gc) causes a garbage collection and returns nil.
gctwa		FSUBR
     Gctwa is  used  to  control  the  garbage  collection  of  "truly
     worthless  atoms,"  which  are atomic symbols which have no value
     and no special properties, and which are not  referenced  by  any
     list  structure,  other  than the obarray (the current obarray if
     there is more than one).
     (gctwa) causes truly worthless atoms to be removed  on  the  next
     garbage collection.
     (gctwa  t)  causes  truly  worthless  atoms to be removed on each
     garbage collection from now on.  Note:  gctwa does  not  evaluate
     its argument.
     (gctwa  nil)  causes  this  continual  removal of truly worthless
     atoms to be shut off, but it does not  affect  whether  the  next
     garbage collection removes twa's.
     The  value returned by gctwa is a fixnum which is 0 if no garbage
     collection of truly worthless atoms will be done, 1 if twa's  are
     to be gc'ed on the next garbage collection, 10 if twa's are to be
     gc'ed  on  all garbage collections, or 11 if both. (These numbers
     are octal.)
11/18/73                         12.6                         Page 111
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
↑d		SWITCH
     If the value of ↑d is non-nil, the garbage  collector  prints  an
     informative message after each garbage collection.
See also the variables gc-daemon (page 103) and gc-lossage (page 103).
Page 112                         12.6                         11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
12.7        The Functions status and sstatus
status		FSUBR
     The  status  function  is used to get the value of various system
     variables.  Its first  argument,  not  evaluated,  is  an  atomic
     symbol  indicating  which  of  its  many  functions status should
     perform.  The use of additional arguments  depends  on  what  the
     first argument is.  Omitted arguments are assumed to be nil.  The
     following "status functions" exist:
STATUS FUNCTIONS FOR THE I/O SYSTEM
     Note:  in  the  following,  c represents an argument specifying a
     character.  If c is non-atomic it is evaluated.  The  value  must
     be  a  fixnum  which  is the ascii code for a character.  If c is
     atomic it is not evaluated.  It may be a fixnum  or  a  character
     object.
     (status   ioc   c)   gives   the   state   (t   or  nil)  of  the
     control-"c"-switch.  For example, (status ioc q) is t if input is
     from a file, nil if input is from the terminal.
     (status uread) returns a  4-list  for  the  current  uread  input
     source, or nil if uread is not being done.
     (status  uwrite)  returns  the corresponding list for the current
     uwrite output destination.
     (status crunit) returns  a  2-list  of  the  current  unit;  i.e.
     device and directory.
     (status  crfile)  returns  a 2-list giving the file names for the
     current file in the "uread" I/O system.
     (status  tabsize)  returns  the  number  of  character  positions
     assumed between tab stops.
     (status  charmode  f)  returns  the  value  of the character-mode
     switch for the file object  f.   If  f  is  nil  or  omitted  the
     terminal  is  assumed.   If this switch is t (the normal case for
     the terminal) output is sent to the  device  as  soon  as  it  is
     generated.  If the switch is nil (the normal case for files other
     than  the  terminal)  output is held until a newline is typed, an
     error occurs, input is requested, or  the  buffer  becomes  full.
     This provides increased efficiency at the cost of not immediately
     seeing all output.
11/18/73                         12.7                         Page 113
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
STATUS FUNCTIONS FOR THE READER
     See  sections 12.1.2 and 12.6.2 for a description of how the data
     examined by these functions is used.  (status chtran c) gets  the
     character  translation  table entry for the character c.  This is
     the ascii code of a character substituted for c when  it  appears
     in a pname being read in.
     (status  syntax c) returns the 18 syntax bits for the character c
     as a fixnum.
     (status macro c) returns nil if c is not a macro character.  If c
     is a macro character it returns a list  of  the  macro  character
     function  and  the type, which is nil for normal macros and s for
     splicing macros.
     (status +) gets the value of the  +  switch  (t  or  nil).   This
     switch  is  normally  nil.   If  it  is  t,  atoms  more than one
     character long beginning with a +  or  a  -  are  interpreted  as
     numbers  by the reader even if they contain letters.  This allows
     the use of input bases greater than ten.
     (status ttyread) returns the value of the ttyread  switch,  which
     is  kept  in  the  readtable.   At  present  this is not used for
     anything  in  the  Multics   implementation.    In   the   pdp-10
     implementation  it  controls  whether tty "force feed" characters
     are used.
STATUS FUNCTIONS FOR THE PRINTR
     (status terpri) returns the  value  (t  or  nil)  of  the  terpri
     switch,  which is kept in the readtable.  This switch is normally
     nil.  If it is t, the output functions such as print and tyo will
     not output any extra newlines when lines longer  than  linel  are
     typed out.
     (status ) returns the value (t or nil) of the  switch, which is
     kept  in  the  readtable.   If this switch is t, the  format for
     fixnums with lots of trailing zeroes is not used.
     (status  abbreviate)  returns  the  value  of  the   abbreviation
     control.   See section 13.7 for a description of the abbreviation
     control.
STATUS FUNCTION FOR THE GARBAGE COLLECTOR
     (status  gctime)  returns  the  number  of   microseconds   spent
     garbage-collecting.
Page 114                         12.7                         11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
STATUS FUNCTIONS FOR CONTROL OF THE EVALUATOR
ENVIRONMENT ENQUIRIES
     (status  date)  returns  a  3-list indicating the current date as
     (year-1900. month-number day)
     (status daytime) returns a 3-list of the 24-hour time of  day  as
     (hour minute second).
     (status  time)  is  the same as (time), the number of seconds the
     system has been up.
     (status  runtime)  is  the  same  as  (runtime),  the  number  of
     microseconds of cpu time that has been used.
     (status  system x) returns a list of the system properties of the
     atomic symbol x, which is evaluated.  This list may contain subr,
     fsubr, macro, or lsubr if x is a  function,  and  value  if  this
     atomic symbol is a system variable.
     (status  uname)  returns  an  atomic  symbol  whose  pname is the
     current user's name.  In the Multics implementation  this  is  in
     the  format  User.Project; the dot will be slashified if print is
     used to display this.
     (status udir) returns the name of the user's directory.   In  the
     ITS  implementation  this  is  the  same  as  the  user's name as
     returned by (status uname).  In the Multics  implementation  this
     is the user's default working directory.
     (status lispversion) returns the version number of lisp.
     (status  jcl)  returns  the  "job  command  line" from ddt in the
     pdp-10 implementation.  In the Multics implementation it  returns
     the  exploded second argument of the lisp command, or else nil if
     the lisp command had only one argument.  If lisp was invoked by
               lisp environment "foo bar"
     (status jcl) => (f o o /  b a r)
The following   status   functions   only   exist   in   the   Multics
     implementation.
     (status  paging)  returns a list of the paging-device page faults
     and total page faults that have been incurred.
11/18/73                         12.7                         Page 115
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
     (status arg n) returns the n+1'th argument of the  lisp  command,
     as  an interned atomic symbol.  Nil is returned if n is more than
     the number of arguments on the lisp command.
MISCELLANEOUS STATUS FUNCTIONS
     (status  toplevel)  returns  the   top-level   form,   which   is
     continually  evaluated when LISP is at its top level.  If this is
     nil, a normal read-eval-print loop is used.
     (status interrupt  n)  returns  the  service  function  for  user
     interrupt channel n.  n is evaluated.
     (status  pagepause) returns the value of the pagepause flag.  See
     (sstatus pagepause) for a description of this flag.
     (status features) returns a  list  of  symbols  representing  the
     features  implemented  in  the  LISP  being  used.  The following
     symbols may appear in this list:
     (status uuolinks) returns a number which represents the number of
     available slots for linking between compiled functions.
               bibop               pdp-10   big-bag-of-pages    memory
                                   management scheme
               lap                 this  LISP  has  a  Lisp   Assembly
                                   Program
               sort                the sorting functions described  in
                                   chapter 9 are present
               edit                the  edit  function  described   in
                                   chapter 17 is present
               fasload             the fasload facility  described  in
                                   chapter 13 is necessary
               ↑f                  the "moby I/O" facility is present
               bignum              the arbitrary-precision  arithmetic
                                   package is included in this LISP
               strings             character strings and the functions
                                   on  them described in chapter 8 are
                                   present
               newio               the  I/O  functions  described   in
                                   chapter  12  are  included  in this
                                   LISP;   if  this  feature  is   not
                                   present    only   some   of   those
                                   functions are available.
               ml                  this LISP is on the Nathlab machine
                                   at MIT
               ai                  this LISP is on the AI  machine  at
                                   MIT
               H6180               this LISP is on the  H6180  Multics
                                   machine at MIT
               its                 this LISP is on some ITS system
Page 116                         12.7                         11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
               Multics             this LISP is on some Multics system
               dec10               this LISP is on  some  DEC  TOPS-10
                                   system;  or  on  some  TENEX system
                                   since the TENEX implementation runs
                                   under a TOPS-10 emulator.
     (car (last (status features))) is generally considered to  be  an
     implementation  name,  such as its or dec10 or Multics.  The main
     idea behind this status call is that an application  package  can
     be  loaded into any MACLISP implementation and can decide what to
     do on the basis of the features it finds available.
     Example:
     (cond ((memq 'bignum (status features))
            (prog2 nil (eval (read)) (read)))  ;use first version
           (t (read) (eval (read)) ))          ;use second version
     (defun factorial (n)          ;bignum version
         (cond ((zerop n) 1)
               ((times n (factorial (sub1 n))))
                  ))
     (defun factorial (n)          ;fixnum-only version
         (do () ((not (> n 13.)))  ;do until n < 13.
               (error "argument too big - factorial"
                      n
                      'wrng-type-arg))
         (cond ((zerop n) 1)
               ((* n (factorial (1- n)))) ))
sstatus		FSUBR
     Sstatus is like status.  It has a first argument which  tells  it
     what  to  do  and  how  to  interpret  the rest of its arguments.
     Sstatus is used to set various system variables.   The  following
     "sstatus functions" exist:
SSTATUS FUNCTIONS FOR THE I/O SYSTEM
     (sstatus ioc ccc) is the same as (ioc ccc)
     (sstatus uread --args--) is the same as (uread --args--)
     (sstatus uwrite --args--) is the same as (uwrite --args--)
     (sstatus crunit --args--) is the same as (crunit --args--)
11/18/73                         12.7                         Page 117
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
     (sstatus charmode x f) sets the character-mode switch of the file
     f  (f may be nil to signify the terminal) to x, which may be t or
     nil.  x and f are evaluated.  f may be omitted, in which case the
     terminal is assumed.
SSTATUS FUNCTIONS FOR THE READER
     See sections 12.1.2 and 12.6.2  for  a  description  of  how  the
     switches and tables set by these functions are used.
     (sstatus  chtran  c  k)  sets  c's character translation to k.  k
     follows the same rules  as  c,  i.e.  it  may  be  a  list  which
     evaluates to a fixnum, or an unevaluated atom such as a fixnum or
     a  character  object.   The value returned is k as a fixnum ascii
     code.
     (sstatus syntax c m) sets c's syntax bits to m.  m  is  evaluated
     and returned.
     Note  that  in the above 3 calls, if c is a macro character it is
     changed back  to  its  standard  syntax  and  chtran  before  the
     requested  operation  is  performed.  However, if in the standard
     readtable c is a macro (i.e. ' and ;), instead of  being  changed
     to  its  standard  syntax  and  chtran  its  syntax is set to 502
     (extended alphabetic) and its chtran is set to itself.
     (sstatus macro c f) makes c a macro  character  which  calls  the
     function f with no arguments.  f is evaluated.  A fourth argument
     to  sstatus  may  be supplied.  It is not evaluated.  If it is an
     atomic symbol whose pname begins with s, c  is  made  a  splicing
     macro.   If  f is nil, instead of c being made a macro-character,
     c's macro abilities are taken away  and  c  becomes  an  ordinary
     extended-alphabetic character.
     (sstatus + x) sets the + switch to t or nil depending on x, which
     is evaluated.  The new value of the + switch is returned.
     (sstatus ttyread x) sets the ttyread switch to t or nil depending
     on  x,  which  is  evaluated.   The  new  value  of the switch is
     returned.
SSTATUS FUNCTIONS FOR THE PRINTER
     (sstatus terpri x) sets the terpri switch.
     (sstatus abbreviate <n>) sets  the  abbreviation  control  to  n.
     (sstatus   abbreviate  nil)  turns  off  abbreviation.   (sstatus
     abbreviate t) turns on a maximal  amount  of  abbreviation.   See
     section 13.7 for a description of the abbreviation control.
Page 118                         12.7                         11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
SSTATUS FUNCTION FOR THE GARBAGE COLLECTOR
     (sstatus gctime n) resets the gctime counter to n and returns the
     previous value of the gctime counter.
MISCELLANEOUS SSTATUS FUNCTIONS
     (sstatus  toplevel  x)  evaluates  and returns x and sets the top
     level form to this value.
     (sstatus uuolinks) causes all links between compiled functions to
     be "unsnapped."  This should be done whenever (nouuo t)  is  done
     to  insure  that  the  interpreter  always  gets a chance to save
     debugging information on every function call.
     (sstatus interrupt n  f)  sets  the  service  function  for  user
     interrupt  channel  n  to  f.  The arguments are evaluated.  F is
     returned.
     (sstatus pagepause x) sets the pagepause switch to x,  which  may
     evaluate  to  t  or  nil.   If  the  pagepause switch is t, and a
     display terminal is being used, LISP will stop when  it  gets  to
     the  end  of  the  screen  and wait for the user to hit control-U
     before it  erases  anything.   (This  feature  is  not  presently
     available in the Multics implementation.)
*rset		SWITCH
     The  value of *rset is the "*rset flag" manipulated by the status
     and sstatus functions.  If *rset  is  t,  the  interpreter  keeps
     extra  information  and  makes  extra checks to aid in debugging.
     *rset should never be setq'ed - always use (sstatus *rset  t)  or
     (sstatus *rset nil).
11/18/73                         12.7                         Page 119
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
12.8        Miscellaneous Functions
sysp		SUBR 1 arg
     The sysp predicate takes an atomic symbol as an argument.  If the
     atomic  symbol is the name of a system function (and has not been
     redefined), sysp returns the type of function  (subr,  lsubr,  or
     fsubr).  Otherwise sysp returns nil.
     Examples:
         (sysp 'foo) => nil
         (sysp 'car) => subr
         (sysp 'cond) => fsubr
Page 120                         12.8                         11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
12.8.1          Time
runtime		SUBR no args
     (runtime)  returns the number of microseconds of cpu time used so
     far by the process in which  LISP  is  running.   The  difference
     between   two   values  of  (runtime)  indicates  the  amount  of
     computation that was done between the two calls to runtime.
time		SUBR no args
     (time) returns the time that the system has been up, in  seconds.
     (As a flonum.)
sleep		SUBR 1 arg
     (sleep  n) causes a real-time delay of n seconds, then returns n.
     n may be a fixnum or a flonum.
See also the alarmclock function, section 11.4.3.
11/18/73                        12.8.1                        Page 121
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
12.8.2          Getting into LISP
                       in the Multics implementation
        The LISP subsystem is entered by means of  the  lisp  command.
     If  lisp  is  called  with  no  arguments, a copy of the standard
     initial environment  containing  all  the  system  functions  and
     variables  is  made the current environment.  If the lisp command
     is issued  with  an  argument,  the  argument  concatenated  with
     ".sv.lisp"  is  the pathname of a saved environment (see the save
     function in section 11.8.3.1) which is copied  into  the  current
     environment.   Additional  arguments  to the lisp command in this
     case  are  actually  arguments  to  the  programs  in  the  saved
     environment,  which  can  retrieve  them  by  using  the function
     'status'.
        The  LISP  subsystem  may  also   be   entered   through   the
     lispcompiler  command,  which  is  like  calling  lisp  with  an
     argument of the pathname of the saved environment containing  the
     LISP compiler.
        When  the standard initial environment is entered, lisp checks
     for a segment named startup.lisp in the user's  home  directory.
     If  such  a  segment  exists,  it  is  read in.  Each form in the
     segment is  evaluated,  but  the  value  is  not  printed.   This
     facility allows users to "customize" LISP.
        When  a  saved environment is entered, (mapc 'eval errlist) is
     done.  This feature can be used to  make  the  saved  environment
     self-starting.
      "...in the pdp-10 implementation"
                         in the ITS implementation
        LISP  may  be entered by the ":LISP" or "LISP↑|K" command.  The
     environment set up  by  this  command  is  the  standard  initial
     environment.   Lisp  checks for a file named .LISP. (INIT) in the
     user's directory.  If it is found, it is read in and each form is
     evaluated.  This allows a user to "customize" lisp.   The  .LISP.
     (INIT) file may begin with a comment in the form
               (comment name number name number ...)
Page 122                       12.8.2.1                       11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
     which  is used to specify allocation.  The names are the names of
     the  various  spaces,  and  the  numbers  are  the  sizes  to  be
     allocated.   If  there  is  no  .LISP. (INIT) file, lisp asks the
     question ALLOC?  A reply of n causes standard allocation, a reply
     of y allows allocation to be specified conversationally.  NB:  it
     is expected that the need for allocation will go away soon.
        LISP  may  be entered by the command :LISP name1 name2 dev dir
     where dev and dir default to DSK and the  user's  directory.   In
     this case the file dev:dir;name1 name2 is read in the same way as
     a .LISP. (INIT) file.
        If  a  lisp  containing  some  data  other  than  the  initial
     environment has been saved (see section 11.8.3.2) as TS NAME, the
     :NAME command will retrieve it.  The first  action  performed  by
     lisp  is  (mapc 'eval errlist), which allows the user programs to
     start up.
                       in the DEC-10 implementation
        Type the monitor command, R LISP.  LISP will ask the  question
     "ALLOC?", and the possible answers are as described above for the
     ITS implementation of LISP.  Similarly to the ITS implementation,
     if  a  lisp  has  been  saved  as NAME, the RUN NAME command will
     retrieve it and the first thing it  will  do  when  retrieved  is
     (mapc 'eval errlist).
11/18/73                       12.8.2.1                       Page 123
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
12.8.3           Getting Out of LISP
        Evaluating  (ioc  z)  will  cause  LISP to temporarily release
     control.  Control can be returned to LISP  by  an  implementation
     defined  method.   There is also an implementation-defined way to
     leave LISP permanently, freeing any storage used by  the  current
     LISP environment or else saving it.
                       in the Multics implementation
        (ioc  z)  will cause a QUIT.  The start command may be used to
     re-enter the lisp subsystem.  release may also be used, in  which
     case LISP will clean itself up.
        There  are  also the functions quit and save.  quit causes the
     lisp subsystem to exit, throwing away  the  current  environment.
     save  causes  the  lisp  subsystem  to  exit,  saving the current
     environment in a  specified  file,  whose  name  always  ends  in
     ".sv.lisp".
quit		SUBR no args
     (quit)  causes the lisp subsystem to remove itself and return  to
     its caller.  The current environment is lost.  (cf. save).
save		FSUBR
     (save foo) saves the current LISP environment  in  a  file  named
     foo.sv.lisp in the working directory.  Foo is not evaluated.  The
     command
               lisp foo
     can  be  used  to  retrieve this saved environment.  All variable
     bindings, file objects, array contents, and function  definitions
     (and  other  properties)  are saved, but the contents of the push
     down lists cannot be saved, so save should only be used from  top
     level.
Page 124                        12.8.3                        11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
     See  also  the  function  cline  (described in section 11.8.4.1),
     which is used to get out of LISP,  execute  one  Multics  command
     line, and return into LISP.
                         in the ITS implementation
        (ioc  z)  will  cause  a  return  to  DDT.   $P may be used to
     re-enter LISP.  (valret ':KILL) will cause LISP to exit, throwing
     away the current environment.   The  macdmp  function,  explained
     below, may be used to save the current environment.
macdmp		LSUBR 0 or 1 args
     If  LISP  is  a  top-level  procedure,  macdmp  simply  logs out.
     Otherwise it prepares the LISP for dumping as follows:
     (1) if the display slave is open, it is closed.
     (2) all bit tables, pdl areas, and free storage lists are  zeroed
         out.  (Remember,  dumping  with $Y uses a special compression
         technique on blocks of zeros.)
     (3) if macdmp was given an  argument,  this  is  explodec'ed  and
         valret'ed  as  with  the  valret function.  Otherwise, macdmp
         returns to DDT with a .BREAK 16,100000.
     Commonly one will write a setup routine  for  some  LISP  package
     like this:  (prog ( ... )
           (terpri)
           (princ 'options:)
           ... read in options ...
           (terpri)
           (princ 'loading)
           ... load in files of functions ...
           (macdmp ':$ALL/ DONE/ -/ hooray!$/↑M))
     The  LISP  (with  some  new  functions  loaded)  is now ready for
     dumping. Alternatively, one might write
              (macdmp '$Y/ USER/;FOO/ BAR/↑M:$ALL/ DONE$/↑M)
     which will do the dump and then print a message when done.
     When such a dumped LISP is loaded and restarted,  the  effect  is
     very  similar  to  a  ↑G  quit: LISP's top level is entered after
     evaluating all items on the errlist. Thus if before the macdmp is
     done the errlist  is  setq'ed  to  some  list  of  initialization
     procedures, these procedures will be invoked when the dumped LISP
     is restarted.
11/18/73                        12.8.3                        Page 125
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
                       in the DEC-10 implementation
     ********** TO BE SUPPLIED *********
Page 126                        12.8.3                        11/18/73
		              Functions for Controlling the Interpreter
                    ***** ROUGH DRAFT #9905 *****
12.8.4          Sending Commands to the Operating System
                       in the Multics implementation
cline		SUBR 1 arg
     (cline  x),  where  x is a character string, executes the Multics
     command x and returns nil.
     Example:
               (cline "who -long")
                         in the ITS implementation
valret		LSUBR 0 or 1 args
     (valret) is like (ioc z); that is, it does a .LOGOUT if LISP is a
     top level procedure, and otherwise valrets ":VK " to DDT.
     (valret x) effectively performs an explodec on x (in  practice  x
     is  some  strange  atomic symbol like :PROCED/ :DISOWN/  ; but it
     may be any s-expression). If the string of characters is  one  of
     "$↑X.",  ":KILL  ",  or  ":KILL↑M"  (the  letters of KILL must be
     capitalized) then valret performs a "silent kill" by executing  a
     .BREAK  16,20000;  otherwise valret performs a .VALUE, giving the
     character string to DDT to evaluate as commands.
     Examples:
     (valret ':PROCED/ :DISOWN/ )
     procedes and disowns the LISP.
     (valret '/ :KILL/ :TECO/↑M)
     kills the LISP and starts up a TECO.
     (valret '0$N)
     causes DDT to print out the contents of all non-zero locations in
     LISP.
11/18/73                        12.8.4                        Page 127
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
                       in the DEC-10 implementation
        There  is  currently  no  way  to  do  this  in   the   DEC-10
     implementation.
Page 128                        12.8.4                        11/18/73
		                           Input and Output
                    ***** ROUGH DRAFT #9905 *****
13.         Input and Output
13.1          Basic I/O
   Input  and  output can be done in LISP in terms of S-expressions or
in terms of characters.  Operations may also be performed  on  certain
devices,  such  as  displays,  robot  arms,  etc.,  in terms which are
peculiar to the particular device,  using  the  so-called  "moby  I/O"
facility.
   Initially we will discuss just I/O on the user's terminal.
   S-expressions  can  be  input  by  using the function read.  (read)
reads one S-expression, which is either a list  enclosed  in  matching
parentheses  or  an  atom  delimited  by a special character such as a
space or a parenthesis. (A parenthesis would be saved up and  used  on
the  next call to read.)  Read returns the S-expression which it read,
converting it from the external representation as characters  to  LISP
internal form.  See Chapter 2 and section 13.1.2.
   (readch)  reads  in  one  character  and  returns it as a character
object.
   (tyi) reads in one character and returns  a  number  which  is  the
ascii code for the character.
   (print x) prints out the S-expression x in a form which is readable
by  humans  but  which  could  also  be  read back into LISP if it was
printed to a file rather than to the terminal.  See section 13.2.3 for
an explanation of how to do this.
   The expression printed out is preceded by a newline and followed by
a space.  If special characters are used with other than their  normal
meanings,  for  example  if  a  parenthesis appears in the pname of an
atom, they are preceded by slashes so that the output  could  be  read
back in.  Strings are enclosed in double quotes for the same reason.
   (prin1  x) is the same as (print x) except that the leading newline
and trailing space are omitted.  Prin1 can be used to  print  multiple
items  on  a  line, but spacing between the items must be provided for
explicitly, for example by evaluating (tyo 40).
   (princ x) is like (prin1 x) except that special characters are  not
slashified  and  strings  are  not quoted.  This makes the output more
11/18/73                         13.1                         Page 129
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
pleasing in certain situations, however it cannot be  read  back  into
LISP.
   (terpri) types out a newline.
   Output of characters can be accomplished using either tyo or princ.
(tyo n) outputs a character whose ascii code is given by the number n.
princ may be used to output character objects.
   As  implied  above,  these  functions can also be used to do I/O on
devices other than  the  terminal.   The  ways  to  do  this  will  be
explained in section 13.2.3.
   Note  that  what  LISP  does when it is at its "top level," that is
when you first start talking to it, is first to  call  read,  then  to
call  eval  on what was read, then to print the result and advance the
terminal to a new line on which the next piece of input may be  typed.
This may be expressed as repeated evaluation of:
    (prog2 (terpri)
           (print (eval (read))) )
Page 130                         13.1                         11/18/73
		                           Input and Output
                    ***** ROUGH DRAFT #9905 *****
13.2          Files
   I/O  in LISP consists of communication between the LISP environment
and sequences of characters called  files,  located  in  the  external
world.   LISP refers to these files by using "file objects," which are
special  objects  within  the  LISP   environment   which   serve   as
representatives  of,  or symbols for, the files in the external world.
Because there is a one-to-one correspondence between  files  and  file
objects,  it is often convenient to confuse the two and call them both
"file."
   The LISP system includes functions which can  manipulate  files  in
various  ways:   A  file may be "opened," that is a file object may be
created and associated with a named file in the external world.
   A file may  be  "closed,"  that  is  the  association  between  the
file-object  and  the  external file may be broken and the file-object
deleted.
   The file-accessing information contained in a  file-object  may  be
examined  or  changed;  for example, the line length of an output file
may be adjusted.
   The characters of information in the external file may be  read  or
written.
   The  attributes  of  the  external  file,  such as its name, may be
changed.
   In order to "open" a file, the external file and  the  file  object
must  be  named  so that a connection may be established between them.
The problem of naming file objects is solved trivially by  making  the
rule that whenever a file object is created its name is decided by the
system  and  returned  as  the  value of the function that created it.
File objects are then referred to in the same way as any S-expression.
Note that the name of a file object does not have a printable form, so
that if you want to manipulate the file  object  by  typing  from  the
terminal  (rather  than from a program), you must keep the file object
as the value of an atomic symbol.
   The naming of files in the outside world is more difficult  because
MACLISP has to operate with several different outside worlds, that is,
under several different operating systems.  It was thought undesirable
to  build  too  many  assumptions  about the operating system into the
language, because that would restrict  the  transporting  of  programs
between MACLISP implementations.
   The  assumptions  that  are  built in are that the operating system
provides named files located in named directories or on named devices,
which may be accessed sequentially  as  streams  of  characters.   The
function   filepos   makes   the  additional  assumption  that  simple
11/18/73                         13.2                         Page 131
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
random-access facilities are available.  An interactive environment is
also assumed.  Some of the I/O functions  assume  that  the  names  of
files may be broken up into an arbitrary number of components, so that
names  take on a form such as "foo.bar.lisp" or "moby mess".  However,
it is  possible  for  a  MACLISP  to  operate  with  somewhat  reduced
effectiveness  under an operating system which does not satisfy all of
these assumptions.
   The user of a program or a subsystem written in LISP  wants  to  be
able  to  type  in  file names in the form customary in the particular
operating system being used, and he wants to see them typed out in the
same form.  But if a program wants to  do  more  with  the  file  name
supplied  by  the  user  than  simply  pass  it  on  to the system I/O
functions, it needs to have that name translated to a uniform internal
format, in which the interesting components of the name  are  seperate
atoms  in a list, not buried inside a character string whose format is
not even known to the program.  To resolve this  conflict,  two  forms
for  file  names have been defined, and functions are provided to make
the implementation-dependent translation from one form to  the  other.
The forms of a file name are called the namelist and the namestring.
   The  namestring  is the implementation dependent form.  Namestrings
are represented as LISP character strings, however atomic symbols  may
also  be used, in which case the pname of the atomic symbol is used as
the character string.  The contents of a namestring is just a sequence
of characters which have meaning to  the  user  and  to  the  function
"namelist,"  which  converts  a namestring to a namelist.  Namestrings
should be read in using the  "readstring"  function  and  printed  out
using "princ," so that no quotes will appear around them.
   A  namelist is a list whose car somehow specifies the device and/or
directory which contains the file, and whose cdr specifies the name of
the  file.   The  exact  way  in   which   the   car   specifies   the
device/directory  is  implementation-dependent.   It  should not be of
concern to programs.  The cdr of a namelist is a list of  names  which
are  the  components  of  the  file  name if the operating system uses
multi-component file names.  Each name is  represented  as  an  atomic
symbol, which is "interned" so that it may be tested with the function
eq.
   An  additional  feature  of  namelists is the "star convention," by
which  a  namelist  may  contain  unspecified  components,  which  are
indicated  by  the  atom *.  Certain other constructions, explained in
section 13.3, may also be used.  The star convention allows  a  single
namelist  to  specify  a  class of files, and allows programs to apply
defaults to their file-name arguments in a straightforward fashion.
   Some additional information about file objects has  been  collected
here.  It is in brief form and will be elaborated in later sections.
   There  is  no way to input file objects to the reader, because they
do not have pnames or anything of that sort, but  for  convenience  in
Page 132                         13.2                         11/18/73
		                           Input and Output
                    ***** ROUGH DRAFT #9905 *****
error messages and debugging the printer will print a file object as a
sharp  sign  (#),  followed  by the namestring of the external file to
which the file object is attached.  # is the character which  is  used
to indicate that an object of unknown type is being printed.
   The  information  contained  within a file object is here described
briefly.
Namelist            the namelist for the external file  of  which  the
                    file object is a representative.
Eoffn               a function which is applied when  the  end  of  an
                    input file is reached.
Endpagefn a function which is applied  when  the  end  of  a  page  is
                    reached (on an output file.)
Linel               the number of characters per  line  on  an  output
                    file.
Charpos   the horizontal position on the line, where  0  is  the  left
                    margin.
Chrct               the number of character positions remaining on the
                    current line of an output file,
Pagel     the number of lines per page.
Linenum   the number of the current line, with 0 being the top of  the
                    page
Pagenum   the number of the current page, with the first page being 0.
Filepos             the position within  the  file  of  the  character
                    currently   being   accessed.    (Not  necessarily
                    meaningful for all kinds of files.)
Other               internal  information  used  by   the   LISP   I/O
                    functions   in  transactions  with  the  operating
                    system.
Note that as a special case nil is considered  to  be  a  file  object
which  represents  the  terminal.   This is in addition to nil's other
identities as an atomic symbol and as a list.  
.in +%undent%
11/18/73                         13.2                         Page 133
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
13.2.1          Naming Files
   Some examples may help clarify the connection between namelists and
namestrings.
   In the Multics system, files are stored  in  a  tree  structure  of
directories.   A file's name consists of a sequence of names seperated
by the ">" character.  The last name is the  name  of  the  file,  and
preceding names are the names of directories in a path from the "root"
directory  down  through  the tree to the file in question.  Each name
may consist of several  compoenents  seperated  by  periods.   Thus  a
typical namestring in the Multics implementation of MACLISP would be
               ">udd>AutoProg>Hacker>hacks>my.new.hack"
The corresponding namelist is:
               (>udd>AutoProg>Hacker>hacks my new hack)
In   addition,   the  start  convention  for  namelists  may  also  be
represented in namestring form.  Some examples of  the  correspondence
are:
     (* foo) == "foo"              - omitted components are *
     (* foo * bar) == "foo.*.bar"
     (* foo . bar) == "foo.**.bar"
     (*foo . *) == "foo.**"
   Multics  LISP  can  also  use  "streams"  for files.  Streams are a
sequential-I/O entity in Multics.  For example, input from and  output
to  the  terminal  are  performed  by  means  of streams.  In LISP the
convention has been defined that  a  "$"  character  in  a  namestring
distinguishes  the  name of a stream from the name of a file stored in
the directory hierarchy.  Thus the namestring
                            "$userinput"
indicates  the  stream  used  for  input  from  the   terminal.    The
corresponding namelist is:
                         (stream userinput)
   In  the  ITS (pdp-10) system, files are stored in directories which
are kept on devices.  Directories may not be kept within  directories,
so  there  is  no  tree  structure.   Each  file-name  has exactly two
components.  Thus a file whose name has first component foo and second
component bar, located in directory comlap on device  ml,  would  have
the namestring:
                          ml:comlap;foo bar
               As a namelist this would be represented:
Page 134                        13.2.1                        11/18/73
		                           Input and Output
                    ***** ROUGH DRAFT #9905 *****
                       ((ml . comlap) foo bar)
If the device and directory were omitted, the namelist would be:
                             (* foo bar)
If  only one component to the name were specified, the second would be
*.
In the DEC-10 implementation, namestrings take the usual
                       dev:name.ext[proj,prog]
form, and the corresponding namelist is
                      ((dev proj prog) name ext)
and *'s are substituted for omitted components in the same way as  for
the ITS version described above.
namelist		SUBR 1 arg
     Namelist  converts  its  argument  to  a  namelist.  Omitted or *
     components in the argument produce *'s in the result.
namestring	SUBR 1 arg
     Namestring converts its argument from a namelist to a namestring.
     It is the opposite of namelist.
shortnamestring	SUBR 1 arg
     shortnamestring is just like namestring except that there  is  no
     mention of directory or device in the resulting string.  Example:
               (shortnamestring '(abc d e)) => "d.e"
11/18/73                        13.2.1                        Page 135
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
names		LSUBR 1 or 2 args
     (names f), where f is a file object, gets f's namelist.
     (names  nil)  gets the default namelist.  In Multics MACLISP, the
     default namelist is initially set to
                         (<working-directory> . *)
     when lisp is entered.
     In ITS MACLISP, the default namelist is initially set to
                               (<udir> . *)
     when lisp is entered, where <udir> is the name by which the  user
     logged in.
     (names nil x) sets the default namelist to x and returns x.
13.2.2          Opening and Closing
openi		SUBR 1 arg
     This  function  is  used to create a file object and associate it
     with a file in the external world.  The argument is a namelist or
     namestring which specifies the file to  be  opened.   The  return
     value is the file object which was created.
     Openi  first  creates a file object and initializes its namelist,
     linel, and eoffn to the defaults.  Its chrct is initialized equal
     to its linel.  Then the namelist argument of openi is merged into
     the namelist of the file object.   See  the  description  of  the
     mergef   function,   in  section  13.3,  for  the  full  details.
     Basically what happens is that components of the  file  name  not
     specified  by the argument to openi are obtained from the default
     namelist.  openi now negotiates  with  the  operating  system  to
     obtain  the  file.   A  fail-act correctable error occurs if this
     does not succeed.
     The file created by openi can be used for input.
     Example:
         (inpush (openi "inputfile1"))
Page 136                        13.2.2                        11/18/73
		                           Input and Output
                    ***** ROUGH DRAFT #9905 *****
openo		SUBR 1 arg
     Openo is like openi except that the file object created  is  used
     for   output.    Any  pre-existing  file  of  the  same  name  is
     over-written.  Example:
         (setq outfiles (list (openo "output.data")))
The following function only exists in the Multics  implementation,  at
     present.
opena		SUBR 1 arg
     Opena  is  just like openo except that if there is a pre-existing
     file with the same name, the output is appended to the end of the
     file, where openo would erase the old contents of  the  file  and
     begin outputting at the beginning of the file.
close		SUBR 1 arg
     (close  x),  where  x is a file, closes x and returns t.  If x is
     already closed nothing happens,  otherwise  the  file  system  is
     directed to return x to a quiescent state.
For a description of the way in which the argument to openi, openo, or
opena has the defaults applied to it, see section 13.3.
13.2.3           Specifying the Source or Destination for I/O
   When  an I/O function is called, the source (file) from which it is
to take its input or the destinations (files) on which it  is  to  put
its  output  may be specified directly as an argument to the function,
or they may be specified by default.  The  default  input  source  and
output  destinations  are specified by several system variables, which
may be setq'ed or lambda-bound by the user.  They are described below.
   infile is the default input source,  if the switch ↑q is t.  If  ↑q
is nil the terminal is used as the default input source.
   outfiles  is a list of default output destinations.  Output is sent
to all of these files if the ↑r switch is t.  Output also goes to  the
terminal unless the ↑w switch is t.
   Note  that  in  the  values  of  infile  and outfiles nil means the
terminal, any anything other than nil must be a file object.
11/18/73                        13.2.3                        Page 137
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
infile		VARIABLE
     The value of infile is a file object which is the  default  input
     source  if ↑q is non-nil.  Infile can also be nil which specifies
     that input will be from the terminal even if ↑q is not nil.   The
     initial value of infile is nil.
↑q		SWITCH
     If  the  value  of ↑q is non-nil, the default input source is the
     value of the atom infile.  If ↑q is nil, the default input source
     is nil, i.e. the terminal.
instack		VARIABLE
     The value of instack is a list of pushed-down values  of  infile.
     It is managed by the function inpush.  The initial value is nil.
outfiles		VARIABLE
     The  value of outfiles is a list of file objects which are output
     destinations if ↑r is not nil.  Elements of the list outfiles may
     be either file objects created by openo or opena, or nil  meaning
     output  to  the  terminal.  Note that output goes to the terminal
     anyway if ↑w is nil, so it is possible to get  double  characters
     this way.
↑r		SWITCH
     If  the  value  of ↑r is non-nil, the default output destinations
     include the files in the list which is  the  value  of  the  atom
     outfiles.
↑w		SWITCH
     If the value of ↑w is non-nil, the default output destinations do
     not  include  the terminal.  (Unless ↑r is on and nil is a member
     of the outfiles list.)
Page 138                        13.2.3                        11/18/73
		                           Input and Output
                    ***** ROUGH DRAFT #9905 *****
Now the basic I/O functions can be explained in full detail:
read		LSUBR 0 to 2 args
     This is the S-expression input function.
     (read) reads an S-expression from the default input source.
     (read f), where f is a file or nil meaning the terminal, reads an
     S-expression from f.  During the reading, infile and ↑q are bound
     so that evaluation of (read) within  a  macro-character  function
     will read from the correct input source.
     (read  x),  where  x  is  not  a file and not nil, passes x as an
     argument to the end-of-file function of the input source  if  the
     end  of  the  file is reached.  Usually this means that read will
     return x if there are no more S-expressions in the file.
     (read t) suppresses the calling of the  end-of-file  function  if
     the end of the file is reached.  Instead, read just returns t.
     (read  x  f)  or (read f x) specifies the end-of-file value x and
     selects the input source f.
readch		LSUBR 0 to 2 args
     Readch reads in one character and  returns  a  character  object.
     The arguments are the same as for read.
readline		LSUBR 0 to 2 args
     readline  reads  in  a  line  of  text,  strips  off  the newline
     character or characters at the end, and returns it in the form of
     a character string.  The arguments are the same as for read.  The
     main use for readline is reading in file names typed by the  user
     at his terminal in response to a question.
tyi		LSUBR 0 to 2 args
     Tyi  inputs one character and returns a fixnum which is the ascii
     code for that character.  The arguments are the same as for read.
11/18/73                        13.2.3                        Page 139
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
tyipeek		LSUBR 0 or 1 arg
     (tyipeek) is like (tyi) except that the character is  not  eaten;
     it  is  still in the input stream where the next call to an input
     function will find it.  Thus (= (tyipeek) (tyi)) is  t.   If  the
     end  of  the  file is reached, tyipeek returns 3, (the ascii code
     for "end of text.") The end of file function is not called.
     (tyipeek n), where  n  is  a  fixnum  <  200  octal,  skips  over
     characters of input until one is reached with an ascii code of n.
     That character is not eaten.
     (tyipeek  n),  where  n  is  a  fixnum  >  1000 octal, skips over
     characters of input until one is reached whose syntax  bits  from
     the readtable, logically anded with (lsh n -9.), are nonzero.
     (tyipeek t) skips over characters of input until the beginning of
     an  S-expression  is reached.  Splicing macro characters, such as
     ";" comments, are not considered to begin an object.  If  one  is
     encountered,  its associated function is called as usual (so that
     the text of the comment  can  be  gobbled  up  or  whatever)  and
     tyipeek continues scanning characters.
prin1		LSUBR 1 or 2 args
     (prin1  x)  outputs x  to the current output destination(s), in a
     form suitable for reading back in.
     (prin1 x  f) outputs x on the file f, or the  terminal  if  f  is
     nil.
print		LSUBR 1 or 2 args
     Print  is  like  prin1  except  that  the output is preceded by a
     newline and followed by a space.  This  is  the  output  function
     most often used.
     (print x) prints x to the default output destinations.
     (print  x  f)  prints x to the file f, or to the terminal if f is
     nil.
Page 140                        13.2.3                        11/18/73
		                           Input and Output
                    ***** ROUGH DRAFT #9905 *****
princ		LSUBR 1 or 2 args
     Princ is  like prin1  except  that  special  characters  are  not
     slashified and strings are  not quoted.
     (princ x) outputs x to  the current output destination(s).
     (princ x f) outputs x to the file f, or the terminal if f is nil.
tyo		LSUBR 1 or 2 args
     (tyo  n)  types  out  the  character whose ascii code is n on the
     current output destination(s).
     (tyo n f) types out the character whoe ascii code  is  n  on  the
     file  f  or  on  the terminal if f is nil.  Tyo returns its first
     argument.
terpri		LSUBR 0 or 1 arg
     (terpri) sends a newline to the current output destination(s).
     (terpri x) sends a newline to x, where x may be an output file or
     nil meaning the terminal.
inpush		SUBR 1 arg
     (inpush x), where x is a file object open for  input  or  nil  to
     specify  the  terminal,  pushes the current input source onto the
     input stack and selects x as the current input source.   This  is
     like
         (setq instack (cons infile instack))
         (setq infile x)
     x is returned.
     (inpush 0) just returns infile.
     (inpush -1) pops a new input source off of the input stack:
         (setq infile (car instack)
               instack (cdr instack))
     The  above  code  is wrong in the case where instack is nil, i.e.
     empty.  In this case inpush leaves instack nil and  makes  infile
11/18/73                        13.2.3                        Page 141
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
     nil, which means the terminal.
     (inpush -n) does (inpush -1) n times.
     (inpush  1)  does  (inpush  (inpush  0)), (inpush +n) does that n
     times.
     The value of inpush is  the  newly  selected  input  source.   If
     inpush causes infile to be set to nil, ↑q is set to nil since the
     terminal has become the input source.
13.2.4           Handling End of File
   Calls  to  the  input  functions  read, readch, readstring, and tyi
specify an argument called the "eofval."  If this argument is  omitted
nil  is  assumed.   If the end of the input file is reached during the
execution of  the  function,  the  eofval  argument  is  used  by  the
following procedure:
   Each  file  object  has an end-of-file handler, its eoffn.  When an
end of file occurs while input is being  taken  from  this  file,  the
eoffn  is  examined. (Eof on the terminal cannot occur.)  If the eoffn
is nil, then the following default action is taken:  If eofval on  the
call  to read was not supplied, then the input file is closed and read
continues taking characters from a new input file popped off the input
stack.  If the input stack is empty, (setq ↑q nil) is  done  and  read
continues reading from the terminal.  If an eofval was supplied on the
call to read, then read immediately returns it.  The input file is not
closed.
   This  is  not strictly true in the case where the input function is
read or readstring and it is in the middle  of  an  object.   In  this
case, rather than allowing the object to cross files, a fail-act error
occurs.  The argument passed to the user interrupt service function is
the  list  (read-eof).   If  the interrupt service function returns an
atom (such as nil), read errs out;  but if it  returns  a  list,  read
goes on reading from the new input source as if there had not been any
end-of-file.
   If  the  eoffn for the input file is not nil, then it is a function
and it is applied with two arguments.  The first argument is the  file
object  that eof'ed.  The second argument is the eofval on the call to
read, or, if an eofval was not supplied, nil.  If  the  eoffn  returns
nil,  the  file  is closed and reading continues from the input source
popped off the input stack.  The above prohibition of objects crossing
eofs applies.  If the eoffn returns t, reading continues from whatever
input source was made the current default one by the  eoffn.   If  the
eoffn  returns  something  other  than t or nil, then read immediately
Page 142                        13.2.4                        11/18/73
		                           Input and Output
                    ***** ROUGH DRAFT #9905 *****
returns whatever the eoffn returned, and the file is not closed unless
the eoffn closes it.
eoffn		LSUBR 1 or 2 args
     (eoffn x), where  x  is  an  input  file,  gets  x's  end-of-file
     function.   The  end-of-file function is called if the end of the
     file is reached during input.
     (eoffn nil) gets the default end-of-file function.
     (eoffn x f) sets x's end-of-file function to f.
     (eoffn nil f) sets the default end-of-file function to f.
     f may be nil, which means that no end-of-file function is  to  be
     used.
11/18/73                        13.2.4                        Page 143
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
13.3           Applying Defaults to File Names
   The  I/O  system  provides  a mechanism for applying defaults which
programs can use and which is used when a file object  is  created  by
the open functions.
   A   default   namelist,   linel,   and  eoffn  are  remembered  for
initializations of file objects.  Output  to  the  terminal  uses  the
default  linel.   These  defaults may be examined or modified by using
the names, linel, or eoffn function with a first argument of nil.  The
chrct for output to the terminal may be examined or modified by  using
the  chrct  function with a first argument of nil.  When a file object
is created, its linel and eoffn are set to the defaults.
   There is also a system of defaults for  file  names  (actually  for
namelists),  which  is  based  on  the use of namelists containing the
special atom *.
   If one of the elements in a namelist is the atom  *,  it  indicates
that that component is not specified.  Thus the namelist
          (* foo bar)
specifies a file named foo.bar but it is not said in what directory or
on what device it exists.  Similarly a namelist like
          (dir foo *)
indicates  a file in directory dir, with a two component name of which
the first component is foo, but the second component is not specified.
   A namelist may also be dotted, that is, it may  end  with  an  atom
rather  than with nil.  If it ends with an atom other than *, i.e.  if
it looks like
                   (devdir name1 name2 name3 . foo)
it  specifies  a  file  whose  name   begins   with   the   components
name1.name2.name3,  ends with the component foo, and may also have any
number of components in between.  For example,  ignoring  directories,
in  a  system  such  as  Multics  where the namestring consists of the
file-name components from  the  namelist  concatenated  together  with
periods, the namelist
          (--  moe larry  .  mung)
could specify all of the following file names:
          moe.larry.mung
          moe.larry.curly.mung
          moe.larry.foo.bar.blech.mung
Page 144                         13.3                         11/18/73
		                           Input and Output
                    ***** ROUGH DRAFT #9905 *****
and  so  on.   This  form  of  namelist  can  be used to apply what is
sometimes called a "default extension."
   A namelist can also have a dotted star, that is it can  be  in  the
form
          (devdir -names-  .  *)
This  specifies  a file whose name begins with the components -names-,
and may have zero or more components following those.  Thus
          (-- mung bung  .  *)
means any of these file names:
          mung.bung
          mung.bung.lung
          mung.bung.foo.goo.zoo
   The  process  of  applying  defaults  to  file  names  consists  of
"merging" two (or more) namelists into a single namelist, where one of
the namelists is a user-supplied file specifier and the other is a set
of  defaults.   For  this  purpose,  the  function mergef is supplied.
Mergef is also used  by  openi  and  openo  when  they  combine  their
argument  with  the  default  namelist to get the namelist of the file
being opened.
mergef		LSUBR 2 or more args
     Mergef is used for applying defaults to  file  specifiers,  which
     may be namelists or namestrings.
     (mergef  x y) returns a namelist obtained by selecting components
     from x  and  y,  which  are  converted  to  namelists.   Where  a
     component  of  x  is  *,  the  corresponding  component  of  y is
     selected.  It is an  error  if  y  is  not  that  long.   When  a
     component  of  x  is  not *, it is selected and the corresponding
     component of y is skipped.  If y ends with a  dotted  atom  other
     than a * this atom is added to the end of the namelist if its not
     already  there.    The same applies if x ends with a dotted atom.
     If x ends with a dotted *, the rest of y is copied over.
     (mergef x nil) strips off the last component of x.
     (mergef w x y z)
        is equivalent to
     (mergef (mergef (mergef w x) y) z).
11/18/73                         13.3                         Page 145
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
13.4          Requests to the Operating System
13.4.1          Manipulating the Terminal
tty		VARIABLE
     The value of the atom tty is initially set to a number describing
     the type of terminal being used.  The  values  presently  defined
     are:
     0         normal terminal with no special capabilities
     1,2       various display terminals
     3         Imlac terminal.
cursorpos		LSUBR 0 or 2 args
     The  cursorpos  function  is  used  to manipulate the cursor on a
     display terminal.
     With no arguments it returns the dotted  pair  (line  .  column),
     where  line is the line number, starting from 0 at the top of the
     screen, and column is the column position, starting from 0 at the
     left edge of the screen.  If the terminal being  used  is  not  a
     display  terminal  with  this  type  of  cursor,  nil is returned
     instead.
     With two arguments, (cursorpos line  column)  moves  the  display
     cursor  to  the  indicated  position  and  returns  t  if  it was
     successful, or nil if the terminal was incapable of doing this.
listen		SUBR no args
     (listen) returns a fixnum which is non-zero if there is any input
     that has been typed in on the terminal but has not yet been read.
13.4.2          File System Operations
Page 146                        13.4.2                        11/18/73
		                           Input and Output
                    ***** ROUGH DRAFT #9905 *****
deletef		SUBR 1 arg
     (deletef x), where x specifies a file, deletes  that  file.   The
     return  value  is the namelist of the file actually deleted, i.e.
     x mergef'ed over the defaults.  Example:
        In the Multics implementation,
         (deletef "foo.bar") => (>udd>ap>junk foo bar)
        In the ITS implementation,
         (deletef "foo bar") => ((ml loser) foo bar)
rename		SUBR 2 args
     (rename x y), where x and y are namelists or namestrings, renames
     the file  specified  by  (mergef  x  (names  nil))  to  the  name
     specified  by  (mergef y x (names nil)).  The directory part of y
     is ignored; a file may not be renamed onto a different device  or
     directory.   The  return value is the namelist of the new name of
     the file.
     Example:
        In the Multics implementation,
         (rename "foo.baz" "*.bar") => (>udd>Bar>Foo foo bar)
               and renames >udd>Bar>Foo>foo.baz to foo.bar.
        In the ITS implementation,
         (rename "foo baz" "* bar") => ((ml loser) foo bar)
               and renames ml:loser;foo baz to foo bar.
allfiles		SUBR 1 arg
     (allfiles x), where x is a namelist, returns a list of  namelists
     which  are  precise; i.e. they do not contain any stars or dotted
     parts.  These are the namelists for all the  files  in  the  file
     system  which  match  the  namelist x.  Whatever search rules are
     customary in the particular operating system are used.
     Allfiles with a precise namelist as an argument can be used as  a
     predicate to determine whether or not a file exists.
clear-input	SUBR 1
     (clear-input  x),  where x is a file or nil meaning the terminal,
     causes any input that has been received from the device  but  has
     not  yet been read to be thrown away, if that makes sense for the
     particular device involved.
11/18/73                        13.4.2                        Page 147
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
force-output		SUBR 1
     (force-output x), where x is a file or nil meaning the  terminal,
     causes any buffered output to be immediately sent to the device.
13.4.3          Random Access to Files
filepos		LSUBR 1 or 2 args
     (filepos x), where x is a file object open for input, returns the
     current  character  position  within  the  file as a fixnum.  The
     beginning of the file is 0.
     (filepos x n), where x is a file object open for input and n is a
     non-negative fixnum, resets the character position of the file to
     position specified by n.  It is an error if  this  position  does
     not  lie  within  the  file  or  if  the  file  is  not  randomly
     accessible.  N is returned.
Page 148                        13.4.3                        11/18/73
		                           Input and Output
                    ***** ROUGH DRAFT #9905 *****
13.5          The Old "Uread" I/O System
        The functions uread, uwrite, ufile, ukill, and crunit are part
     of  an  older  LISP  I/O   system.    They   are   retained   for
     compatibility.   Various "status" functions are also part of this
     older I/O system.  (See section 12.7)
        These five functions name files in a different  way  from  the
     other I/O functions.  A file is named by a 4-list,
                           (name1 name2 dev dir)
     Name1  and  name2  together  make  up  the "filename," dev is the
     "device," and dir is the "directory."  In the ITS  implementation
     of MACLISP, these go together to make up the ITS file name:
                           DEV: DIR; NAME1 NAME2
     In  the  DEC-10  implementation, dev is the device name, name1 is
     the file name, name2 is the extension, and dir is a list  of  two
     fixnums,  the project number and the programmer number.  Thus the
     4-list
                        (name1 ext dev (proj prog))
     represents the file
                         dev:name1.ext[proj,prog]
     In the Multics implementation, dev is  ignored  and  dir  is  the
     directory  pathname.   The  entry-name  is name1.name2.  Thus the
     Multics filename is:
                              dir>name1.name2
        These five functions maintain their own set of defaults, which
     are updated every time one of these functions is called, so  that
     the  defaults  correspond  to  the  last file that was used.  The
     defaults may be examined with (status crfile), which returns  the
     first  two  elements  of  the default 4-list, and (status crunit)
     which returns the last two.
        It is not necessary to specify all four parts  of  the  4-list
     when  one of these five functions is used.  Any omitted parts are
     taken from the defaults.
        These  functions  are  fsubrs  which  do  not  evaluate  their
     arguments.  They may be applied to a 4-list, e.g.
                   (apply 'uread '(foo bar dsk comlap))
     or they may be called with the 4-list as four arguments, which is
     convenient when calling them from top level.
11/18/73                         13.5                         Page 149
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
uread		FSUBR
     This  function  selects  an  input  file.  The argument list is a
     4-list as described  above.   The  specified  file  is  made  the
     default  input  source.   Note  that  the ↑q switch mst be turned
     onbefore input will be automatically taken from this file.
uwrite		FSUBR
     Uwrite opens an output file.  When done  with  this  file,  ufile
     must  be  used to close it and give it a name.  The arguments are
     the last two elements of a  4-list,  specifying  the  device  and
     directory  on  which  the  file  is to be written.  The first two
     parts of the 4-list are not specified until the file is ufile'd.
ufile		FSUBR
     (ufile name1 name2) closes the uwrite output file  and  gives  it
     the  name  name1.name2.   (ufile)  takes name1 and name2 from the
     defaults.
crunit		FSUBR
     (crunit) gets the current device and directory.
     (crunit dev dir) sets the device and directory  and  returns  it.
     The arguments are not evaluated.  Example:
         (crunit) => (dsk >udd>Bar>Foo>subdirectory)
ukill		FSUBR
     (ukill   -args-),  where  -args-  are  like  uread,  deletes  the
     specified file.
uread		VARIABLE
     The value of  uread  is  a  file  object  being  used  for  input
     initiated  by  the uread function, or nil if no file is currently
     being uread.
Page 150                         13.5                         11/18/73
		                           Input and Output
                    ***** ROUGH DRAFT #9905 *****
uwrite		VARIABLE
     The value of uwrite is  a  file  object  being  used  for  output
     initiated  by the uwrite function, or nil if no file is currently
     being uwritten.
There are also some status/sstatus functions  associated  with  these.
These  are  (status  crunit),  (status  crfile),  (status  uread), and
(status uwrite).
11/18/73                         13.5                         Page 151
		                    LISP/MACLISP Reference Manual
                    ***** ROUGH DRAFT #9905 *****
13.6           Advanced Use of the Reader
13.6.1          The Obarray
obarray		VARIABLE & ARRAY
     The value of obarray is an array which is a table of known atomic
     symbols - when an atomic symbol is read in it  is  "interned"  on
     this obarray, that is made eq to any atomic symbols with the same
     pname that were previously read in.  If an atomic symbol, such as
     one  created  by  (gensym),  is not in this table an atom read in
     with the same pname will not be the same atom - there will be two
     seperate copies.
     The obarray may be manipulated by the functions remob and intern.
     A new obarray may be created by  using  the  makoblist  function.
     The  atom  obarray  may  be  setq'ed or lambda-bound to different
     obarrays at different times, which allows multiple sets of atomic
     symbols to be kept seperate  -  you  can  have  different  atomic
     symbols with the same pname interned on different obarrays at the
     same time.
     Note  that  the  value  of  obarray is not an atomic symbol which
     names an array, but the array itself,  obtainable  by  (get  name
     'array).
     The  array  property  of obarray is the same array as its initial
     value.
     Example of the use of multiple obarrays:
          (setq private-obarray
                (get (makoblist 'private-obarray) 'array))
                    ;make another obarray.
          ((lambda (obarray) (read)) private-obarray)
                    ;read using atoms on private obarray
                    ;instead of regular one
makoblist		SUBR 1 arg
     (makoblist nil) returns a list of  lists  of  atoms  which  is  a
     representation of the current obarray.
     (makoblist  'foo)  gives the atom foo an array property of a copy
     of the current obarray.
Page 152                        13.6.1                        11/18/73
		                           Input and Output
                    ***** ROUGH DRAFT #9905 *****
See also the functions remob (page 50) and intern (page 50.)
13.6.2          The Readtable
readtable		VARIABLE & ARRAY
     The value of readtable is an array which contains tables used  by
     the  reader  to  determine the meaning of input characters.  This
     array may be manipulated using the functions status, sstatus, and
     setsyntax.  Multiple readtable-arrays may be constructed by using
     the  makreadtable  function,  and  the  atom  readtable  may   be
     lambda-bound or setq'ed to one or another of these readtables.
     Note  that  the  value of readtable∪β          ***** ROUGH DRAFT #9905 *****
See also the functions remob (page 50) and intern (page 50.)
13.6.2          The Readtable
readtable		VARIABLE & ARRAY
     The value of readtable is an array which contains tables used  by
     the  reader  to  determine the meaning of input characters.  This
     array may be manipulated using the functions status, sstatus, and
     setsyntax.  Multiple readtable-arrays may be constructed by using
     the  makreadtable  function,  and