Initial revision
authorArthur Gleckler <edu/mit/csail/zurich/arthur>
Fri, 20 Dec 1991 15:43:26 +0000 (15:43 +0000)
committerArthur Gleckler <edu/mit/csail/zurich/arthur>
Fri, 20 Dec 1991 15:43:26 +0000 (15:43 +0000)
v7/doc/ref-manual/scheme.texinfo [new file with mode: 0644]
v7/doc/user-manual/user.texinfo [new file with mode: 0644]

diff --git a/v7/doc/ref-manual/scheme.texinfo b/v7/doc/ref-manual/scheme.texinfo
new file mode 100644 (file)
index 0000000..1809b5f
--- /dev/null
@@ -0,0 +1,12384 @@
+\input texinfo @c -*-texinfo-*-
+@iftex
+@finalout
+@end iftex
+@comment %**start of header (This is for running Texinfo on a region.)
+@setfilename scheme
+@settitle MIT Scheme Reference
+@comment %**end of header (This is for running Texinfo on a region.)
+@setchapternewpage odd
+@synindex vr fn
+
+@comment Parts of this document are essentially plagiarized from "Common
+@comment Lisp: The Language".  Those parts are marked by the following
+@comment comment lines:
+@comment
+@comment **** begin CLTL ****
+@comment **** end CLTL ****
+
+@comment This TeX macro is used in the description of the entry formats.
+@comment It is similar to the @deffn macro, but doesn't screw around
+@comment with the left margin or make an entry in the index.
+@tex
+
+\gdef\defnameexample #1#2{%
+\advance \hsize by -\leftskip %
+\advance \hsize by -\rightskip %
+\noindent        %
+\setbox0=\hbox{\hskip \deflastargmargin{\rm #2}\hskip \deftypemargin}%
+\dimen0=\hsize \advance \dimen0 by -\wd0 % compute size for first line
+\dimen1=\hsize \advance \dimen1 by -\defargsindent %size for continuations
+\parshape 2 0in \dimen0 \defargsindent \dimen1     %
+% Now output arg 2 ("Function" or some such)
+% ending at \deftypemargin from the right margin,
+% but stuck inside a box of width 0 so it does not interfere with linebreaking
+\rlap{\rightline{{\rm #2}\hskip \deftypemargin}}%
+\tolerance=10000 \hbadness=10000    % Make all lines underfull and no complaints
+\hskip \deftypemargin  % Indent function name slightly
+{\df #1}\enskip        % Generate function name
+}
+
+\gdef\deffnheaderexample #1#2#3{%
+\begingroup\defnameexample {#2}{#1}\defunargs{#3}\endgroup}
+
+\gdef\defmethparsebodyexample #1#2#3#4 {\begingroup\inENV %
+\medbreak %
+% Define the end token that this defining construct specifies
+% so that it will exit this group.
+\def#1{\endgraf\endgroup\medbreak}%
+\def#2##1 {\begingroup\obeylines\activeparens\spacesplit{#3{##1}}}%
+\parindent=0in %
+\begingroup\obeylines\activeparens\spacesplit{#3{#4}}}
+
+\gdef\deffnexample{\defmethparsebodyexample\Edeffnexample\deffnexamplex\deffnheaderexample}
+
+% Don't let TeX put extra vspace around math displays ($$ ... $$),
+% because these always appear inside @tex ... @end tex commands
+% that put space there to begin with.
+\abovedisplayskip=0pt plus 3pt
+\abovedisplayshortskip=0pt plus 3pt
+\belowdisplayskip=0pt plus 3pt
+\belowdisplayshortskip=0pt plus 3pt
+
+@end tex
+
+@ifinfo
+This file documents the MIT Scheme system.
+
+Copyright @copyright{} 1988, 1989, 1990, 1991 Massachusetts Institute of Technology
+
+This material was developed by the Scheme project at the Massachusetts
+Institute of Technology, Department of Electrical Engineering and Computer
+Science.  Permission to copy this document, to redistribute it, and to use
+it for any purpose is granted, subject to the following restrictions and
+understandings.
+
+@enumerate
+@item
+Any copy made of this document must include this copyright notice in
+full.
+
+@item
+Users of this document agree to make their best efforts (a) to return to
+the MIT Scheme project any improvements or extensions that they make, so
+that these may be included in future releases; and (b) to inform MIT of
+noteworthy uses of this document.
+
+@item
+All materials developed as a consequence of the use of this document shall
+duly acknowledge such use, in accordance with the usual standards of
+acknowledging credit in academic research.
+
+@item
+MIT has made no warrantee or representation that the contents of this
+document will be error-free, and MIT is under no obligation to provide any
+services, by way of maintenance, update, or otherwise.
+
+@item
+In conjunction with products arising from the use of this material, there
+shall be no use of the name of the Massachusetts Institute of Technology
+nor of any adaptation thereof in any advertising, promotional, or sales
+literature without prior written consent from MIT in each case.
+@end enumerate
+@end ifinfo
+
+@titlepage
+@title{MIT Scheme Reference Manual}
+@subtitle Edition 1.1
+@subtitle for Scheme Release 7.1.3
+@subtitle November 1991
+@author by Chris Hanson
+@author the MIT Scheme Team
+@author and a cast of thousands
+
+@page
+
+@vskip 0pt plus 1filll
+Copyright @copyright{} 1988, 1989, 1990, 1991 Massachusetts Institute of Technology
+
+This material was developed by the Scheme project at the Massachusetts
+Institute of Technology, Department of Electrical Engineering and Computer
+Science.  Permission to copy this document, to redistribute it, and to use
+it for any purpose is granted, subject to the following restrictions and
+understandings.
+
+@enumerate
+@item
+Any copy made of this document must include this copyright notice in
+full.
+
+@item
+Users of this document agree to make their best efforts (a) to return to
+the MIT Scheme project any improvements or extensions that they
+make, so that these may be included in future releases; and (b) to
+inform MIT of noteworthy uses of this document.
+
+@item
+All materials developed as a consequence of the use of this document shall
+duly acknowledge such use, in accordance with the usual standards of
+acknowledging credit in academic research.
+
+@item
+MIT has made no warrantee or representation that the contents of
+this document will be error-free, and MIT is under no obligation to
+provide any services, by way of maintenance, update, or otherwise.
+
+@item
+In conjunction with products arising from the use of this material,
+there shall be no use of the name of the Massachusetts Institute of
+Technology nor of any adaptation thereof in any advertising,
+promotional, or sales literature without prior written consent from
+MIT in each case.
+@end enumerate
+@end titlepage
+
+@node Top, Overview, (dir), (dir)
+
+@ifinfo
+Scheme is the UnCommon Lisp.  This Info file is the programmer reference
+document for the MIT implementation of Scheme.  It describes the
+facilities available for developing programs in MIT Scheme, and the
+``public'' parts of the implementation.
+@end ifinfo
+
+@menu
+* Overview::                    Overview
+* Special Forms::               Special Forms
+* Equivalence Predicates::      Equivalence Predicates
+* Numbers::                     Numbers
+* Characters::                  Characters
+* Strings::                     Strings
+* Lists::                       Lists
+* Vectors::                     Vectors
+* Bit Strings::                 Bit Strings
+* Miscellaneous Datatypes::     Miscellaneous Datatypes
+* Associations::                Associations
+* Procedures::                  Procedures
+* Environments::                Environments
+* Input/Output::                Input/Output
+* File-System Interface::       File-System Interface
+* Error System::                Error System
+* Graphics::                    Graphics
+* Procedure Index::             Index of Procedures, Special Forms, and Variables
+* Concept Index::               Index of Concepts
+
+ --- The Detailed Node Listing ---
+
+Overview
+
+* Notational Conventions::      Notational Conventions
+* Scheme Concepts::             Scheme Concepts
+* Lexical Conventions::         Lexical Conventions
+* Expressions::                 Expressions
+
+Notational Conventions
+
+* Errors::                      Errors
+* Examples::                    Examples
+* Entry Format::                Entry Format
+
+Scheme Concepts
+
+* Variable Bindings::           Variable Bindings
+* Environment Concepts::        Environment Concepts
+* Initial and Current Environments::  Initial and Current Environments
+* Static Scoping::              Static Scoping
+* True and False::              True and False
+* External Representations::    External Representations
+* Disjointness of Types::       Disjointness of Types
+* Storage Model::               Storage Model
+
+Lexical Conventions
+
+* Whitespace::                  Whitespace
+* Delimiters::                  Delimiters
+* Identifiers::                 Identifiers
+* Uppercase and Lowercase::     Uppercase and Lowercase
+* Naming Conventions::          Naming Conventions
+* Comments::                    Comments
+* Additional Notations::        Additional Notations
+
+Expressions
+
+* Literal Expressions::         Literal Expressions
+* Variable References::         Variable References
+* Special Form Syntax::         Special Form Syntax
+* Procedure Call Syntax::       Procedure Call Syntax
+
+Special Forms
+
+* Lambda Expressions::          Lambda Expressions
+* Lexical Binding::             Lexical Binding
+* Fluid Binding::               Fluid Binding
+* Definitions::                 Definitions
+* Assignments::                 Assignments
+* Quoting::                     Quoting
+* Conditionals::                Conditionals
+* Sequencing::                  Sequencing
+* Iteration::                   Iteration
+
+Definitions
+
+* Top-Level Definitions::       Top-Level Definitions
+* Internal Definitions::        Internal Definitions
+
+Numbers
+
+* Numerical types::             Numerical types
+* Exactness::                   Exactness
+* Implementation restrictions::  Implementation restrictions
+* Syntax of numerical constants::  Syntax of numerical constants
+* Numerical operations::        Numerical operations
+* Numerical input and output::  Numerical input and output
+* Fixnum and Flonum Operations::  Fixnum and Flonum Operations
+
+Fixnum and Flonum Operations
+
+* Fixnum Operations::           Fixnum Operations
+* Flonum Operations::           Flonum Operations
+
+Characters
+
+* External Representation of Characters::  External Representation of Characters
+* Comparison of Characters::    Comparison of Characters
+* Miscellaneous Character Operations::  Miscellaneous Character Operations
+* Internal Representation of Characters::  Internal Representation of Characters
+* ASCII Characters::            ASCII Characters
+* Character Sets::              Character Sets
+
+Strings
+
+* Construction of Strings::     Construction of Strings
+* Selecting String Components::  Selecting String Components
+* Comparison of Strings::       Comparison of Strings
+* Alphabetic Case in Strings::  Alphabetic Case in Strings
+* Cutting and Pasting Strings::  Cutting and Pasting Strings
+* Searching Strings::           Searching Strings
+* Matching Strings::            Matching Strings
+* Modification of Strings::     Modification of Strings
+* Variable-Length Strings::     Variable-Length Strings
+* Byte Vectors::                Byte Vectors
+
+Lists
+
+* Pairs::                       Pairs
+* Construction of Lists::       Construction of Lists
+* Selecting List Components::   Selecting List Components
+* Cutting and Pasting Lists::   Cutting and Pasting Lists
+* Filtering Lists::             Filtering Lists
+* Searching Lists::             Searching Lists
+* Mapping of Lists::            Mapping of Lists
+* Reduction of Lists::          Reduction of Lists
+* Miscellaneous List Operations::  Miscellaneous List Operations
+
+Vectors
+
+* Construction of Vectors::     Construction of Vectors
+* Selecting Vector Components::  Selecting Vector Components
+* Cutting Vectors::             Cutting Vectors
+* Modifying Vectors::           Modifying Vectors
+
+Bit Strings
+
+* Construction of Bit Strings::  Construction of Bit Strings
+* Selecting Bit String Components::  Selecting Bit String Components
+* Cutting and Pasting Bit Strings::  Cutting and Pasting Bit Strings
+* Bitwise Operations on Bit Strings::  Bitwise Operations on Bit Strings
+* Modification of Bit Strings::  Modification of Bit Strings
+* Integer Conversions of Bit Strings::  Integer Conversions of Bit Strings
+
+Miscellaneous Datatypes
+
+* Booleans::                    Booleans
+* Symbols::                     Symbols
+* Cells::                       Cells
+* Records::                     Records
+* Promises::                    Promises
+* Streams::                     Streams
+* Weak Pairs::                  Weak Pairs
+
+Associations
+
+* Association Lists::           Association Lists
+* 1D Tables::                   1D Tables
+* The Association Table::       The Association Table
+* Hash Tables::                 Hash Tables
+* Hashing::                     Hashing
+
+Procedures
+
+* Procedure Operations::        Procedure Operations
+* Primitive Procedures::        Primitive Procedures
+* Continuations::               Continuations
+* Application Hooks::           Application Hooks
+
+Environments
+
+* Environment Operations::      Environment Operations
+* Environment Variables::       Environment Variables
+* REPL Environment::            REPL Environment
+* Interpreter Environments::    Interpreter Environments
+
+Input/Output
+
+* Ports::                       Ports
+* File Ports::                  File Ports
+* String Ports::                String Ports
+* Input Procedures::            Input Procedures
+* Output Procedures::           Output Procedures
+* Format::                      Format
+* Custom Output::               Custom Output
+* Port Primitives::             Port Primitives
+
+Port Primitives
+
+* Input Port Primitives::       Input Port Primitives
+* Output Port Primitives::      Output Port Primitives
+
+File-System Interface
+
+* Pathnames::                   Pathnames
+* Working Directory::           Working Directory
+* File Manipulation::           File Manipulation
+* Directory Reader::            Directory Reader
+
+Pathnames
+
+* Filenames and Pathnames::     Filenames and Pathnames
+* Components of Pathnames::     Components of Pathnames
+* Operations on Pathnames::     Operations on Pathnames
+
+Error System
+
+* Simple Errors::               Simple Errors
+* Error Handler::               Error Handler
+* Error Messages::              Error Messages
+* Condition Types::             Condition Types
+* Condition Instances::         Condition Instances
+* Condition Signalling::        Condition Signalling
+* Condition Handling::          Condition Handling
+* Predefined Errors::           Predefined Errors
+
+Graphics
+
+* Opening and Closing of Graphics Devices::  Opening and Closing of Graphics Devices
+* Coordinates for Graphics::    Coordinates for Graphics
+* Drawing Graphics::            Drawing Graphics
+* Characteristics of Graphics Output::  Characteristics of Graphics Output
+* Buffering of Graphics Output::  Buffering of Graphics Output
+* Clipping of Graphics Output::  Clipping of Graphics Output
+* Custom Graphics Operations::  Custom Graphics Operations
+* X Graphics::                  X Graphics
+* Starbase Graphics::           Starbase Graphics
+
+X Graphics
+
+* X Graphics Type::             X Graphics Type
+* Utilities for X Graphics::    Utilities for X Graphics
+* Custom Operations on X Graphics Devices::  Custom Operations on X Graphics Devices
+@end menu
+
+@node Acknowledgements, Overview, Top, Top
+@unnumbered Acknowledgements
+
+While "a cast of thousands" may be an overstatement, it is certainly the
+case that this document represents the work of many people.  First and
+foremost, thanks go to the authors of the @cite{Revised^4 Report on the
+Algorithmic Language Scheme}, from which much of this document is
+derived.  Thanks also to BBN Advanced Computers Inc.@: for the use of
+parts of their @cite{Butterfly Scheme Reference}, and to Margaret
+O'Connell for translating it from BBN's text-formatting language to
+ours.
+
+Special thanks to Richard Stallman, Bob Chassell, and Brian Fox, all of
+the Free Software Foundation, for creating and maintaining the Texinfo
+formatting language in which this document is written.
+
+This report describes research done at the Artificial Intelligence
+Laboratory of the Massachusetts Institute of Technology.  Support for
+the laboratory's artificial intelligence research is provided in part by
+the Advanced Research Projects Agency of the Department of Defense under
+Office of Naval Research contracts N00014-85-K-0124 and
+N00014-86-K-0180.
+
+@node Overview, Special Forms, Acknowledgements, Top
+@chapter Overview
+
+This manual is a detailed description of the MIT Scheme runtime system.
+It is intended to be a reference document for programmers.  It does not
+describe how to run Scheme or how to interact with it --- that is the
+subject of the @cite{MIT Scheme User's Manual}.
+
+This chapter summarizes the semantics of Scheme, briefly describes the
+MIT Scheme programming environment, and explains the syntactic and
+lexical conventions of the language.  Subsequent chapters describe
+special forms, numerous data abstractions, and facilities for input and
+output.
+
+@cindex standard Scheme (defn)
+@cindex Scheme standard
+@cindex R4RS
+Throughout this manual, we will make frequent references to
+@dfn{standard Scheme}, which is the language defined by the document
+@cite{Revised^4 Report on the Algorithmic Language Scheme}, by William
+Clinger, Jonathan Rees, et al.@:, or by @sc{ieee} Std. 1178-1990,
+@cite{IEEE Standard for the Scheme Programming Language} (in fact,
+several parts of this document are copied from the @cite{Revised
+Report}).  MIT Scheme is an extension of standard Scheme.
+
+These are the significant semantic characteristics of the Scheme
+language:
+
+@table @asis
+@item Variables are statically scoped
+@cindex static scoping (defn)
+@cindex scope (see region)
+Scheme is a @dfn{statically scoped} programming language, which means that
+each use of a variable is associated with a lexically apparent binding
+of that variable.  Algol is another statically scoped language.
+
+@item Types are latent
+@cindex latent types (defn)
+@cindex manifest types (defn)
+@cindex weak types (defn)
+@cindex strong types (defn)
+@cindex dynamic types (defn)
+@cindex static types (defn)
+@cindex types, latent (defn)
+@cindex types, manifest (defn)
+Scheme has @dfn{latent} types as opposed to @dfn{manifest} types, which
+means that Scheme associates types with values (or objects) rather than
+with variables.  Other languages with latent types (also referred to as
+@dfn{weakly} typed or @dfn{dynamically} typed languages) include APL,
+Snobol, and other dialects of Lisp.  Languages with manifest types
+(sometimes referred to as @dfn{strongly} typed or @dfn{statically} typed
+languages) include Algol 60, Pascal, and C.
+
+@item Objects have unlimited extent
+@cindex extent, of objects
+All objects created during a Scheme computation, including procedures
+and continuations, have unlimited extent; no Scheme object is ever
+destroyed.  The system doesn't run out of memory because the garbage
+collector reclaims the storage occupied by an object when the object
+cannot possibly be needed by a future computation.  Other languages in
+which most objects have unlimited extent include APL and other Lisp
+dialects.
+
+@item Proper tail recursion
+@cindex proper tail recursion (defn)
+@cindex tail recursion (defn)
+@cindex recursion (see tail recursion)
+Scheme is @dfn{properly tail-recursive}, which means that iterative
+computation can occur in constant space, even if the iterative
+computation is described by a syntactically recursive procedure.  With a
+tail-recursive implementation, you can express iteration using the
+ordinary procedure-call mechanics; special iteration expressions are
+provided only for syntactic convenience.
+
+@item Procedures are objects
+Scheme procedures are objects, which means that you can create them
+dynamically, store them in data structures, return them as the results
+of other procedures, and so on.  Other languages with such procedure
+objects include Common Lisp and ML.
+
+@item Continuations are explicit
+In most other languages, continuations operate behind the scenes.  In
+Scheme, continuations are objects; you can use continuations for
+implementing a variety of advanced control constructs, including
+non-local exits, backtracking, and coroutines.
+
+@item Arguments are passed by value
+Arguments to Scheme procedures are passed by value, which means that
+Scheme evaluates the argument expressions before the procedure gains
+control, whether or not the procedure needs the result of the
+evaluations.  ML, C, and APL are three other languages that pass
+arguments by value.  In languages such as SASL and Algol 60, argument
+expressions are not evaluated unless the values are needed by the
+procedure.
+@end table
+
+@findex read
+Scheme uses a parenthesized-list Polish notation to describe programs
+and (other) data.  The syntax of Scheme, like that of most Lisp
+dialects, provides for great expressive power, largely due to its
+simplicity.  An important consequence of this simplicity is the
+susceptibility of Scheme programs and data to uniform treatment by other
+Scheme programs.  As with other Lisp dialects, the @code{read} primitive
+parses its input; that is, it performs syntactic as well as lexical
+decomposition of what it reads.
+
+@menu
+* Notational Conventions::      Notational Conventions
+* Scheme Concepts::             Scheme Concepts
+* Lexical Conventions::         Lexical Conventions
+* Expressions::                 Expressions
+@end menu
+
+@node Notational Conventions, Scheme Concepts, Overview, Overview
+@section Notational Conventions
+@cindex notational conventions
+@cindex conventions, notational
+
+This section details the notational conventions used throughout the rest
+of this document.
+
+@menu
+* Errors::                      Errors
+* Examples::                    Examples
+* Entry Format::                Entry Format
+@end menu
+
+@node Errors, Examples, Notational Conventions, Notational Conventions
+@subsection Errors
+@cindex errors, notational conventions
+
+@cindex signal an error (defn)
+@cindex must be, notational convention
+@findex signal-error
+When this manual uses the phrase ``an error will be signalled,'' it
+means that Scheme will call @code{signal-error}, which normally halts
+execution of the program and prints an error message.
+
+When this manual uses the phrase ``it is an error,'' it means that the
+specified action is not valid in Scheme, but the system may or may not
+signal the error.  When this manual says that something ``must be,'' it
+means that violating the requirement is an error.
+
+@node Examples, Entry Format, Errors, Notational Conventions
+@subsection Examples
+@cindex examples
+
+@cindex => notational convention
+@cindex result of evaluation, in examples
+@cindex evaluation, in examples
+@cindex specified result, in examples
+This manual gives many examples showing the evaluation of expressions.
+The examples have a common format that shows the expression being
+evaluated on the left hand side, an ``arrow'' in the middle, and the
+value of the expression written on the right.  For example:
+
+@example
+(+ 1 2)          @result{}  3
+@end example
+
+Sometimes the arrow and value will be moved under the expression, due to
+lack of space.  Occasionally we will not care what the value is, in
+which case both the arrow and the value are omitted.
+
+@cindex error--> notational convention
+@cindex error, in examples
+If an example shows an evaluation that results in an error, the error
+message is shown, prefaced by @samp{@error{}}:
+
+@example
+(+ 1 'foo)                      @error{} Illegal datum
+@end example
+
+@cindex -| notational convention
+@cindex printed output, in examples
+An example that shows printed output marks it with @samp{@print{}}:
+
+@example
+(begin (write 'foo) 'bar)
+     @print{} foo
+     @result{} bar
+@end example
+
+@cindex unspecified result (defn)
+@cindex result, unspecified (defn)
+When this manual indicates that the value returned by some expression is
+@dfn{unspecified}, it means that the expression will evaluate to some
+object without signalling an error, but that programs should not depend
+on the value in any way.
+
+@node Entry Format,  , Examples, Notational Conventions
+@subsection Entry Format
+@cindex entry format
+@cindex format, entry
+
+Each description of an MIT Scheme variable, special form, or
+procedure begins with one or more header lines in this format:
+
+@iftex
+@deffnexample @var{category} @var{template}
+@end deffnexample
+@end iftex
+@ifinfo
+@display
+* @var{category}: @var{template}
+@end display
+@end ifinfo
+
+@noindent
+where @var{category} specifies the kind of item (``variable'', ``special
+form'', or ``procedure''), and how the item conforms to standard Scheme, as
+follows:
+
+@table @asis
+@item @var{category}
+@var{Category}, with no extra marking, indicates that the item is described
+in the @cite{Revised^4 Report on the Algorithmic Language Scheme}.
+
+@item @var{category}+
+A plus sign after @var{category} indicates that the item is an MIT
+Scheme extension.
+@cindex + in entries
+@cindex plus sign, in entries
+@end table
+
+@noindent
+The form of @var{template} is interpreted depending on @var{category}.
+
+@table @asis
+@item Variable
+@var{Template} consists of the variable's name.
+@cindex variable, entry category
+
+@item Special Form
+@var{Template} starts with the syntactic keyword of the special form,
+followed by a description of the special form's syntax.  The description
+is written using the following conventions.
+@cindex special form, entry category
+
+@findex else
+@findex cond
+Named components are italicized in the printed manual, and uppercase in
+the Info file.  ``Noise'' keywords, such as the @code{else} keyword in
+the @code{cond} special form, are set in a fixed width font in the
+printed manual; in the Info file they are not distinguished.
+Parentheses indicate themselves.
+
+@cindex ellipsis, in entries
+@cindex ... in entries
+A horizontal ellipsis (@dots{}) is describes repeated components.
+Specifically,
+
+@display
+@var{thing} @dots{}
+@end display
+
+@noindent
+indicates @emph{zero} or more occurrences of @var{thing}, while
+
+@display
+@var{thing} @var{thing} @dots{}
+@end display
+
+@noindent
+indicates @emph{one} or more occurrences of @var{thing}.
+
+@cindex bracket, in entries
+@cindex [ in entries
+@cindex ] in entries
+@cindex optional component, in entries
+Brackets, @code{[ ]}, enclose optional components.
+
+@cindex body, of special form (defn)
+@findex lambda
+Several special forms (e.g.@: @code{lambda}) have an internal component
+consisting of a series of expressions; usually these expressions are
+evaluated sequentially under conditions that are specified in the
+description of the special form.  This sequence of expressions is commonly
+referred to as the @dfn{body} of the special form.
+
+@item Procedure
+@var{Template} starts with the name of the variable to which the
+procedure is bound, followed by a description of the procedure's
+arguments.  The arguments are described using ``lambda list'' notation
+(@pxref{Lambda Expressions}), except that brackets are used to denote
+optional arguments, and ellipses are used to denote ``rest'' arguments.
+@cindex procedure, entry format
+
+The names of the procedure's arguments are italicized in the printed
+manual, and uppercase in the Info file.
+
+When an argument names a Scheme data type, it indicates that the
+argument must be that type of data object.  For example,
+
+@iftex
+@deffnexample procedure cdr pair
+@end deffnexample
+@end iftex
+@ifinfo
+@display
+* procedure: cdr PAIR
+@end display
+@end ifinfo
+
+@noindent
+indicates that the standard Scheme procedure @code{cdr} takes one argument,
+which must be a pair.
+
+In addition to the standard data-type names (@var{pair}, @var{list},
+@var{boolean}, @var{string}, etc.), the following names as arguments
+also imply type restrictions:
+
+@table @var
+@item object
+any object
+@item thunk
+a procedure of no arguments
+@item x
+@itemx y
+a real number
+@item q
+@itemx n
+an integer
+@item k
+an exact non-negative integer
+@end table
+@end table
+
+Some examples:
+
+@iftex
+@deffnexample procedure list object @dots{}
+@end deffnexample
+@end iftex
+@ifinfo
+@display
+* procedure: list OBJECT @dots{}
+@end display
+@end ifinfo
+
+@noindent
+indicates that the standard Scheme procedure @code{list} takes zero or
+more arguments, each of which may be any Scheme object.
+
+@iftex
+@deffnexample procedure write-char char [output-port]
+@end deffnexample
+@end iftex
+@ifinfo
+@display
+* procedure: write-char CHAR [OUTPUT-PORT]
+@end display
+@end ifinfo
+
+@noindent
+indicates that the standard Scheme procedure @code{write-char} must be
+called with a character, @var{char}, and may also be called with a
+character and an output port.
+
+@node Scheme Concepts, Lexical Conventions, Notational Conventions, Overview
+@section Scheme Concepts
+@cindex scheme concepts
+
+@menu
+* Variable Bindings::           Variable Bindings
+* Environment Concepts::        Environment Concepts
+* Initial and Current Environments::  Initial and Current Environments
+* Static Scoping::              Static Scoping
+* True and False::              True and False
+* External Representations::    External Representations
+* Disjointness of Types::       Disjointness of Types
+* Storage Model::               Storage Model
+@end menu
+
+@node Variable Bindings, Environment Concepts, Scheme Concepts, Scheme Concepts
+@subsection Variable Bindings
+@cindex variable binding
+@cindex binding, of variable
+
+@cindex bound variable (defn)
+@cindex value, of variable (defn)
+@cindex name, of value (defn)
+@cindex location, of variable
+Any identifier that is not a syntactic keyword may be used as a variable
+(@pxref{Identifiers}).  A variable may name a location where a value can
+be stored.  A variable that does so is said to be @dfn{bound} to the
+location.  The value stored in the location to which a variable is bound
+is called the variable's @dfn{value}.  (The variable is sometimes said
+to @dfn{name} the value or to be @dfn{bound to} the value.)
+
+@cindex unassigned variable (defn)
+@cindex error, unassigned variable
+A variable may be bound but still not have a value; such a variable is
+said to be @dfn{unassigned}.  Referencing an unassigned variable signals
+an ``Unassigned Variable'' error.  Unassigned variables are useful only
+in combination with side effects (@pxref{Assignments}).
+
+@node Environment Concepts, Initial and Current Environments, Variable Bindings, Scheme Concepts
+@subsection Environment Concepts
+
+@cindex environment (defn)
+@cindex unbound variable (defn)
+@cindex error, unbound variable (defn)
+An @dfn{environment} is a set of variable bindings.  If an environment
+has no binding for a variable, that variable is said to be @dfn{unbound}
+in that environment.  Referencing an unbound variable signals an
+``Unbound Variable'' error.
+
+@cindex extension, of environment (defn)
+@cindex environment, extension (defn)
+@cindex shadowing, of variable binding (defn)
+@cindex parent, of environment (defn)
+@cindex child, of environment (defn)
+@cindex inheritance, of environment bindings (defn)
+A new environment can be created by @dfn{extending} an existing
+environment with a set of new bindings.  Note that ``extending an
+environment'' does @strong{not} modify the environment; rather, it
+creates a new environment that contains the new bindings and the old
+ones.  The new bindings @dfn{shadow} the old ones; that is, if an
+environment that contains a binding for @code{x} is extended with a new
+binding for @code{x}, then only the new binding is seen when @code{x} is
+looked up in the extended environment.  Sometimes we say that the
+original environment is the @dfn{parent} of the new one, or that the new
+environment is a @dfn{child} of the old one, or that the new environment
+@dfn{inherits} the bindings in the old one.
+
+@findex let
+@findex let*
+@findex letrec
+@findex do
+@findex define
+Procedure calls extend an environment, as do @code{let}, @code{let*},
+@code{letrec}, and @code{do} expressions.  Internal definitions
+(@pxref{Internal Definitions}) also extend an environment.  (Actually,
+all the constructs that extend environments can be expressed in terms of
+procedure calls, so there is really just one fundamental mechanism for
+environment extension.)  A top-level definition (@pxref{Top-Level
+Definitions}) may add a binding to an existing environment.
+
+@node Initial and Current Environments, Static Scoping, Environment Concepts, Scheme Concepts
+@subsection Initial and Current Environments
+
+@cindex initial environment (defn)
+@cindex environment, initial (defn)
+MIT Scheme provides an @dfn{initial environment} that contains all
+of the variable bindings described in this manual.  Most environments
+are ultimately extensions of this initial environment.  In Scheme, the
+environment in which your programs execute is actually a child
+(extension) of the environment containing the system's bindings.  Thus,
+system names are visible to your programs, but your names do not
+interfere with system programs.
+
+@cindex current environment (defn)
+@cindex environment, current (defn)
+@cindex REP loop (defn)
+@cindex REP loop, environment of
+@findex user-initial-environment
+@findex ge
+The environment in effect at some point in a program is called the
+@dfn{current environment} at that point.  In particular, every @sc{rep}
+loop has a current environment.  (@sc{rep} stands for
+``read-eval-print''; the @sc{rep} loop is the Scheme program that reads
+your input, evaluates it, and prints the result.)  The environment of
+the top-level @sc{rep} loop (the one you are in when Scheme starts up)
+starts as @code{user-initial-environment}, although it can be changed by
+the @code{ge} procedure.  When a new @sc{rep} loop is created, its
+environment is determined by the program that creates it.  @sc{rep}
+loops that are created by the error handler use the environment in which
+the error occurred, if possible, or failing that they use the previous
+@sc{rep} loop's environment.
+
+@example
+@group
+1 ]=> z                                     @error{} Unbound variable
+
+2 Error-> (define z 3)
+
+2 Error-> z                                 @result{}  3
+
+2 Error-> <Control-G> interrupt typed
+
+1 ]=> z                                     @result{}  3
+@end group
+@end example
+
+@node Static Scoping, True and False, Initial and Current Environments, Scheme Concepts
+@subsection Static Scoping
+@cindex scoping, static
+@cindex static scoping
+
+@cindex dynamic binding, versus static scoping
+Scheme is a statically scoped language with block structure.  In this
+respect, it is like Algol and Pascal, and unlike most other dialects of
+Lisp except for Common Lisp.
+
+@cindex binding expression (defn)
+@cindex expression, binding (defn)
+The fact that Scheme is statically scoped (rather than
+dynamically bound) means that the environment that is extended (and
+becomes current) when a procedure is called is the environment in which
+the procedure was created (i.e., in which the procedure's defining
+lambda expression was evaluated), not the environment in which the
+procedure is called.  Because all the other Scheme @dfn{binding
+expressions} can be expressed in terms of procedures, this determines
+how all bindings behave.
+
+Consider the following definitions, made at the top-level @sc{rep} loop
+(in the initial environment):
+
+@example
+@group
+(define x 1)
+(define (f x) (g 2))
+(define (g y) (+ x y))
+(f 5)                                       @result{}  3 @r{; not} 7
+@end group
+@end example
+
+Here @code{f} and @code{g} are bound to procedures created in the
+initial environment.  Because Scheme is statically scoped, the call to
+@code{g} from @code{f} extends the initial environment (the one in which
+@code{g} was created) with a binding of @code{y} to @code{2}.  In this
+extended environment, @code{y} is @code{2} and @code{x} is @code{1}.
+(In a dynamically bound Lisp, the call to @code{g} would extend the
+environment in effect during the call to @code{f}, in which @code{x} is
+bound to @code{5} by the call to @code{f}, and the answer would be
+@code{7}.)
+
+@cindex lexical scoping (defn)
+@cindex scoping, lexical (defn)
+@cindex region, of variable binding (defn)
+@cindex variable, binding region (defn)
+@findex lambda
+Note that with static scoping, you can tell what binding a variable
+reference refers to just from looking at the text of the program; the
+referenced binding cannot depend on how the program is used.  That is,
+the nesting of environments (their parent-child relationship)
+corresponds to the nesting of binding expressions in program text.
+(Because of this connection to the text of the program, static scoping
+is also called @dfn{lexical} scoping.)  For each place where a variable
+is bound in a program there is a corresponding @dfn{region} of the
+program text within which the binding is effective.  For example, the
+region of a binding established by a @code{lambda} expression is the
+entire body of the @code{lambda} expression.  The documentation of each
+binding expression explains what the region of the bindings it makes is.
+A use of a variable (that is, a reference to or assignment of a
+variable) refers to the innermost binding of that variable whose region
+contains the variable use.  If there is no such region, the use refers
+to the binding of the variable in the global environment (which is an
+ancestor of all other environments, and can be thought of as a region in
+which all your programs are contained).
+
+@node True and False, External Representations, Static Scoping, Scheme Concepts
+@subsection True and False
+
+@cindex boolean object
+@cindex true, boolean object
+@cindex false, boolean object
+@findex #t
+@findex #f
+In Scheme, the boolean values true and false are denoted by @code{#t}
+and @code{#f}.  However, any Scheme value can be treated as a boolean
+for the purpose of a conditional test.  This manual uses the word
+@dfn{true} to refer to any Scheme value that counts as true, and the
+word @dfn{false} to refer to any Scheme value that counts as false.  In
+conditional tests, all values count as true except for @code{#f}, which
+counts as false (@pxref{Conditionals}).
+
+Implementation note: In MIT Scheme, @code{#f} and the empty list
+are the same object, and the printed representation of @code{#f} is
+always @samp{()}.  As this contradicts the Scheme standard, MIT
+Scheme will soon be changed to make @code{#f} and the empty list
+different objects.
+
+@node External Representations, Disjointness of Types, True and False, Scheme Concepts
+@subsection External Representations
+
+@cindex external representation (defn)
+@cindex representation, external (defn)
+An important concept in Scheme is that of the
+@dfn{external representation} of an object as a sequence of characters.
+For example, an external representation of the integer 28 is the
+sequence of characters @samp{28}, and an external representation of a
+list consisting of the integers 8 and 13 is the sequence of characters
+@samp{(8 13)}.
+
+The external representation of an object is not necessarily unique.  The
+integer 28 also has representations @samp{#e28.000} and @samp{#x1c}, and
+the list in the previous paragraph also has the representations @samp{(
+08 13 )} and @samp{(8 . (13 . ( )))}.
+
+Many objects have standard external representations, but some, such as
+procedures and circular data structures, do not have standard
+representations (although particular implementations may defined
+representations for them).
+
+An external representation may be written in a program to obtain the
+corresponding object (@pxref{Quoting}).
+
+@findex read
+@findex write
+External representations can also be used for input and output.  The
+procedure @code{read} parses external representations, and the procedure
+@code{write} generates them.  Together, they provide an elegant and
+powerful input/output facility.
+
+Note that the sequence of characters @samp{(+ 2 6)} is @emph{not} an
+external representation of the integer 8, even though it @emph{is} an
+expression that evaluates to the integer 8; rather, it is an external
+representation of a three-element list, the elements of which are the
+symbol @code{+} and the integers @code{2} and @code{6}.  Scheme's syntax
+has the property that any sequence of characters that is an expression
+is also the external representation of some object.  This can lead to
+confusion, since it may not be obvious out of context whether a given
+sequence of characters is intended to denote data or program, but it is
+also a source of power, since it facilitates writing programs such as
+interpreters and compilers that treat programs as data or data as
+programs.
+
+@node Disjointness of Types, Storage Model, External Representations, Scheme Concepts
+@subsection Disjointness of Types
+
+Every object satisfies at most one of the following predicates (but
+@pxref{True and False}, for an exception):
+
+@example
+@group
+bit-string?     null?           string?
+boolean?        number?         symbol?
+cell?           pair?           vector?
+char?           procedure?      weak-pair?
+environment?    promise?
+@end group
+@end example
+
+@node Storage Model,  , Disjointness of Types, Scheme Concepts
+@subsection Storage Model
+
+This section describes a model that can be used to understand Scheme's
+use of storage.
+
+@cindex location
+@findex string-set!
+Variables and objects such as pairs, vectors, and strings implicitly
+denote locations or sequences of locations.  A string, for example,
+denotes as many locations as there are characters in the string.  (These
+locations need not correspond to a full machine word.)  A new value may
+be stored into one of these locations using the @code{string-set!}
+procedure, but the string continues to denote the same locations as
+before.
+  
+@findex car
+@findex vector-ref
+@findex string-ref
+@findex eqv?
+An object fetched from a location, by a variable reference or by a
+procedure such as @code{car}, @code{vector-ref}, or @code{string-ref},
+is equivalent in the sense of @code{eqv?} to the object last stored in
+the location before the fetch.
+
+Every location is marked to show whether it is in use.  No variable or
+object ever refers to a location that is not in use.  Whenever this
+document speaks of storage being allocated for a variable or object,
+what is meant is that an appropriate number of locations are chosen from
+the set of locations that are not in use, and the chosen locations are
+marked to indicate that they are now in use before the variable or
+object is made to denote them.
+
+@cindex constant
+@cindex mutable
+@cindex immutable
+@findex symbol->string
+In many systems it is desirable for constants (i.e.@: the values of
+literal expressions) to reside in read-only memory.  To express this, it
+is convenient to imagine that every object that denotes locations is
+associated with a flag telling whether that object is mutable or
+immutable.  The constants and the strings returned by
+@code{symbol->string} are then the immutable objects, while all objects
+created by other procedures are mutable.  It is an error to attempt to
+store a new value into a location that is denoted by an immutable
+object.
+
+@node Lexical Conventions, Expressions, Scheme Concepts, Overview
+@section Lexical Conventions
+@cindex lexical conventions
+@cindex conventions, lexical
+
+This section describes Scheme's lexical conventions.
+
+@menu
+* Whitespace::                  Whitespace
+* Delimiters::                  Delimiters
+* Identifiers::                 Identifiers
+* Uppercase and Lowercase::     Uppercase and Lowercase
+* Naming Conventions::          Naming Conventions
+* Comments::                    Comments
+* Additional Notations::        Additional Notations
+@end menu
+
+@node Whitespace, Delimiters, Lexical Conventions, Lexical Conventions
+@subsection Whitespace
+
+@cindex whitespace, in programs (defn)
+@cindex token, in programs (defn)
+@dfn{Whitespace} characters are spaces, newlines, tabs, and page breaks.
+Whitespace is used to improve the readability of your programs and to
+separate tokens from each other, when necessary.  (A @dfn{token} is an
+indivisible lexical unit such as an identifier or number.)  Whitespace
+is otherwise insignificant.  Whitespace may occur between any two
+tokens, but not within a token.  Whitespace may also occur inside a
+string, where it is significant.
+
+@node Delimiters, Identifiers, Whitespace, Lexical Conventions
+@subsection Delimiters
+
+@cindex delimiter, in programs (defn)
+All whitespace characters are @dfn{delimiters}.  In addition, the
+following characters act as delimiters:
+
+@example
+(  )  ;  "  '  `  |
+@end example
+
+Finally, these next characters act as delimiters, despite the fact that
+Scheme does not define any special meaning for them:
+
+@example
+[  ]  @{  @}
+@end example
+
+For example, if the value of the variable @code{name} is
+@code{"max"}:
+
+@example
+(list"Hi"name(+ 1 2))                   @result{}  ("Hi" "max" 3)
+@end example
+
+@node Identifiers, Uppercase and Lowercase, Delimiters, Lexical Conventions
+@subsection Identifiers
+
+@cindex identifier (defn)
+An @dfn{identifier} is a sequence of one or more non-delimiter
+characters.  Identifiers are used in several ways in Scheme
+programs:
+
+@itemize @bullet
+@item
+Certain identifiers are reserved for use as syntactic keywords; they
+should not be used as variables (for a list of the initial syntactic
+keywords, @pxref{Special Form Syntax}).
+@cindex syntactic keyword, identifier as
+
+@item
+Any identifier that is not a syntactic keyword can be used as a
+variable.
+@cindex variable, identifier as
+
+@item
+When an identifier appears as a literal or within a literal, it denotes
+a symbol.
+@cindex literal, identifier as
+@end itemize
+
+Scheme accepts most of the identifiers that other programming languages
+allow.  MIT Scheme allows all of the identifiers that standard
+Scheme does, plus many more.
+
+MIT Scheme defines a potential identifier to be a sequence of
+non-delimiter characters that does not begin with either of the
+characters @samp{#} or @samp{,}.  Any such sequence of characters, that
+is not a syntactically valid number (@pxref{Numbers}), is considered to
+be a valid identifier.  Note that, although it is legal for @samp{#} and
+@samp{,} to appear in an identifier (other than in the first character
+position), it is poor programming practice.
+
+Here are some examples of identifiers:
+
+@example
+lambda             q
+list->vector       soup
++                  V17a
+<=?                a34kTMNs
+the-word-recursion-has-many-meanings
+@end example
+
+@node Uppercase and Lowercase, Naming Conventions, Identifiers, Lexical Conventions
+@subsection Uppercase and Lowercase
+@cindex uppercase
+@cindex lowercase
+
+@cindex alphabetic case-insensitivity of programs (defn)
+@cindex case-insensitivity of programs (defn)
+@cindex sensitivity, to case in programs (defn)
+@cindex insensitivity, to case in programs (defn)
+Scheme doesn't distinguish uppercase and lowercase forms of a letter
+except within character and string constants; in other words, Scheme is
+@dfn{case-insensitive}.  For example, @samp{Foo} is the same identifier
+as @samp{FOO}, and @samp{#x1AB} is the same number as @samp{#X1ab}.  But
+@samp{#\a} and @samp{#\A} are different characters.
+
+@node Naming Conventions, Comments, Uppercase and Lowercase, Lexical Conventions
+@subsection Naming Conventions
+@cindex naming conventions
+@cindex conventions, naming
+
+@cindex predicate (defn)
+@cindex ? in predicate names
+A @dfn{predicate} is a procedure that always returns a boolean value
+(@code{#t} or @code{#f}).  By convention, predicates usually have names
+that end in @samp{?}.
+
+@cindex mutation procedure (defn)
+@cindex ! in mutation procedure names
+A @dfn{mutation procedure} is a procedure that alters a data structure.
+By convention, mutation procedures usually have names that end in
+@samp{!}.
+
+@node Comments, Additional Notations, Naming Conventions, Lexical Conventions
+@subsection Comments
+
+@cindex comment, in programs (defn)
+@cindex semicolon, as external representation
+@cindex ; as external representation
+The beginning of a comment is indicated with a semicolon (@code{;}).
+Scheme ignores everything on a line in which a semicolon appears, from
+the semicolon until the end of the line.  The entire comment, including
+the newline character that terminates it, is treated as
+whitespace.
+
+@cindex extended comment, in programs (defn)
+@cindex comment, extended, in programs (defn)
+@cindex #| as external representation
+An alternative form of comment (sometimes called an @dfn{extended
+comment}) begins with the characters @samp{#|} and ends with the
+characters @samp{|#}.  This alternative form is an MIT Scheme extension.
+As with ordinary comments, all of the characters in an extended comment,
+including the leading @samp{#|} and trailing @samp{|#}, are treated as
+whitespace.  Comments of this form may extend over multiple lines, and
+additionally may be nested (unlike the comments of the programming
+language C, which have a similar syntax).
+
+@example
+@group
+;;; This is a comment about the FACT procedure.  Scheme
+;;; ignores all of this comment.  The FACT procedure computes
+;;; the factorial of a non-negative integer.
+@end group
+
+@group
+#|
+This is an extended comment.
+Such comments are useful for commenting out code fragments.
+|#
+@end group
+
+@group
+(define fact
+  (lambda (n)
+    (if (= n 0)                      ;This is another comment:
+        1                            ;Base case: return 1
+        (* n (fact (- n 1))))))
+@end group
+@end example
+
+@node Additional Notations,  , Comments, Lexical Conventions
+@subsection Additional Notations
+
+@cindex characters, special, in programs
+@cindex special characters, in programs
+The following list describes additional notations used in Scheme.
+@xref{Numbers} for a description of the notations used for numbers.
+
+@table @code
+@item + - .
+The plus sign, minus sign, and period are used in numbers, and may also
+occur in an identifier.  A delimited period (not occurring within a
+number or identifier) is used in the notation for pairs and to indicate
+a ``rest'' parameter in a formal parameter list (@pxref{Lambda
+Expressions}).
+
+@item ( )
+Parentheses are used for grouping and to notate lists (@pxref{Lists}).
+
+@item "
+The double quote delimits strings (@pxref{Strings}).
+
+@item \
+The backslash is used in the syntax for character constants
+(@pxref{Characters}) and as an escape character within string constants
+(@pxref{Strings}).
+
+@item ;
+The semicolon starts a comment.
+
+@item '
+The single quote indicates literal data; it suppresses evaluation
+(@pxref{Quoting}).
+
+@item `
+The backquote indicates almost-constant data (@pxref{Quoting}).
+
+@item ,
+The comma is used in conjunction with the backquote (@pxref{Quoting}).
+
+@item ,@@
+A comma followed by an at-sign is used in conjunction with the backquote
+(@pxref{Quoting}).
+
+@item #
+The sharp (or pound) sign has different uses, depending on the character
+that immediately follows it:
+
+@item #t #f
+These character sequences denote the boolean constants
+(@pxref{Booleans}).
+
+@item #\
+This character sequence introduces a character constant
+(@pxref{Characters}).
+
+@item #(
+This character sequence introduces a vector constant (@pxref{Vectors}).
+A close parenthesis, @samp{)}, terminates a vector constant.
+
+@item #e #i #b #o #d #x
+These character sequences are used in the notation for numbers
+(@pxref{Numbers}).
+
+@item #|
+This character sequence introduces an extended comment.  The comment is
+terminated by the sequence @samp{|#}.  This notation is an MIT Scheme
+extension.
+
+@item #!
+This character sequence is used to denote a small set of named
+constants.  Currently there are only two of these, @code{#!optional} and
+@code{#!rest}, both of which are used in the @code{lambda} special form
+to mark certain parameters as being ``optional'' or ``rest'' parameters.
+This notation is an MIT Scheme extension.
+@findex #!optional
+@findex #!rest
+@findex lambda
+
+@item #*
+This character sequence introduces a bit string (@pxref{Bit Strings}).
+This notation is an MIT Scheme extension.
+@end table
+
+@node Expressions,  , Lexical Conventions, Overview
+@section Expressions
+
+@cindex expression (defn)
+A Scheme @dfn{expression} is a construct that returns a value.  An
+expression may be a @emph{literal}, a @emph{variable reference}, a
+@emph{special form}, or a @emph{procedure call}.
+
+@menu
+* Literal Expressions::         Literal Expressions
+* Variable References::         Variable References
+* Special Form Syntax::         Special Form Syntax
+* Procedure Call Syntax::       Procedure Call Syntax
+@end menu
+
+@node Literal Expressions, Variable References, Expressions, Expressions
+@subsection Literal Expressions
+
+@cindex literal expression (defn)
+@cindex constant expression (defn)
+@cindex expression, literal (defn)
+@cindex expression, constant (defn)
+@dfn{Literal} constants may be written by using an external
+representation of the data.  In general, the external representation
+must be @emph{quoted} (@pxref{Quoting}); but some external
+representations can be used without quotation.
+
+@example
+"abc"                                   @result{}  "abc"
+145932                                  @result{}  145932
+#t                                      @result{}  #t
+#\a                                     @result{}  #\a
+@end example
+
+The external representation of numeric constants, string constants,
+character constants, and boolean constants evaluate to the constants
+themselves.  Symbols, pairs, lists, and vectors require quoting.
+
+@node Variable References, Special Form Syntax, Literal Expressions, Expressions
+@subsection Variable References
+
+@cindex variable reference (defn)
+@cindex reference, variable (defn)
+@cindex unbound variable
+@cindex unassigned variable
+An expression consisting of an identifier (@pxref{Identifiers}) is a
+@dfn{variable reference}; the identifier is the name of the variable
+being referenced.  The value of the variable reference is the value
+stored in the location to which the variable is bound.  An error is
+signalled if the referenced variable is unbound or unassigned.
+
+@example
+(define x 28)
+x                                       @result{}  28
+@end example
+
+@node Special Form Syntax, Procedure Call Syntax, Variable References, Expressions
+@subsection Special Form Syntax
+
+@example
+(@var{keyword} @var{component} @dots{})
+@end example
+
+@cindex expression, special form (defn)
+@cindex special form (defn)
+@cindex form, special (defn)
+@cindex keyword, of special form (defn)
+@cindex syntactic keyword (defn)
+A parenthesized expression that starts with a @dfn{syntactic keyword} is
+a @dfn{special form}.  Each special form has its own syntax, which is
+described later in the manual.  The following list contains all of the
+syntactic keywords that are defined when MIT Scheme is initialized:
+
+@example
+@group
+access                  define-syntax           macro
+and                     delay                   make-environment
+begin                   do                      named-lambda
+bkpt                    error                   or
+case                    fluid-let               quasiquote
+cond                    if                      quote
+cons-stream             in-package              scode-quote
+declare                 lambda                  sequence
+default-object?         let                     set!
+define                  let*                    the-environment
+define-integrable       let-syntax              unassigned?
+define-macro            letrec                  using-syntax
+define-structure        local-declare
+@end group
+@end example
+
+@node Procedure Call Syntax,  , Special Form Syntax, Expressions
+@subsection Procedure Call Syntax
+
+@example
+(@var{operator} @var{operand} @dots{})
+@end example
+
+@cindex expression, procedure call (defn)
+@cindex procedure call (defn)
+@cindex operator, of procedure call (defn)
+@cindex operand, of procedure call (defn)
+A @dfn{procedure call} is written by simply enclosing in parentheses
+expressions for the procedure to be called (the @dfn{operator}) and the
+arguments to be passed to it (the @dfn{operands}).  The @var{operator}
+and @var{operand} expressions are evaluated and the resulting procedure
+is passed the resulting arguments.  @xref{Lambda Expressions}, for a
+more complete description of this.
+
+@cindex combination (defn)
+Another name for the procedure call expression is @dfn{combination}.
+This word is more specific in that it always refers to the expression;
+``procedure call'' sometimes refers to the @emph{process} of calling a
+procedure.
+
+@cindex order, of argument evaluation
+@cindex evaluation order, of arguments
+@cindex argument evaluation order
+Unlike some other dialects of Lisp, Scheme always evaluates the operator
+expression and the operand expressions with the same evaluation rules,
+and the order of evaluation is unspecified.
+
+@example
+@group
+(+ 3 4)                                 @result{}  7
+((if #f = *) 3 4)                       @result{}  12
+@end group
+@end example
+
+@findex +
+@findex *
+@findex lambda
+A number of procedures are available as the values of variables in the
+initial environment; for example, the addition and multiplication
+procedures in the above examples are the values of the variables
+@code{+} and @code{*}.  New procedures are created by evaluating
+@code{lambda} expressions.
+
+@cindex syntactic keyword
+@findex apply
+If the @var{operator} is a syntactic keyword, then the expression is not
+treated as a procedure call: it is a special form.  Thus you should not
+use syntactic keywords as procedure names.  If you were to bind one of
+these keywords to a procedure, you would have to use @code{apply} to
+call the procedure.  MIT Scheme signals an error when such a
+binding is attempted.
+
+@node Special Forms, Equivalence Predicates, Overview, Top
+@chapter Special Forms
+
+@cindex special form
+A special form is an expression that follows special evaluation rules.
+This chapter describes the basic Scheme special forms.
+
+@menu
+* Lambda Expressions::          Lambda Expressions
+* Lexical Binding::             Lexical Binding
+* Fluid Binding::               Fluid Binding
+* Definitions::                 Definitions
+* Assignments::                 Assignments
+* Quoting::                     Quoting
+* Conditionals::                Conditionals
+* Sequencing::                  Sequencing
+* Iteration::                   Iteration
+@end menu
+
+@node Lambda Expressions, Lexical Binding, Special Forms, Special Forms
+@section Lambda Expressions
+
+@deffn {special form} lambda formals expression expression @dots{}
+@cindex lambda expression (defn)
+@cindex procedure, construction
+@cindex procedure, closing environment (defn)
+@cindex procedure, invocation environment (defn)
+@cindex construction, of procedure
+@cindex closing environment, of procedure (defn)
+@cindex invocation environment, of procedure (defn)
+@cindex environment, of procedure
+@cindex environment, procedure closing (defn)
+@cindex environment, procedure invocation (defn)
+A @code{lambda} expression evaluates to a procedure.  The environment in
+effect when the @code{lambda} expression is evaluated is remembered as
+part of the procedure; it is called the @dfn{closing environment}.  When
+the procedure is later called with some arguments, the closing
+environment is extended by binding the variables in the formal parameter
+list to fresh locations, and the locations are filled with the arguments
+according to rules about to be given.  The new environment created by
+this process is referred to as the @dfn{invocation environment}.
+
+@cindex region of variable binding, lambda
+@cindex variable binding, lambda
+Once the invocation environment has been constructed, the
+@var{expression}s in the body of the @code{lambda} expression are
+evaluated sequentially in it.  This means that the region of the
+variables bound by the @code{lambda} expression is all of the
+@var{expression}s in the body.  The result of evaluating the last
+@var{expression} in the body is returned as the result of the procedure
+call.
+
+@cindex lambda list (defn)
+@cindex parameter list, of lambda (defn)
+@cindex formal parameter list, of lambda (defn)
+@var{Formals}, the formal parameter list, is often referred to as a
+@dfn{lambda list}.
+
+The process of matching up formal parameters with arguments is somewhat
+involved.  There are three types of parameters, and the matching treats
+each in sequence:
+
+@need 1000
+@table @asis
+@item Required
+All of the @dfn{required} parameters are matched against the arguments
+first.  If there are fewer arguments than required parameters, a ``Wrong
+Number of Arguments'' error is signalled; this error is also signalled
+if there are more arguments than required parameters and there are no
+further parameters.
+@cindex required parameter (defn)
+@cindex parameter, required (defn)
+
+@item Optional
+Once the required parameters have all been matched, the @dfn{optional}
+parameters are matched against the remaining arguments.  If there are
+fewer arguments than optional parameters, the unmatched parameters are
+bound to special objects called @dfn{default objects}.  If there are
+more arguments than optional parameters, and there are no further
+parameters, a ``Wrong Number of Arguments'' error is signalled.
+@cindex optional parameter (defn)
+@cindex parameter, optional (defn)
+@cindex default object (defn)
+
+@findex default-object?
+The predicate @code{default-object?}, which is true only of default
+objects, can be used to determine which optional parameters were
+supplied, and which were defaulted.
+
+@item Rest
+Finally, if there is a @dfn{rest} parameter (there can only be one), any
+remaining arguments are made into a list, and the list is bound to the
+rest parameter.  (If there are no remaining arguments, the rest
+parameter is bound to the empty list.)
+@cindex rest parameter (defn)
+@cindex parameter, rest (defn)
+
+In Scheme, unlike some other Lisp implementations, the list to which a
+rest parameter is bound is always freshly allocated.  It has infinite
+extent and may be modified without affecting the procedure's caller.
+@end table
+
+@findex #!optional
+@findex #!rest
+Specially recognized keywords divide the @var{formals} parameters into
+these three classes.  The keywords used here are @samp{#!optional},
+@samp{.}, and @samp{#!rest}.  Note that only @samp{.} is defined by
+standard Scheme --- the other keywords are MIT Scheme extensions.
+@samp{#!rest} has the same meaning as @samp{.} in @var{formals}.
+
+The use of these keywords is best explained by means of examples.  The
+following are typical lambda lists, followed by descriptions of which
+parameters are required, optional, and rest.  We will use @samp{#!rest}
+in these examples, but anywhere it appears @samp{.} could be used
+instead.
+
+@table @code
+@item (a b c)
+@code{a}, @code{b}, and @code{c} are all required.  The procedure must
+be passed exactly three arguments.
+
+@item (a b #!optional c)
+@code{a} and @code{b} are required, @code{c} is optional.  The procedure
+may be passed either two or three arguments.
+
+@item (#!optional a b c)
+@code{a}, @code{b}, and @code{c} are all optional.  The procedure may be
+passed any number of arguments between zero and three, inclusive.
+
+@item a
+@itemx (#!rest a)
+These two examples are equivalent.  @code{a} is a rest parameter.  The
+procedure may be passed any number of arguments.
+
+@item (a b #!optional c d #!rest e)
+@code{a} and @code{b} are required, @code{c} and @code{d} are optional,
+and @code{e} is rest.  The procedure may be passed two or more
+arguments.
+@end table
+
+Some examples of @code{lambda} expressions:
+
+@example
+(lambda (x) (+ x x))            @result{}  #[compound-procedure 53]
+
+((lambda (x) (+ x x)) 4)                @result{}  8
+
+(define reverse-subtract
+  (lambda (x y)
+    (- y x)))
+(reverse-subtract 7 10)                 @result{}  3
+
+(define foo
+  (let ((x 4))
+    (lambda (y) (+ x y))))
+(foo 6)                                 @result{}  10
+@end example
+@end deffn
+
+@deffn {special form+} named-lambda formals expression expression @dots{}
+@cindex named lambda (defn)
+The @code{named-lambda} special form is similar to @code{lambda}, except
+that the first ``required parameter'' in @var{formals} is not a
+parameter but the @dfn{name} of the resulting procedure; thus
+@var{formals} must have at least one required parameter.  This name has
+no semantic meaning, but is included in the external representation of
+the procedure, making it useful for debugging.  In MIT Scheme,
+@code{lambda} is implemented as @code{named-lambda}, with a special name
+that means ``unnamed''.
+
+@example
+@group
+(named-lambda (f x) (+ x x))    @result{}  #[compound-procedure 53 f]
+((named-lambda (f x) (+ x x)) 4)        @result{}  8
+@end group
+@end example
+@end deffn
+
+@node Lexical Binding, Fluid Binding, Lambda Expressions, Special Forms
+@section Lexical Binding
+
+@cindex lexical binding expression
+@cindex binding expression, lexical
+@cindex block structure
+The three binding constructs @code{let}, @code{let*}, and @code{letrec},
+give Scheme block structure.  The syntax of the three constructs is
+identical, but they differ in the regions they establish for their
+variable bindings.  In a @code{let} expression, the initial values are
+computed before any of the variables become bound.  In a @code{let*}
+expression, the evaluations and bindings are sequentially interleaved.
+And in a @code{letrec} expression, all the bindings are in effect while
+the initial values are being computed (thus allowing mutually recursive
+definitions).
+
+@deffn {special form} let ((@var{variable} @var{init}) @dots{}) expression expression @dots{}
+@cindex region of variable binding, let
+@cindex variable binding, let
+The @var{init}s are evaluated in the current environment (in some
+unspecified order), the @var{variable}s are bound to fresh locations
+holding the results, the @var{expression}s are evaluated sequentially in
+the extended environment, and the value of the last @var{expression} is
+returned.  Each binding of a @var{variable} has the @var{expression}s as
+its region.
+
+MIT Scheme allows any of the @var{init}s to be omitted, in which
+case the corresponding @var{variable}s are unassigned.
+
+@cindex lambda, implicit in let
+Note that the following are equivalent:
+
+@example
+(let ((@var{variable} @var{init}) @dots{}) @var{expression} @var{expression} @dots{})
+((lambda (@var{variable} @dots{}) @var{expression} @var{expression} @dots{}) @var{init} @dots{})
+@end example
+
+Some examples:
+
+@example
+@group
+(let ((x 2) (y 3))
+  (* x y))                              @result{}  6
+@end group
+
+@group
+(let ((x 2) (y 3))
+  (let ((foo (lambda (z) (+ x y z)))
+        (x 7))
+    (foo 4)))                           @result{}  9
+@end group
+@end example
+
+@xref{Iteration}, for information on ``named @code{let}''.
+@end deffn
+
+@deffn {special form} let* ((@var{variable} @var{init}) @dots{}) expression expression @dots{}
+@cindex region of variable binding, let*
+@cindex variable binding, let*
+@code{let*} is similar to @code{let}, but the bindings are performed
+sequentially from left to right, and the region of a binding is that
+part of the @code{let*} expression to the right of the binding.  Thus
+the second binding is done in an environment in which the first binding
+is visible, and so on.
+
+Note that the following are equivalent:
+
+@example
+@group
+(let* ((@var{variable1} @var{init1})
+       (@var{variable2} @var{init2})
+       @dots{}
+       (@var{variableN} @var{initN}))
+   @var{expression}
+   @var{expression} @dots{})
+@end group
+
+@group
+(let ((@var{variable1} @var{init1}))
+  (let ((@var{variable2} @var{init2}))
+    @dots{}
+      (let ((@var{variableN} @var{initN}))
+        @var{expression}
+        @var{expression} @dots{})
+    @dots{}))
+@end group
+@end example
+
+An example:
+
+@example
+@group
+(let ((x 2) (y 3))
+  (let* ((x 7)
+         (z (+ x y)))
+    (* z x)))                           @result{}  70
+@end group
+@end example
+@end deffn
+
+@deffn {special form} letrec ((@var{variable} @var{init}) @dots{}) expression expression @dots{}
+@cindex region of variable binding, letrec
+@cindex variable binding, letrec
+The @var{variable}s are bound to fresh locations holding unassigned
+values, the @var{init}s are evaluated in the extended environment (in
+some unspecified order), each @var{variable} is assigned to the result
+of the corresponding @var{init}, the @var{expression}s are evaluated
+sequentially in the extended environment, and the value of the last
+@var{expression} is returned.  Each binding of a @var{variable} has the
+entire @code{letrec} expression as its region, making it possible to
+define mutually recursive procedures.
+
+MIT Scheme allows any of the @var{init}s to be omitted, in which
+case the corresponding @var{variable}s are unassigned.
+
+@example
+@group
+(letrec ((even?
+          (lambda (n)
+            (if (zero? n)
+                #t
+                (odd? (- n 1)))))
+         (odd?
+          (lambda (n)
+            (if (zero? n)
+                #f
+                (even? (- n 1))))))
+  (even? 88))                           @result{}  #t
+@end group
+@end example
+
+@findex lambda
+@findex delay
+One restriction on @code{letrec} is very important: it shall be possible
+to evaluated each @var{init} without assigning or referring to the value
+of any @var{variable}.  If this restriction is violated, then it is an
+error.  The restriction is necessary because Scheme passes arguments by
+value rather than by name.  In the most common uses of @code{letrec},
+all the @var{init}s are @code{lambda} or @code{delay} expressions and
+the restriction is satisfied automatically.
+@end deffn
+
+@node Fluid Binding, Definitions, Lexical Binding, Special Forms
+@section Fluid Binding
+
+@deffn {special form+} fluid-let ((@var{variable} @var{init}) @dots{}) expression expression @dots{}
+@cindex binding expression, fluid (or dynamic)
+@cindex fluid binding
+@cindex dynamic binding
+@cindex variable binding, fluid-let
+The @var{init}s are evaluated in the current environment (in some
+unspecified order), the current values of the @var{variable}s are saved,
+the results are assigned to the @var{variable}s, the @var{expression}s
+are evaluated sequentially in the current environment, the
+@var{variable}s are restored to their original values, and the value of
+the last @var{expression} is returned.
+
+@findex let
+The syntax of this special form is similar to that of @code{let}, but
+@code{fluid-let} temporarily rebinds existing variables.  Unlike
+@code{let}, @code{fluid-let} creates no new bindings; instead it
+@emph{assigns} the values of each @var{init} to the binding (determined
+by the rules of lexical scoping) of its corresponding @var{variable}.
+
+@cindex unassigned variable, and dynamic bindings
+MIT Scheme allows any of the @var{init}s to be omitted, in which
+case the corresponding @var{variable}s are temporarily unassigned.
+
+An error is signalled if any of the @var{variable}s are unbound.
+However, because @code{fluid-let} operates by means of side effects, it
+is valid for any @var{variable} to be unassigned when the form is
+entered.
+
+Here is an example showing the difference between @code{fluid-let} and
+@code{let}.  First see how @code{let} affects the binding of a variable:
+
+@example
+@group
+(define variable #t)
+(define (access-variable) variable)
+variable                                @result{}  #t
+(let ((variable #f))
+  (access-variable))                    @result{}  #t
+variable                                @result{}  #t
+@end group
+@end example
+
+@code{access-variable} returns @code{#t} in this case because it
+is defined in an environment with @code{variable} bound to
+@code{#t}.  @code{fluid-let}, on the other hand, temporarily reuses an
+existing variable:
+
+@example
+@group
+variable                                @result{}  #t
+(fluid-let ((variable #f))              @r{;reuses old binding}
+  (access-variable))                    @result{}  #f
+variable                                @result{}  #t
+@end group
+@end example
+
+@cindex extent, of dynamic binding (defn)
+The @dfn{extent} of a dynamic binding is defined to be the time period
+during which the variable contains the new value.  Normally this time
+period begins when the body is entered and ends when it is exited; on a
+sequential machine it is normally a contiguous time period.  However,
+because Scheme has first-class continuations, it is possible to leave
+the body and then reenter it, as many times as desired.  In this
+situation, the extent becomes non-contiguous.
+
+@cindex dynamic binding, and continuations
+@cindex continuation, and dynamic binding
+When the body is exited by invoking a continuation, the new value is
+saved, and the variable is set to the old value.  Then, if the body is
+reentered by invoking a continuation, the old value is saved, and the
+variable is set to the new value.  In addition, side effects to the
+variable that occur both inside and outside of body are preserved, even
+if continuations are used to jump in and out of body repeatedly.
+
+Here is a complicated example that shows the interaction between dynamic
+binding and continuations:
+
+@example
+@group
+(define (complicated-fluid-binding)
+  (let ((variable 1)
+        (inside-continuation))
+    (write-line variable)
+    (call-with-current-continuation
+     (lambda (outside-continuation)
+       (fluid-let ((variable 2))
+         (write-line variable)
+         (set! variable 3)
+         (call-with-current-continuation
+          (lambda (k)
+            (set! inside-continuation k)
+            (outside-continuation #t)))
+         (write-line variable)
+         (set! inside-continuation #f))))
+    (write-line variable)
+    (if inside-continuation
+        (begin
+          (set! variable 4)
+          (inside-continuation #f)))))
+@end group
+@end example
+
+@noindent
+Evaluating @samp{(complicated-fluid-binding)} writes the following on
+the console:
+
+@example
+@group
+1
+2
+1
+3
+4
+@end group
+@end example
+
+@noindent
+Commentary: the first two values written are the initial binding of
+@code{variable} and its new binding after the @code{fluid-let}'s body is
+entered.  Immediately after they are written, @code{variable} is set to
+@samp{3}, and then @code{outside-continuation} is invoked, causing us to
+exit the body.  At this point, @samp{1} is written, demonstrating that
+the original value of @code{variable} has been restored, because we have
+left the body.  Then we set @code{variable} to @samp{4} and reenter the
+body by invoking @code{inside-continuation}.  At this point, @samp{3} is
+written, indicating that the side effect that previously occurred within
+the body has been preserved.  Finally, we exit body normally, and write
+@samp{4}, demonstrating that the side effect that occurred outside of
+the body was also preserved.
+@end deffn
+
+@node Definitions, Assignments, Fluid Binding, Special Forms
+@section Definitions
+@cindex definition
+
+@deffn {special form} define variable [expression]
+@deffnx {special form} define @var{formals} expression expression @dots{}
+@cindex variable, adding to environment
+@cindex definition, top-level (defn)
+@cindex definition, internal (defn)
+@cindex top-level definition (defn)
+@cindex internal definition (defn)
+@findex lambda
+@findex let
+@findex let*
+@findex letrec
+@findex fluid-let
+Definitions are valid in some but not all contexts where expressions are
+allowed.  Definitions may only occur at the top level of a program and
+at the beginning of a lambda body (that is, the body of a @code{lambda},
+@code{let}, @code{let*}, @code{letrec}, @code{fluid-let}, or ``procedure
+@code{define}'' expression).  A definition that occurs at the top level
+of a program is called a @dfn{top-level definition}, and a definition
+that occurs at the beginning of a body is called an @dfn{internal
+definition}.
+
+@cindex lambda, implicit in define
+@cindex procedure define (defn)
+@cindex define, procedure (defn)
+@findex named-lambda
+In the second form of @code{define} (called ``@dfn{procedure
+@code{define}}''), the component @var{formals} is identical to the
+component of the same name in a @code{named-lambda} expression.  In
+fact, these two expressions are equivalent:
+
+@example
+@group
+(define (@var{name1} @var{name2} @dots{})
+  @var{expression}
+  @var{expression} @dots{})
+@end group
+
+@group
+(define @var{name1}
+  (named-lambda (@var{name1} @var{name2} @dots{})
+    @var{expression}
+    @var{expression} @dots{}))
+@end group
+@end example
+@end deffn
+
+@menu
+* Top-Level Definitions::       Top-Level Definitions
+* Internal Definitions::        Internal Definitions
+@end menu
+
+@node Top-Level Definitions, Internal Definitions, Definitions, Definitions
+@subsection Top-Level Definitions
+@cindex top-level definition
+@cindex definition, top-level
+
+@cindex variable binding, top-level definition
+A top-level definition,
+
+@example
+(define @var{variable} @var{expression})
+@end example
+
+@noindent
+has essentially the same effect as this assignment expression, if
+@var{variable} is bound:
+
+@example
+(set! @var{variable} @var{expression})
+@end example
+
+@cindex unassigned variable, and definition
+@findex set!
+If @var{variable} is not bound, however, @code{define} binds
+@var{variable} to a new location in the current environment before
+performing the assignment (it is an error to perform a @code{set!} on an
+unbound variable).  If you omit @var{expression}, the variable is
+unassigned; an attempt to reference such a variable signals an
+``Unassigned Variable'' error.
+
+@example
+(define add3
+   (lambda (x) (+ x 3)))                @result{}  @r{unspecified}
+(add3 3)                                @result{}  6
+
+(define first car)                      @result{}  @r{unspecified}
+(first '(1 2))                          @result{}  1
+
+(define bar)                            @result{}  @r{unspecified}
+bar                                     @error{} Unassigned variable
+@end example
+
+@node Internal Definitions,  , Top-Level Definitions, Definitions
+@subsection Internal Definitions
+
+@cindex internal definition
+@cindex definition, internal
+@cindex region of variable binding, internal definition
+@cindex variable binding, internal definition
+@findex lambda
+@findex let
+@findex let*
+@findex letrec
+@findex fluid-let
+@findex define
+An @dfn{internal definition} is a definition that occurs at the
+beginning of a @var{body} (that is, the body of a @code{lambda},
+@code{let}, @code{let*}, @code{letrec}, @code{fluid-let}, or ``procedure
+@code{define}'' expression), rather than at the top level of a program.
+The variable defined by an internal definition is local to the
+@var{body}.  That is, @var{variable} is bound rather than assigned, and
+the region of the binding is the entire @var{body}.  For example,
+
+@example
+@group
+(let ((x 5))
+  (define foo (lambda (y) (bar x y)))
+  (define bar (lambda (a b) (+ (* a b) a)))
+  (foo (+ x 3)))                        @result{}  45
+@end group
+@end example
+
+@findex letrec
+A @var{body} containing internal definitions can always be converted
+into a completely equivalent @code{letrec} expression.  For example, the
+@code{let} expression in the above example is equivalent to
+
+@cindex letrec, implicit in define
+@example
+@group
+(let ((x 5))
+  (letrec ((foo (lambda (y) (bar x y)))
+           (bar (lambda (a b) (+ (* a b) a))))
+    (foo (+ x 3))))
+@end group
+@end example
+
+@need 1000
+@node Assignments, Quoting, Definitions, Special Forms
+@section Assignments
+@cindex assignment
+
+@deffn {special form} set! variable [expression]
+@cindex variable, assigning values to
+@cindex unassigned variable, and assignment
+If @var{expression} is specified, evaluates @var{expression}, and stores
+the resulting value in the location to which @var{variable} is bound.
+If @var{expression} is omitted, @var{variable} is altered to be
+unassigned; subsequent references to such @var{variable} are
+``Unassigned Variable'' errors.  In either case, the value of the
+@code{set!} expression is unspecified.
+
+@var{Variable} must be bound either in some region enclosing the
+@code{set!} expression, or at the top level.  However, @var{variable} is
+permitted to be unassigned when the @code{set!} form is entered.
+
+@example
+@group
+(define x 2)                            @result{}  @r{unspecified}
+(+ x 1)                                 @result{}  3
+(set! x 4)                              @result{}  @r{unspecified}
+(+ x 1)                                 @result{}  5
+@end group
+@end example
+
+@cindex access, used with set!
+@findex access
+@var{Variable} may be an @code{access} expression
+(@pxref{Environments}).  This allows you to assign variables in an
+arbitrary environment.  For example,
+
+@example
+@group
+(define x (let ((y 0)) (the-environment)))
+(define y 'a)
+y                                       @result{}  a
+(access y x)                            @result{}  0
+(set! (access y x) 1)                   @result{}  @r{unspecified}
+y                                       @result{}  a
+(access y x)                            @result{}  1
+@end group
+@end example
+@end deffn
+
+@node Quoting, Conditionals, Assignments, Special Forms
+@section Quoting
+@cindex quoting
+
+This section describes the expressions that are used to modify or
+prevent the evaluation of objects.
+
+@deffn {special form} quote datum
+@cindex external representation, and quote
+@cindex literal, and quote
+@cindex constant, and quote
+@code{(quote @var{datum})} evaluates to @var{datum}.  @var{Datum} may be
+any external representation of a Scheme object (@pxref{External
+Representations}).  Use @code{quote} to include literal constants in
+Scheme code.
+
+@example
+@group
+(quote a)                               @result{}  a
+(quote #(a b c))                        @result{}  #(a b c)
+(quote (+ 1 2))                         @result{}  (+ 1 2)
+@end group
+@end example
+
+@cindex ' as external representation
+@cindex apostrophe, as external representation
+@cindex quote, as external representation
+@findex '
+@code{(quote @var{datum})} may be abbreviated as @code{'@var{datum}}.
+The two notations are equivalent in all respects.
+
+@example
+@group
+'a                                      @result{}  a
+'#(a b c)                               @result{}  #(a b c)
+'(+ 1 2)                                @result{}  (+ 1 2)
+'(quote a)                              @result{}  'a
+''a                                     @result{}  'a
+@end group
+@end example
+
+Numeric constants, string constants, character constants, and boolean
+constants evaluate to themselves, so they don't need to be quoted.
+
+@example
+@group
+'"abc"                                  @result{}  "abc"
+"abc"                                   @result{}  "abc"
+'145932                                 @result{}  145932
+145932                                  @result{}  145932
+'#t                                     @result{}  #t
+#t                                      @result{}  #t
+'#\a                                    @result{}  #\a
+#\a                                     @result{}  #\a
+@end group
+@end example
+@end deffn
+
+@deffn {special form} quasiquote template
+@cindex external representation, and quasiquote
+@cindex literal, and quasiquote
+@cindex constant, and quasiquote
+@findex equal?
+``Backquote'' or ``quasiquote'' expressions are useful for constructing
+a list or vector structure when most but not all of the desired
+structure is known in advance.  If no commas appear within the
+@var{template}, the result of evaluating @code{`@var{template}} is
+equivalent (in the sense of @code{equal?}) to the result of evaluating
+@code{'@var{template}}.  If a comma appears within the @var{template},
+however, the expression following the comma is evaluated (``unquoted'')
+and its result is inserted into the structure instead of the comma and
+the expression.  If a comma appears followed immediately by an at-sign
+(@@), then the following expression shall evaluate to a list; the
+opening and closing parentheses of the list are then ``stripped away''
+and the elements of the list are inserted in place of the comma at-sign
+expression sequence.
+
+@example
+`(list ,(+ 1 2) 4)                           @result{}  (list 3 4)
+
+(let ((name 'a)) `(list ,name ',name))       @result{}  (list a 'a)
+
+`(a ,(+ 1 2) ,@@(map abs '(4 -5 6)) b)        @result{}  (a 3 4 5 6 b)
+
+`((foo ,(- 10 3)) ,@@(cdr '(c)) . ,(car '(cons)))
+                                             @result{}  ((foo 7) . cons)
+
+`#(10 5 ,(sqrt 4) ,@@(map sqrt '(16 9)) 8)
+                                             @result{}  #(10 5 2 4 3 8)
+
+`,(+ 2 3)                                    @result{}  5
+@end example
+
+@cindex nesting, of quasiquote expressions
+Quasiquote forms may be nested.  Substitutions are made only for
+unquoted components appearing at the same nesting level as the outermost
+backquote.  The nesting level increases by one inside each successive
+quasiquotation, and decreases by one inside each unquotation.
+
+@example
+@group
+`(a `(b ,(+ 1 2) ,(foo ,(+ 1 3) d) e) f)
+     @result{}  (a `(b ,(+ 1 2) ,(foo 4 d) e) f)
+
+(let ((name1 'x)
+      (name2 'y))
+   `(a `(b ,,name1 ,',name2 d) e))
+     @result{}  (a `(b ,x ,'y d) e)
+@end group
+@end example
+
+@cindex backquote, as external representation
+@cindex ` as external representation
+@cindex comma, as external representation
+@cindex , as external representation
+@cindex ,@@ as external representation
+@findex unquote
+@findex unquote-splicing
+@findex `
+@findex ,
+@findex ,@@
+The notations @code{`@var{template}} and (@code{quasiquote
+@var{template}}) are identical in all respects.
+@code{,@var{expression}} is identical to @code{(unquote
+@var{expression})} and @code{,@@@var{expression}} is identical to
+@code{(unquote-splicing @var{expression})}.
+
+@example
+@group
+(quasiquote (list (unquote (+ 1 2)) 4))
+     @result{}  (list 3 4)
+
+'(quasiquote (list (unquote (+ 1 2)) 4))
+     @result{}  `(list ,(+ 1 2) 4)
+     @emph{i.e.,} (quasiquote (list (unquote (+ 1 2)) 4))
+@end group
+@end example
+
+Unpredictable behavior can result if any of the symbols
+@code{quasiquote}, @code{unquote}, or @code{unquote-splicing} appear in
+a @var{template} in ways otherwise than as described above.
+@end deffn
+
+@node Conditionals, Sequencing, Quoting, Special Forms
+@section Conditionals
+
+@cindex expression, conditional (defn)
+@cindex conditional expression (defn)
+@cindex true, in conditional expression (defn)
+@cindex false, in conditional expression (defn)
+@findex #f
+@findex #t
+The behavior of the @dfn{conditional expressions} is determined by
+whether objects are true or false.  The conditional expressions count
+only @code{#f} as false.  They count everything else, including
+@code{#t}, pairs, symbols, numbers, strings, vectors, and procedures as
+true (but @pxref{True and False}).
+
+In the descriptions that follow, we say that an object has ``a true
+value'' or ``is true'' when the conditional expressions treat it as
+true, and we say that an object has ``a false value'' or ``is false''
+when the conditional expressions treat it as false.
+
+@deffn {special form} if predicate consequent [alternative]
+@var{Predicate}, @var{consequent}, and @var{alternative} are
+expressions.  An @code{if} expression is evaluated as follows: first,
+@var{predicate} is evaluated.  If it yields a true value, then
+@var{consequent} is evaluated and its value is returned.  Otherwise
+@var{alternative} is evaluated and its value is returned.  If
+@var{predicate} yields a false value and no @var{alternative} is
+specified, then the result of the expression is unspecified.
+
+An @code{if} expression evaluates either @var{consequent} or
+@var{alternative}, never both.  Programs should not depend on the value
+of an @code{if} expression that has no @var{alternative}.
+
+@example
+(if (> 3 2) 'yes 'no)                   @result{}  yes
+(if (> 2 3) 'yes 'no)                   @result{}  no
+(if (> 3 2)
+    (- 3 2)
+    (+ 3 2))                            @result{}  1
+@end example
+@end deffn
+
+@deffn {special form} cond clause clause @dots{}
+@cindex cond clause
+@cindex clause, of cond expression
+Each @var{clause} has this form:
+
+@example
+(@var{predicate} @var{expression} @dots{})
+@end example
+
+@noindent
+@cindex else clause, of cond expression (defn)
+@findex else
+where @var{predicate} is any expression.  The last @var{clause} may be
+an @dfn{@code{else} clause}, which has the form:
+
+@example
+(else @var{expression} @var{expression} @dots{})
+@end example
+
+A @code{cond} expression does the following:
+
+@enumerate
+@item
+Evaluates the @var{predicate} expressions of successive @var{clause}s in
+order, until one of the @var{predicate}s evaluates to a true
+value.
+
+@item
+When a @var{predicate} evaluates to a true value, @code{cond} evaluates
+the @var{expression}s in the associated @var{clause} in left to right
+order, and returns the result of evaluating the last @var{expression} in
+the @var{clause} as the result of the entire @code{cond} expression.
+
+If the selected @var{clause} contains only the @var{predicate} and no
+@var{expression}s, @code{cond} returns the value of the @var{predicate}
+as the result.
+
+@item
+If all @var{predicate}s evaluate to false values, and there is no
+@code{else} clause, the result of the conditional expression is
+unspecified; if there is an @code{else} clause, @code{cond} evaluates
+its @var{expression}s (left to right) and returns the value of the last
+one.
+@end enumerate
+
+@example
+@group
+(cond ((> 3 2) 'greater)
+      ((< 3 2) 'less))                  @result{}  greater
+
+(cond ((> 3 3) 'greater)
+      ((< 3 3) 'less)
+      (else 'equal))                    @result{}  equal
+@end group
+@end example
+
+Normally, programs should not depend on the value of a @code{cond}
+expression that has no @code{else} clause.  However, some Scheme
+programmers prefer to write @code{cond} expressions in which at least
+one of the @var{predicate}s is always true.  In this style, the final
+@var{clause} is equivalent to an @code{else} clause.
+
+@cindex => in cond clause
+@findex =>
+Scheme supports an alternative @var{clause} syntax:
+
+@example
+(@var{predicate} => @var{recipient})
+@end example
+
+@noindent
+where @var{recipient} is an expression.  If @var{predicate} evaluates to
+a true value, then @var{recipient} is evaluated.  Its value must be a
+procedure of one argument; this procedure is then invoked on the value
+of the @var{predicate}.
+
+@example
+(cond ((assv 'b '((a 1) (b 2))) => cadr)
+      (else #f))                        @result{}  2
+@end example
+@end deffn
+
+@deffn {special form} case key clause clause @dots{}
+@cindex case clause
+@cindex clause, of case expression
+@var{Key} may be any expression.  Each @var{clause} has this
+form:
+
+@example
+((@var{object} @dots{}) @var{expression} @var{expression} @dots{})
+@end example
+
+@cindex else clause, of case expression (defn)
+@findex else
+No @var{object} is evaluated, and all the @var{object}s must be
+distinct.  The last @var{clause} may be an @dfn{@code{else} clause},
+which has the form:
+
+@example
+(else @var{expression} @var{expression} @dots{})
+@end example
+
+A @code{case} expression does the following:
+
+@enumerate
+@item
+Evaluates @var{key} and compares the result with each
+@var{object}.
+
+@item
+If the result of evaluating @var{key} is equivalent (in the sense of
+@code{eqv?}; @pxref{Equivalence Predicates}) to an @var{object},
+@code{case} evaluates the @var{expression}s in the corresponding
+@var{clause} from left to right and returns the result of evaluating the
+last @var{expression} in the @var{clause} as the result of the
+@code{case} expression.
+@findex eqv?
+
+@item
+If the result of evaluating @var{key} is different from every
+@var{object}, and if there's an @code{else} clause, @code{case}
+evaluates its @var{expression}s and returns the result of the last one
+as the result of the @code{case} expression.  If there's no @code{else}
+clause, @code{case} returns an unspecified result.  Programs should not
+depend on the value of a @code{case} expression that has no @code{else}
+clause.
+@end enumerate
+
+For example,
+
+@example
+(case (* 2 3)
+   ((2 3 5 7) 'prime)
+   ((1 4 6 8 9) 'composite))            @result{}  composite
+
+(case (car '(c d))
+   ((a) 'a)
+   ((b) 'b))                            @result{}  @r{unspecified}
+
+(case (car '(c d))
+   ((a e i o u) 'vowel)
+   ((w y) 'semivowel)
+   (else 'consonant))                   @result{}  consonant
+@end example
+@end deffn
+
+@deffn {special form} and expression @dots{}
+The @var{expression}s are evaluated from left to right, and the value of
+the first @var{expression} that evaluates to a false value is returned.
+Any remaining @var{expression}s are not evaluated.  If all the
+@var{expression}s evaluate to true values, the value of the last
+@var{expression} is returned.  If there are no @var{expression}s then
+@code{#t} is returned.
+
+@example
+@group
+(and (= 2 2) (> 2 1))                   @result{}  #t
+(and (= 2 2) (< 2 1))                   @result{}  #f
+(and 1 2 'c '(f g))                     @result{}  (f g)
+(and)                                   @result{}  #t
+@end group
+@end example
+@end deffn
+
+@deffn {special form} or expression @dots{}
+The @var{expression}s are evaluated from left to right, and the value of
+the first @var{expression} that evaluates to a true value is returned.
+Any remaining @var{expression}s are not evaluated.  If all
+@var{expression}s evaluate to false values, the value of the last
+@var{expression} is returned.  If there are no @var{expression}s then
+@code{#f} is returned.
+
+@example
+@group
+(or (= 2 2) (> 2 1))                    @result{}  #t
+(or (= 2 2) (< 2 1))                    @result{}  #t
+(or #f #f #f)                           @result{}  #f
+(or (memq 'b '(a b c)) (/ 3 0))         @result{}  (b c)
+@end group
+@end example
+@end deffn
+
+@node Sequencing, Iteration, Conditionals, Special Forms
+@section Sequencing
+@cindex sequencing expressions
+
+@deffn {special form} begin expression expression @dots{}
+The @var{expression}s are evaluated sequentially from left to right, and
+the value of the last @var{expression} is returned.  This expression
+type is used to sequence side effects such as input and output.
+
+@example
+@group
+(define x 0)
+(begin (set! x 5)
+       (+ x 1))                 @result{}  6
+
+(begin (display "4 plus 1 equals ")
+       (display (+ 4 1)))
+                                @print{}  4 plus 1 equals 5
+                                @result{}  @r{unspecified}
+@end group
+@end example
+
+@cindex implicit begin
+Often the use of @code{begin} is unnecessary, because many special forms
+already support sequences of expressions (that is, they have an implicit
+@code{begin}).  Some of these special forms are:
+
+@example
+@group
+case
+cond
+define          @r{;``procedure @code{define}'' only}
+do
+fluid-let
+lambda
+let
+let*
+letrec
+named-lambda
+@end group
+@end example
+@findex case
+@findex cond
+@findex define
+@findex do
+@findex fluid-let
+@findex lambda
+@findex let
+@findex let*
+@findex letrec
+@findex named-lambda
+
+@findex sequence
+The obsolete special form @code{sequence} is identical to @code{begin}.
+It should not be used in new code.
+@end deffn
+
+@node Iteration,  , Sequencing, Special Forms
+@section Iteration
+
+@cindex expression, iteration (defn)
+@cindex iteration expression (defn)
+@cindex looping (see iteration expressions)
+@cindex tail recursion, vs. iteration expression
+The @dfn{iteration expressions} are: ``named @code{let}'' and @code{do}.
+They are also binding expressions, but are more commonly referred to as
+iteration expressions.  Because Scheme is properly tail-recursive, you
+don't need to use these special forms to express iteration; you can
+simply use appropriately written ``recursive'' procedure calls.
+
+@deffn {special form} let name ((@var{variable} @var{init}) @dots{}) expression expression @dots{}
+@cindex named let (defn)
+MIT Scheme permits a variant on the syntax of @code{let} called
+``named @code{let}'' which provides a more general looping construct
+than @code{do}, and may also be used to express recursions.
+
+Named @code{let} has the same syntax and semantics as ordinary
+@code{let} except that @var{name} is bound within the @var{expression}s
+to a procedure whose formal arguments are the @var{variable}s and whose
+body is the @var{expression}s.  Thus the execution of the
+@var{expression}s may be repeated by invoking the procedure named by
+@var{name}.
+
+@cindex unassigned variable, and named let
+MIT Scheme allows any of the @var{init}s to be omitted, in which
+case the corresponding @var{variable}s are unassigned.
+
+Note: the following expressions are equivalent:
+
+@example
+@group
+(let @var{name} ((@var{variable} @var{init}) @dots{})
+  @var{expression}
+  @var{expression} @dots{})
+
+((letrec ((@var{name}
+           (named-lambda (@var{name} @var{variable} @dots{})
+             @var{expression}
+             @var{expression} @dots{})))
+   @var{name})
+ @var{init} @dots{})
+@end group
+@end example
+
+Here is an example:
+
+@example
+@group
+(let loop
+     ((numbers '(3 -2 1 6 -5))
+      (nonneg '())
+      (neg '()))
+  (cond ((null? numbers)
+         (list nonneg neg))
+        ((>= (car numbers) 0)
+         (loop (cdr numbers)
+               (cons (car numbers) nonneg)
+               neg))
+        (else
+         (loop (cdr numbers)
+               nonneg
+               (cons (car numbers) neg)))))
+
+     @result{}  ((6 1 3) (-5 -2))
+@end group
+@end example
+@end deffn
+
+@deffn {special form} do ((@var{variable} @var{init} @var{step}) @dots{}) (@var{test} @var{expression} @dots{}) command @dots{}
+@code{do} is an iteration construct.  It specifies a set of variables to
+be bound, how they are to be initialized at the start, and how they are
+to be updated on each iteration.  When a termination condition is met,
+the loop exits with a specified result value.
+
+@code{do} expressions are evaluated as follows: The @var{init}
+expressions are evaluated (in some unspecified order), the
+@var{variable}s are bound to fresh locations, the results of the
+@var{init} expressions are stored in the bindings of the
+@var{variable}s, and then the iteration phase begins.
+
+Each iteration begins by evaluating @var{test}; if the result is false,
+then the @var{command} expressions are evaluated in order for effect,
+the @var{step} expressions are evaluated in some unspecified order, the
+@var{variable}s are bound to fresh locations, the results of the
+@var{step}s are stored in the bindings of the @var{variable}s, and the
+next iteration begins.
+
+If @var{test} evaluates to a true value, then the @var{expression}s are
+evaluated from left to right and the value of the last @var{expression}
+is returned as the value of the @code{do} expression.  If no
+@var{expression}s are present, then the value of the @code{do}
+expression is unspecified in standard Scheme; in MIT Scheme, the
+value of @var{test} is returned.
+
+@cindex region of variable binding, do
+@cindex variable binding, do
+The region of the binding of a @var{variable} consists of the entire
+@code{do} expression except for the @var{init}s.  It is an error for a
+@var{variable} to appear more than once in the list of @code{do}
+variables.
+
+A @var{step} may be omitted, in which case the effect is the same as if
+@code{(@var{variable} @var{init} @var{variable})} had been written
+instead of @code{(@var{variable} @var{init})}.
+
+@example
+@group
+(do ((vec (make-vector 5))
+      (i 0 (+ i 1)))
+    ((= i 5) vec)
+   (vector-set! vec i i))               @result{}  #(0 1 2 3 4)
+@end group
+
+@group
+(let ((x '(1 3 5 7 9)))
+   (do ((x x (cdr x))
+        (sum 0 (+ sum (car x))))
+       ((null? x) sum)))                @result{}  25
+@end group
+@end example
+@end deffn
+
+@node Equivalence Predicates, Numbers, Special Forms, Top
+@chapter Equivalence Predicates
+
+@cindex predicate (defn)
+@cindex predicate, equivalence (defn)
+@cindex equivalence predicate (defn)
+@cindex comparison, for equivalence
+@findex eq?
+@findex eqv?
+@findex equal?
+A @dfn{predicate} is a procedure that always returns a boolean value
+(@code{#t} or @code{#f}).  An @dfn{equivalence predicate} is the
+computational analogue of a mathematical equivalence relation (it is
+symmetric, reflexive, and transitive).  Of the equivalence predicates
+described in this section, @code{eq?} is the finest or most
+discriminating, and @code{equal?} is the coarsest.  @code{eqv?} is
+slightly less discriminating than @code{eq?}.
+
+@deffn procedure eqv? obj1 obj2
+The @code{eqv?} procedure defines a useful equivalence relation on
+objects.  Briefly, it returns @code{#t} if @var{obj1} and @var{obj2}
+should normally be regarded as the same object.
+
+The @code{eqv?} procedure returns @code{#t} if:
+
+@itemize @bullet
+@item
+@var{obj1} and @var{obj2} are both @code{#t} or both @code{#f}.
+
+@item
+@var{obj1} and @var{obj2} are both interned symbols and
+
+@example
+(string=? (symbol->string @var{obj1})
+          (symbol->string @var{obj2}))
+     @result{} #t
+@end example
+@findex string=?
+@findex symbol->string
+
+@item
+@var{obj1} and @var{obj2} are both numbers, are numerically equal
+according to the @code{=} procedure, and are either both exact or both
+inexact (@pxref{Numbers}).
+@findex =
+
+@item
+@var{obj1} and @var{obj2} are both characters and are the same character
+according to the @code{char=?} procedure (@pxref{Characters}).
+@findex char=?
+
+@item
+both @var{obj1} and @var{obj2} are the empty list.
+
+@item
+@var{obj1} and @var{obj2} are procedures whose location tags are equal.
+
+@item
+@var{obj1} and @var{obj2} are pairs, vectors, strings, bit strings,
+records, cells, or weak pairs that denote the same locations in the
+store.
+@end itemize
+
+@noindent
+The @code{eqv?} procedure returns @code{#f} if:
+
+@itemize @bullet
+@item
+@var{obj1} and @var{obj2} are of different types.
+
+@item
+one of @var{obj1} and @var{obj2} is @code{#t} but the other is
+@code{#f}.
+
+@item
+@var{obj1} and @var{obj2} are symbols but
+
+@example
+(string=? (symbol->string @var{obj1})
+          (symbol->string @var{obj2}))
+     @result{} #f
+@end example
+@findex string=?
+@findex symbol->string
+
+@item
+one of @var{obj1} and @var{obj2} is an exact number but the other is an
+inexact number.
+
+@item
+@var{obj1} and @var{obj2} are numbers for which the @code{=} procedure
+returns @code{#f}.
+@findex =
+
+@item
+@var{obj1} and @var{obj2} are characters for which the @code{char=?}
+procedure returns @code{#f}.
+@findex char=?
+
+@item
+one of @var{obj1} and @var{obj2} is the empty list but the other is not.
+
+@item
+@var{obj1} and @var{obj2} are procedures that would behave differently
+(return a different value or have different side effects) for some
+arguments.
+
+@item
+@var{obj1} and @var{obj2} are pairs, vectors, strings, bit strings,
+records, cells, or weak pairs that denote distinct locations.
+@end itemize
+
+Some examples:
+
+@example
+@group
+(eqv? 'a 'a)                    @result{}  #t
+(eqv? 'a 'b)                    @result{}  #f
+(eqv? 2 2)                      @result{}  #t
+(eqv? '() '())                  @result{}  #t
+(eqv? 100000000 100000000)      @result{}  #t
+(eqv? (cons 1 2) (cons 1 2))    @result{}  #f
+(eqv? (lambda () 1)
+      (lambda () 2))            @result{}  #f
+(eqv? #f 'nil)                  @result{}  #f
+(let ((p (lambda (x) x)))
+  (eqv? p p))                   @result{}  #t
+@end group
+@end example
+
+The following examples illustrate cases in which the above rules do not
+fully specify the behavior of @code{eqv?}.  All that can be said about
+such cases is that the value returned by @code{eqv?} must be a boolean.
+
+@example
+@group
+(eqv? "" "")                    @result{}  @r{unspecified}
+(eqv? '#() '#())                @result{}  @r{unspecified}
+(eqv? (lambda (x) x)
+      (lambda (x) x))           @result{}  @r{unspecified}
+(eqv? (lambda (x) x)
+      (lambda (y) y))           @result{}  @r{unspecified}
+@end group
+@end example
+
+The next set of examples shows the use of @code{eqv?} with procedures
+that have local state.  @code{gen-counter} must return a distinct
+procedure every time, since each procedure has its own internal counter.
+@code{gen-loser}, however, returns equivalent procedures each time,
+since the local state does not affect the value or side effects of the
+procedures.
+
+@example
+@group
+(define gen-counter
+  (lambda ()
+    (let ((n 0))
+      (lambda () (set! n (+ n 1)) n))))
+(let ((g (gen-counter)))
+  (eqv? g g))                   @result{}  #t
+(eqv? (gen-counter) (gen-counter))
+                                @result{}  #f
+@end group
+
+@group
+(define gen-loser
+  (lambda ()
+    (let ((n 0))
+      (lambda () (set! n (+ n 1)) 27))))
+(let ((g (gen-loser)))
+  (eqv? g g))                   @result{}  #t
+(eqv? (gen-loser) (gen-loser))
+                                @result{}  @r{unspecified}
+@end group
+
+@group
+(letrec ((f (lambda () (if (eqv? f g) 'both 'f)))
+         (g (lambda () (if (eqv? f g) 'both 'g)))
+  (eqv? f g))
+                                @result{}  @r{unspecified}
+
+(letrec ((f (lambda () (if (eqv? f g) 'f 'both)))
+         (g (lambda () (if (eqv? f g) 'g 'both)))
+  (eqv? f g))
+                                @result{}  #f
+@end group
+@end example
+
+Objects of distinct types must never be regarded as the same object.
+
+Since it is an error to modify constant objects (those returned by
+literal expressions), the implementation may share structure between
+constants where appropriate.  Thus the value of @code{eqv?} on constants
+is sometimes unspecified.
+
+@example
+(let ((x '(a)))
+  (eqv? x x))                    @result{}  #t
+(eqv? '(a) '(a))                 @result{}  @r{unspecified}
+(eqv? "a" "a")                   @result{}  @r{unspecified}
+(eqv? '(b) (cdr '(a b)))         @result{}  @r{unspecified}
+@end example
+
+Rationale: The above definition of @code{eqv?} allows implementations
+latitude in their treatment of procedures and literals: implementations
+are free either to detect or to fail to detect that two procedures or
+two literals are equivalent to each other, and can decide whether or not
+to merge representations of equivalent objects by using the same pointer
+or bit pattern to represent both.
+@end deffn
+
+@deffn procedure eq? obj1 obj2
+@code{eq?} is similar to @code{eqv?} except that in some cases it is
+capable of discerning distinctions finer than those detectable by
+@code{eqv?}.
+
+@code{eq?} and @code{eqv?} are guaranteed to have the same
+behavior on symbols, booleans, the empty list, pairs, and non-empty
+strings and vectors.  @code{eq?}'s behavior on numbers and characters is
+implementation-dependent, but it will always return either true or
+false, and will return true only when @code{eqv?} would also return
+true.  @code{eq?} may also behave differently from @code{eqv?} on empty
+vectors and empty strings.
+
+@example
+(eq? 'a 'a)                     @result{}  #t
+(eq? '(a) '(a))                 @result{}  @r{unspecified}
+(eq? (list 'a) (list 'a))       @result{}  #f
+(eq? "a" "a")                   @result{}  @r{unspecified}
+(eq? "" "")                     @result{}  @r{unspecified}
+(eq? '() '())                   @result{}  #t
+(eq? 2 2)                       @result{}  @r{unspecified}
+(eq? #\A #\A)                   @result{}  @r{unspecified}
+(eq? car car)                   @result{}  #t
+(let ((n (+ 2 3)))
+  (eq? n n))                    @result{}  @r{unspecified}
+(let ((x '(a)))
+  (eq? x x))                    @result{}  #t
+(let ((x '#()))
+  (eq? x x))                    @result{}  #t
+(let ((p (lambda (x) x)))
+  (eq? p p))                    @result{}  #t
+@end example
+
+Rationale: It will usually be possible to implement @code{eq?} much more
+efficiently than @code{eqv?}, for example, as a simple pointer
+comparison instead of as some more complicated operation.  One reason is
+that it may not be possible to compute @code{eqv?} of two numbers in
+constant time, whereas @code{eq?} implemented as pointer comparison will
+always finish in constant time.  @code{eq?} may be used like @code{eqv?}
+in applications using procedures to implement objects with state since
+it obeys the same constraints as @code{eqv?}.
+@end deffn
+
+@deffn procedure equal? obj1 obj2
+@cindex circular structure
+@code{equal?} recursively compares the contents of pairs, vectors, and
+strings, applying @code{eqv?} on other objects such as numbers, symbols,
+and records.  A rule of thumb is that objects are generally
+@code{equal?} if they print the same.  @code{equal?} may fail to
+terminate if its arguments are circular data structures.
+
+@example
+@group
+(equal? 'a 'a)                  @result{}  #t
+(equal? '(a) '(a))              @result{}  #t
+(equal? '(a (b) c)
+        '(a (b) c))             @result{}  #t
+(equal? "abc" "abc")            @result{}  #t
+(equal? 2 2)                    @result{}  #t
+(equal? (make-vector 5 'a)
+        (make-vector 5 'a))     @result{}  #t
+(equal? (lambda (x) x)
+        (lambda (y) y))         @result{}  @r{unspecified}
+@end group
+@end example
+@end deffn
+
+@node Numbers, Characters, Equivalence Predicates, Top
+@chapter Numbers
+@cindex number
+
+(This section is largely taken from the @cite{Revised^4 Report on the
+Algorithmic Language Scheme}.)
+
+Numerical computation has traditionally been neglected by the Lisp
+community.  Until Common Lisp there was no carefully thought out
+strategy for organizing numerical computation, and with the exception of
+the MacLisp system little effort was made to execute numerical code
+efficiently.  This report recognizes the excellent work of the Common
+Lisp committee and accepts many of their recommendations.  In some ways
+this report simplifies and generalizes their proposals in a manner
+consistent with the purposes of Scheme.
+
+It is important to distinguish between the mathematical numbers, the
+Scheme numbers that attempt to model them, the machine representations
+used to implement the Scheme numbers, and notations used to write
+numbers.  This report uses the types @emph{number}, @emph{complex},
+@emph{real}, @emph{rational}, and @emph{integer} to refer to both
+mathematical numbers and Scheme numbers.  Machine representations such
+as fixed point and floating point are referred to by names such as
+@emph{fixnum} and @emph{flonum}.
+
+@menu
+* Numerical types::             Numerical types
+* Exactness::                   Exactness
+* Implementation restrictions::  Implementation restrictions
+* Syntax of numerical constants::  Syntax of numerical constants
+* Numerical operations::        Numerical operations
+* Numerical input and output::  Numerical input and output
+* Fixnum and Flonum Operations::  Fixnum and Flonum Operations
+@end menu
+
+@node Numerical types, Exactness, Numbers, Numbers
+@section Numerical types
+@cindex numerical types
+
+Mathematically, numbers may be arranged into a tower of subtypes in
+which each level is a subset of the level above it:
+
+@display
+@group
+number
+complex
+real
+rational
+integer
+@end group
+@end display
+
+For example, 3 is an integer.  Therefore 3 is also a rational, a real,
+and a complex.  The same is true of the Scheme numbers that model 3.
+For Scheme numbers, these types are defined by the predicates
+@code{number?}, @code{complex?}, @code{real?}, @code{rational?}, and
+@code{integer?}.
+
+There is no simple relationship between a number's type and its
+representation inside a computer.  Although most implementations of
+Scheme will offer at least two different representations of 3, these
+different representations denote the same integer.
+
+Scheme's numerical operations treat numbers as abstract data, as
+independent of their representation as possible.  Although an
+implementation of Scheme may use fixnum, flonum, and perhaps other
+representations for numbers, this should not be apparent to a casual
+programmer writing simple programs.
+
+It is necessary, however, to distinguish between numbers that are
+represented exactly and those that may not be.  For example, indexes
+into data structures must be known exactly, as must some polynomial
+coefficients in a symbolic algebra system.  On the other hand, the
+results of measurements are inherently inexact, and irrational numbers
+may be approximated by rational and therefore inexact approximations.
+In order to catch uses of inexact numbers where exact numbers are
+required, Scheme explicitly distinguishes exact from inexact numbers.
+This distinction is orthogonal to the dimension of type.
+
+@node Exactness, Implementation restrictions, Numerical types, Numbers
+@section Exactness
+@cindex exactness
+
+Scheme numbers are either @emph{exact} or @emph{inexact}.  A number is
+exact if it was written as an exact constant or was derived from exact
+numbers using only exact operations.  A number is inexact if it was
+written as an inexact constant, if it was derived using inexact
+ingredients, or if it was derived using inexact operations. Thus
+inexactness is a contagious property of a number.
+
+If two implementations produce exact results for a computation that did
+not involve inexact intermediate results, the two ultimate results will
+be mathematically equivalent.  This is generally not true of
+computations involving inexact numbers since approximate methods such as
+floating point arithmetic may be used, but it is the duty of each
+implementation to make the result as close as practical to the
+mathematically ideal result.
+
+@findex +
+Rational operations such as @code{+} should always produce exact results
+when given exact arguments.  If the operation is unable to produce an
+exact result, then it may either report the violation of an
+implementation restriction or it may silently coerce its result to an
+inexact value.  @xref{Implementation restrictions}.
+
+@findex inexact->exact
+With the exception of @code{inexact->exact}, the operations described in
+this section must generally return inexact results when given any
+inexact arguments.  An operation may, however, return an exact result if
+it can prove that the value of the result is unaffected by the
+inexactness of its arguments.  For example, multiplication of any number
+by an exact zero may produce an exact zero result, even if the other
+argument is inexact.
+
+@node Implementation restrictions, Syntax of numerical constants, Exactness, Numbers
+@section Implementation restrictions
+@cindex implementation restriction
+
+Implementations of Scheme are not required to implement the whole tower
+of subtypes (@pxref{Numerical types}), but they must implement a
+coherent subset consistent with both the purposes of the implementation
+and the spirit of the Scheme language.  For example, an implementation
+in which all numbers are real may still be quite useful.@footnote{MIT
+Scheme implements the whole tower of numerical types.  It has
+unlimited-precision exact integers and exact rationals.  Flonums are
+used to implement all inexact reals; on machines that support @sc{ieee}
+floating-point arithmetic these are double-precision floating-point
+numbers.}
+
+Implementations may also support only a limited range of numbers of any
+type, subject to the requirements of this section.  The supported range
+for exact numbers of any type may be different from the supported range
+for inexact numbers of that type.  For example, an implementation that
+uses flonums to represent all its inexact real numbers may support a
+practically unbounded range of exact integers and rationals while
+limiting the range of inexact reals (and therefore the range of inexact
+integers and rationals) to the dynamic range of the flonum format.
+Furthermore the gaps between the representable inexact integers and
+rationals are likely to be very large in such an implementation as the
+limits of this range are approached.
+
+@findex length
+@findex vector-length
+@findex string-length
+An implementation of Scheme must support exact integers throughout the
+range of numbers that may be used for indexes of lists, vectors, and
+strings or that may result from computing the length of a list, vector,
+or string.  The @code{length}, @code{vector-length}, and
+@code{string-length} procedures must return an exact integer, and it is
+an error to use anything but an exact integer as an index.  Furthermore
+any integer constant within the index range, if expressed by an exact
+integer syntax, will indeed be read as an exact integer, regardless of
+any implementation restrictions that may apply outside this range.
+Finally, the procedures listed below will always return an exact integer
+result provided all their arguments are exact integers and the
+mathematically expected result is representable as an exact integer
+within the implementation:
+
+@example
+@group
+*                gcd                modulo
++                imag-part          numerator
+-                inexact->exact     quotient
+abs              lcm                rationalize
+angle            magnitude          real-part
+ceiling          make-polar         remainder
+denominator      make-rectangular   round
+expt             max                truncate
+floor            min
+@end group
+@end example
+
+@findex /
+Implementations are encouraged, but not required, to support exact
+integers and exact rationals of practically unlimited size and
+precision, and to implement the above procedures and the @code{/}
+procedure in such a way that they always return exact results when given
+exact arguments.  If one of these procedures is unable to deliver an
+exact result when given exact arguments, then it may either report a
+violation of an implementation restriction or it may silently coerce its
+result to an inexact number.  Such a coercion may cause an error
+later.
+
+An implementation may use floating point and other approximate
+representation strategies for inexact numbers.  This report recommends,
+but does not require, that the @sc{ieee} 32-bit and 64-bit floating
+point standards be followed by implementations that use flonum
+representations, and that implementations using other representations
+should match or exceed the precision achievable using these floating
+point standards.
+
+@findex sqrt
+In particular, implementations that use flonum representations must
+follow these rules: A flonum result must be represented with at least as
+much precision as is used to express any of the inexact arguments to
+that operation.  It is desirable (but not required) for potentially
+inexact operations such as @code{sqrt}, when applied to exact arguments,
+to produce exact answers whenever possible (for example the square root
+of an exact 4 ought to be an exact 2).  If, however, an exact number is
+operated upon so as to produce an inexact result (as by @code{sqrt}),
+and if the result is represented as a flonum, then the most precise
+flonum format available must be used; but if the result is represented
+in some other way then the representation must have at least as much
+precision as the most precise flonum format available.
+
+Although Scheme allows a variety of written notations for numbers, any
+particular implementation may support only some of them.@footnote{MIT
+Scheme implements all of the written notations for numbers.} For
+example, an implementation in which all numbers are real need not
+support the rectangular and polar notations for complex numbers.  If an
+implementation encounters an exact numerical constant that it cannot
+represent as an exact number, then it may either report a violation of
+an implementation restriction or it may silently represent the constant
+by an inexact number.
+
+@node Syntax of numerical constants, Numerical operations, Implementation restrictions, Numbers
+@section Syntax of numerical constants
+@cindex number, external representation
+@cindex external representation, for number
+
+@findex #b
+@findex #o
+@findex #d
+@findex #x
+@cindex #b as external representation
+@cindex #o as external representation
+@cindex #d as external representation
+@cindex #x as external representation
+A number may be written in binary, octal, decimal, or hexadecimal by the
+use of a radix prefix.  The radix prefixes are @code{#b} (binary),
+@code{#o} (octal), @code{#d} (decimal), and @code{#x} (hexadecimal).
+With no radix prefix, a number is assumed to be expressed in
+decimal.
+
+@findex #e
+@findex #i
+@findex #
+@cindex #e as external representation
+@cindex #i as external representation
+@cindex # in external representation of number
+A numerical constant may be specified to be either exact or inexact by a
+prefix.  The prefixes are @code{#e} for exact, and @code{#i} for
+inexact.  An exactness prefix may appear before or after any radix
+prefix that is used.  If the written representation of a number has no
+exactness prefix, the constant may be either inexact or exact.  It is
+inexact if it contains a decimal point, an exponent, or a @code{#}
+character in the place of a digit, otherwise it is exact.
+
+@cindex s, as exponent marker in number
+@cindex f, as exponent marker in number
+@cindex d, as exponent marker in number
+@cindex l, as exponent marker in number
+@cindex e, as exponent marker in number
+@cindex exponent marker (defn)
+@cindex precision, of inexact number
+@cindex numeric precision, inexact
+@cindex internal representation, for inexact number
+@cindex short precision, of inexact number
+@cindex single precision, of inexact number
+@cindex double precision, of inexact number
+@cindex long precision, of inexact number
+In systems with inexact numbers of varying precisions it may be useful
+to specify the precision of a constant.  For this purpose, numerical
+constants may be written with an @dfn{exponent marker} that indicates
+the desired precision of the inexact representation.  The letters
+@code{s}, @code{f}, @code{d}, and @code{l} specify the use of
+@emph{short}, @emph{single}, @emph{double}, and @emph{long} precision,
+respectively.  (When fewer than four internal inexact representations
+exist, the four size specifications are mapped onto those available.
+For example, an implementation with two internal representations may map
+short and single together and long and double together.)  In addition,
+the exponent marker @code{e} specifies the default precision for the
+implementation.  The default precision has at least as much precision as
+@emph{double}, but implementations may wish to allow this default to be
+set by the user.
+
+@example
+@group
+3.14159265358979F0
+       @r{Round to single ---} 3.141593
+0.6L0
+       @r{Extend to long ---} .600000000000000
+@end group
+@end example
+
+@node Numerical operations, Numerical input and output, Syntax of numerical constants, Numbers
+@section Numerical operations
+@cindex numerical operations
+
+@xref{Entry Format} for a summary of the naming conventions used to
+specify restrictions on the types of arguments to numerical routines.
+The examples used in this section assume that any numerical constant
+written using an exact notation is indeed represented as an exact
+number.  Some examples also assume that certain numerical constants
+written using an inexact notation can be represented without loss of
+accuracy; the inexact constants were chosen so that this is likely to be
+true in implementations that use flonums to represent inexact
+numbers.
+
+@deffn procedure number? object
+@deffnx procedure complex? object
+@deffnx procedure real? object
+@deffnx procedure rational? object
+@deffnx procedure integer? object
+@cindex type predicate, for number
+These numerical type predicates can be applied to any kind of argument,
+including non-numbers.  They return @code{#t} if the object is of the
+named type, and otherwise they return @code{#f}.  In general, if a type
+predicate is true of a number then all higher type predicates are also
+true of that number.  Consequently, if a type predicate is false of a
+number, then all lower type predicates are also false of that
+number.@footnote{In MIT Scheme the @code{rational?} procedure is the
+same as @code{real?}, and the @code{complex?} procedure is the same as
+@code{number?}.}
+
+@findex zero?
+@findex =
+If @var{z} is an inexact complex number, then @code{(real? @var{z})} is
+true if and only if @code{(zero? (imag-part @var{z}))} is true.  If
+@var{x} is an inexact real number, then @code{(integer? @var{x})} is
+true if and only if @code{(= @var{x} (round @var{x}))}.
+
+@example
+@group
+(complex? 3+4i)         @result{}  #t
+(complex? 3)            @result{}  #t
+(real? 3)               @result{}  #t
+(real? -2.5+0.0i)       @result{}  #t
+(real? #e1e10)          @result{}  #t
+(rational? 6/10)        @result{}  #t
+(rational? 6/3)         @result{}  #t
+(integer? 3+0i)         @result{}  #t
+(integer? 3.0)          @result{}  #t
+(integer? 8/4)          @result{}  #t
+@end group
+@end example
+
+Note: The behavior of these type predicates on inexact numbers is
+unreliable, since any inaccuracy may affect the result.
+
+@end deffn
+
+@deffn procedure exact? z
+@deffnx procedure inexact? z
+These numerical predicates provide tests for the exactness of a
+quantity.  For any Scheme number, precisely one of these predicates is
+true.
+@end deffn
+
+@deffn {procedure+} exact-integer? object
+@deffnx {procedure+} exact-nonnegative-integer? object
+@deffnx {procedure+} exact-rational? object
+These procedures test for some very common types of numbers.  These
+tests could be written in terms of simpler predicates, but are more
+efficient.
+@end deffn
+
+@deffn procedure = z1 z2 z3 @dots{}
+@deffnx procedure < x1 x2 x3 @dots{}
+@deffnx procedure > x1 x2 x3 @dots{}
+@deffnx procedure <= x1 x2 x3 @dots{}
+@deffnx procedure >= x1 x2 x3 @dots{}
+@cindex ordering, of numbers
+@cindex comparison, of numbers
+@cindex equivalence predicate, for numbers
+These procedures return @code{#t} if their arguments are (respectively):
+equal, monotonically increasing, monotonically decreasing, monotonically
+nondecreasing, or monotonically nonincreasing.
+
+These predicates are transitive.  Note that the traditional
+implementations of these predicates in Lisp-like languages are not
+transitive.
+
+Note: While it is not an error to compare inexact numbers using these
+predicates, the results may be unreliable because a small inaccuracy may
+affect the result; this is especially true of @code{=} and @code{zero?}.
+When in doubt, consult a numerical analyst.
+@end deffn
+
+@deffn procedure zero? z
+@deffnx procedure positive? x
+@deffnx procedure negative? x
+@deffnx procedure odd? x
+@deffnx procedure even? x
+@cindex zero
+@cindex positive number
+@cindex negative number
+@cindex odd number
+@cindex even number
+These numerical predicates test a number for a particular property,
+returning @code{#t} or @code{#f}.  See note above regarding inexact
+numbers.
+@end deffn
+
+@deffn procedure max x1 x2 @dots{}
+@deffnx procedure min x1 x2 @dots{}
+@cindex minimum, of numbers
+@cindex maximum, of numbers
+These procedures return the maximum or minimum of their
+arguments.
+
+@example
+@group
+(max 3 4)              @result{}  4    @r{; exact}
+(max 3.9 4)            @result{}  4.0  @r{; inexact}
+@end group
+@end example
+
+Note: If any argument is inexact, then the result will also be inexact
+(unless the procedure can prove that the inaccuracy is not large enough
+to affect the result, which is possible only in unusual
+implementations).  If @code{min} or @code{max} is used to compare
+numbers of mixed exactness, and the numerical value of the result cannot
+be represented as an inexact number without loss of accuracy, then the
+procedure may report a violation of an implementation
+restriction.@footnote{MIT Scheme signals an error in this case.}
+@end deffn
+
+@deffn procedure + z1 @dots{}
+@deffnx procedure * z1 @dots{}
+@cindex addition, of numbers
+@cindex sum, of numbers
+@cindex identity, additive
+@cindex multiplication, of numbers
+@cindex product, of numbers
+@cindex identity, multiplicative
+These procedures return the sum or product of their arguments.
+
+@example
+@group
+(+ 3 4)                 @result{}  7
+(+ 3)                   @result{}  3
+(+)                     @result{}  0
+(* 4)                   @result{}  4
+(*)                     @result{}  1
+@end group
+@end example
+@end deffn
+
+@deffn procedure - z1 z2 @dots{}
+@deffnx procedure / z1 z2 @dots{}
+@cindex subtraction, of numbers
+@cindex difference, of numbers
+@cindex inverse, additive, of number
+@cindex division, of numbers
+@cindex quotient, of numbers
+@cindex inverse, multiplicative, of number
+With two or more arguments, these procedures return the difference or
+quotient of their arguments, associating to the left.  With one
+argument, however, they return the additive or multiplicative inverse of
+their argument.
+
+@example
+@group
+(- 3 4)                 @result{}  -1
+(- 3 4 5)               @result{}  -6
+(- 3)                   @result{}  -3
+(/ 3 4 5)               @result{}  3/20
+(/ 3)                   @result{}  1/3
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} 1+ z
+@deffnx {procedure+} -1+ z
+@code{(1+ z)} is equivalent to @code{(+ z 1)}; @code{(-1+ z)} is
+equivalent to @code{(- z 1)}.
+@end deffn
+
+@deffn procedure abs x
+@cindex absolute value, of number
+@cindex magnitude, of real number
+@code{abs} returns the magnitude of its argument.
+
+@example
+(abs -7)                @result{}  7
+@end example
+@end deffn
+
+@deffn procedure quotient n1 n2
+@deffnx procedure remainder n1 n2
+@deffnx procedure modulo n1 n2
+@cindex division, of integers
+@cindex quotient, of integers
+@cindex remainder, of integers
+@cindex modulus, of integers
+@cindex integer division
+These procedures implement number-theoretic (integer) division: for
+positive integers @var{n1} and @var{n2}, if @var{n3} and @var{n4} are
+integers such that
+@tex
+$$n_1=n_2n_3+n_4$$
+$$0\leq n_4<n_2$$
+@end tex
+@ifinfo
+
+@example
+@var{n1} = (@var{n2} * @var{n3}) + @var{n4}
+
+0 <= @var{n4} < @var{n2}
+@end example
+
+@end ifinfo
+@noindent
+then
+
+@example
+@group
+(quotient @var{n1} @var{n2})        @result{}  @var{n3}
+(remainder @var{n1} @var{n2})       @result{}  @var{n4}
+(modulo @var{n1} @var{n2})          @result{}  @var{n4}
+@end group
+@end example
+
+@noindent
+For integers @var{n1} and @var{n2} with @var{n2} not equal to 0,
+
+@example
+@group
+(= @var{n1} 
+   (+ (* @var{n2} (quotient @var{n1} @var{n2}))
+      (remainder @var{n1} @var{n2})))
+                                    @result{}  #t
+@end group
+@end example
+
+@noindent
+provided all numbers involved in that computation are exact.
+
+The value returned by @code{quotient} always has the sign of the product
+of its arguments.  @code{remainder} and @code{modulo} differ on negative
+arguments --- the @code{remainder} always has the sign of the dividend,
+the @code{modulo} always has the sign of the divisor:
+
+@example
+@group
+(modulo 13 4)           @result{}  1
+(remainder 13 4)        @result{}  1
+
+(modulo -13 4)          @result{}  3
+(remainder -13 4)       @result{}  -1
+
+(modulo 13 -4)          @result{}  -3
+(remainder 13 -4)       @result{}  1
+
+(modulo -13 -4)         @result{}  -1
+(remainder -13 -4)      @result{}  -1
+
+(remainder -13 -4.0)    @result{}  -1.0  @r{; inexact}
+@end group
+@end example
+
+@findex integer-truncate
+Note that @code{quotient} is the same as @code{integer-truncate}.
+@end deffn
+
+@deffn {procedure+} integer-floor n1 n2
+@deffnx {procedure+} integer-ceiling n1 n2
+@deffnx {procedure+} integer-truncate n1 n2
+@deffnx {procedure+} integer-round n1 n2
+These procedures combine integer division with rounding.  For example,
+the following are equivalent:
+
+@example
+@group
+(integer-floor @var{n1} @var{n2})
+(floor (/ @var{n1} @var{n2}))
+@end group
+@end example
+
+@noindent
+However, the former is faster and does not produce an intermediate
+result.
+
+@findex quotient
+Note that @code{integer-truncate} is the same as @code{quotient}.
+@end deffn
+
+@deffn {procedure+} integer-divide n1 n2
+@deffnx {procedure+} integer-divide-quotient qr
+@deffnx {procedure+} integer-divide-remainder qr
+@findex quotient
+@findex remainder
+@code{integer-divide} is equivalent to performing both @code{quotient}
+and @code{remainder} at once.  The result of @code{integer-divide} is an
+object with two components; the procedures
+@code{integer-divide-quotient} and @code{integer-divide-remainder}
+select those components.  These procedures are useful when both the
+quotient and remainder are needed; often computing both of these numbers
+simultaneously is much faster than computing them separately.
+
+For example, the following are equivalent:
+
+@example
+@group
+(lambda (n d)
+  (cons (quotient n d)
+        (remainder n d)))
+
+(lambda (n d)
+  (let ((qr (integer-divide n d)))
+    (cons (integer-divide-quotient qr)
+          (integer-divide-remainder qr))))
+@end group
+@end example
+@end deffn
+
+@deffn procedure gcd n1 @dots{}
+@deffnx procedure lcm n1 @dots{}
+@cindex greatest common divisor, of numbers
+@cindex least common multiple, of numbers
+These procedures return the greatest common divisor or least common
+multiple of their arguments.  The result is always non-negative.
+
+@example
+@group
+(gcd 32 -36)            @result{}  4
+(gcd)                   @result{}  0
+
+(lcm 32 -36)            @result{}  288
+(lcm 32.0 -36)          @result{}  288.0  @r{; inexact}
+(lcm)                   @result{}  1
+@end group
+@end example
+@end deffn
+
+@deffn procedure numerator q
+@deffnx procedure denominator q
+These procedures return the numerator or denominator of their argument;
+the result is computed as if the argument was represented as a fraction
+in lowest terms.  The denominator is always positive.  The denominator
+of 0 is defined to be 1.
+
+@example
+@group
+(numerator (/ 6 4))  @result{}  3
+(denominator (/ 6 4))  @result{}  2
+(denominator (exact->inexact (/ 6 4))) @result{} 2.0
+@end group
+@end example
+@end deffn
+
+@deffn procedure floor x
+@deffnx procedure ceiling x
+@deffnx procedure truncate x
+@deffnx procedure round x
+These procedures return integers.  @code{floor} returns the largest
+integer not larger than @var{x}.  @code{ceiling} returns the smallest
+integer not smaller than @var{x}.  @code{truncate} returns the integer
+closest to @var{x} whose absolute value is not larger than the absolute
+value of @var{x}.  @code{round} returns the closest integer to @var{x},
+rounding to even when @var{x} is halfway between two integers.
+
+Rationale: @code{round} rounds to even for consistency with the rounding
+modes required by the @sc{ieee} floating point standard.
+
+Note: If the argument to one of these procedures is inexact, then the
+result will also be inexact.  If an exact value is needed, the result
+should be passed to the @code{inexact->exact} procedure (or use one of
+the procedures below).
+
+@example
+@group
+(floor -4.3)          @result{}  -5.0
+(ceiling -4.3)        @result{}  -4.0
+(truncate -4.3)       @result{}  -4.0
+(round -4.3)          @result{}  -4.0
+
+(floor 3.5)           @result{}  3.0
+(ceiling 3.5)         @result{}  4.0
+(truncate 3.5)        @result{}  3.0
+(round 3.5)           @result{}  4.0  @r{; inexact}
+
+(round 7/2)           @result{}  4    @r{; exact}
+(round 7)             @result{}  7
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} floor->exact x
+@deffnx {procedure+} ceiling->exact x
+@deffnx {procedure+} truncate->exact x
+@deffnx {procedure+} round->exact x
+These procedures are similar to the preceding procedures except that
+they always return an exact result.  For example, the following are
+equivalent
+
+@example
+@group
+(floor->exact x)
+(inexact->exact (floor x))
+@end group
+@end example
+
+@noindent
+except that the former is faster and has fewer range restrictions.
+@end deffn
+
+@deffn procedure rationalize x y
+@deffnx {procedure+} rationalize->exact x y
+@cindex simplest rational (defn)
+@cindex rational, simplest (defn)
+@code{rationalize} returns the @emph{simplest} rational number differing
+from @var{x} by no more than @var{y}.  A rational number @var{r1} is
+@emph{simpler} than another rational number @var{r2} if
+@t{@var{r1}=@var{p1}/@var{q1}} and @t{@var{r2}=@var{p2}/@var{q2}} (both
+in lowest terms) and @t{|@var{p1}|<=|@var{p2}|} and
+@t{|@var{q1}|<=|@var{q2}|}.  Thus @t{3/5} is simpler than @t{4/7}.
+Although not all rationals are comparable in this ordering (consider
+@t{2/7} and @t{3/5}) any interval contains a rational number that is
+simpler than every other rational number in that interval (the simpler
+@t{2/5} lies between @t{2/7} and @t{3/5}).  Note that @t{0=0/1} is the
+simplest rational of all.
+
+@example
+@group
+(rationalize (inexact->exact .3) 1/10)  @result{} 1/3    @r{; exact}
+(rationalize .3 1/10)                   @result{} #i1/3  @r{; inexact}
+@end group
+@end example
+
+@code{rationalize->exact} is similar to @code{rationalize} except that
+it always returns an exact result.
+@end deffn
+
+@deffn {procedure+} simplest-rational x y
+@deffnx {procedure+} simplest-exact-rational x y
+@code{simplest-rational} returns the simplest rational number between
+@var{x} and @var{y} inclusive; @code{simplest-exact-rational} is similar
+except that it always returns an exact result.
+
+These procedures implement the same functionality as @code{rationalize}
+and @code{rationalize->exact}, except that they specify the input range
+by its endpoints; @code{rationalize} specifies the range by its center
+point and its (half-) width.
+@end deffn
+
+@deffn procedure exp z
+@deffnx procedure log z
+@deffnx procedure sin z
+@deffnx procedure cos z
+@deffnx procedure tan z
+@deffnx procedure asin z
+@deffnx procedure acos z
+@deffnx procedure atan z
+@deffnx procedure atan y x
+@findex angle
+@findex make-rectangular
+These procedures compute the usual transcendental functions.  @code{log}
+computes the natural logarithm of @var{z} (not the base ten logarithm).
+@code{asin}, @code{acos}, and @code{atan} compute arcsine, arccosine,
+and arctangent, respectively.  The two-argument variant of @code{atan}
+computes @code{(angle (make-rectangular @var{x} @var{y}))} (see
+below).
+
+In general, the mathematical functions log, arcsine, arccosine, and
+arctangent are multiply defined.  For nonzero real @var{x}, the value of
+log @var{x} is defined to be the one whose imaginary part lies in the
+range minus @var{pi} (exclusive) to @var{pi} (inclusive).  log 0 is
+undefined.  The value of log @var{z} when @var{z} is complex is defined
+according to the formula
+@tex
+$$\log z = \log {\rm magnitude}(z) + i {\rm angle} (z)$$
+@end tex
+@ifinfo
+
+@example
+log @var{z} = log magnitude(@var{z}) + i angle(@var{z})
+@end example
+
+@end ifinfo
+With log defined this way, the values of arcsine, arccosine, and
+arctangent are according to the following formulae:
+@tex
+$$\sin^{-1} z = -i \log (i z + \sqrt{1 - z^2})$$
+$$\cos^{-1} z = \pi / 2 - \sin^{-1} z$$
+$$\tan^{-1} z = (\log (1 + i z) - \log (1 - i z)) / (2 i)$$
+@end tex
+@ifinfo
+
+@example
+arcsin(@var{z}) = -i log(i @var{z} + sqrt(1 - @var{z}^2))
+arccos(@var{z}) = pi/2 - arcsin(@var{z})
+arctan(@var{z}) = (log(1 + i @var{z}) + log(1 - i @var{z})) / (2 i)
+@end example
+
+@end ifinfo
+The above specification follows @cite{Common Lisp: the Language}, which
+in turn cites @cite{Principal Values and Branch Cuts in Complex APL};
+refer to these sources for more detailed discussion of branch cuts,
+boundary conditions, and implementation of these functions.  When it is
+possible these procedures produce a real result from a real
+argument.
+@end deffn
+
+@deffn procedure sqrt z
+Returns the principal square root of @var{z}.  The result will have
+either positive real part, or zero real part and non-negative imaginary
+part.
+@end deffn
+
+@deffn procedure expt z1 z2
+Returns @var{z1} raised to the power @var{z2}:
+@tex
+$${z_1}^{z_2} = e^{z_2 \log {z_1}}$$
+$0^0$ is defined to be equal to 1.
+@end tex
+@ifinfo
+
+@example
+@var{z1}^@var{z2} = e^(@var{z2} log @var{z1})
+@end example
+
+@noindent
+0^0 is defined to be equal to 1.
+@end ifinfo
+@end deffn
+
+@deffn procedure make-rectangular x1 x2
+@deffnx procedure make-polar x1 x2
+@deffnx procedure real-part z
+@deffnx procedure imag-part z
+@deffnx procedure magnitude z
+@deffnx procedure angle z
+@deffnx {procedure+} conjugate z
+Suppose @var{x1}, @var{x2}, @var{x3}, and @var{x4} are real numbers and
+@var{z} is a complex number such that
+@tex
+ $$ z = x_1 + x_2\hbox{$i$}
+ = x_3 \cdot e^{{\displaystyle{\hbox{$i$}} x_4}}$$
+@end tex
+@ifinfo
+
+@example
+@var{z} = @var{x1} + @var{x2} i = @var{x3} e^(i @var{x4})
+@end example
+
+@end ifinfo
+@noindent
+Then @code{make-rectangular} and @code{make-polar} return @var{z},
+@code{real-part} returns @var{x1}, @code{imag-part} returns @var{x2},
+@code{magnitude} returns @var{x3}, and @code{angle} returns @var{x4}.
+In the case of @code{angle}, whose value is not uniquely determined by
+the preceding rule, the value returned will be the one in the range
+minus @var{pi} (exclusive) to @var{pi} (inclusive).
+
+@code{conjugate} returns the complex conjugate of @var{z}.
+@end deffn
+
+@deffn procedure exact->inexact z
+@deffnx procedure inexact->exact z
+@code{exact->inexact} returns an inexact representation of @var{z}.  The
+value returned is the inexact number that is numerically closest to the
+argument.  If an exact argument has no reasonably close inexact
+equivalent, then a violation of an implementation restriction may be
+reported; MIT Scheme signals an error in this case.
+
+@code{inexact->exact} returns an exact representation of @var{z}.  The
+value returned is the exact number that is numerically closest to the
+argument.  If an inexact argument has no reasonably close exact
+equivalent, then a violation of an implementation restriction may be
+reported; MIT Scheme signals an error in this case.
+
+These procedures implement the natural one-to-one correspondence between
+exact and inexact integers throughout an implementation-dependent range.
+@xref{Implementation restrictions}.
+@end deffn
+
+@node Numerical input and output, Fixnum and Flonum Operations, Numerical operations, Numbers
+@section Numerical input and output
+@cindex numerical input and output
+
+@deffn procedure number->string number [radix]
+@var{Radix} must be an exact integer, either 2, 8, 10, or 16.  If
+omitted, @var{radix} defaults to 10.  The procedure
+@code{number->string} takes a number and a radix and returns as a string
+an external representation of the given number in the given radix such
+that
+
+@example
+@group
+(let ((number @var{number})
+      (radix @var{radix}))
+  (eqv? number
+        (string->number (number->string number radix)
+                        radix)))
+@end group
+@end example
+
+@noindent
+is true.  It is an error if no possible result makes this expression
+true.
+
+If @var{number} is inexact, the radix is 10, and the above expression
+can be satisfied by a result that contains a decimal point, then the
+result contains a decimal point and is expressed using the minimum
+number of digits (exclusive of exponent and trailing zeroes) needed to
+make the above expression true; otherwise the format of the result is
+unspecified.
+
+The result returned by @code{number->string} never contains an explicit
+radix prefix.
+
+Note: The error case can occur only when @var{number} is not a complex
+number or is a complex number with an non-rational real or imaginary
+part.
+
+Rationale: If @var{number} is an inexact number represented using
+flonums, and the radix is 10, then the above expression is normally
+satisfied by a result containing a decimal point.  The unspecified case
+allows for infinities, NaNs, and non-flonum representations.
+@end deffn
+
+@deffn procedure string->number string [radix]
+Returns a number of the maximally precise representation expressed by
+the given @var{string}.  @var{Radix} must be an exact integer, either 2,
+8, 10, or 16.  If supplied, @var{radix} is a default radix that may be
+overridden by an explicit radix prefix in @var{string} (e.g.@:
+@code{"#o177"}).  If @var{radix} is not supplied, then the default radix
+is 10.  If @var{string} is not a syntactically valid notation for a
+number, then @code{string->number} returns @code{#f}.
+
+@example
+@group
+(string->number "100")        @result{}  100
+(string->number "100" 16)     @result{}  256
+(string->number "1e2")        @result{}  100.0
+(string->number "15##")       @result{}  1500.0
+@end group
+@end example
+@end deffn
+
+@node Fixnum and Flonum Operations,  , Numerical input and output, Numbers
+@section Fixnum and Flonum Operations
+
+This section describes numerical operations that are restricted forms of
+the operations described above.  These operations are useful because
+they compile very efficiently.  However, care should be exercised: if
+used improperly, these operations can return incorrect answers, or even
+malformed objects that confuse the garbage collector.
+
+@menu
+* Fixnum Operations::           Fixnum Operations
+* Flonum Operations::           Flonum Operations
+@end menu
+
+@node Fixnum Operations, Flonum Operations, Fixnum and Flonum Operations, Fixnum and Flonum Operations
+@subsection Fixnum Operations
+
+@cindex fixnum (defn)
+A @dfn{fixnum} is an exact integer that is small enough to fit in a
+machine word.  In MIT Scheme, fixnums are typically 24 or 26 bits,
+depending on the machine; it is reasonable to assume that fixnums are at
+least 24 bits.  Fixnums are signed; they are encoded using 2's
+complement.
+
+All exact integers that are small enough to be encoded as fixnums are
+always encoded as fixnums --- in other words, any exact integer that is
+not a fixnum is too big to be encoded as such.  For this reason, small
+constants such as @code{0} or @code{1} are guaranteed to be fixnums.
+
+@deffn {procedure+} fix:fixnum? object
+@cindex type predicate, for fixnum
+Returns @code{#t} if @var{object} is a fixnum; otherwise returns
+@code{#f}.
+@end deffn
+
+Here is an expression that determines the largest fixnum:
+
+@example
+@group
+(let loop ((n 0))
+  (let ((m (+ n 1)))
+    (if (fix:fixnum? m)
+        (loop m)
+        n)))
+@end group
+@end example
+
+@noindent
+A similar expression determines the smallest fixnum.
+
+@deffn {procedure+} fix:= fixnum fixnum
+@deffnx {procedure+} fix:< fixnum fixnum
+@deffnx {procedure+} fix:> fixnum fixnum
+@deffnx {procedure+} fix:<= fixnum fixnum
+@deffnx {procedure+} fix:>= fixnum fixnum
+@cindex equivalence predicate, for fixnums
+These are the standard order and equality predicates on fixnums.  When
+compiled, they do not check the types of their arguments.
+@end deffn
+
+@deffn {procedure+} fix:zero? fixnum
+@deffnx {procedure+} fix:positive? fixnum
+@deffnx {procedure+} fix:negative? fixnum
+These procedures compare their argument to zero.  When compiled, they do
+not check the type of their argument.  The code produced by the
+following expressions is identical:
+
+@example
+@group
+(fix:zero? @var{fixnum})
+(fix:= @var{fixnum} 0)
+@end group
+@end example
+
+@noindent
+Similarly, @code{fix:positive?} and @code{fix:negative?} produce code
+identical to equivalent expressions using @code{fix:>} and @code{fix:<}.
+@end deffn
+
+@deffn {procedure+} fix:+ fixnum fixnum
+@deffnx {procedure+} fix:- fixnum fixnum
+@deffnx {procedure+} fix:* fixnum fixnum
+@deffnx {procedure+} fix:quotient fixnum fixnum
+@deffnx {procedure+} fix:remainder fixnum fixnum
+@deffnx {procedure+} fix:gcd fixnum fixnum
+@deffnx {procedure+} fix:1+ fixnum
+@deffnx {procedure+} fix:-1+ fixnum
+These procedures are the standard arithmetic operations on fixnums.
+When compiled, they do not check the types of their arguments.
+Furthermore, they do not check to see if the result can be encoded as a
+fixnum.  If the result is too large to be encoded as a fixnum, a
+malformed object is returned, with potentially disastrous effect on the
+garbage collector.
+@end deffn
+
+@deffn {procedure+} fix:divide fixnum fixnum
+@findex integer-divide
+@findex integer-divide-quotient
+@findex integer-divide-remainder
+This procedure is like @code{integer-divide}, except that its arguments
+and its results must be fixnums.  It should be used in conjunction with
+@code{integer-divide-quotient} and @code{integer-divide-remainder}.
+@end deffn
+
+@cindex logical operations, on fixnums
+@cindex bitwise-logical operations, on fixnums
+The following are @dfn{bitwise-logical} operations on fixnums.
+
+@deffn {procedure+} fix:not fixnum
+This returns the bitwise-logical inverse of its argument.  When
+compiled, it does not check the type of its argument.
+
+@example
+@group
+(fix:not 0)                             @result{}  -1
+(fix:not -1)                            @result{}  0
+(fix:not 1)                             @result{}  -2
+(fix:not -34)                           @result{}  33
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} fix:and fixnum fixnum
+This returns the bitwise-logical ``and'' of its arguments.  When
+compiled, it does not check the types of its arguments.
+
+@example
+@group
+(fix:and #x43 #x0f)                     @result{}  3
+(fix:and #x43 #xf0)                     @result{}  #x40
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} fix:andc fixnum fixnum
+Returns the bitwise-logical ``and'' of the first argument with the
+bitwise-logical inverse of the second argument.  When compiled, it does
+not check the types of its arguments.
+
+@example
+@group
+(fix:andc #x43 #x0f)                    @result{}  #x40
+(fix:andc #x43 #xf0)                    @result{}  3
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} fix:or fixnum fixnum
+This returns the bitwise-logical ``inclusive or'' of its arguments.
+When compiled, it does not check the types of its arguments.
+
+@example
+@group
+(fix:or #x40 3)                         @result{} #x43
+(fix:or #x41 3)                         @result{} #x43
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} fix:xor fixnum fixnum
+This returns the bitwise-logical ``exclusive or'' of its arguments.
+When compiled, it does not check the types of its arguments.
+
+@example
+@group
+(fix:xor #x40 3)                        @result{} #x43
+(fix:xor #x41 3)                        @result{} #x42
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} fix:lsh fixnum1 fixnum2
+This procedure returns the result of logically shifting @var{fixnum1} by
+@var{fixnum2} bits.  If @var{fixnum2} is positive, @var{fixnum1} is
+shifted left; if negative, it is shifted right.  When compiled, it does
+not check the types of its arguments, nor the validity of its result.
+
+@example
+@group
+(fix:lsh 1 10)                          @result{}  #x400
+(fix:lsh #432 -10)                      @result{}  1
+(fix:lsh -1 3)                          @result{}  -8
+(fix:lsh -128 -4)                       @result{}  -8
+@end group
+@end example
+@end deffn
+
+@node Flonum Operations,  , Fixnum Operations, Fixnum and Flonum Operations
+@subsection Flonum Operations
+
+@cindex flonum (defn)
+A @dfn{flonum} is an inexact real number that is implemented as a
+floating-point number.  In MIT Scheme, all inexact real numbers are
+flonums.  For this reason, constants such as @code{0.} and @code{2.3}
+are guaranteed to be flonums.
+
+@deffn {procedure+} flo:flonum? object
+@cindex type predicate, for flonum
+Returns @code{#t} if @var{object} is a flonum; otherwise returns @code{#f}.
+@end deffn
+
+@deffn {procedure+} flo:= flonum1 flonum2
+@deffnx {procedure+} flo:< flonum1 flonum2
+@deffnx {procedure+} flo:> flonum1 flonum2
+@cindex equivalence predicate, for flonums
+These procedures are the standard order and equality predicates on
+flonums.  When compiled, they do not check the types of their arguments.
+@end deffn
+
+@deffn {procedure+} flo:zero? flonum
+@deffnx {procedure+} flo:positive? flonum
+@deffnx {procedure+} flo:negative? flonum
+Each of these procedures compares its argument to zero.  When compiled,
+they do not check the type of their argument.
+@end deffn
+
+@deffn {procedure+} flo:+ flonum1 flonum2
+@deffnx {procedure+} flo:- flonum1 flonum2
+@deffnx {procedure+} flo:* flonum1 flonum2
+@deffnx {procedure+} flo:/ flonum1 flonum2
+These procedures are the standard arithmetic operations on flonums.
+When compiled, they do not check the types of their arguments.
+@end deffn
+
+@deffn {procedure+} flo:negate flonum
+This procedure returns the negation of its argument.  When compiled, it
+does not check the type of its argument.  Equivalent to @code{(flo:- 0
+@var{flonum})}.
+@end deffn
+
+@deffn {procedure+} flo:abs flonum
+@deffnx {procedure+} flo:exp flonum
+@deffnx {procedure+} flo:log flonum
+@deffnx {procedure+} flo:sin flonum
+@deffnx {procedure+} flo:cos flonum
+@deffnx {procedure+} flo:tan flonum
+@deffnx {procedure+} flo:asin flonum
+@deffnx {procedure+} flo:acos flonum
+@deffnx {procedure+} flo:atan flonum
+@deffnx {procedure+} flo:sqrt flonum
+@deffnx {procedure+} flo:expt flonum1 flonum2
+@deffnx {procedure+} flo:floor flonum
+@deffnx {procedure+} flo:ceiling flonum
+@deffnx {procedure+} flo:truncate flonum
+@deffnx {procedure+} flo:round flonum
+@deffnx {procedure+} flo:floor->exact flonum
+@deffnx {procedure+} flo:ceiling->exact flonum
+@deffnx {procedure+} flo:truncate->exact flonum
+@deffnx {procedure+} flo:round->exact flonum
+These procedures are flonum versions of the corresponding procedures.
+When compiled, they do not check the types of their arguments.
+@end deffn
+
+@deffn {procedure+} flo:atan2 flonum1 flonum2
+@findex atan
+This is the flonum version of @code{atan} with two arguments.  When
+compiled, it does not check the types of its arguments.
+@end deffn
+
+@node Characters, Strings, Numbers, Top
+@chapter Characters
+
+@cindex character (defn)
+Characters are objects that represent printed characters, such as
+letters and digits.@footnote{Some of the details in this section depend
+on the fact that the underlying operating system uses the @sc{ascii}
+character set.  This may change when someone ports MIT Scheme to a
+non-@sc{ascii} operating system.}
+
+@menu
+* External Representation of Characters::  External Representation of Characters
+* Comparison of Characters::    Comparison of Characters
+* Miscellaneous Character Operations::  Miscellaneous Character Operations
+* Internal Representation of Characters::  Internal Representation of Characters
+* ASCII Characters::            ASCII Characters
+* Character Sets::              Character Sets
+@end menu
+
+@node External Representation of Characters, Comparison of Characters, Characters, Characters
+@section External Representation of Characters
+@cindex external representation, for character
+
+@cindex #\ as external representation
+@findex #\
+Characters are written using the notation @code{#\@var{character}} or
+@code{#\@var{character-name}}.  For example:
+
+@example
+#\a                     @r{; lowercase letter}
+#\A                     @r{; uppercase letter}
+#\(                     @r{; left parenthesis}
+#\space                 @r{; the space character}
+#\newline               @r{; the newline character}
+@end example
+@findex #\space
+@findex #\newline
+
+@noindent
+Case is significant in @code{#\@var{character}}, but not in
+@code{#\@var{character-name}}.  If @var{character} in
+@code{#\@var{character}} is a letter, @var{character} must be followed
+by a delimiter character such as a space or parenthesis.  Characters
+written in the @code{#\} notation are self-evaluating; you don't need to
+quote them.
+
+@cindex bucky bit, prefix (defn)
+@cindex control, bucky bit prefix (defn)
+@cindex meta, bucky bit prefix (defn)
+@cindex super, bucky bit prefix (defn)
+@cindex hyper, bucky bit prefix (defn)
+@cindex top, bucky bit prefix (defn)
+A character name may include one or more @dfn{bucky bit} prefixes to
+indicate that the character includes one or more of the keyboard shift
+keys Control, Meta, Super, Hyper, or Top (note that the Control bucky
+bit prefix is not the same as the @sc{ascii} control key).  The bucky
+bit prefixes and their meanings are as follows (case is not
+significant):
+
+@example
+@group
+Key             Bucky bit prefix        Bucky bit
+---             ----------------        ---------
+
+Meta            M- or Meta-                 1
+Control         C- or Control-              2
+Super           S- or Super-                4
+Hyper           H- or Hyper-                8
+Top             T- or Top-                 16
+@end group
+@end example
+
+@noindent
+For example,
+
+@example
+@group
+#\c-a                   @r{; Control-a}
+#\meta-b                @r{; Meta-b}
+#\c-s-m-h-a             @r{; Control-Meta-Super-Hyper-A}
+@end group
+@end example
+
+@cindex character, named (defn)
+@cindex name, of character
+The following @var{character-name}s are supported, shown here with their
+@sc{ascii} equivalents:
+
+@example
+@group
+Character Name          ASCII Name
+--------------          ----------
+
+altmode                 ESC
+backnext                US
+backspace               BS
+call                    SUB
+linefeed                LF
+page                    FF
+return                  CR
+rubout                  DEL
+space
+tab                     HT
+@end group
+@end example
+@findex #\altmode
+@findex #\backnext
+@findex #\backspace
+@findex #\call
+@findex #\linefeed
+@findex #\page
+@findex #\return
+@findex #\rubout
+@findex #\space
+@findex #\tab
+
+@noindent
+@cindex newline character (defn)
+@findex #\newline
+In addition, @code{#\newline} is either @code{#\linefeed} or
+@code{#\return}, depending on the operating system that Scheme is
+running under.  All of the standard @sc{ascii} names for non-printing
+characters are supported:
+
+@example
+@group
+NUL     SOH     STX     ETX     EOT     ENQ     ACK     BEL
+BS      HT      LF      VT      FF      CR      SO      SI
+DLE     DC1     DC2     DC3     DC4     NAK     SYN     ETB
+CAN     EM      SUB     ESC     FS      GS      RS      US
+DEL
+@end group
+@end example
+
+@deffn {procedure+} char->name char [slashify?]
+Returns a string corresponding to the printed representation of
+@var{char}.  This is the @var{character} or @var{character-name}
+component of the external representation, combined with the appropriate
+bucky bit prefixes.
+
+@example
+(char->name #\a)                        @result{}  "a"
+(char->name #\space)                    @result{}  "Space"
+(char->name #\c-a)                      @result{}  "C-a"
+(char->name #\control-a)                @result{}  "C-a"
+@end example
+
+@findex read
+@var{Slashify?}, if specified and true, says to insert the necessary
+backslash characters in the result so that @code{read} will parse it
+correctly.  In other words, the following generates the external
+representation of @var{char}:
+
+@example
+(string-append "#\\" (char->name @var{char} #t))
+@end example
+
+@noindent
+If @var{slashify?} is not specified, it defaults to @code{#f}.
+@end deffn
+
+@deffn {procedure+} name->char string
+Converts a string that names a character into the character specified.
+If @var{string} does not name any character, signals an error.
+
+@example
+(name->char "a")                        @result{}  #\a
+(name->char "space")                    @result{}  #\Space
+(name->char "c-a")                      @result{}  #\C-a
+(name->char "control-a")                @result{}  #\C-a
+@end example
+@end deffn
+
+@node Comparison of Characters, Miscellaneous Character Operations, External Representation of Characters, Characters
+@section Comparison of Characters
+@cindex ordering, of characters
+@cindex comparison, of characters
+@cindex equivalence predicates, for characters
+
+@deffn procedure char=? char1 char2
+@deffnx procedure char<? char1 char2
+@deffnx procedure char>? char1 char2
+@deffnx procedure char<=? char1 char2
+@deffnx procedure char>=? char1 char2
+@deffnx {procedure} char-ci=? char1 char2
+@deffnx {procedure} char-ci<? char1 char2
+@deffnx {procedure} char-ci>? char1 char2
+@deffnx {procedure} char-ci<=? char1 char2
+@deffnx {procedure} char-ci>=? char1 char2
+@cindex equivalence predicate, for characters
+Returns @code{#t} if the specified characters are have the appropriate
+order relationship to one another; otherwise returns @code{#f}.  The
+@code{-ci} procedures don't distinguish uppercase and lowercase letters.
+
+Character ordering follows these rules:
+
+@itemize @bullet
+@item
+The digits are in order; for example, @code{(char<? #\0 #\9)} returns
+@code{#t}.
+
+@item
+The uppercase characters are in order; for example, @code{(char<? #\A
+#\B)} returns @code{#t}.
+
+@item
+The lowercase characters are in order; for example, @code{(char<? #\a
+#\b)} returns @code{#t}.
+@end itemize
+
+@cindex standard character
+@cindex character, standard
+@findex char-standard?
+In addition, MIT Scheme orders those characters that satisfy
+@code{char-standard?} the same way that @sc{ascii} does.  Specifically,
+all the digits precede all the uppercase letters, and all the upper-case
+letters precede all the lowercase letters.
+
+Characters are ordered by first comparing their bucky bits part and then
+their code part.  In particular, characters without bucky bits come
+before characters with bucky bits.
+@end deffn
+
+@node Miscellaneous Character Operations, Internal Representation of Characters, Comparison of Characters, Characters
+@section Miscellaneous Character Operations
+
+@deffn procedure char? object
+@cindex type predicate, for character
+Returns @code{#t} if @var{object} is a character; otherwise returns
+@code{#f}.
+@end deffn
+
+@deffn procedure char-upcase char
+@deffnx procedure char-downcase char
+@cindex uppercase, character conversion
+@cindex lowercase, character conversion
+@cindex case conversion, of character
+@findex char-ci=?
+Returns the uppercase or lowercase equivalent of @var{char} if
+@var{char} is a letter; otherwise returns @var{char}.  These procedures
+return a character @var{char2} such that @code{(char-ci=? @var{char}
+@var{char2})}.
+@end deffn
+
+@deffn {procedure+} char->digit char [radix]
+If @var{char} is a character representing a digit in the given
+@var{radix}, returns the corresponding integer value.  If you specify
+@var{radix} (which must be an exact integer between 2 and 36 inclusive),
+the conversion is done in that base, otherwise it is done in base 10.
+If @var{char} doesn't represent a digit in base @var{radix},
+@code{char->digit} returns @code{#f}.
+
+Note that this procedure is insensitive to the alphabetic case of
+@var{char}.
+
+@example
+@group
+(char->digit #\8)                       @result{}  8
+(char->digit #\e 16)                    @result{}  14
+(char->digit #\e)                       @result{}  #f
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} digit->char digit [radix]
+Returns a character that represents @var{digit} in the radix given by
+@var{radix}.  @var{Radix} must be an exact integer between 2 and 36
+(inclusive), and defaults to 10.  @var{Digit}, which must be an
+exact non-negative integer, should be less than @var{radix}; if
+@var{digit} is greater than or equal to @var{radix}, @code{digit->char}
+returns @code{#f}.
+
+@example
+@group
+(digit->char 8)                         @result{}  #\8
+(digit->char 14 16)                     @result{}  #\E
+@end group
+@end example
+@end deffn
+
+@node Internal Representation of Characters, ASCII Characters, Miscellaneous Character Operations, Characters
+@section Internal Representation of Characters
+@cindex internal representation, for character
+
+@cindex character code (defn)
+@cindex character bits (defn)
+@cindex code, of character (defn)
+@cindex bucky bit, of character (defn)
+@cindex ASCII character
+An MIT Scheme character consists of a @dfn{code} part and a @dfn{bucky
+bits} part.  The MIT Scheme set of characters can represent more
+characters than @sc{ascii} can; it includes characters with Super,
+Hyper, and Top bucky bits, as well as Control and Meta.  Every
+@sc{ascii} character corresponds to some MIT Scheme character, but not
+vice versa.@footnote{Note that the Control bucky bit is different from
+the @sc{ascii} control key.  This means that @code{#\SOH} (@sc{ascii}
+ctrl-A) is different from @code{#\C-A}.  In fact, the Control bucky bit
+is completely orthogonal to the @sc{ascii} control key, making possible
+such characters as @code{#\C-SOH}.}
+
+MIT Scheme uses a 7-bit @sc{ascii} character code with 5 bucky
+bits.  The least significant bucky bit, Meta, is stored adjacent to the
+MSB of the character code, allowing the least significant 8 bits of a
+character object to be interpreted as ordinary @sc{ascii} with a meta
+bit.  This is compatible with standard practice for 8-bit characters
+when meta bits are employed.
+
+@deffn {procedure+} make-char code bucky-bits
+@cindex construction, of character
+Builds a character from @var{code} and @var{bucky-bits}.  Both
+@var{code} and @var{bucky-bits} must be exact non-negative integers in
+the appropriate range.  Use @code{char-code} and @code{char-bits} to
+extract the code and bucky bits from the character.  If @code{0} is
+specified for @var{bucky-bits}, @code{make-char} produces an ordinary
+character; otherwise, the appropriate bits are turned on as follows:
+
+@example
+@group
+1               Meta
+2               Control
+4               Super
+8               Hyper
+16              Top
+@end group
+@end example
+
+For example,
+
+@example
+@group
+(make-char 97 0)                        @result{}  #\a
+(make-char 97 1)                        @result{}  #\M-a
+(make-char 97 2)                        @result{}  #\C-a
+(make-char 97 3)                        @result{}  #\C-M-a
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} char-bits char
+@cindex selection, of character component
+@cindex component selection, of character
+Returns the exact integer representation of @var{char}'s bucky bits.
+For example,
+
+@example
+(char-bits #\a)                         @result{}  0
+(char-bits #\m-a)                       @result{}  1
+(char-bits #\c-a)                       @result{}  2
+(char-bits #\c-m-a)                     @result{}  3
+@end example
+@end deffn
+
+@deffn {procedure+} char-code char
+Returns the character code of @var{char}, an exact integer.  For
+example,
+
+@example
+(char-code #\a)                         @result{}  97
+(char-code #\c-a)                       @result{}  97
+@end example
+@end deffn
+
+@defvr {variable+} char-code-limit
+@defvrx {variable+} char-bits-limit
+These variables define the (exclusive) upper limits for the character
+code and bucky bits (respectively).  The character code and bucky bits
+are always exact non-negative integers, and are strictly less than the
+value of their respective limit variable.
+@end defvr
+
+@deffn procedure char->integer char
+@deffnx procedure integer->char k
+@code{char->integer} returns the character code representation for
+@var{char}.  @code{integer->char} returns the character whose character
+code representation is @var{k}.
+
+@findex char-ascii?
+@findex char->ascii
+In MIT Scheme, if @code{(char-ascii? @var{char})} is true, then
+
+@example
+(eqv? (char->ascii @var{char}) (char->integer @var{char}))
+@end example
+
+@noindent
+However, this behavior is not required by the Scheme standard, and
+code that depends on it is not portable to other implementations.
+
+@findex char<=?
+@findex <=
+These procedures implement order isomorphisms between the set of
+characters under the @code{char<=?} ordering and some subset of the
+integers under the @code{<=} ordering.  That is, if
+
+@example
+(char<=? a b)  @result{}  #t    @r{and}    (<= x y)  @result{}  #t
+@end example
+
+and @code{x} and @code{y} are in the range of @code{char->integer},
+then
+
+@example
+@group
+(<= (char->integer a)
+    (char->integer b))                  @result{}  #t
+(char<=? (integer->char x)
+         (integer->char y))             @result{}  #t
+@end group
+@end example
+@end deffn
+
+@defvr {variable+} char-integer-limit
+The range of @code{char->integer} is defined to be the exact
+non-negative integers that are less than the value of this variable
+(exclusive).
+@end defvr
+
+@node ASCII Characters, Character Sets, Internal Representation of Characters, Characters
+@section ASCII Characters
+
+MIT Scheme internally uses @sc{ascii} codes for @sc{i/o}, and stores
+character objects in a fashion that makes it convenient to convert
+between @sc{ascii} codes and characters.  Also, character strings are
+implemented as byte vectors whose elements are @sc{ascii} codes; these
+codes are converted to character objects when accessed.  For these
+reasons it is sometimes desirable to be able to convert between
+@sc{ascii} codes and characters.
+
+@cindex ASCII character (defn)
+@cindex character, ASCII (defn)
+Not all characters can be represented as @sc{ascii} codes.  A character
+that has an equivalent @sc{ascii} representation is called an @dfn{ASCII
+character}.
+
+@deffn {procedure+} char-ascii? char
+Returns the @sc{ascii} code for @var{char} if @var{char} has an
+@sc{ascii} representation; otherwise returns @code{#f}.
+
+@findex char-bits
+In the current implementation, the characters that satisfy this
+predicate are those in which the Control, Super, Hyper, and Top bucky
+bits are turned off.  All characters for which the @code{char-bits}
+procedure returns @code{0} or @code{1} (i.e.@: no bucky bits, or just
+Meta) count as legal @sc{ascii} characters.
+@end deffn
+
+@deffn {procedure+} char->ascii char
+Returns the @sc{ascii} code for @var{char}.  An error is signalled if
+@var{char} doesn't have an @sc{ascii} representation.
+@end deffn
+
+@deffn {procedure+} ascii->char code
+@var{Code} must be the exact integer representation of an @sc{ascii}
+code.  This procedure returns the character corresponding to @var{code}.
+@end deffn
+
+@node Character Sets,  , ASCII Characters, Characters
+@section Character Sets
+@cindex character set
+@cindex set, of characters
+
+MIT Scheme's character-set abstraction is used to represent groups
+of characters, such as the letters or digits.  Character sets may
+contain only @sc{ascii} characters; in the future this may be changed to
+allow the full range of characters.
+
+There is no meaningful external representation for character sets; use
+@code{char-set-members} to examine their contents.  There is (at
+present) no specific equivalence predicate for character sets; use
+@code{equal?} for this purpose.
+
+@deffn {procedure+} char-set? object
+@cindex type predicate, for character set
+Returns @code{#t} if @var{object} is a character set; otherwise returns
+@code{#f}.@footnote{Because character sets are implemented as strings,
+@code{string?} returns @code{#t} for character set objects.  However,
+string operations aren't meaningful with character sets.}
+@end deffn
+
+@defvr {variable+} char-set:upper-case
+@defvrx {variable+} char-set:lower-case
+@defvrx {variable+} char-set:alphabetic
+@defvrx {variable+} char-set:numeric
+@defvrx {variable+} char-set:alphanumeric
+@defvrx {variable+} char-set:whitespace
+@defvrx {variable+} char-set:not-whitespace
+@defvrx {variable+} char-set:graphic
+@defvrx {variable+} char-set:not-graphic
+@defvrx {variable+} char-set:standard
+These variables contain predefined character sets.
+To see the contents of one of these sets, use @code{char-set-members}.
+
+@cindex alphabetic character (defn)
+@cindex character, alphabetic (defn)
+@cindex numeric character (defn)
+@cindex character, numeric (defn)
+@cindex alphanumeric character (defn)
+@cindex character, alphanumeric (defn)
+@cindex whitespace character (defn)
+@cindex character, whitespace (defn)
+@cindex graphic character (defn)
+@cindex character, graphic (defn)
+@cindex standard character (defn)
+@cindex character, standard (defn)
+@findex #\space
+@findex #\tab
+@findex #\page
+@findex #\linefeed
+@findex #\return
+@findex #\newline
+@dfn{Alphabetic} characters are the 52 upper and lower case letters.
+@dfn{Numeric} characters are the 10 decimal digits.  @dfn{Alphanumeric}
+characters are those in the union of these two sets.  @dfn{Whitespace}
+characters are @code{#\space}, @code{#\tab}, @code{#\page},
+@code{#\linefeed}, and @code{#\return}.  @var{Graphic} characters are
+the printing characters and @code{#\space}.  @var{Standard} characters
+are the printing characters, @code{#\space}, and @code{#\newline}.
+These are the printing characters:
+
+@example
+@group
+! " # $ % & ' ( ) * + , - . /
+0 1 2 3 4 5 6 7 8 9
+: ; < = > ? @@
+A B C D E F G H I J K L M N O P Q R S T U V W X Y Z
+[ \ ] ^ _ `
+a b c d e f g h i j k l m n o p q r s t u v w x y z
+@{ | @} ~
+@end group
+@end example
+@end defvr
+
+@deffn {procedure} char-upper-case? char
+@deffnx {procedure} char-lower-case? char
+@deffnx {procedure} char-alphabetic? char
+@deffnx {procedure} char-numeric? char
+@deffnx {procedure+} char-alphanumeric? char
+@deffnx {procedure} char-whitespace? char
+@deffnx {procedure+} char-graphic? char
+@deffnx {procedure+} char-standard? object
+These predicates are defined in terms of the respective character sets
+defined above.
+@end deffn
+
+@deffn {procedure+} char-set-members char-set
+Returns a newly allocated list of the characters in @var{char-set}.
+@end deffn
+
+@deffn {procedure+} char-set-member? char-set char
+Returns @code{#t} if the @var{char} is in @var{char-set}; otherwise
+returns @code{#f}.
+@end deffn
+
+@deffn {procedure+} char-set char @dots{}
+@cindex construction, of character set
+Returns a character set consisting of the specified @sc{ascii}
+characters.  With no arguments, @code{char-set} returns an empty
+character set.
+@end deffn
+
+@deffn {procedure+} chars->char-set chars
+Returns a character set consisting of @var{chars}, which must be a list
+of @sc{ascii} characters.  This is equivalent to @code{(apply char-set
+@var{chars})}.
+@end deffn
+
+@deffn {procedure+} ascii-range->char-set lower upper
+@var{Lower} and @var{upper} must be exact non-negative integers
+representing @sc{ascii} character codes, and @var{lower} must be less
+than or equal to @var{upper}.  This procedure creates and returns a new
+character set consisting of the characters whose @sc{ascii} codes are
+between @var{lower} (inclusive) and @var{upper} (exclusive).
+@end deffn
+
+@deffn {procedure+} predicate->char-set predicate
+@var{Predicate} must be a procedure of one argument.
+@code{predicate->char-set} creates and returns a character set
+consisting of the @sc{ascii} characters for which @var{predicate} is
+true.
+@end deffn
+
+@deffn {procedure+} char-set-difference char-set1 char-set2
+Returns a character set consisting of the characters that are in
+@var{char-set1} but aren't in @var{char-set2}.
+@end deffn
+
+@deffn {procedure+} char-set-intersection char-set1 char-set2
+Returns a character set consisting of the characters that are in both
+@var{char-set1} and @var{char-set2}.
+@end deffn
+
+@deffn {procedure+} char-set-union char-set1 char-set2
+Returns a character set consisting of the characters that are in one or
+both of @var{char-set1} and @var{char-set2}.
+@end deffn
+
+@deffn {procedure+} char-set-invert char-set
+Returns a character set consisting of the @sc{ascii} characters that are
+not in @var{char-set}.
+@end deffn
+
+@node Strings, Lists, Characters, Top
+@chapter Strings
+
+@cindex string, character (defn)
+@findex char-ascii?
+A @dfn{string} is a mutable sequence of characters.  In the current
+implementation of MIT Scheme, the elements of a string must all
+satisfy the predicate @code{char-ascii?}; if someone ports MIT
+Scheme to a non-@sc{ascii} operating system this requirement will
+change.
+
+@cindex external representation, for string
+@cindex " as external representation
+@cindex double quote, as external representation
+@cindex \ as escape character in string
+@cindex backslash, as escape character in string
+@cindex escape character, for string
+@findex "
+@findex \
+A string is written as a sequence of characters enclosed within double
+quotes @code{" "}.  To include a double quote inside a string, precede
+the double quote with a backslash @code{\} (escape it), as in
+
+@example
+"The word \"recursion\" has many meanings."
+@end example
+
+@noindent
+The printed representation of this string is
+
+@example
+The word "recursion" has many meanings.
+@end example
+
+@noindent
+To include a backslash inside a string, precede it with another
+backslash; for example,
+
+@example
+"Use #\\Control-q to quit."
+@end example
+
+@noindent
+The printed representation of this string is
+
+@example
+Use #\Control-q to quit.
+@end example
+
+@findex \t
+@findex \n
+@findex \f
+@findex #\tab
+@findex #\newline
+@findex #\page
+The effect of a backslash that doesn't precede a double quote or
+backslash is unspecified in standard Scheme, but MIT Scheme
+specifies the effect for three other characters: @code{\t}, @code{\n},
+and @code{\f}.  These escape sequences are respectively translated into
+the following characters: @code{#\tab}, @code{#\newline}, and
+@code{#\page}.  Finally, a backslash followed by exactly three octal
+digits is translated into the character whose @sc{ascii} code is those
+digits.
+
+If a string literal is continued from one line to another, the string
+will contain the newline character (@code{#\newline}) at the line break.
+
+@cindex length, of string (defn)
+@cindex index, of string (defn)
+@cindex valid index, of string (defn)
+@cindex string length (defn)
+@cindex string index (defn)
+The @dfn{length} of a string is the number of characters that it
+contains.  This number is an exact non-negative integer that is
+established when the string is created (but @pxref{Variable-Length
+Strings}).  Each character in a string has an @dfn{index}, which is a
+number that indicates the character's position in the string.  The index
+of the first (leftmost) character in a string is 0, and the index of the
+last character is one less than the length of the string.  The
+@dfn{valid indexes} of a string are the exact non-negative integers less
+than the length of the string.
+
+@cindex substring (defn)
+@cindex start, of substring (defn)
+@cindex end, of substring (defn)
+A number of the string procedures operate on substrings.  A
+@dfn{substring} is a segment of a @var{string}, which is specified by
+two integers @var{start} and @var{end} satisfying these relationships:
+
+@example
+0 <= @var{start} <= @var{end} <= (string-length @var{string})
+@end example
+
+@noindent
+@var{Start} is the index of the first character in the substring, and
+@var{end} is one greater than the index of the last character in the
+substring.  Thus if @var{start} and @var{end} are equal, they refer to
+an empty substring, and if @var{start} is zero and @var{end} is the
+length of @var{string}, they refer to all of @var{string}.
+
+@cindex case sensitivity, of string operations
+@cindex -ci, in string procedure name
+Some of the procedures that operate on strings ignore the difference
+between uppercase and lowercase.  The versions that ignore case include
+@samp{-ci} (for ``case insensitive'') in their names.
+
+@menu
+* Construction of Strings::     Construction of Strings
+* Selecting String Components::  Selecting String Components
+* Comparison of Strings::       Comparison of Strings
+* Alphabetic Case in Strings::  Alphabetic Case in Strings
+* Cutting and Pasting Strings::  Cutting and Pasting Strings
+* Searching Strings::           Searching Strings
+* Matching Strings::            Matching Strings
+* Modification of Strings::     Modification of Strings
+* Variable-Length Strings::     Variable-Length Strings
+* Byte Vectors::                Byte Vectors
+@end menu
+
+@node Construction of Strings, Selecting String Components, Strings, Strings
+@section Construction of Strings
+@cindex construction, of string
+
+@deffn {procedure} make-string k [char]
+Returns a newly allocated string of length @var{k}.  If you specify
+@var{char}, all elements of the string are initialized to @var{char},
+otherwise the contents of the string are unspecified.  @var{Char} must
+satisfy the predicate @code{char-ascii?}.
+@end deffn
+
+@deffn {procedure+} string char @dots{}
+Returns a newly allocated string consisting of the specified characters.
+The arguments must all satisfy @code{char-ascii?}.
+
+@example
+(string #\a)                                @result{}  "a"
+(string #\a #\b #\c)                        @result{}  "abc"
+(string #\a #\space #\b #\space #\c)        @result{}  "a b c"
+(string)                                    @result{}  ""
+@end example
+
+@findex char->string
+For compatibility with old code, @code{char->string} is a synonym for
+this procedure.
+@end deffn
+
+@deffn procedure list->string char-list
+@cindex list, converting to string
+@findex string->list
+@var{Char-list} must be a list of @sc{ascii} characters.
+@code{list->string} returns a newly allocated string formed from the
+elements of @var{char-list}.  This is equivalent to @code{(apply string
+@var{char-list})}.  The inverse of this operation is
+@code{string->list}.
+@end deffn
+
+@deffn {procedure} string-copy string
+@cindex copying, of string
+Returns a newly allocated copy of @var{string}.
+
+Note regarding variable-length strings: the maximum length of the result
+depends only on the length of @var{string}, not its maximum length.  If
+you wish to copy a string and preserve its maximum length, do the
+following:
+
+@example
+(define (string-copy-preserving-max-length string)
+  (let ((length))
+    (dynamic-wind 
+     (lambda ()
+       (set! length (string-length string))
+       (set-string-length! string (string-maximum-length string)))
+     (lambda ()
+       (string-copy string))
+     (lambda ()
+       (set-string-length! string length)))))
+@end example
+@end deffn
+
+@node Selecting String Components, Comparison of Strings, Construction of Strings, Strings
+@section Selecting String Components
+@cindex selection, of string component
+@cindex component selection, of string
+
+@deffn procedure string? object
+@cindex type predicate, for string
+Returns @code{#t} if @var{object} is a string; otherwise returns
+@code{#f}.
+@end deffn
+
+@deffn procedure string-length string
+Returns the length of @var{string} as an exact non-negative integer.
+@end deffn
+
+@deffn procedure string-null? string
+@cindex empty string, predicate for
+@cindex null string, predicate for
+Returns @code{#t} if @var{string} has zero length; otherwise returns
+@code{#f}.
+@end deffn
+
+@deffn procedure string-ref string k
+Returns character @var{k} of @var{string}.  @var{K} must be a valid index
+of @var{string}.
+@end deffn
+
+@deffn {procedure} string-set! string k char
+Stores @var{char} in element @var{k} of @var{string} and returns an
+unspecified value.  @var{K} must be a valid index of @var{string}, and
+@var{char} must satisfy the predicate @code{char-ascii?}.
+@end deffn
+
+@need 1000
+@node Comparison of Strings, Alphabetic Case in Strings, Selecting String Components, Strings
+@section Comparison of Strings
+@cindex ordering, of strings
+@cindex comparison, of strings
+
+@deffn procedure string=? string1 string2
+@deffnx {procedure+} substring=? string1 start end string2 start end
+@deffnx {procedure} string-ci=? string1 string2
+@deffnx {procedure+} substring-ci=? string1 start end string2 start end
+@cindex equivalence predicate, for strings
+Returns @code{#t} if the two strings (substrings) are the same length
+and contain the same characters in the same (relative) positions;
+otherwise returns @code{#f}.  @code{string-ci=?} and
+@code{substring-ci=?} don't distinguish uppercase and lowercase letters,
+but @code{string=?} and @code{substring=?} do.
+@end deffn
+
+@deffn procedure string<? string1 string2
+@deffnx {procedure+} substring<? string1 start1 end1 string2 start2 end2
+@deffnx procedure string>? string1 string2
+@deffnx procedure string<=? string1 string2
+@deffnx procedure string>=? string1 string2
+@deffnx {procedure} string-ci<? string1 string2
+@deffnx {procedure+} substring-ci<? string1 start1 end1 string2 start2 end2
+@deffnx {procedure} string-ci>? string1 string2
+@deffnx {procedure} string-ci<=? string1 string2
+@deffnx {procedure} string-ci>=? string1 string2
+These procedures compare strings (substrings) according to the order of
+the characters they contain (also @pxref{Comparison of Characters}).
+The arguments are compared using a lexicographic (or dictionary) order.
+If two strings differ in length but are the same up to the length of the
+shorter string, the shorter string is considered to be less than the
+longer string.
+@end deffn
+
+@deffn {procedure+} string-compare string1 string2 if-eq if-lt if-gt
+@deffnx {procedure+} string-compare-ci string1 string2 if-eq if-lt if-gt
+@var{If-eq}, @var{if-lt}, and @var{if-gt} are procedures of no arguments
+(thunks).  The two strings are compared; if they are equal, @var{if-eq}
+is applied, if @var{string1} is less than @var{string2}, @var{if-lt} is
+applied, else if @var{string1} is greater than @var{string2},
+@var{if-gt} is applied.  The value of the procedure is the value of the
+thunk that is applied.
+
+@code{string-compare} distinguishes uppercase and lowercase letters;
+@code{string-compare-ci} does not.
+@end deffn
+
+@deffn {procedure+} string-hash string
+@deffnx {procedure+} string-hash-mod string k
+@cindex hashing, of string
+@findex string=?
+@findex =
+@code{string-hash} returns an exact non-negative integer that can be used
+for storing the specified @var{string} in a hash table.  Equal strings
+(in the sense of @code{string=?}) return equal (@code{=}) hash codes,
+and non-equal but similar strings are usually mapped to distinct hash
+codes.
+
+@code{string-hash-mod} is like @code{string-hash}, except that it limits
+the result to a particular range based on the exact non-negative integer
+@var{k}.  The following are equivalent:
+
+@example
+@group
+(string-hash-mod @var{string} @var{k})
+(modulo (string-hash @var{string}) @var{k})
+@end group
+@end example
+@end deffn
+
+@node Alphabetic Case in Strings, Cutting and Pasting Strings, Comparison of Strings, Strings
+@section Alphabetic Case in Strings
+@cindex alphabetic case, of string
+@cindex case, of string
+@cindex capitalization, of string
+@cindex uppercase, in string
+@cindex lowercase, in string
+
+@deffn {procedure+} string-capitalized? string
+@deffnx {procedure+} substring-capitalized? string start end
+These procedures @code{#t} if the first character in the string
+(substring) is an uppercase letter and none of the remaining characters
+are uppercase letters.  If the first character is not an uppercase
+letter or if any of the remaining characters are uppercase letters, they
+return @code{#f}.  If the string (substring) contains less than two
+letters, they return @code{#f}.
+@end deffn
+
+@deffn {procedure+} string-upper-case? string
+@deffnx {procedure+} substring-upper-case? string start end
+@deffnx {procedure+} string-lower-case? string
+@deffnx {procedure+} substring-lower-case? string start end
+These procedures return @code{#t} if all the letters in the string
+(substring) are of the correct case, otherwise they return @code{#f}.
+The string (substring) must contain at least one letter or the
+procedures return @code{#f}.
+@end deffn
+
+@deffn {procedure+} string-capitalize string
+@deffnx {procedure+} string-capitalize! string
+@code{string-capitalize} returns a newly allocated copy of @var{string}
+in which the first character is uppercase and the remaining letters are
+lowercase.  For example, @code{"abcDEF"} becomes @code{"Abcdef"}.
+@code{string-capitalize!} is the destructive version of
+@code{string-capitalize}: it alters @var{string} and returns an
+unspecified value.
+@end deffn
+
+@deffn {procedure+} string-downcase string
+@deffnx {procedure+} string-downcase! string
+@deffnx {procedure+} substring-downcase! string start end
+@code{string-downcase} returns a newly allocated copy of @var{string} in
+which all uppercase letters are changed to lowercase.
+@code{string-downcase!} is the destructive version of
+@code{string-downcase}: it alters @var{string} and returns an
+unspecified value.  @code{substring-downcase!} destructively changes the
+case of the specified part of @var{string}.
+@end deffn
+
+@deffn {procedure+} string-upcase string
+@deffnx {procedure+} string-upcase! string
+@deffnx {procedure+} substring-upcase! string start end
+@code{string-upcase} returns a newly allocated copy of @var{string} in
+which all lowercase letters are changed to uppercase.
+@code{string-upcase!} is the destructive version of
+@code{string-upcase}: it alters @var{string} and returns an unspecified
+value.  @code{substring-upcase!} destructively changes the case of the
+specified part of @var{string}.
+@end deffn
+
+@node Cutting and Pasting Strings, Searching Strings, Alphabetic Case in Strings, Strings
+@section Cutting and Pasting Strings
+@cindex cutting, of string
+@cindex pasting, of strings
+
+@deffn {procedure} string-append string @dots{}
+@cindex appending, of strings
+Returns a newly allocated string made from the concatenation of the given
+strings.  With no arguments, @code{string-append} returns the empty
+string (@code{""}).
+@end deffn
+
+@deffn procedure substring string start end
+Returns a newly allocated string formed from the characters of
+@var{string} beginning with index @var{start} (inclusive) and ending
+with @var{end} (exclusive).
+@end deffn
+
+@deffn {procedure+} string-head string end
+Returns a newly allocated copy of the initial substring of @var{string},
+up to but excluding @var{end}.  It could have been defined by:
+
+@example
+(define (string-head string end)
+  (substring string 0 end))
+@end example
+@end deffn
+
+@deffn {procedure+} string-tail string start
+Returns a newly allocated copy of the final substring of @var{string},
+starting at index @var{start} and going to the end of @var{string}.  It
+could have been defined by:
+
+@example
+(define (string-tail string start)
+  (substring string start (string-length string)))
+@end example
+@end deffn
+
+@deffn {procedure+} string-pad-left string k [char]
+@deffnx {procedure+} string-pad-right string k [char]
+@cindex padding, of string
+@findex #\space
+These procedures return a newly allocated string created by padding
+@var{string} out to length @var{k}, using @var{char}.  If @var{char} is
+not given, it defaults to @code{#\space}.  If @var{k} is less than the
+length of @var{string}, these procedures are equivalent to
+@code{string-head}.  @code{string-pad-left} adds padding characters or
+truncates from the beginning of the string (lowest indices), while
+@code{string-pad-right} does so at the end of the string (highest
+indices).
+@end deffn
+
+@deffn {procedure+} string-trim string [char-set]
+@deffnx {procedure+} string-trim-left string [char-set]
+@deffnx {procedure+} string-trim-right string [char-set]
+@cindex trimming, of string
+@findex char-set:whitespace
+Returns a newly allocated string created by removing all characters that
+are not in @var{char-set} from: (@code{string-trim}) both ends of
+@var{string}; (@code{string-trim-left}) the beginning of @var{string};
+or (@code{string-trim-right}) the end of @var{string}.  @var{Char-set}
+defaults to @code{char-set:whitespace}.
+@end deffn
+
+@node Searching Strings, Matching Strings, Cutting and Pasting Strings, Strings
+@section Searching Strings
+@cindex searching, of string
+@cindex character, searching string for
+
+@deffn {procedure+} string-find-next-char string char
+@deffnx {procedure+} substring-find-next-char string start end char
+@deffnx {procedure+} string-find-next-char-ci string char
+@deffnx {procedure+} substring-find-next-char-ci string start end char
+Returns the index of the first occurrence of @var{char} in the string
+(substring); returns @code{#f} if @var{char} does not appear in the
+string.  For the substring procedures, the index returned is relative to
+the entire string, not just the substring.  The @code{-ci} procedures
+don't distinguish uppercase and lowercase letters.
+@end deffn
+
+@deffn {procedure+} string-find-next-char-in-set string char-set
+@deffnx {procedure+} substring-find-next-char-in-set string start end char-set
+Returns the index of the first character in the string (substring) that
+is also in @var{char-set}.  For the substring procedure, the index
+returned is relative to the entire string, not just the substring.
+@end deffn
+
+@deffn {procedure+} string-find-previous-char string char
+@deffnx {procedure+} substring-find-previous-char string start end char
+@deffnx {procedure+} string-find-previous-char-ci string char
+@deffnx {procedure+} substring-find-previous-char-ci string start end char
+Returns the index of the last occurrence of @var{char} in the string
+(substring); returns @code{#f} if @var{char} doesn't appear in the
+string.  For the substring procedures, the index returned is relative to
+the entire string, not just the substring.  The @code{-ci} procedures
+don't distinguish uppercase and lowercase letters.
+@end deffn
+
+@deffn {procedure+} string-find-previous-char-in-set string char-set
+@deffnx {procedure+} substring-find-previous-char-in-set string start end char-set
+Returns the index of the last character in the string (substring) that
+is also in @var{char-set}.  For the substring procedure, the index
+returned is relative to the entire string, not just the substring.
+@end deffn
+
+@node Matching Strings, Modification of Strings, Searching Strings, Strings
+@section Matching Strings
+@cindex matching, of strings
+
+@deffn {procedure+} string-match-forward string1 string2
+@deffnx {procedure+} substring-match-forward string1 start end string2 start end
+@deffnx {procedure+} string-match-forward-ci string1 string2
+@deffnx {procedure+} substring-match-forward-ci string1 start end string2 start end
+Compares the two strings (substrings), starting from the beginning, and
+returns the number of characters that are the same.  If the two strings
+(substrings) start differently, returns 0.  The @code{-ci} procedures
+don't distinguish uppercase and lowercase letters.
+@end deffn
+
+@deffn {procedure+} string-match-backward string1 string2
+@deffnx {procedure+} substring-match-backward string1 start end string2 start end
+@deffnx {procedure+} string-match-backward-ci string1 string2
+@deffnx {procedure+} substring-match-backward-ci string1 start end string2 start end
+Compares the two strings (substrings), starting from the end and
+matching toward the front, returning the number of characters that are
+the same.  If the two strings (substrings) end differently, returns 0.
+The @code{-ci} procedures don't distinguish uppercase and lowercase
+letters.
+@end deffn
+
+@deffn {procedure+} string-prefix? string1 string2
+@deffnx {procedure+} substring-prefix? string1 start1 end1 string2 start2 end2
+@deffnx {procedure+} string-prefix-ci? string1 string2
+@deffnx {procedure+} substring-prefix-ci? string1 start1 end1 string2 start2 end2
+@cindex prefix, of string
+These procedures return @code{#t} if the first string (substring) forms
+the prefix of the second; otherwise returns @code{#f}.  The @code{-ci}
+procedures don't distinguish uppercase and lowercase letters.
+
+@example
+(string-prefix? "abc" "abcdef")         @result{}  #t
+@end example
+@end deffn
+
+@deffn {procedure+} string-suffix? string1 string2
+@deffnx {procedure+} substring-suffix? string1 start1 end1 string2 start2 end2
+@deffnx {procedure+} string-suffix-ci? string1 string2
+@deffnx {procedure+} substring-suffix-ci? string1 start1 end1 string2 start2 end2
+@cindex suffix, of string
+These procedures return @code{#t} if the first string (substring) forms
+the suffix of the second; otherwise returns @code{#f}.  The @code{-ci}
+procedures don't distinguish uppercase and lowercase letters.
+
+@example
+(string-suffix? "def" "abcdef")         @result{}  #t
+@end example
+@end deffn
+
+@node Modification of Strings, Variable-Length Strings, Matching Strings, Strings
+@section Modification of Strings
+@cindex modification, of string
+@cindex replacement, of string component
+@cindex filling, of string
+@cindex moving, of string elements
+
+@deffn {procedure+} string-replace string char1 char2
+@deffnx {procedure+} substring-replace string start end char1 char2
+@deffnx {procedure+} string-replace! string char1 char2
+@deffnx {procedure+} substring-replace! string start end char1 char2
+These procedures replace all occurrences of @var{char1} with @var{char2}
+in the original string (substring).  @code{string-replace} and
+@code{substring-replace} return a newly allocated string containing the
+result.  @code{string-replace!} and @code{substring-replace!}
+destructively modify @var{string} and return an unspecified value.
+@end deffn
+
+@deffn {procedure} string-fill! string char
+Stores @var{char} in every element of @var{string} and returns an
+unspecified value.
+@end deffn
+
+@deffn {procedure+} substring-fill! string start end char
+Stores @var{char} in elements @var{start} (inclusive) to @var{end}
+(exclusive) of @var{string} and returns an unspecified value.
+@end deffn
+
+@deffn {procedure+} substring-move-left! string1 start1 end1 string2 start2
+@deffnx {procedure+} substring-move-right! string1 start1 end1 string2 start2
+@findex eqv?
+Copies the characters from @var{start1} to @var{end1} of @var{string1}
+into @var{string2} at the @var{start2}-th position.  The characters are
+copied as follows (note that this is only important when @var{string1}
+and @var{string2} are @code{eqv?}):
+
+@table @code
+@item substring-move-left!
+The copy starts at the left end and moves toward the right (from smaller
+indices to larger).  Thus if @var{string1} and @var{string2} are the
+same, this procedure moves the characters toward the left inside the
+string.
+
+@item substring-move-right!
+The copy starts at the right end and moves toward the left (from larger
+indices to smaller).  Thus if @var{string1} and @var{string2} are the
+same, this procedure moves the characters toward the right inside the
+string.
+@end table
+@end deffn
+
+@node Variable-Length Strings, Byte Vectors, Modification of Strings, Strings
+@section Variable-Length Strings
+
+@cindex length, of string
+@cindex maximum length, of string (defn)
+MIT Scheme allows the length of a string to be dynamically adjusted in a
+limited way.  This feature works as follows.  When a new string is
+allocated, by whatever method, it has a specific length.  At the time of
+allocation, it is also given a @dfn{maximum length}, which is guaranteed
+to be at least as large as the string's length.  (Sometimes the maximum
+length will be slightly larger than the length, but it is a bad idea to
+count on this.  Programs should assume that the maximum length is the
+same as the length at the time of the string's allocation.)  After the
+string is allocated, the operation @code{set-string-length!} can be used
+to alter the string's length to any value between 0 and the string's
+maximum length, inclusive.
+
+@deffn {procedure+} string-maximum-length string
+Returns the maximum length of @var{string}.  The following is
+guaranteed:
+
+@example
+@group
+(<= (string-length string)
+    (string-maximum-length string))     @result{}  #t
+@end group
+@end example
+@findex string-length
+
+The maximum length of a string @emph{never} changes.
+@end deffn
+
+@deffn {procedure+} set-string-length! string k
+Alters the length of @var{string} to be @var{k}, and returns an
+unspecified value.  @var{K} must be less than or equal to the maximum
+length of @var{string}.  @code{set-string-length!} does not change the
+maximum length of @var{string}.
+@end deffn
+
+@node Byte Vectors,  , Variable-Length Strings, Strings
+@section Byte Vectors
+@cindex byte vector
+@cindex vector, byte
+
+@findex string-ref
+MIT Scheme implements strings as packed vectors of 8-bit @sc{ascii}
+bytes.  Most of the string operations, such as @code{string-ref}, coerce
+these 8-bit codes into character objects.  However, some lower-level
+operations are made available for use.
+
+@deffn {procedure+} vector-8b-ref string k
+Returns character @var{k} of @var{string} as an @sc{ascii} code.
+@var{K} must be a valid index of @var{string}.
+@end deffn
+
+@deffn {procedure+} vector-8b-set! string k ascii
+Stores @var{ascii} in element @var{k} of @var{string} and returns an
+unspecified value.  @var{K} must be a valid index of @var{string}, and
+@var{ascii} must be a valid @sc{ascii} code.
+@end deffn
+
+@deffn {procedure+} vector-8b-fill! string start end
+Stores @var{ascii} in elements @var{start} (inclusive) to @var{end}
+(exclusive) of @var{string} and returns an unspecified value.
+@var{Ascii} must be a valid @sc{ascii} code.
+@end deffn
+
+@deffn {procedure+} vector-8b-find-next-char string start end ascii
+@deffnx {procedure+} vector-8b-find-next-char-ci string start end ascii
+Returns the index of the first occurrence of @var{ascii} in the given
+substring; returns @code{#f} if @var{ascii} does not appear.  The index
+returned is relative to the entire string, not just the substring.
+@var{Ascii} must be a valid @sc{ascii} code.
+
+@code{vector-8b-find-next-char-ci} doesn't distinguish uppercase and
+lowercase letters.
+@end deffn
+
+@deffn {procedure+} vector-8b-find-previous-char string start end ascii
+@deffnx {procedure+} vector-8b-find-previous-char-ci string start end ascii
+Returns the index of the last occurrence of @var{ascii} in the given
+substring; returns @code{#f} if @var{ascii} does not appear.  The index
+returned is relative to the entire string, not just the substring.
+@var{Ascii} must be a valid @sc{ascii} code.
+
+@code{vector-8b-find-previous-char-ci} doesn't distinguish uppercase and
+lowercase letters.
+@end deffn
+
+@node Lists, Vectors, Strings, Top
+@chapter Lists
+
+@cindex pair (defn)
+@cindex dotted pair (see pair)
+@cindex car field, of pair (defn)
+@cindex cdr field, of pair (defn)
+A @dfn{pair} (sometimes called a @dfn{dotted pair}) is a record
+structure with two fields called the @dfn{car} and @dfn{cdr} fields (for
+historical reasons).  Pairs are created by the procedure @code{cons}.
+The car and cdr fields are accessed by the procedures @code{car} and
+@code{cdr}.  The car and cdr fields are assigned by the procedures
+@code{set-car!} and @code{set-cdr!}.
+
+@cindex list (defn)
+Pairs are used primarily to represent @dfn{lists}.  A list can be
+defined recursively as either the empty list or a pair whose cdr is
+a list.  More precisely, the set of lists is defined as the smallest set
+@var{X} such that
+
+@itemize @bullet
+@item
+The empty list is in @var{X}.
+
+@item
+If @var{list} is in @var{X}, then any pair whose cdr field contains
+@var{list} is also in @var{X}.
+@end itemize
+
+@cindex element, of list (defn)
+@cindex length, of list (defn)
+@cindex empty list (defn)
+The objects in the car fields of successive pairs of a list are the
+@dfn{elements} of the list.  For example, a two-element list is a pair
+whose car is the first element and whose cdr is a pair whose car is the
+second element and whose cdr is the empty list.  The @dfn{length} of a
+list is the number of elements, which is the same as the number of
+pairs.  The @dfn{empty list} is a special object of its own type (it is
+not a pair); it has no elements and its length is zero.@footnote{The
+above definitions imply that all lists have finite length and are
+terminated by the empty list.}
+
+@cindex dotted notation, for pair (defn)
+@cindex notation, dotted (defn)
+@cindex external representation, for pair
+@cindex pair, external representation
+@cindex ( as external representation
+@cindex ) as external representation
+@cindex . as external representation
+@cindex parenthesis, as external representation
+@cindex dot, as external representation
+@cindex period, as external representation
+@findex (
+@findex )
+@findex .
+The most general notation (external representation) for Scheme pairs is
+the ``dotted'' notation @code{(@var{c1} . @var{c2})} where @var{c1} is
+the value of the car field and @var{c2} is the value of the cdr field.
+For example, @code{(4 . 5)} is a pair whose car is @code{4} and whose
+cdr is @code{5}.  Note that @code{(4 . 5)} is the external
+representation of a pair, not an expression that evaluates to a pair.
+
+@cindex external representation, for list
+@cindex list, external representation
+@cindex external representation, for empty list
+@cindex empty list, external representation
+@findex ()
+A more streamlined notation can be used for lists: the elements of the
+list are simply enclosed in parentheses and separated by spaces.  The
+empty list is written @code{()}.  For example, the following are
+equivalent notations for a list of symbols:
+
+@example
+@group
+(a b c d e)
+(a . (b . (c . (d . (e . ())))))
+@end group
+@end example
+
+@findex set-cdr!
+Whether a given pair is a list depends upon what is stored in the cdr
+field.  When the @code{set-cdr!} procedure is used, an object can be a
+list one moment and not the next:
+
+@example
+@group
+(define x (list 'a 'b 'c))
+(define y x)
+y                                       @result{}  (a b c)
+(list? y)                               @result{}  #t
+(set-cdr! x 4)                          @result{}  @r{unspecified}
+x                                       @result{}  (a . 4)
+(eqv? x y)                              @result{}  #t
+y                                       @result{}  (a . 4)
+(list? y)                               @result{}  #f
+(set-cdr! x x)                          @result{}  @r{unspecified}
+(list? y)                               @result{}  #f
+@end group
+@end example
+
+@cindex improper list (defn)
+@cindex list, improper (defn)
+A chain of pairs that doesn't end in the empty list is called an
+@dfn{improper list}.  Note that an improper list is not a list.  The
+list and dotted notations can be combined to represent improper lists,
+as the following equivalent notations show:
+
+@example
+@group
+(a b c . d)
+(a . (b . (c . d)))
+@end group
+@end example
+
+@findex quote
+@findex quasiquote
+@findex unquote
+@findex unquote-splicing
+@findex '
+@findex `
+@findex ,
+@findex ,@@
+@findex read
+Within literal expressions and representations of objects read by the
+@code{read} procedure, the forms @code{'@var{datum}},
+@code{`@var{datum}}, @code{,@var{datum}}, and @code{,@@@var{datum}}
+denote two-element lists whose first elements are the symbols
+@code{quote}, @code{quasiquote}, @code{unquote}, and
+@code{unquote-splicing}, respectively.  The second element in each case
+is @var{datum}.  This convention is supported so that arbitrary Scheme
+programs may be represented as lists.  Among other things, this permits
+the use of the @code{read} procedure to parse Scheme programs.
+
+@menu
+* Pairs::                       Pairs
+* Construction of Lists::       Construction of Lists
+* Selecting List Components::   Selecting List Components
+* Cutting and Pasting Lists::   Cutting and Pasting Lists
+* Filtering Lists::             Filtering Lists
+* Searching Lists::             Searching Lists
+* Mapping of Lists::            Mapping of Lists
+* Reduction of Lists::          Reduction of Lists
+* Miscellaneous List Operations::  Miscellaneous List Operations
+@end menu
+
+@node Pairs, Construction of Lists, Lists, Lists
+@section Pairs
+
+This section describes the simple operations that are available for
+constructing and manipulating arbitrary graphs constructed from pairs.
+
+@deffn procedure pair? object
+@cindex type predicate, for pair
+Returns @code{#t} if @var{object} is a pair; otherwise returns
+@code{#f}.
+
+@example
+@group
+(pair? '(a . b))                        @result{}  #t
+(pair? '(a b c))                        @result{}  #t
+(pair? '())                             @result{}  #f
+(pair? '#(a b))                         @result{}  #f
+@end group
+@end example
+@end deffn
+
+@deffn procedure cons obj1 obj2
+@cindex construction, of pair
+@findex eqv?
+Returns a newly allocated pair whose car is @var{obj1} and whose cdr is
+@var{obj2}.  The pair is guaranteed to be different (in the sense of
+@code{eqv?}) from every previously existing object.
+
+@example
+@group
+(cons 'a '())                           @result{}  (a)
+(cons '(a) '(b c d))                    @result{}  ((a) b c d)
+(cons "a" '(b c))                       @result{}  ("a" b c)
+(cons 'a 3)                             @result{}  (a . 3)
+(cons '(a b) 'c)                        @result{}  ((a b) . c)
+@end group
+@end example
+@end deffn
+
+@deffn procedure car pair
+@cindex selection, of pair component
+@cindex component selection, of pair
+Returns the contents of the car field of @var{pair}.  Note that it is an
+error to take the @code{car} of the empty list.
+
+@example
+@group
+(car '(a b c))                          @result{}  a
+(car '((a) b c d))                      @result{}  (a)
+(car '(1 . 2))                          @result{}  1
+(car '())                               @error{} Illegal datum
+@end group
+@end example
+@end deffn
+
+@deffn procedure cdr pair
+Returns the contents of the cdr field of @var{pair}.  Note that it is an
+error to take the @code{cdr} of the empty list.
+
+@example
+@group
+(cdr '((a) b c d))                      @result{}  (b c d)
+(cdr '(1 . 2))                          @result{}  2
+(cdr '())                               @error{} Illegal datum
+@end group
+@end example
+@end deffn
+
+@deffn procedure set-car! pair object
+Stores @var{object} in the car field of @var{pair}.  The value returned
+by @code{set-car!} is unspecified.
+
+@example
+@group
+(define (f) (list 'not-a-constant-list))
+(define (g) '(constant-list))
+(set-car! (f) 3)                        @result{}  @r{unspecified}
+(set-car! (g) 3)                        @error{} Illegal datum
+@end group
+@end example
+@end deffn
+
+@deffn procedure set-cdr! pair object
+Stores @var{object} in the cdr field of @var{pair}.  The value returned
+by @code{set-cdr!} is unspecified.
+@end deffn
+
+@deffn procedure caar pair
+@deffnx procedure cadr pair
+@deffnx procedure cdar pair
+@deffnx procedure cddr pair
+@deffnx procedure caaar pair
+@deffnx procedure caadr pair
+@deffnx procedure cadar pair
+@deffnx procedure caddr pair
+@deffnx procedure cdaar pair
+@deffnx procedure cdadr pair
+@deffnx procedure cddar pair
+@deffnx procedure cdddr pair
+@deffnx procedure caaaar pair
+@deffnx procedure caaadr pair
+@deffnx procedure caadar pair
+@deffnx procedure caaddr pair
+@deffnx procedure cadaar pair
+@deffnx procedure cadadr pair
+@deffnx procedure caddar pair
+@deffnx procedure cadddr pair
+@deffnx procedure cdaaar pair
+@deffnx procedure cdaadr pair
+@deffnx procedure cdadar pair
+@deffnx procedure cdaddr pair
+@deffnx procedure cddaar pair
+@deffnx procedure cddadr pair
+@deffnx procedure cdddar pair
+@deffnx procedure cddddr pair
+These procedures are compositions of @code{car} and @code{cdr}; for
+example, @code{caddr} could be defined by
+
+@example
+(define caddr (lambda (x) (car (cdr (cdr x)))))
+@end example
+@end deffn
+
+@deffn {procedure+} general-car-cdr object path
+This procedure is a generalization of @code{car} and @code{cdr}.
+@var{Path} encodes a particular sequence of @code{car} and @code{cdr}
+operations, which @code{general-car-cdr} executes on @var{object}.
+@var{Path} is an exact non-negative integer that encodes the operations
+in a bitwise fashion: a zero bit represents a @code{cdr} operation, and
+a one bit represents a @code{car}.  The bits are executed LSB to MSB,
+and the most significant one bit, rather than being interpreted as an
+operation, signals the end of the sequence.@footnote{Note that
+@var{path} is restricted to a machine-dependent range, usually the size
+of a machine word.  On many machines, this means that the maximum length
+of @var{path} will be 30 operations (32 bits, less the sign bit and the
+``end-of-sequence'' bit).}
+
+For example, the following are equivalent:
+@example
+(general-car-cdr @var{object} #b1011)
+(cdr (car (car @var{object})))
+@end example
+
+Here is a partial table of path/operation equivalents:
+
+@example
+@group
+#b10    cdr
+#b11    car
+#b100   cddr
+#b101   cdar
+#b110   cadr
+#b111   caar
+#b1000  cdddr
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} tree-copy tree
+@cindex copying, of tree
+@cindex tree, copying
+This copies an arbitrary @var{tree} constructed from pairs, copying both
+the car and cdr elements of every pair.  This could have been defined by
+
+@example
+@group
+(define (tree-copy tree)
+  (let loop ((tree tree))
+    (if (pair? tree)
+        (cons (loop (car tree)) (loop (cdr tree)))
+        tree)))
+@end group
+@end example
+@end deffn
+
+@node Construction of Lists, Selecting List Components, Pairs, Lists
+@section Construction of Lists
+@cindex construction, of list
+
+@deffn procedure list object @dots{}
+Returns a list of its arguments.
+
+@example
+@group
+(list 'a (+ 3 4) 'c)                    @result{}  (a 7 c)
+(list)                                  @result{}  ()
+@end group
+@end example
+
+These expressions are equivalent:
+
+@example
+@group
+(list @var{obj1} @var{obj2} @dots{} @var{objN})
+(cons @var{obj1} (cons @var{obj2} @dots{} (cons @var{objN} '()) @dots{}))
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} make-list k [element]
+This procedure returns a newly allocated list of length @var{k},
+whose elements are all @var{element}.  If @var{element} is not supplied,
+it defaults to the empty list.
+@end deffn
+
+@deffn {procedure+} cons* object object @dots{}
+@findex list
+@code{cons*} is similar to @code{list}, except that @code{cons*} conses
+together the last two arguments rather than consing the last argument
+with the empty list.  If the last argument is not a list the result is
+an improper list.  If the last argument is a list, the result is a list
+consisting of the initial arguments and all of the items in the final
+argument.  If there is only one argument, the result is the argument.
+
+@example
+@group
+(cons* 'a 'b 'c)                        @result{}  (a b . c)
+(cons* 'a 'b '(c d))                    @result{}  (a b c d)
+(cons* 'a)                              @result{}  a
+@end group
+@end example
+
+These expressions are equivalent:
+
+@example
+@group
+(cons* @var{obj1} @var{obj2} @dots{} @var{objN-1} @var{objN})
+(cons @var{obj1} (cons @var{obj2} @dots{} (cons @var{objN-1} @var{objN}) @dots{}))
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} list-copy list
+Returns a newly allocated copy of @var{list}.  This copies each of the
+pairs comprising @var{list}.  This could have been defined by
+
+@example
+@group
+(define (list-copy list)
+  (if (null? list)
+      '()
+      (cons (car list)
+            (list-copy (cdr list)))))
+@end group
+@end example
+@end deffn
+
+@deffn procedure vector->list vector
+@deffnx {procedure+} subvector->list vector start end
+@cindex vector, converting to list
+@findex list->vector
+@code{vector->list} returns a newly allocated list of the elements of
+@var{vector}.  @code{subvector->list} returns a newly allocated list of the
+elements of the given subvector.  The inverse of @code{vector->list} is
+@code{list->vector}.
+
+@example
+(vector->list '#(dah dah didah))        @result{}  (dah dah didah)
+@end example
+@end deffn
+
+@deffn {procedure} string->list string
+@deffnx {procedure} substring->list string start end
+@cindex string, converting to list
+@findex list->string
+@code{string->list} returns a newly allocated list of the character
+elements of @var{string}.@*
+@code{substring->list} returns a newly allocated list of the character
+elements of the given substring.  The inverse of @code{string->list} is
+@code{list->string}.
+
+@example
+(string->list "abcd")                   @result{}  (#\a #\b #\c #\d)
+(substring->list "abcdef" 1 3)          @result{}  (#\b #\c)
+@end example
+@end deffn
+
+@node Selecting List Components, Cutting and Pasting Lists, Construction of Lists, Lists
+@section Selecting List Components
+@cindex selection, of list component
+@cindex component selection, of list
+
+@deffn {procedure+} list? object
+@cindex type predicate, for list
+@cindex circular list
+Returns @code{#t} if @var{object} is a list, otherwise returns
+@code{#f}.  By definition, all lists have finite length and are
+terminated by the empty list.  This procedure returns an answer even for
+circular structures.
+
+@findex pair?
+@findex null?
+Any @var{object} satisfying this predicate will also satisfy exactly one
+of @code{pair?} or @code{null?}.
+
+@example
+@group
+(list? '(a b c))                        @result{}  #t
+(list? '())                             @result{}  #t
+(list? '(a . b))                        @result{}  #f
+(let ((x (list 'a)))
+  (set-cdr! x x)
+  (list? x))                            @result{}  #f
+@end group
+@end example
+@end deffn
+
+@deffn procedure length list
+Returns the length of @var{list}.
+
+@example
+@group
+(length '(a b c))                       @result{}  3
+(length '(a (b) (c d e)))               @result{}  3
+(length '())                            @result{}  0
+@end group
+@end example
+@end deffn
+
+@deffn procedure null? object
+@cindex type predicate, for empty list
+@cindex empty list, predicate for
+Returns @code{#t} if @var{object} is the empty list; otherwise returns
+@code{#f} (but @pxref{True and False}).
+
+@example
+@group
+(null? '(a . b))                        @result{}  #f
+(null? '(a b c))                        @result{}  #f
+(null? '())                             @result{}  #t
+@end group
+@end example
+@end deffn
+
+@deffn procedure list-ref list k
+@cindex index, of list (defn)
+@cindex valid index, of list (defn)
+@cindex list index (defn)
+Returns the @var{k}th element of @var{list}, using zero-origin indexing.
+The @dfn{valid indexes} of a list are the exact non-negative integers
+less than the length of the list.  The first element of a list has index
+@code{0}, the second has index @code{1}, and so on.
+
+@example
+(list-ref '(a b c d) 2)                 @result{}  c
+(list-ref '(a b c d)
+          (inexact->exact (round 1.8)))
+     @result{}  c
+@end example
+
+@findex list-tail
+@code{(list-ref @var{list} @var{k})} is equivalent to @code{(car
+(list-tail @var{list} @var{k}))}.
+@end deffn
+
+@deffn {procedure+} first list
+@deffnx {procedure+} second list
+@deffnx {procedure+} third list
+@deffnx {procedure+} fourth list
+@deffnx {procedure+} fifth list
+@deffnx {procedure+} sixth list
+@deffnx {procedure+} seventh list
+@deffnx {procedure+} eighth list
+@deffnx {procedure+} ninth list
+@deffnx {procedure+} tenth list
+Returns the specified element of @var{list}, signalling an error if
+@var{list} is not long enough to contain the specified element (for
+example, if the argument to @code{seventh} is a list that contains only
+six elements).
+@end deffn
+
+@node Cutting and Pasting Lists, Filtering Lists, Selecting List Components, Lists
+@section Cutting and Pasting Lists
+@cindex cutting, of list
+@cindex pasting, of lists
+
+@deffn {procedure+} sublist list start end
+@var{Start} and @var{end} must be exact integers satisfying
+
+@example
+0 <= @var{start} <= @var{end} <= (length @var{list})
+@end example
+
+Returns a newly allocated list formed from the elements of @var{list}
+beginning at index @var{start} (inclusive) and ending at @var{end}
+(exclusive).
+@end deffn
+
+@deffn {procedure+} list-head list k
+Returns a newly allocated list consisting of the first @var{k} elements of
+@var{list}.  @var{K} must not be greater than the length of
+@var{list}.
+
+We could have defined @code{list-head} this way:
+
+@example
+@group
+(define (list-head list k)
+  (sublist list 0 k))
+@end group
+@end example
+@end deffn
+
+@deffn procedure list-tail list k
+Returns the sublist of @var{list} obtained by omitting the first @var{k}
+elements.  The result, if it is not the empty list, shares structure
+with @var{list}.  @var{K} must not be greater than the length of
+@var{list}.
+@end deffn
+
+@deffn {procedure} append list @dots{}
+@cindex appending, of lists
+Returns a list consisting of the elements of the first @var{list}
+followed by the elements of the other @var{list}s.
+
+@example
+@group
+(append '(x) '(y))                      @result{}  (x y)
+(append '(a) '(b c d))                  @result{}  (a b c d)
+(append '(a (b)) '((c)))                @result{}  (a (b) (c))
+(append)                                @result{}  ()
+@end group
+@end example
+
+The resulting list is always newly allocated, except that it shares
+structure with the last @var{list} argument.  The last argument may
+actually be any object; an improper list results if the last argument is
+not a proper list.
+
+@example
+@group
+(append '(a b) '(c . d))                @result{}  (a b c . d)
+(append '() 'a)                         @result{}  a
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} append! list @dots{}
+Returns a list that is the argument @var{list}s concatenated together.
+The arguments are changed rather than copied.  (Compare this with
+@code{append}, which copies arguments rather than destroying them.)  For
+example:
+
+@example
+@group
+(define x '(a b c))
+(define y '(d e f))
+(define z '(g h))
+(append! x y z)                         @result{}  (a b c d e f g h)
+x                                       @result{}  (a b c d e f g h)
+y                                       @result{}  (d e f g h)
+z                                       @result{}  (g h)
+@end group
+@end example
+@end deffn
+
+@node Filtering Lists, Searching Lists, Cutting and Pasting Lists, Lists
+@section Filtering Lists
+@cindex filtering, of list
+@cindex deletion, of list element
+
+@deffn {procedure+} list-transform-positive list predicate
+@deffnx {procedure+} list-transform-negative list predicate
+These procedures return a newly allocated copy of @var{list} containing
+only the elements for which @var{predicate} is (respectively) true or
+false.  @var{Predicate} must be a procedure of one argument.
+@end deffn
+
+@deffn {procedure+} delq element list
+@deffnx {procedure+} delv element list
+@deffnx {procedure+} delete element list
+@findex eq?
+@findex eqv?
+@findex equal?
+Returns a newly allocated copy of @var{list} with all entries equal to
+@var{element} removed.  @code{delq} uses @code{eq?} to compare
+@var{element} with the entries in @var{list}, @code{delv} uses
+@code{eqv?}, and @code{delete} uses @code{equal?}.
+@end deffn
+
+@deffn {procedure+} delq! element list
+@deffnx {procedure+} delv! element list
+@deffnx {procedure+} delete! element list
+@findex eq?
+@findex eqv?
+@findex equal?
+Returns a list consisting of the top-level elements of @var{list} with
+all entries equal to @var{element} removed.  These procedures are like
+@code{delq}, @code{delv}, and @code{delete} except that they
+destructively modify @var{list}.  @code{delq!} uses @code{eq?} to
+compare element with the entries in @var{list}, @code{delv!} uses
+@code{eqv?}, and @code{delete!} uses @code{equal?}.  Because the result
+may not be @code{eq?} to @var{list}, it is desirable to do something
+like @code{(set! x (delete! x))}.
+
+@example
+@group
+(define x '(a b c b))
+(delete 'b x)                           @result{}  (a c)
+x                                       @result{}  (a b c b)
+
+(define x '(a b c b))
+(delete! 'b x)                          @result{}  (a c)
+x                                       @result{}  (a c)
+@r{;; Returns correct result:}
+(delete! 'a x)                          @result{}  (c)
+
+@r{;; Didn't modify what x points to:}
+x                                       @result{}  (a c)
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} delete-member-procedure deletor predicate
+@findex list-deletor
+@findex list-deletor!
+@findex delv
+@findex delete!
+Returns a deletion procedure similar to @code{delv} or @code{delete!}.
+@var{Deletor} should be one of the procedures @code{list-deletor} or
+@code{list-deletor!}.  @var{Predicate} must be an equivalence predicate.
+The returned procedure accepts exactly two arguments: first, an object
+to be deleted, and second, a list of objects from which it is to be
+deleted.  If @var{deletor} is @code{list-deletor}, the procedure
+returns a newly allocated copy of the given list in which all entries
+equal to the given object have been removed.  If @var{deletor} is
+@code{list-deletor!}, the procedure returns a list consisting of the
+top-level elements of the given list with all entries equal to the given
+object removed; the given list is destructively modified to produce the
+result.  In either case @var{predicate} is used to compare the given
+object to the elements of the given list.
+
+Here are some examples that demonstrate how
+@code{delete-member-procedure} could have been used to implement
+@code{delv} and @code{delete!}:
+
+@example
+@group
+(define delv (delete-member-procedure list-deletor eqv?))
+(define delete! (delete-member-procedure list-deletor! equal?))
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} list-deletor predicate
+@deffnx {procedure+} list-deletor! predicate
+These procedures each return a procedure that deletes elements from
+lists.  @var{Predicate} must be a procedure of one argument.  The
+returned procedure accepts exactly one argument, which must be a proper
+list, and applies @var{predicate} to each of the elements of the
+argument, deleting those for which it is true.
+
+The procedure returned by @code{list-deletor} deletes elements
+non-destructively, by returning a newly allocated copy of the argument
+with the appropriate elements removed.  The procedure returned by
+@code{list-deletor!} performs a destructive deletion.
+@end deffn
+
+@node Searching Lists, Mapping of Lists, Filtering Lists, Lists
+@section Searching Lists
+@cindex searching, of list
+
+@deffn {procedure+} list-search-positive list predicate
+@deffnx {procedure+} list-search-negative list predicate
+Returns the first element in @var{list} for which @var{predicate} is
+(respectively) true or false; returns @code{#f} if it doesn't find such
+an element.  (This means that if @var{predicate} is true (false) for
+@code{#f}, it may be impossible to distinguish a successful result from
+an unsuccessful one.)  @var{Predicate} must be a procedure of one
+argument.
+@end deffn
+
+@deffn procedure memq object list
+@deffnx procedure memv object list
+@deffnx procedure member object list
+@findex eq?
+@findex eqv?
+@findex equal?
+These procedures return the first pair of @var{list} whose car is
+@var{object}; the returned pair is always one from which @var{list} is
+composed.  If @var{object} does not occur in @var{list}, @code{#f}
+(n.b.: not the empty list) is returned.  @code{memq} uses @code{eq?} to
+compare @var{object} with the elements of @var{list}, while @code{memv}
+uses @code{eqv?} and @code{member} uses @code{equal?}.@footnote{Although
+they are often used as predicates, @code{memq}, @code{memv}, and
+@code{member} do not have question marks in their names because they
+return useful values rather than just @code{#t} or @code{#f}.}
+
+@example
+@group
+(memq 'a '(a b c))                      @result{}  (a b c)
+(memq 'b '(a b c))                      @result{}  (b c)
+(memq 'a '(b c d))                      @result{}  #f
+(memq (list 'a) '(b (a) c))             @result{}  #f
+(member (list 'a) '(b (a) c))           @result{}  ((a) c)
+(memq 101 '(100 101 102))               @result{}  @r{unspecified}
+(memv 101 '(100 101 102))               @result{}  (101 102)
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} member-procedure predicate
+Returns a procedure similar to @code{memq}, except that @var{predicate},
+which must be an equivalence predicate, is used instead of @code{eq?}.
+This could be used to define @code{memv} as follows:
+
+@example
+(define memv (member-procedure eqv?))
+@end example
+@end deffn
+
+@need 1000
+@node Mapping of Lists, Reduction of Lists, Searching Lists, Lists
+@section Mapping of Lists
+@cindex mapping, of list
+
+@deffn {procedure} map procedure list list @dots{}
+@var{Procedure} must be a procedure taking as many arguments as there
+are @var{list}s.  If more than one @var{list} is given, then they must
+all be the same length.  @code{map} applies @var{procedure} element-wise
+to the elements of the @var{list}s and returns a list of the results, in
+order from left to right.  The dynamic order in which @var{procedure} is
+applied to the elements of the @var{list}s is unspecified; use
+@code{for-each} to sequence side effects.
+
+@example
+@group
+(map cadr '((a b) (d e) (g h)))           @result{}  (b e h)
+(map (lambda (n) (expt n n)) '(1 2 3 4))  @result{}  (1 4 27 256)
+(map + '(1 2 3) '(4 5 6))                 @result{}  (5 7 9)
+(let ((count 0))
+  (map (lambda (ignored)
+         (set! count (+ count 1))
+         count)
+       '(a b c)))                         @result{}  @r{unspecified}
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} map* initial-value procedure list1 list2 @dots{}
+Similar to @code{map}, except that the resulting list is terminated by
+@var{initial-value} rather than the empty list.  The following are
+equivalent:
+
+@example
+@group
+(map @var{procedure} @var{list} @var{list} @dots{})
+(map* '() @var{procedure} @var{list} @var{list} @dots{})
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} append-map procedure list list @dots{}
+@deffnx {procedure+} append-map* initial-value procedure list list @dots{}
+@findex append
+Similar to @code{map} and @code{map*}, respectively, except that the
+results of applying @var{procedure} to the elements of @var{list}s are
+concatenated together by @code{append} rather than by @code{cons}.  The
+following are equivalent, except that the former is more efficient:
+
+@example
+@group
+(append-map @var{procedure} @var{list} @var{list} @dots{})
+(apply append (map @var{procedure} @var{list} @var{list} @dots{}))
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} append-map! procedure list list @dots{}
+@deffnx {procedure+} append-map*! initial-value procedure list list @dots{}
+@findex append!
+Similar to @code{map} and @code{map*}, respectively, except that the
+results of applying @var{procedure} to the elements of @var{list}s are
+concatenated together by @code{append!} rather than by @code{cons}.  The
+following are equivalent, except that the former is more efficient:
+
+@example
+@group
+(append-map! @var{procedure} @var{list} @var{list} @dots{})
+(apply append! (map @var{procedure} @var{list} @var{list} @dots{}))
+@end group
+@end example
+@end deffn
+
+@deffn {procedure} for-each procedure list list @dots{}
+The arguments to @code{for-each} are like the arguments to @code{map},
+but @code{for-each} calls @var{procedure} for its side effects rather
+than for its values.  Unlike @code{map}, @code{for-each} is guaranteed
+to call @var{procedure} on the elements of the @var{list}s in order from
+the first element to the last, and the value returned by @code{for-each}
+is unspecified.
+
+@example
+(let ((v (make-vector 5)))
+  (for-each (lambda (i)
+              (vector-set! v i (* i i)))
+            '(0 1 2 3 4))
+  v)                            @result{}  #(0 1 4 9 16)
+@end example
+@end deffn
+
+@node Reduction of Lists, Miscellaneous List Operations, Mapping of Lists, Lists
+@section Reduction of Lists
+@cindex reduction, of list
+
+@deffn {procedure+} reduce procedure initial list
+Combines all the elements of @var{list} using the binary operation
+@var{procedure}.  For example, using @code{+} one can add up all the
+elements:
+
+@example
+(reduce + 0 list-of-numbers)
+@end example
+
+The argument @var{initial} is used only if @var{list} is empty; in this
+case @var{initial} is the result of the call to @code{reduce}.  If
+@var{list} has a single argument, it is returned.  Otherwise, the arguments
+are reduced in a left-associative fashion.  For example:
+
+@example
+@group
+(reduce + 0 '(1 2 3 4))                 @result{}  10
+(reduce + 0 '(1 2))                     @result{}  3
+(reduce + 0 '(1))                       @result{}  1
+(reduce + 0 '())                        @result{}  0
+(reduce list '() '(1 2 3 4))            @result{}  (((1 2) 3) 4)
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} reduce-right procedure initial list
+Like @code{reduce} except that it is right-associative.
+
+@example
+(reduce-right list '() '(1 2 3 4))      @result{}  (1 (2 (3 4)))
+@end example
+@end deffn
+
+@deffn {procedure+} there-exists? list predicate
+@var{Predicate} must be a procedure of one argument.  Applies
+@var{predicate} to each element of @var{list}, in order from left to
+right.  If @var{predicate} is true for any element of @var{list}, that
+value is immediately returned as the value of @code{there-exists?};
+@var{predicate} will not be applied to the remaining elements of
+@var{list}.  If @var{predicate} returns @code{#f} for all of the
+elements of @var{list}, then @code{#f} is returned.
+@end deffn
+
+@deffn {procedure+} for-all? list predicate
+@var{Predicate} must be a procedure of one argument.  Applies
+@var{predicate} to each element of @var{list}, in order from left to
+right.  If @var{predicate} returns @code{#f} for any element of
+@var{list}, @code{#f} is immediately returned as the value of
+@code{for-all?}; @var{predicate} will not be applied to the remaining
+elements of @var{list}.  If @var{predicate} is true for all of the
+elements of @var{list}, then @code{#t} is returned.
+@end deffn
+
+@node Miscellaneous List Operations,  , Reduction of Lists, Lists
+@section Miscellaneous List Operations
+
+@deffn {procedure+} circular-list object @dots{}
+@deffnx {procedure+} make-circular-list k [element]
+@cindex circular list
+@cindex construction, of circular list
+@findex list
+@findex make-list
+These procedures are like @code{list} and @code{make-list},
+respectively, except that the returned lists are circular.
+@code{circular-list} could have been defined like this:
+
+@example
+@group
+(define (circular-list . objects)
+  (append! objects objects))
+@end group
+@end example
+@end deffn
+
+@deffn procedure reverse list
+@cindex reversal, of list
+Returns a newly allocated list consisting of the top-level elements of
+@var{list} in reverse order.
+
+@example
+@group
+(reverse '(a b c))                      @result{}  (c b a)
+(reverse '(a (b c) d (e (f))))          @result{}  ((e (f)) d (b c) a)
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} reverse! list
+Returns a list consisting of the top-level elements of @var{list} in
+reverse order.  @code{reverse!} is like @code{reverse}, except that it
+destructively modifies @var{list}.  Because the result may not be
+@code{eqv?} to @var{list}, it is desirable to do something like
+@code{(set! x (reverse! x))}.
+@end deffn
+
+@deffn {procedure+} last-pair list
+Returns the last pair in @var{list}, which may be an improper list.
+@code{last-pair} could have been defined this way:
+
+@example
+@group
+(define last-pair
+  (lambda (x)
+    (if (pair? (cdr x))
+        (last-pair (cdr x))
+        x)))
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} except-last-pair list
+@deffnx {procedure+} except-last-pair! list
+These procedures remove the last pair from @var{list}.  @var{List} may
+be an improper list, except that it must consist of at least one pair.
+@code{except-last-pair} returns a newly allocated copy of @var{list}
+that omits the last pair.  @code{except-last-pair!} destructively
+removes the last pair from @var{list} and returns @var{list}.  If the
+cdr of @var{list} is not a pair, the empty list is returned by either
+procedure.
+@end deffn
+
+@deffn {procedure+} sort list procedure
+@cindex total ordering (defn)
+@var{Procedure} must be a procedure of two arguments that defines a
+@dfn{total ordering} on the elements of @var{list}.  In other words, if
+@var{x} and @var{y} are two distinct elements of @var{list}, then it
+must be the case that
+
+@example
+@group
+(and (@var{procedure} @var{x} @var{y})
+     (@var{procedure} @var{y} @var{x}))
+     @result{}  #f
+@end group
+@end example
+
+@code{sort} returns a newly allocated list whose elements are the
+elements of @var{list}, except that the elements are rearranged so that
+they are sorted in the order defined by @var{procedure}.  So, for
+example, if the elements of @var{list} are numbers, and @var{procedure}
+is @code{<}, then the resulting list is sorted in monotonically
+nondecreasing order.  Likewise, if @var{procedure} is @code{>}, the
+resulting list is sorted in monotonically nonincreasing order.  To be
+precise, if @var{x} and @var{y} are any two adjacent elements in the
+resulting list, where @var{x} precedes @var{y}, it is the case that
+
+@example
+@group
+(@var{procedure} @var{y} @var{x})
+     @result{}  #f
+@end group
+@end example
+@end deffn
+
+@node Vectors, Bit Strings, Lists, Top
+@chapter Vectors
+
+@cindex vector (defn)
+@dfn{Vectors} are heterogenous structures whose elements are indexed by
+exact non-negative integers.  A vector typically occupies less space
+than a list of the same length, and the average time required to access
+a randomly chosen element is typically less for the vector than for the
+list.
+
+@cindex length, of vector (defn)
+@cindex index, of vector (defn)
+@cindex valid index, of vector (defn)
+@cindex vector length (defn)
+@cindex vector index (defn)
+The @dfn{length} of a vector is the number of elements that it contains.
+This number is an exact non-negative integer that is fixed when the
+vector is created.  The @dfn{valid indexes} of a vector are the exact
+non-negative integers less than the length of the vector.  The first
+element in a vector is indexed by zero, and the last element is indexed
+by one less than the length of the vector.
+
+@cindex external representation, for vector
+@cindex #( as external representation
+@cindex parenthesis, as external representation
+@findex #(
+Vectors are written using the notation @code{#(@var{object} @dots{})}.
+For example, a vector of length 3 containing the number zero in element
+0, the list @code{(2 2 2 2)} in element 1, and the string @code{"Anna"}
+in element 2 can be written as
+
+@example
+#(0 (2 2 2 2) "Anna")
+@end example
+
+@noindent
+Note that this is the external representation of a vector, not an
+expression evaluating to a vector.  Like list constants, vector
+constants must be quoted:
+
+@example
+'#(0 (2 2 2 2) "Anna")          @result{}  #(0 (2 2 2 2) "Anna")
+@end example
+
+@cindex subvector (defn)
+@cindex start, of subvector (defn)
+@cindex end, of subvector (defn)
+A number of the vector procedures operate on subvectors.  A
+@dfn{subvector} is a segment of a vector, which is specified by two
+exact non-negative integers, @var{start} and @var{end}.  @var{Start} is
+the index of the first element that is included in the subvector, and
+@var{end} is one greater than the index of the last element that is
+included in the subvector.  Thus if @var{start} and @var{end} are the
+same, they refer to a null subvector, and if @var{start} is zero and
+@var{end} is the length of the vector, they refer to the entire vector.
+
+@menu
+* Construction of Vectors::     Construction of Vectors
+* Selecting Vector Components::  Selecting Vector Components
+* Cutting Vectors::             Cutting Vectors
+* Modifying Vectors::           Modifying Vectors
+@end menu
+
+@node Construction of Vectors, Selecting Vector Components, Vectors, Vectors
+@section Construction of Vectors
+@cindex construction, of vector
+
+@deffn {procedure} make-vector k [object]
+Returns a newly allocated vector of @var{k} elements.  If @var{object}
+is specified, @code{make-vector} initializes each element of the vector
+to @var{object}.  Otherwise the initial elements of the result are
+unspecified.
+@end deffn
+
+@deffn procedure vector object @dots{}
+@findex list
+Returns a newly allocated vector whose elements are the given arguments.
+@code{vector} is analogous to @code{list}.
+
+@example
+(vector 'a 'b 'c)                       @result{}  #(a b c)
+@end example
+@end deffn
+
+@deffn {procedure+} vector-copy vector
+@cindex copying, of vector
+Returns a newly allocated vector that is a copy of @var{vector}.
+@end deffn
+
+@deffn procedure list->vector list
+@cindex list, converting to vector
+@findex vector->list
+Returns a newly allocated vector initialized to the elements of
+@var{list}.  The inverse of @code{list->vector} is @code{vector->list}.
+
+@example
+(list->vector '(dididit dah))           @result{}  #(dididit dah)
+@end example
+@end deffn
+
+@deffn {procedure+} make-initialized-vector k initialization
+Similar to @code{make-vector}, except that the elements of the result
+are determined by calling the procedure @var{initialization} on the
+indices.  For example:
+
+@example
+@group
+(make-initialized-vector 5 (lambda (x) (* x x)))
+     @result{}  #(0 1 4 9 16)
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} vector-grow vector k
+@cindex growing, of vector
+@var{K} must be greater than or equal to the length of @var{vector}.
+Returns a newly allocated vector of length @var{k}.  The first
+@code{(vector-length @var{vector})} elements of the result are
+initialized from the corresponding elements of @var{vector}.  The
+remaining elements of the result are unspecified.
+@end deffn
+
+@node Selecting Vector Components, Cutting Vectors, Construction of Vectors, Vectors
+@section Selecting Vector Components
+@cindex selection, of vector component
+@cindex component selection, of vector
+
+@deffn procedure vector? object
+@cindex type predicate, for vector
+Returns @code{#t} if @var{object} is a vector; otherwise returns
+@code{#f}.
+@end deffn
+
+@deffn procedure vector-length vector
+Returns the number of elements in @var{vector}.
+@end deffn
+
+@deffn procedure vector-ref vector k
+Returns the contents of element @var{k} of @var{vector}.  @var{K} must
+be a valid index of @var{vector}.
+
+@example
+(vector-ref '#(1 1 2 3 5 8 13 21) 5)    @result{}  8
+@end example
+@end deffn
+
+@deffn procedure vector-set! vector k object
+Stores @var{object} in element @var{k} of @var{vector} and returns an
+unspecified value.  @var{K} must be a valid index of
+@var{vector}.
+
+@example
+@group
+(let ((vec (vector 0 '(2 2 2 2) "Anna")))
+  (vector-set! vec 1 '("Sue" "Sue"))
+  vec)
+     @result{}  #(0 ("Sue" "Sue") "Anna")
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} vector-first vector
+@deffnx {procedure+} vector-second vector
+@deffnx {procedure+} vector-third vector
+@deffnx {procedure+} vector-fourth vector
+@deffnx {procedure+} vector-fifth vector
+@deffnx {procedure+} vector-sixth vector
+@deffnx {procedure+} vector-seventh vector
+@deffnx {procedure+} vector-eighth vector
+These procedures access the first several elements of @var{vector} in
+the obvious way.  It is an error if @var{vector}'s length is too small.
+@end deffn
+
+@node Cutting Vectors, Modifying Vectors, Selecting Vector Components, Vectors
+@section Cutting Vectors
+@cindex cutting, of vector
+
+@deffn {procedure+} subvector vector start end
+Returns a newly allocated vector that contains the elements of
+@var{vector} between index @var{start} (inclusive) and @var{end}
+(exclusive).
+@end deffn
+
+@deffn {procedure+} vector-head vector end
+Equivalent to
+
+@example
+(subvector @var{vector} 0 @var{end})
+@end example
+@end deffn
+
+@deffn {procedure+} vector-tail vector start
+Equivalent to
+
+@example
+(subvector @var{vector} @var{start} (vector-length @var{vector}))
+@end example
+@end deffn
+
+@node Modifying Vectors,  , Cutting Vectors, Vectors
+@section Modifying Vectors
+@cindex modification, of vector
+@cindex filling, of vector
+@cindex moving, of vector elements
+
+@deffn {procedure} vector-fill! vector object
+@deffnx {procedure+} subvector-fill! vector start end object
+Stores @var{object} in every element of the vector (subvector) and
+returns an unspecified value.
+@end deffn
+
+@deffn {procedure+} subvector-move-left! vector1 start1 end1 vector2 start2
+@deffnx {procedure+} subvector-move-right! vector1 start1 end1 vector2 start2
+Destructively copies the elements of @var{vector1}, starting with index
+@var{start1} (inclusive) and ending with @var{end1} (exclusive), into
+@var{vector2} starting at index @var{start2} (inclusive).
+@var{Vector1}, @var{start1}, and @var{end1} must be valid subvector, and
+@var{start2} must be a valid index for @var{vector2}.  The length of the
+source subvector must not exceed the length of @var{vector2} minus the
+index @var{start2}.
+
+The elements are copied as follows (note that this is only important when
+@var{vector1} and @var{vector2} are @code{eqv?}):
+
+@table @code
+@item subvector-move-left!
+The copy starts at the left end and moves toward the right (from smaller
+indices to larger).  Thus if @var{vector1} and @var{vector2} are the
+same, this procedure moves the elements toward the left inside the
+vector.
+
+@item subvector-move-right!
+The copy starts at the right end and moves toward the left (from larger
+indices to smaller).  Thus if @var{vector1} and @var{vector2} are the
+same, this procedure moves the elements toward the right inside the
+vector.
+@end table
+@end deffn
+
+@node Bit Strings, Miscellaneous Datatypes, Vectors, Top
+@chapter Bit Strings
+
+@cindex bit string (defn)
+@cindex string, of bits (defn)
+A @dfn{bit string} is a sequence of bits.  Bit strings can be used to
+represent sets or to manipulate binary data.  The elements of a bit
+string are numbered from zero up to the number of bits in the string
+less one, in @emph{right to left order}, (the rightmost bit is numbered
+zero).  When you convert from a bit string to an integer, the zero-th
+bit is associated with the zero-th power of two, the first bit is
+associated with the first power, and so on.
+
+@cindex length, of bit string (defn)
+@cindex index, of bit string (defn)
+@cindex valid index, of bit string (defn)
+@cindex bit string length (defn)
+@cindex bit string index (defn)
+The @dfn{length} of a bit string is the number of bits that it contains.
+This number is an exact non-negative integer that is fixed when the bit
+string is created.  The @dfn{valid indexes} of a bit string are the
+exact non-negative integers less than the length of the bit string.
+
+@cindex external representation, for bit string
+@cindex #* as external representation
+@cindex asterisk, as external representation
+Bit strings may contain zero or more bits.  They are not limited by the
+length of a machine word.  In the printed representation of a bit
+string, the contents of the bit string are preceded by @samp{#*}.  The
+contents are printed starting with the most significant bit (highest
+index).
+
+Note that the external representation of bit strings uses a bit ordering
+that is the reverse of the representation for bit strings in Common
+Lisp.  It is likely that MIT Scheme's representation will be
+changed in the future, to be compatible with Common Lisp.  For the time
+being this representation should be considered a convenience for viewing
+bit strings rather than a means of entering them as data.
+
+@example
+@group
+#*11111
+#*1010
+#*00000000
+#*
+@end group
+@end example
+
+All of the bit-string procedures are MIT Scheme extensions.
+
+@menu
+* Construction of Bit Strings::  Construction of Bit Strings
+* Selecting Bit String Components::  Selecting Bit String Components
+* Cutting and Pasting Bit Strings::  Cutting and Pasting Bit Strings
+* Bitwise Operations on Bit Strings::  Bitwise Operations on Bit Strings
+* Modification of Bit Strings::  Modification of Bit Strings
+* Integer Conversions of Bit Strings::  Integer Conversions of Bit Strings
+@end menu
+
+@node Construction of Bit Strings, Selecting Bit String Components, Bit Strings, Bit Strings
+@section Construction of Bit Strings
+@cindex construction, of bit string
+
+@deffn {procedure+} make-bit-string k initialization
+Returns a newly allocated bit string of length @var{k}.  If
+@var{initialization} is @code{#f}, the bit string is filled with 0 bits;
+otherwise, the bit string is filled with 1 bits.
+
+@example
+(make-bit-string 7 #f)                  @result{}  #*0000000
+@end example
+@end deffn
+
+@deffn {procedure+} bit-string-allocate k
+Returns a newly allocated bit string of length @var{k}, but does not
+initialize it.
+@end deffn
+
+@deffn {procedure+} bit-string-copy bit-string
+@cindex copying, of bit string
+Returns a newly allocated copy of @var{bit-string}.
+@end deffn
+
+@node Selecting Bit String Components, Cutting and Pasting Bit Strings, Construction of Bit Strings, Bit Strings
+@section Selecting Bit String Components
+
+@deffn {procedure+} bit-string? object
+@cindex type predicate, for bit string
+Returns @code{#t} if @var{object} is a bit string; otherwise returns
+@code{#f}.
+@end deffn
+
+@deffn {procedure+} bit-string-length bit-string
+@cindex length, of bit string
+Returns the length of @var{bit-string}.
+@end deffn
+
+@deffn {procedure+} bit-string-ref bit-string k
+@cindex selection, of bit string component
+@cindex component selection, of bit string
+Returns @code{#t} if the @var{k}th bit is 1; otherwise returns
+@code{#f}.  @var{K} must be a valid index of @var{bit-string}.
+@end deffn
+
+@deffn {procedure+} bit-string-set! bit-string k
+Sets the @var{k}th bit in @var{bit-string} to 1 and returns an
+unspecified value.  @var{K} must be a valid index of @var{bit-string}.
+@end deffn
+
+@deffn {procedure+} bit-string-clear! bit-string k
+Sets the @var{k}th bit in @var{bit-string} to 0 and returns an
+unspecified value.  @var{K} must be a valid index of @var{bit-string}.
+@end deffn
+
+@node Cutting and Pasting Bit Strings, Bitwise Operations on Bit Strings, Selecting Bit String Components, Bit Strings
+@section Cutting and Pasting Bit Strings
+@cindex cutting, of bit string
+@cindex pasting, of bit strings
+
+@deffn {procedure+} bit-string-append bit-string-1 bit-string-2
+@cindex appending, of bit strings
+Appends the two bit string arguments, returning a newly allocated bit
+string as its result.  In the result, the bits copied from
+@var{bit-string-1} are less significant (smaller indices) than those
+copied from @var{bit-string-2}.
+@end deffn
+
+@deffn {procedure+} bit-substring bit-string start end
+@cindex substring, of bit string
+Returns a newly allocated bit string whose bits are copied from
+@var{bit-string}, starting at index @var{start} (inclusive) and ending
+at @var{end} (exclusive).
+@end deffn
+
+@node Bitwise Operations on Bit Strings, Modification of Bit Strings, Cutting and Pasting Bit Strings, Bit Strings
+@section Bitwise Operations on Bit Strings
+
+@deffn {procedure+} bit-string-zero? bit-string
+Returns @code{#t} if @var{bit-string} contains only 0 bits; otherwise
+returns @code{#f}.
+@end deffn
+
+@deffn {procedure+} bit-string=? bit-string-1 bit-string-2
+@cindex equivalence predicate, for bit strings
+@cindex comparison, of bit strings
+Compares the two bit string arguments and returns @code{#t} if they are the
+same length and contain the same bits; otherwise returns @code{#f}.
+@end deffn
+
+@deffn {procedure+} bit-string-not bit-string
+@cindex inverse, of bit string
+Returns a newly allocated bit string that is the bitwise-logical
+negation of @var{bit-string}.
+@end deffn
+
+@deffn {procedure+} bit-string-movec! target-bit-string bit-string
+The destructive version of @code{bit-string-not}.  The arguments
+@var{target-bit-string} and @var{bit-string} must be bit strings of the
+same length.  The bitwise-logical negation of @var{bit-string} is
+computed and the result placed in @var{target-bit-string}.  The value of
+this procedure is unspecified.
+@end deffn
+
+@deffn {procedure+} bit-string-and bit-string-1 bit-string-2
+Returns a newly allocated bit string that is the bitwise-logical ``and''
+of the arguments.  The arguments must be bit strings of identical
+length.
+@end deffn
+
+@deffn {procedure+} bit-string-andc bit-string-1 bit-string-2
+Returns a newly allocated bit string that is the bitwise-logical ``and''
+of @var{bit-string-1} with the bitwise-logical negation of
+@var{bit-string-2}.  The arguments must be bit strings of identical
+length.
+@end deffn
+
+@deffn {procedure+} bit-string-or bit-string-1 bit-string-2
+Returns a newly allocated bit string that is the bitwise-logical
+``inclusive or'' of the arguments.  The arguments must be bit strings of
+identical length.
+@end deffn
+
+@deffn {procedure+} bit-string-xor bit-string-1 bit-string-2
+Returns a newly allocated bit string that is the bitwise-logical
+``exclusive or'' of the arguments.  The arguments must be bit strings of
+identical length.
+@end deffn
+
+@deffn {procedure+} bit-string-and! target-bit-string bit-string
+@deffnx {procedure+} bit-string-or! target-bit-string bit-string
+@deffnx {procedure+} bit-string-xor! target-bit-string bit-string
+@deffnx {procedure+} bit-string-andc! target-bit-string bit-string
+These are destructive versions of the above operations.  The arguments
+@var{target-bit-string} and @var{bit-string} must be bit strings of the
+same length.  Each of these procedures performs the corresponding
+bitwise-logical operation on its arguments, places the result into
+@var{target-bit-string}, and returns an unspecified result.
+@end deffn
+
+@node Modification of Bit Strings, Integer Conversions of Bit Strings, Bitwise Operations on Bit Strings, Bit Strings
+@section Modification of Bit Strings
+@cindex modification, of bit string
+@cindex filling, of bit string
+@cindex moving, of bit string elements
+
+@deffn {procedure+} bit-string-fill! bit-string initialization
+Fills @var{bit-string} with zeroes if @var{initialization} is @code{#f};
+otherwise fills @var{bit-string} with ones.  Returns an unspecified
+value.
+@end deffn
+
+@deffn {procedure+} bit-string-move! target-bit-string bit-string
+Moves the contents of @var{bit-string} into @var{target-bit-string}.  Both
+arguments must be bit strings of the same length.  The results of the
+operation are undefined if the arguments are the same bit string.
+@end deffn
+
+@deffn {procedure+} bit-substring-move-right! bit-string-1 start1 end1 bit-string-2 start2
+Destructively copies the bits of @var{bit-string-1}, starting at index
+@var{start1} (inclusive) and ending at @var{end1} (exclusive), into
+@var{bit-string-2} starting at index @var{start2} (inclusive).
+@var{Start1} and @var{end1} must be valid substring indices for
+@var{bit-string-1}, and @var{start2} must be a valid index for
+@var{bit-string-2}.  The length of the source substring must not exceed
+the length of @var{bit-string-2} minus the index @var{start2}.
+
+The bits are copied starting from the MSB and working towards the LSB; the
+direction of copying only matters when @var{bit-string-1} and
+@var{bit-string-2} are @code{eqv?}.
+@end deffn
+
+@need 1000
+@node Integer Conversions of Bit Strings,  , Modification of Bit Strings, Bit Strings
+@section Integer Conversions of Bit Strings
+@cindex integer, converting to bit string
+
+@deffn {procedure+} unsigned-integer->bit-string length integer
+Both @var{length} and @var{integer} must be exact non-negative integers.
+Converts @var{integer} into a newly allocated bit string of @var{length}
+bits.  Signals an error if @var{integer} is too large to be represented
+in @var{length} bits.
+@end deffn
+
+@deffn {procedure+} signed-integer->bit-string length integer
+@var{Length} must be an exact non-negative integer, and @var{integer}
+may be any exact integer.  Converts @var{integer} into a newly allocated
+bit string of @var{length} bits, using two's complement encoding for
+negative numbers.  Signals an error if @var{integer} is too large to be
+represented in @var{length} bits.
+@end deffn
+
+@deffn {procedure+} bit-string->unsigned-integer bit-string
+@deffnx {procedure+} bit-string->signed-integer bit-string
+Converts @var{bit-string} into an exact integer.
+@code{bit-string->signed-integer} regards @var{bit-string} as a two's
+complement representation of a signed integer, and produces an integer
+of like sign and absolute value.  @code{bit-string->unsigned-integer}
+regards @var{bit-string} as an unsigned quantity and converts to an
+integer accordingly.
+@end deffn
+
+@node Miscellaneous Datatypes, Associations, Bit Strings, Top
+@chapter Miscellaneous Datatypes
+
+@menu
+* Booleans::                    Booleans
+* Symbols::                     Symbols
+* Cells::                       Cells
+* Records::                     Records
+* Promises::                    Promises
+* Streams::                     Streams
+* Weak Pairs::                  Weak Pairs
+@end menu
+
+@node Booleans, Symbols, Miscellaneous Datatypes, Miscellaneous Datatypes
+@section Booleans
+
+@findex #t
+@findex #f
+@cindex #t as external representation
+@cindex #f as external representation
+@cindex boolean object (defn)
+@cindex true, boolean object (defn)
+@cindex false, boolean object (defn)
+The @dfn{boolean objects} are @dfn{true} and @dfn{false}.  The boolean
+constant true is written as @samp{#t}, and the boolean constant false is
+written as @samp{#f}.
+
+@findex if
+@findex cond
+@findex and
+@findex or
+The primary use for boolean objects is in the conditional expressions
+@code{if}, @code{cond}, @code{and}, and @code{or}; the behavior of these
+expressions is determined by whether objects are true or false.  These
+expressions count only @code{#f} as false.  They count everything else,
+including @code{#t}, pairs, symbols, numbers, strings, vectors, and
+procedures as true (but @pxref{True and False}).
+
+@findex t
+@findex nil
+Programmers accustomed to other dialects of Lisp should note that Scheme
+distinguishes @code{#f} and the empty list from the symbol @code{nil}.
+Similarly, @code{#t} is distinguished from the symbol @code{t}.  In
+fact, the boolean objects (and the empty list) are not symbols at all.
+
+Boolean constants evaluate to themselves, so you don't need to quote
+them.
+
+@example
+@group
+#t                                      @result{}  #t
+#f                                      @result{}  #f
+'#f                                     @result{}  #f
+t                                       @error{} Unbound variable
+@end group
+@end example
+
+@defvr {variable+} false
+@defvrx {variable+} true
+These variables are bound to the objects @code{#f} and @code{#t}
+respectively.  The compiler, given some standard declarations, replaces
+references to these variables with their respective values.
+
+Note that the symbol @code{true} is not equivalent to @code{#t}, and the
+symbol @code{false} is not equivalent to @code{#f}.
+@end defvr
+
+@deffn procedure boolean? object
+@cindex type predicate, for boolean
+Returns @code{#t} if @var{object} is either @code{#t} or @code{#f};
+otherwise returns @code{#f}.
+
+@example
+(boolean? #f)                           @result{}  #t
+(boolean? 0)                            @result{}  #f
+@end example
+@end deffn
+
+@deffn procedure not object
+@deffnx {procedure+} false? object
+@cindex false, predicate for
+@cindex inverse, of boolean object
+These procedures returns @code{#t} if @var{object} is false; otherwise
+they return @code{#f}.  In other words they @emph{invert} boolean
+values.  These two procedures have identical semantics; their names are
+different to give different connotations to the test.
+
+@example
+(not #t)                                @result{}  #f
+(not 3)                                 @result{}  #f
+(not (list 3))                          @result{}  #f
+(not #f)                                @result{}  #t
+@end example
+@end deffn
+
+@deffn {procedure+} boolean=? obj1 obj2
+@cindex boolean object, equivalence predicate
+@cindex equivalence predicate, for boolean objects
+@cindex comparison, of boolean objects
+This predicate is true iff @var{obj1} and @var{obj2} are either both true
+or both false.
+@end deffn
+
+@deffn {procedure+} boolean/and object @dots{}
+This procedure returns @code{#t} if none of its arguments are @code{#f}.
+Otherwise it returns @code{#f}.
+@end deffn
+
+@deffn {procedure+} boolean/or object @dots{}
+This procedure returns @code{#f} if all of its arguments are @code{#f}.
+Otherwise it returns @code{#t}.
+@end deffn
+
+@node Symbols, Cells, Booleans, Miscellaneous Datatypes
+@section Symbols
+
+@cindex symbol (defn)
+@cindex interned symbol (defn)
+@cindex uninterned symbol (defn)
+@cindex property list, of symbol
+@cindex disembodied property list
+@findex read
+MIT Scheme provides two types of symbols: @dfn{interned} and
+@dfn{uninterned}.  Interned symbols are far more common than uninterned
+symbols, and there are more ways to create them.  Interned symbols have
+an external representation that is recognized by the procedure
+@code{read}; uninterned symbols do not.@footnote{In older dialects of
+Lisp, uninterned symbols were fairly important.  This was true because
+symbols were complicated data structures: in addition to having value
+cells (and sometimes, function cells), these structures contained
+@dfn{property lists}.  Because of this, uninterned symbols were often
+used merely for their property lists --- sometimes an uninterned symbol
+used this way was referred to as a @dfn{disembodied property list}.  In
+MIT Scheme, symbols do not have property lists, or any other components
+besides their names.  There is a different data structure similar to
+disembodied property lists: one-dimensional tables (@pxref{1D Tables}).
+For these reasons, uninterned symbols are not very useful in MIT Scheme.
+In fact, their primary purpose is to simplify the generation of unique
+variable names in programs that generate Scheme code.}
+
+@findex string=?
+@findex eqv?
+Interned symbols have an extremely useful property: any two interned
+symbols whose names are the same, in the sense of @code{string=?}, are
+the same object (i.e.@: they are @code{eqv?} to one another).  The term
+@dfn{interned} refers to the process of @dfn{interning} by which this is
+accomplished.  Uninterned symbols do not share this property.
+
+@cindex case, of interned symbol
+@cindex alphabetic case, of interned symbol
+@findex write
+The names of interned symbols are not distinguished by their alphabetic
+case.  Because of this, MIT Scheme converts all alphabetic
+characters in the name of an interned symbol to a specific case (lower
+case) when the symbol is created.  When the name of an interned symbol
+is referenced (using @code{symbol->string}) or written (using
+@code{write}) it appears in this case.  It is a bad idea to depend on
+the name being lower case.  In fact, it is preferable to take this one
+step further: don't depend on the name of a symbol being in a uniform
+case.
+
+@cindex external representation, for symbol
+@findex read
+@findex write
+The rules for writing an interned symbol are the same as the rules for
+writing an identifier (@pxref{Identifiers}).  Any interned symbol that
+has been returned as part of a literal expression, or read using the
+@code{read} procedure and subsequently written out using the
+@code{write} procedure, will read back in as the identical symbol (in
+the sense of @code{eqv?}).
+
+Usually it is also true that reading in an interned symbol that was
+previously written out produces the same symbol.  An exception are
+symbols created by the procedures @code{string->symbol} and
+@code{intern}; they can create symbols for which this write/read
+invariance may not hold because the symbols' names contain special
+characters or letters in the non-standard case.@footnote{MIT Scheme
+reserves a specific set of interned symbols for its own use.  If you use
+these reserved symbols it is possible that you could break specific
+pieces of software that depend on them.  The reserved symbols all have
+names beginning with the characters @samp{#[} and ending with the
+character @samp{]}; thus none of these symbols can be read by the
+procedure @code{read} and hence are not likely to be used by accident.
+For example, @code{(intern "#[unnamed-procedure]")} produces a reserved
+symbol.}
+
+@findex read
+The external representation for uninterned symbols is special, to
+distinguish them from interned symbols and prevent them from being
+recognized by the @code{read} procedure:
+
+@example
+@group
+(string->uninterned-symbol "foo")
+     @result{}  #[uninterned-symbol 30 foo]
+@end group
+@end example
+
+In this section, the procedures that return symbols as values will
+either always return interned symbols, or always return uninterned
+symbols.  The procedures that accept symbols as arguments will always
+accept either interned or uninterned symbols, and do not distinguish the
+two.
+
+@deffn procedure symbol? object
+@cindex type predicate, for symbol
+Returns @code{#t} if @var{object} is a symbol, otherwise returns
+@code{#f}.
+
+@example
+@group
+(symbol? 'foo)                                  @result{}  #t
+(symbol? (car '(a b)))                          @result{}  #t
+(symbol? "bar")                                 @result{}  #f
+@end group
+@end example
+@end deffn
+
+@deffn procedure symbol->string symbol
+@cindex name, of symbol
+@cindex print name, of symbol
+@findex string=?
+@findex string-set!
+Returns the name of @var{symbol} as a string.  If @var{symbol} was
+returned by @code{string->symbol}, the value of this procedure will be
+identical (in the sense of @code{string=?}) to the string that was
+passed to @code{string->symbol}.  It is an error to apply mutation
+procedures such as @code{string-set!} to strings returned by this
+procedure.
+
+@example
+@group
+(symbol->string 'flying-fish)           @result{}  "flying-fish"
+(symbol->string 'Martin)                @result{}  "martin"
+(symbol->string (string->symbol "Malvina"))
+                                        @result{}  "Malvina"
+@end group
+@end example
+
+Note that two distinct uninterned symbols can have the same name.
+@end deffn
+
+@deffn {procedure+} intern string
+@cindex interning, of symbols
+@cindex construction, of symbols
+Returns the interned symbol whose name is @var{string}.  Converts
+@var{string} to the standard alphabetic case before generating the
+symbol.  This is the preferred way to create interned symbols, as it
+guarantees the following independent of which case the implementation
+uses for symbols' names:
+
+@example
+(eq? 'bitBlt (intern "bitBlt")) @result{}     #t
+@end example
+
+The user should take care that @var{string} obeys the rules for
+identifiers (@pxref{Identifiers}), otherwise the resulting symbol cannot
+be read as itself.
+@end deffn
+
+@deffn procedure string->symbol string
+@cindex string, interning as symbol
+Returns the interned symbol whose name is @var{string}.  Although you
+can use this procedure to create symbols with names containing special
+characters or lowercase letters, it's usually a bad idea to create such
+symbols because they cannot be read as themselves.  See
+@code{symbol->string}.
+
+@example
+@group
+(eq? 'mISSISSIppi 'mississippi)         @result{}  #t
+(string->symbol "mISSISSIppi")
+     @result{}  @r{the symbol with the name} "mISSISSIppi"
+(eq? 'bitBlt (string->symbol "bitBlt")) @result{}  #f
+(eq? 'JollyWog
+      (string->symbol
+        (symbol->string 'JollyWog)))    @result{}  #t
+(string=? "K. Harper, M.D."
+           (symbol->string
+             (string->symbol
+               "K. Harper, M.D.")))     @result{}  #t
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} string->uninterned-symbol string
+Returns a newly allocated uninterned symbol whose name is @var{string}.
+It is unimportant what case or characters are used in
+@var{string}.
+
+Note: this is the fastest way to make a symbol.
+@end deffn
+
+@deffn {procedure+} generate-uninterned-symbol [object]
+@cindex gensym (see uninterned symbol)
+@findex eqv?
+Returns a newly allocated uninterned symbol that is guaranteed not to be
+@code{eqv?} to any other object in the Scheme system.  The symbol's name
+consists of a string (initially @code{"G"}) followed by an integer that
+is incremented on every call (the integer is initially 0).  The optional
+@var{object} can be an integer or a symbol.  If @var{object} is a
+symbol, the string prefix of all subsequently generated symbol names
+will be that symbol's name.  If @var{object} is an integer, the integer
+suffix of all subsequently generated symbol names will start counting
+from that value.
+
+@example
+@group
+(generate-uninterned-symbol)
+     @result{}  #[uninterned-symbol 31 g0]
+(generate-uninterned-symbol)
+     @result{}  #[uninterned-symbol 32 g1]
+(generate-uninterned-symbol 'this)
+     @result{}  #[uninterned-symbol 33 this2]
+(generate-uninterned-symbol)
+     @result{}  #[uninterned-symbol 34 this3]
+(generate-uninterned-symbol 100)
+     @result{}  #[uninterned-symbol 35 this100]
+(generate-uninterned-symbol)
+     @result{}  #[uninterned-symbol 36 this101]
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} symbol-append symbol @dots{}
+@cindex appending, of symbols
+@cindex pasting, of symbols
+Returns the interned symbol whose name is formed by concatenating the
+names of the given symbols.  This procedure preserves the case of the
+names of its arguments, so if one or more of the arguments' names has
+non-standard case, the result will also have non-standard case.
+
+@example
+(symbol-append 'foo- 'bar)              @result{}  foo-bar
+@r{;; the arguments may be uninterned:}
+(symbol-append 'foo- (string->uninterned-symbol "baz"))
+                                        @result{}  foo-baz
+@r{;; the result has the same case as the arguments:}
+(symbol-append 'foo- (string->symbol "BAZ"))    @result{}  foo-BAZ
+@end example
+@end deffn
+
+@deffn {procedure+} symbol-hash symbol
+@cindex hashing, of symbol
+@findex string-hash
+Returns a hash number for @var{symbol}, which is computed by calling
+@code{string-hash} on @var{symbol}'s name.
+@end deffn
+
+@node Cells, Records, Symbols, Miscellaneous Datatypes
+@section Cells
+
+@cindex cell (defn)
+@dfn{Cells} are data structures similar to pairs except that they have
+only one element.  They are useful for managing state.
+
+@deffn {procedure+} cell? object
+@cindex type predicate, for cell
+Returns @code{#t} if @var{object} is a cell; otherwise returns
+@code{#f}.
+@end deffn
+
+@deffn {procedure+} make-cell object
+@cindex construction, of cell
+Returns a newly allocated cell whose contents is @var{object}.
+@end deffn
+
+@deffn {procedure+} cell-contents cell
+@cindex selection, of cell component
+@cindex component selection, of cell
+Returns the current contents of @var{cell}.
+@end deffn
+
+@deffn {procedure+} set-cell-contents! cell object
+Alters the contents of @var{cell} to be @var{object}.  Returns an
+unspecified value.
+@end deffn
+
+@deffn {procedure+} bind-cell-contents! cell object thunk
+Alters the contents of @var{cell} to be @var{object}, calls @var{thunk}
+with no arguments, then restores the original contents of @var{cell} and
+returns the value returned by @var{thunk}.  This is completely
+equivalent to fluid binding of a variable, including the behavior when
+continuations are used (@pxref{Fluid Binding}).
+@end deffn
+
+@node Records, Promises, Cells, Miscellaneous Datatypes
+@section Records
+
+MIT Scheme provides a @dfn{record} abstraction, which is a simple and
+flexible mechanism for building structures with named components.  This
+abstraction will very likely be a part of the next edition of the Scheme
+standard.  The procedures defined in this section that are expected to
+be in the standard are not marked with @samp{+}.
+
+@deffn {procedure} make-record-type type-name field-names
+@cindex record-type descriptor (defn)
+Returns a @dfn{record-type descriptor}, a value representing a new data
+type, disjoint from all others.  The @var{type-name} argument must be a
+string, but is only used for debugging purposes (such as the printed
+representation of a record of the new type).  The @var{field-names}
+argument is a list of symbols naming the @dfn{fields} of a record of the
+new type.  It is an error if the list contains any duplicates.  It is
+unspecified how record-type descriptors are represented.
+@end deffn
+
+@deffn {procedure} record-constructor record-type [field-names]
+Returns a procedure for constructing new members of the type represented
+by @var{record-type}.  The returned procedure accepts exactly as many
+arguments as there are symbols in the given list, @var{field-names};
+these are used, in order, as the initial values of those fields in a new
+record, which is returned by the constructor procedure.  The values of
+any fields not named in the list of @var{field-names} are unspecified.
+The @var{field-names} argument defaults to the list of field-names in
+the call to @code{make-record-type} that created the type represented by
+@var{record-type}; if the @var{field-names} argument is provided, it is
+an error if it contains any duplicates or any symbols not in the default
+list.
+@end deffn
+
+@deffn {procedure} record-predicate record-type
+Returns a procedure for testing membership in the type represented by
+@var{record-type}.  The returned procedure accepts exactly one argument
+and returns @code{#t} if the argument is a member of the indicated
+record type; it returns @code{#f} otherwise.
+@end deffn
+
+@deffn {procedure} record-accessor record-type field-name
+Returns a procedure for reading the value of a particular field of a
+member of the type represented by @var{record-type}.  The returned
+procedure accepts exactly one argument which must be a record of the
+appropriate type; it returns the current value of the field named by the
+symbol @var{field-name} in that record.  The symbol @var{field-name}
+must be a member of the list of field names in the call to
+@code{make-record-type} that created the type represented by
+@var{record-type}.
+@end deffn
+
+@deffn {procedure} record-updater record-type field-name
+Returns a procedure for writing the value of a particular field of a
+member of the type represented by @var{record-type}.  The returned
+procedure accepts exactly two arguments: first, a record of the
+appropriate type, and second, an arbitrary Scheme value; it modifies the
+field named by the symbol @var{field-name} in that record to contain the
+given value.  The returned value of the updater procedure is
+unspecified.  The symbol @var{field-name} must be a member of the list
+of field names in the call to @code{make-record-type} that created the
+type represented by @var{record-type}.
+@end deffn
+
+@deffn {procedure} record? object
+@cindex type predicate, for record
+Returns @code{#t} if @var{object} is a record of any type and @code{#f}
+otherwise.@footnote{In the current implementation of MIT Scheme, any
+object that satisfies this predicate also satisfies @code{vector?}.
+However, we plan to change the implementation to make records distinct
+from all other data types.} Note that @code{record?} may be true of any
+Scheme value; of course, if it returns @code{#t} for some particular
+value, then @code{record-type-descriptor} is applicable to that value
+and returns an appropriate descriptor.
+@end deffn
+
+@deffn {procedure} record-type-descriptor record
+Returns the record-type descriptor representing the type of
+@var{record}.  That is, for example, if the returned descriptor were
+passed to @code{record-predicate}, the resulting predicate would return
+@code{#t} when passed @var{record}.  Note that it is not necessarily the
+case that the returned descriptor is the one that was passed to
+@code{record-constructor} in the call that created the constructor
+procedure that created @var{record}.@footnote{However, in MIT Scheme,
+the record-type descriptor representing a given record type is unique.}
+@end deffn
+
+@deffn {procedure+} record-type? object
+@cindex type predicate, for record type
+Returns @code{#t} if @var{object} is a record-type descriptor; otherwise
+returns @code{#f}.
+@end deffn
+
+@deffn {procedure} record-type-name record-type
+Returns the type name associated with the type represented by
+@var{record-type}.  The returned value is @code{eqv?} to the
+@var{type-name} argument given in the call to @code{make-record-type}
+that created the type represented by @var{record-type}.
+@end deffn
+
+@deffn {procedure} record-type-field-names record-type
+Returns a list of the symbols naming the fields in members of the type
+represented by @var{record-type}.  The returned value is @code{equal?}
+to the @var{field-names} argument given in the call to
+@code{make-record-type} that created the type represented by
+@var{record-type}.@footnote{In MIT Scheme, the returned list is always
+newly allocated.}
+@end deffn
+
+@node Promises, Streams, Records, Miscellaneous Datatypes
+@section Promises
+
+@deffn {special form} delay expression
+@cindex promise (defn)
+@cindex promise, construction
+@cindex construction, of promise
+@cindex lazy evaluation (defn)
+@cindex call by need evaluation (defn)
+@cindex evaluation, lazy (defn)
+@cindex evaluation, call by need (defn)
+The @code{delay} construct is used together with the procedure
+@code{force} to implement @dfn{lazy evaluation} or @dfn{call by need}.
+@code{(delay @var{expression})} returns an object called a @dfn{promise}
+which at some point in the future may be asked (by the @code{force}
+procedure) to evaluate @var{expression} and deliver the resulting value.
+@end deffn
+
+@deffn procedure force promise
+@cindex promise, forcing
+@cindex forcing, of promise
+@cindex memoization, of promise
+Forces the value of @emph{promise}.  If no value has been computed for
+the promise, then a value is computed and returned.  The value of the
+promise is cached (or ``memoized'') so that if it is forced a second
+time, the previously computed value is returned without any
+recomputation.
+
+@example
+@group
+(force (delay (+ 1 2)))                 @result{}  3
+
+(let ((p (delay (+ 1 2))))
+  (list (force p) (force p)))           @result{}  (3 3)
+
+(define a-stream
+  (letrec ((next
+            (lambda (n)
+              (cons n (delay (next (+ n 1)))))))
+    (next 0)))
+
+(define head car)
+
+(define tail
+  (lambda (stream)
+    (force (cdr stream))))
+
+(head (tail (tail a-stream)))           @result{}  2
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} promise? object
+@cindex type predicate, for promise
+Returns @code{#t} if @var{object} is a promise; otherwise returns
+@code{#f}.
+@end deffn
+
+@deffn {procedure+} promise-forced? promise
+Returns @code{#t} if @var{promise} has been forced and its value cached;
+otherwise returns @code{#f}.
+@end deffn
+
+@deffn {procedure+} promise-value promise
+If @var{promise} has been forced and its value cached, this procedure
+returns the cached value.  Otherwise, an error is signalled.
+@end deffn
+
+@code{force} and @code{delay} are mainly intended for programs written
+in functional style.  The following examples should not be considered to
+illustrate good programming style, but they illustrate the property that
+the value of a promise is computed at most once.
+
+@example
+@group
+(define count 0)
+
+(define p
+  (delay
+   (begin
+     (set! count (+ count 1))
+     (* x 3))))
+
+(define x 5)
+
+count                                   @result{}  0
+p                                       @result{}  #[promise 54]
+(force p)                               @result{}  15
+p                                       @result{}  #[promise 54]
+count                                   @result{}  1
+(force p)                               @result{}  15
+count                                   @result{}  1
+@end group
+@end example
+
+Here is a possible implementation of @code{delay} and @code{force}.  We
+define the expression
+
+@example
+(delay @var{expression})
+@end example
+
+@noindent
+to have the same meaning as the procedure call
+
+@example
+(make-promise (lambda () @var{expression}))
+@end example
+
+@noindent
+where @code{make-promise} is defined as follows:
+
+@example
+@group
+(define make-promise
+  (lambda (proc)
+    (let ((already-run? #f)
+          (result #f))
+      (lambda ()
+        (cond ((not already-run?)
+               (set! result (proc))
+               (set! already-run? #t)))
+        result))))
+@end group
+@end example
+
+Promises are implemented here as procedures of no arguments, and
+@code{force} simply calls its argument.
+
+@example
+@group
+(define force
+  (lambda (promise)
+    (promise)))
+@end group
+@end example
+
+Various extensions to this semantics of @code{delay} and @code{force}
+are supported in some implementations (none of these are currently
+supported in MIT Scheme):
+
+@itemize @bullet
+@item
+Calling @code{force} on an object that is not a promise may simply
+return the object.
+
+@item
+It may be the case that there is no means by which a promise can be
+operationally distinguished from its forced value.  That is, expressions
+like the following may evaluate to either @code{#t} or @code{#f},
+depending on the implementation:
+
+@example
+@group
+(eqv? (delay 1) 1)              @result{}  @r{unspecified}
+(pair? (delay (cons 1 2)))      @result{}  @r{unspecified}
+@end group
+@end example
+
+@item
+Some implementations will implement ``implicit forcing'', where the
+value of a promise is forced by primitive procedures like @code{car} and
+@code{+}:
+
+@example
+(+ (delay (* 3 7)) 13)          @result{}  34
+@end example
+@end itemize
+
+@node Streams, Weak Pairs, Promises, Miscellaneous Datatypes
+@section Streams
+
+@cindex stream (defn)
+In addition to promises, MIT Scheme supports a higher-level abstraction
+called @dfn{streams}.  Streams are similar to lists, except that the
+tail of a stream is not computed until it is referred to.
+This allows streams to be used to represent infinitely long lists.
+
+@deffn {procedure+} stream object @dots{}
+@cindex construction, of stream
+@findex the-empty-stream
+Returns a newly allocated stream whose elements are the arguments.  Note
+that the expression @code{(stream)} returns the empty stream, or
+end-of-stream marker.@footnote{The variable @code{the-empty-stream},
+which is bound to the end-of-stream marker, is provided for
+compatibility with old code; use @code{(stream)} in new code.}
+@end deffn
+
+@deffn {procedure+} list->stream list
+@cindex list, converting to stream
+Returns a newly allocated stream whose elements are the elements of
+@var{list}.  Equivalent to @code{(apply stream @var{list})}.
+@end deffn
+
+@deffn {procedure+} stream->list stream
+@cindex stream, converting to list
+Returns a newly allocated list whose elements are the elements of
+@var{stream}.  If @var{stream} has infinite length this procedure will
+not terminate.  This could have been defined by
+
+@example
+@group
+(define (stream->list stream)
+  (if (stream-null? stream)
+      '()
+      (cons (stream-car stream)
+            (stream->list (stream-cdr stream)))))
+@end group
+@end example
+@end deffn
+
+@deffn {special form+} cons-stream object expression
+Returns a newly allocated stream pair.  Equivalent to @code{(cons
+@var{object} (delay @var{expression}))}.
+@end deffn
+
+@deffn {procedure+} stream-pair? object
+@cindex type predicate, for stream pair
+Returns @code{#t} if @var{object} is a pair whose cdr contains a
+promise.  Otherwise returns @code{#f}.  This could have been defined by
+
+@example
+@group
+(define (stream-pair? object)
+  (and (pair? object)
+       (promise? (cdr object))))
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} stream-car stream
+@findex car
+@findex head
+Returns the first element in @var{stream}.  @code{stream-car} is
+equivalent to @code{car}.@footnote{@code{head}, a synonym for
+@code{stream-car}, is provided for compatibility with old code; use
+@code{stream-car} in new code.}
+@end deffn
+
+@deffn {procedure+} stream-cdr stream
+@findex force
+@findex cdr
+@findex tail
+Returns the first tail of @var{stream}.  Equivalent to @code{(force
+(cdr @var{stream}))}.@footnote{@code{tail}, a synonym for
+@code{stream-cdr}, is provided for compatibility with old code; use
+@code{stream-cdr} in new code.}
+@end deffn
+
+@deffn {procedure+} stream-null? stream
+@cindex empty stream, predicate for
+@findex null?
+@findex empty-stream?
+Returns @code{#t} if @var{stream} is the end-of-stream marker;
+otherwise returns @code{#f}.  This is equivalent to @code{null?}, but
+should be used whenever testing for the end of a
+stream.@footnote{@code{empty-stream?}, a synonym for
+@code{stream-null?}, is provided for compatibility with old code; use
+@code{stream-null?} in new code.}
+@end deffn
+
+@deffn {procedure+} stream-length stream
+@cindex length, of stream
+Returns the number of elements in @var{stream}.  If @var{stream} has an
+infinite number of elements this procedure will not terminate.  Note
+that this procedure forces all of the promises that comprise
+@var{stream}.
+@end deffn
+
+@deffn {procedure+} stream-ref stream k
+@cindex selecting, of stream component
+@cindex component selection, of stream
+Returns the element of @var{stream} that is indexed by @var{k}; that is,
+the @var{k}th element.  @var{K} must be an exact non-negative integer
+strictly less than the length of @var{stream}.
+@end deffn
+
+@deffn {procedure+} stream-tail stream k
+Returns the tail of @var{stream} that is indexed by @var{k}; that is,
+the @var{k}th tail.  This is equivalent to performing @code{stream-cdr}
+@var{k} times.  @var{K} must be an exact non-negative integer strictly
+less than the length of @var{stream}.
+@end deffn
+
+@deffn {procedure+} stream-map stream procedure
+@cindex mapping, of stream
+Returns a newly allocated stream, each element being the result of
+invoking @var{procedure} with the corresponding element of @var{stream}
+as its argument.  @var{Procedure} must be a procedure of one argument.
+@end deffn
+
+@node Weak Pairs,  , Streams, Miscellaneous Datatypes
+@section Weak Pairs
+
+@cindex weak pair (defn)
+@cindex pair, weak (defn)
+@dfn{Weak pairs} are a mechanism for building data structures that point
+at objects without protecting them from garbage collection.  The car of
+a weak pair holds its pointer weakly, while the cdr holds its pointer in
+the normal way.  If the object in the car of a weak pair is not held
+normally by any other data structure, it will be garbage-collected.
+
+@findex pair?
+Note: weak pairs are @emph{not} pairs; that is, they do not satisfy the
+predicate @code{pair?}.
+
+@deffn {procedure+} weak-pair? object
+@cindex type predicate, for weak pair
+Returns @code{#t} if @var{object} is a weak pair; otherwise returns
+@code{#f}.
+@end deffn
+
+@deffn {procedure+} weak-cons car cdr
+@cindex construction, of weak pair
+Allocates and returns a new weak pair, with components @var{car} and
+@var{cdr}.  The @var{car} component is held weakly.
+@end deffn
+
+@deffn {procedure+} weak-pair/car? weak-pair
+This predicate returns @code{#f} if the car of @var{weak-pair} has been
+garbage-collected; otherwise returns @code{#t}.  In other words, it is
+true if @var{weak-pair} has a valid car component.
+@end deffn
+
+@deffn {procedure+} weak-car weak-pair
+@cindex selection, of weak pair component
+@cindex component selection, of weak pair
+Returns the car component of @var{weak-pair}.  If the car component has
+been garbage-collected, this operation returns @code{#f}, but it can
+also return @code{#f} if that is the value that was stored in the car.
+@end deffn
+
+Normally, @code{weak-pair/car?} is used to determine if @code{weak-car}
+would return a valid value.  An obvious way of doing this would be:
+
+@example
+@group
+(if (weak-pair/car? x)
+    (weak-car x)
+    @dots{})
+@end group
+@end example
+
+@noindent
+However, since a garbage collection could occur between the call to
+@code{weak-pair/car?} and @code{weak-car}, this would not always work
+correctly.  Instead, the following should be used, which always works:
+
+@example
+@group
+(or (weak-car x)
+    (and (not (weak-pair/car? x))
+         @dots{}))
+@end group
+@end example
+
+The reason that the latter expression works is that @code{weak-car}
+returns @code{#f} in just two instances: when the car component is
+@code{#f}, and when the car component has been garbage-collected.  In
+the former case, if a garbage collection happens between the two calls,
+it won't matter, because @code{#f} will never be garbage-collected.  And
+in the latter case, it also won't matter, because the car component no
+longer exists and cannot be affected by the garbage collector.
+
+@deffn {procedure+} weak-set-car! weak-pair object
+Sets the car component of @var{weak-pair} to @var{object} and returns an
+unspecified result.
+@end deffn
+
+@deffn {procedure+} weak-cdr weak-pair
+Returns the cdr component of @var{weak-cdr}.
+@end deffn
+
+@deffn {procedure+} weak-set-cdr! weak-pair object
+Sets the cdr component of @var{weak-pair} to @var{object} and returns an
+unspecified result.
+@end deffn
+
+@node Associations, Procedures, Miscellaneous Datatypes, Top
+@chapter Associations
+
+MIT Scheme provides several mechanisms for associating objects with
+one another.  Each of these mechanisms creates a link between one or
+more objects, called @dfn{keys}, and some other object, called a
+@dfn{datum}.  Beyond this common idea, however, each of the mechanisms
+has various different properties that make it appropriate in different
+situations:
+
+@itemize @bullet
+@item
+@dfn{Association lists} are one of Lisp's oldest association mechanisms.
+Because they are made from ordinary pairs, they are easy to build and
+manipulate, and very flexible in use.  However, the average lookup time
+for an association list is linear in the number of associations.
+
+@item
+@dfn{1D tables} have a very simple interface, making them easy to use,
+and offer the feature that they do not prevent their keys from being
+reclaimed by the garbage collector.  Like association lists, their
+average lookup time is linear in the number of associations; but 1D
+tables aren't as flexible.
+
+@item
+@dfn{The association table} is MIT Scheme's equivalent to the
+@dfn{property lists} of Lisp.  It has the advantages that the keys may
+be any type of object and that it does not prevent the keys from being
+reclaimed by the garbage collector.  However, two linear-time lookups
+must be performed, one for each key, whereas for traditional property
+lists only one is lookup required for both keys.
+
+@item
+@dfn{Hash tables} are a powerful mechanism with nearly constant-time
+access to large amounts of data.  However, the overhead for hash tables
+is somewhat high, both in time and space, making them unsuitable for
+small tables.  And hash tables are not as flexible as association lists.
+@end itemize
+
+@menu
+* Association Lists::           Association Lists
+* 1D Tables::                   1D Tables
+* The Association Table::       The Association Table
+* Hash Tables::                 Hash Tables
+* Hashing::                     Hashing
+@end menu
+
+@node Association Lists, 1D Tables, Associations, Associations
+@section Association Lists
+
+@comment **** begin CLTL ****
+@cindex association list (defn)
+@cindex list, association (defn)
+@cindex alist (defn)
+@cindex key, of association list element (defn)
+An @dfn{association list}, or @dfn{alist}, is a data structure used very
+frequently in Scheme.  An alist is a list of pairs, each of which is
+called an @dfn{association}.  The car of an association is called the
+@dfn{key}.
+
+An advantage of the alist representation is that an alist can be
+incrementally augmented simply by adding new entries to the front.
+Moreover, because the searching procedures @code{assv} et al.@: search the
+alist in order, new entries can ``shadow'' old entries.  If an alist is
+viewed as a mapping from keys to data, then the mapping can be not only
+augmented but also altered in a non-destructive manner by adding new
+entries to the front of the alist.@footnote{This introduction is taken
+from @cite{Common Lisp, The Language}, second edition, p.@: 431.}
+@comment **** end CLTL ****
+
+@deffn {procedure+} alist? object
+@cindex type predicate, for alist
+@findex list?
+Returns @code{#t} if @var{object} is an association list (including the
+empty list); otherwise returns @code{#f}.  Any @var{object} satisfying this
+predicate also satisfies @code{list?}.
+@end deffn
+
+@deffn procedure assq object alist
+@deffnx procedure assv object alist
+@deffnx procedure assoc object alist
+@cindex searching, of alist
+@findex eq?
+@findex eqv?
+@findex equal?
+These procedures find the first pair in @var{alist} whose car field is
+@var{object}, and return that pair; the returned pair is always an
+@emph{element} of @var{alist}, @emph{not} one of the pairs from which
+@var{alist} is composed.  If no pair in @var{alist} has @var{object} as
+its car, @code{#f} (n.b.: not the empty list) is returned.  @code{assq}
+uses @code{eq?} to compare @var{object} with the car fields of the pairs
+in @var{alist}, while @code{assv} uses @code{eqv?} and @code{assoc} uses
+@code{equal?}.@footnote{Although they are often used as predicates,
+@code{assq}, @code{assv}, and @code{assoc} do not have question marks in
+their names because they return useful values rather than just @code{#t}
+or @code{#f}.}
+
+@example
+@group
+(define e '((a 1) (b 2) (c 3)))
+(assq 'a e)                             @result{}  (a 1)
+(assq 'b e)                             @result{}  (b 2)
+(assq 'd e)                             @result{}  #f
+(assq (list 'a) '(((a)) ((b)) ((c))))   @result{}  #f
+(assoc (list 'a) '(((a)) ((b)) ((c))))  @result{}  ((a))
+(assq 5 '((2 3) (5 7) (11 13)))         @result{}  @r{unspecified}
+(assv 5 '((2 3) (5 7) (11 13)))         @result{}  (5 7)
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} association-procedure predicate selector
+Returns an association procedure that is similar to @code{assv}, except
+that @var{selector} (a procedure of one argument) is used to select the
+key from the association, and @var{predicate} (an equivalence predicate)
+is used to compare the key to the given item.  This can be used to make
+association lists whose elements are, say, vectors instead of pairs
+(also @pxref{Searching Lists}).
+
+For example, here is how @code{assv} could be implemented:
+@example
+(define assv (association-procedure eqv? car))
+@end example
+
+Another example is a ``reverse association'' procedure:
+
+@example
+(define rassv (association-procedure eqv? cdr))
+@end example
+@end deffn
+
+@deffn {procedure+} del-assq object alist
+@deffnx {procedure+} del-assv object alist
+@deffnx {procedure+} del-assoc object alist
+@cindex deletion, of alist element
+@findex eq?
+@findex eqv?
+@findex equal?
+These procedures return a newly allocated copy of @var{alist} in which
+all associations with keys equal to @var{object} have been removed.
+@code{del-assq} uses @code{eq?} to compare @var{object} with the keys,
+while @code{del-assv} uses @code{eqv?} and @code{del-assoc} uses
+@code{equal?}.
+
+@example
+@group
+(define a
+  '((butcher . "231 e22nd St.")
+    (baker . "515 w23rd St.")
+    (hardware . "988 Lexington Ave.")))
+
+(del-assq 'baker a)
+     @result{}
+     ((butcher . "231 e22nd St.")
+      (hardware . "988 Lexington Ave."))
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} del-assq! object alist
+@deffnx {procedure+} del-assv! object alist
+@deffnx {procedure+} del-assoc! object alist
+@findex eq?
+@findex eqv?
+@findex equal?
+These procedures remove from @var{alist} all associations with keys
+equal to @var{object}.  They return the resulting list.
+@code{del-assq!} uses @code{eq?} to compare @var{object} with the keys,
+while @code{del-assv!} uses @code{eqv?} and @code{del-assoc!} uses
+@code{equal?}.  These procedures are like @code{del-assq},
+@code{del-assv}, and @code{del-assoc}, respectively, except that they
+destructively modify @var{alist}.
+@end deffn
+
+@deffn {procedure+} delete-association-procedure deletor predicate selector
+@findex list-deletor
+@findex list-deletor!
+This returns a deletion procedure similar to @code{del-assv} or
+@code{del-assq!}.  The @var{predicate} and @var{selector} arguments are
+the same as those for @code{association-procedure}, while the
+@var{deletor} argument should be either the procedure
+@code{list-deletor} (for non-destructive deletions), or the procedure
+@code{list-deletor!} (for destructive deletions).
+
+For example, here is a possible implementation of @code{del-assv}:
+
+@example
+@group
+(define del-assv 
+  (delete-association-procedure list-deletor eqv? car))
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} alist-copy alist
+@cindex copying, of alist
+@findex list-copy
+Returns a newly allocated copy of @var{alist}.  This is similar to
+@code{list-copy} except that the ``association'' pairs, i.e.@: the
+elements of the list @var{alist}, are also copied.  @code{alist-copy}
+could have been implemented like this:
+
+@example
+@group
+(define (alist-copy alist)
+  (if (null? alist)
+      '()
+      (cons (cons (car (car alist)) (cdr (car alist)))
+            (alist-copy (cdr alist)))))
+@end group
+@end example
+@end deffn
+
+@node 1D Tables, The Association Table, Association Lists, Associations
+@section 1D Tables
+
+@cindex 1D table (defn)
+@cindex one-dimensional table (defn)
+@cindex table, one-dimensional (defn)
+@cindex weak pair, and 1D table
+@dfn{1D tables} (``one-dimensional'' tables) are similar to association
+lists.  In a 1D table, unlike an association list, the keys of the table
+are held @dfn{weakly}: if a key is garbage-collected, its associated
+value in the table is removed.
+
+@cindex property list
+1D tables can often be used as a higher-performance alternative to the
+two-dimensional association table (@pxref{The Association Table}).  If
+one of the keys being associated is a compound object such as a vector,
+a 1D table can be stored in one of the vector's slots.  Under these
+circumstances, accessing items in a 1D table will be comparable in
+performance to using a property list in a conventional Lisp.
+
+@deffn {procedure+} make-1d-table
+Returns a newly allocated empty 1D table.
+@end deffn
+
+@deffn {procedure+} 1d-table? object
+@cindex type predicate, for 1D table
+@findex list?
+Returns @code{#t} if @var{object} is a 1D table, otherwise returns
+@code{#f}.  Any object that satisfies this predicate also satisfies
+@code{list?}.
+@end deffn
+
+@deffn {procedure+} 1d-table/put! 1d-table key datum
+Creates an association between @var{key} and @var{datum} in
+@var{1d-table}.  Returns an unspecified value.
+@end deffn
+
+@deffn {procedure+} 1d-table/remove! 1d-table key
+Removes any association for @var{key} in @var{1d-table} and returns an
+unspecified value.
+@end deffn
+
+@deffn {procedure+} 1d-table/get 1d-table key default
+Returns the @var{datum} associated with @var{key} in @var{1d-table}.  If
+there is no association for @var{key}, @var{default} is returned.
+@end deffn
+
+@deffn {procedure+} 1d-table/lookup 1d-table key if-found if-not-found
+@var{If-found} must be a procedure of one argument, and
+@var{if-not-found} must be a procedure of no arguments.  If
+@var{1d-table} contains an association for @var{key}, @var{if-found} is
+invoked on the @var{datum} of the association.  Otherwise,
+@var{if-not-found} is invoked with no arguments.  In either case, the
+result of the invoked procedure is returned as the result of
+@code{1d-table/lookup}.
+@end deffn
+
+@deffn {procedure+} 1d-table/alist 1d-table
+Returns a newly allocated association list that contains the same
+information as @var{1d-table}.
+@end deffn
+
+@node The Association Table, Hash Tables, 1D Tables, Associations
+@section The Association Table
+
+@cindex association table (defn)
+@cindex table, association (defn)
+@cindex property list
+@findex eq?
+MIT Scheme provides a generalization of the property-list mechanism
+found in most other implementations of Lisp: a global two-dimensional
+@dfn{association table}.  This table is indexed by two keys, called
+@var{x-key} and @var{y-key} in the following procedure descriptions.
+These keys and the datum associated with them can be arbitrary objects.
+@code{eq?} is used to discriminate keys.
+
+Think of the association table as a matrix: a single datum can be
+accessed using both keys, a column using @var{x-key} only, and a row
+using @var{y-key} only.
+
+@deffn {procedure+} 2d-put! x-key y-key datum
+Makes an entry in the association table that associates @var{datum} with
+@var{x-key} and @var{y-key}.  Returns an unspecified result.
+@end deffn
+
+@deffn {procedure+} 2d-remove! x-key y-key
+If the association table has an entry for @var{x-key} and @var{y-key},
+it is removed and @code{#t} is returned.  Otherwise @code{#f} is
+returned.
+@end deffn
+
+@deffn {procedure+} 2d-get x-key y-key
+Returns the @var{datum} associated with @var{x-key} and @var{y-key}.
+Returns @code{#f} if no such association exists.
+@end deffn
+
+@deffn {procedure+} 2d-get-alist-x x-key
+Returns an association list of all entries in the association table that
+are associated with @var{x-key}.  The result is a list of
+@code{(@var{y-key} . @var{datum})} pairs.  Returns the empty list if no
+entries for @var{x-key} exist.
+
+@example
+@group
+(2d-put! 'foo 'bar 5)
+(2d-put! 'foo 'baz 6)
+(2d-get-alist-x 'foo)                   @result{}  ((baz . 6) (bar . 5))
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} 2d-get-alist-y y-key
+Returns an association list of all entries in the association table that
+are associated with @var{y-key}.  The result is a list of
+@code{(@var{x-key} . @var{datum})} pairs.  Returns the empty list if no
+entries for @var{y-key} exist.
+
+@example
+@group
+(2d-put! 'bar 'foo 5)
+(2d-put! 'baz 'foo 6)
+(2d-get-alist-y 'foo)                   @result{}  ((baz . 6) (bar . 5))
+@end group
+@end example
+@end deffn
+
+@node Hash Tables, Hashing, The Association Table, Associations
+@section Hash Tables
+
+@cindex hash table
+Hash tables are a fast, powerful mechanism for storing large numbers of
+associations.  MIT Scheme's hash tables feature automatic growth,
+customizable growth parameters, and customizable hash functions.
+
+@cindex run-time-loadable option
+@cindex option, run-time-loadable
+The hash-table implementation is a run-time-loadable option.  To use
+hash tables, execute
+
+@example
+(load-option 'hash-table)
+@end example
+@findex load-option
+
+@noindent
+once before calling any of the procedures defined here.
+
+@deffn {procedure+} make-object-hash-table [k]
+@findex eq?
+Returns a newly allocated hash table that accepts arbitrary objects as
+keys, and uses @code{eq?} to compare the keys.  The keys are weakly
+held, i.e.@: the hash table does not protect them from being reclaimed
+by the garbage collector.  @var{K} specifies the initial usable size of
+the hash table, and defaults to 10 if not specified.  The entries of the
+hash table are weak pairs whose car field is the @var{key} and whose cdr
+field is the @var{datum}.
+@end deffn
+
+@deffn {procedure+} make-string-hash-table [k]
+@findex string=?
+Returns a newly allocated hash table that accepts strings as keys, and
+compares them with @code{string=?}.  The keys are strongly held, i.e.@:
+while in the hash table they will not be reclaimed by the garbage
+collector.  @var{K} specifies the initial usable size of the hash table,
+and defaults to 10 if not specified.  The entries of the hash table are
+ordinary pairs whose car field is the @var{key} and whose cdr field is
+the @var{datum}.
+@end deffn
+
+@deffn {procedure+} make-symbol-hash-table [k]
+@findex eq?
+Returns a newly allocated hash table that accepts symbols as keys, and
+compares them with @code{eq?}.  The keys are strongly held, i.e.@: while
+in the hash table they will not be reclaimed by the garbage collector.
+@var{K} specifies the initial usable size of the hash table, and
+defaults to 10 if not specified.  The entries of the hash table are
+ordinary pairs whose car field is the @var{key} and whose cdr field is
+the @var{datum}.
+@end deffn
+
+@deffn {procedure+} hash-table? object
+@cindex type predicate, for hash table
+Returns @code{#t} if @var{object} is a hash table, otherwise returns
+@code{#f}.
+@end deffn
+
+@deffn {procedure+} hash-table/put! hash-table key datum
+Associates @var{datum} with @var{key} in @var{hash-table} and returns an
+unspecified result.
+@end deffn
+
+@deffn {procedure+} hash-table/remove! hash-table key
+If @var{hash-table} has an association for @var{key}, removes it.
+Returns an unspecified result.
+@end deffn
+
+@deffn {procedure+} hash-table/clear! hash-table
+Removes all associations in @var{hash-table} and returns an unspecified
+result.
+@end deffn
+
+@deffn {procedure+} hash-table/get hash-table key default
+Returns the @var{datum} associated with @var{key} in @var{hash-table}.
+If there is no association for @var{key}, @var{default} is returned.
+@end deffn
+
+@deffn {procedure+} hash-table/lookup hash-table key if-found if-not-found
+@var{If-found} must be a procedure of one argument, and
+@var{if-not-found} must be a procedure of no arguments.  If
+@var{hash-table} contains an association for @var{key}, @var{if-found}
+is invoked on the @var{datum} of the association.  Otherwise,
+@var{if-not-found} is invoked with no arguments.  In either case, the
+result yielded by the invoked procedure is returned as the result of
+@code{hash-table/lookup}.
+@end deffn
+
+@deffn {procedure+} hash-table/for-each hash-table procedure
+@var{Procedure} must be a procedure of two arguments.  Invokes
+@var{procedure} once for each association in @var{hash-table}, passing
+the association's @var{key} and @var{datum} as arguments, in that order.
+Returns an unspecified result.  @var{Procedure} must not modify
+@var{hash-table}, with one exception: it is permitted to call
+@code{hash-table/remove!} to remove the entry being processed.
+@end deffn
+
+@deffn {procedure+} hash-table/entries-list hash-table
+Returns a newly allocated list of the entries in @var{hash-table}.  The
+elements of the list are usually either pairs or weak pairs, depending
+on the type of hash table.
+@end deffn
+
+@deffn {procedure+} hash-table/entries-vector hash-table
+Returns a newly allocated vector of the entries in @var{hash-table}.
+Equivalent to
+
+@example
+(list->vector (hash-table/entries-list @var{hash-table}))
+@end example
+@end deffn
+
+@deffn {procedure+} hash-table/clean! hash-table
+If @var{hash-table} is a type of hash table that holds its @var{key}s
+weakly, this procedure recovers any space that was being used to record
+associations for objects that have been reclaimed by the garbage
+collector.  Otherwise, this procedure does nothing.  In either case, it
+returns an unspecified result.
+@end deffn
+
+@deffn {procedure+} hash-table/constructor key-hash key=? make-entry entry-valid? entry-key entry-value set-entry-value!
+Returns a constructor procedure for a hash table.  The returned
+procedure accepts one optional argument @var{k}, which specifies the
+initial usable size of the table, and returns a newly allocated hash
+table; @code{k} defaults to @code{10} if not supplied.  The arguments to
+@code{hash-table/constructor} define the characteristics of the hash
+table as follows:
+
+@table @var
+@item key-hash
+The hashing function.  A procedure that accepts two arguments, a
+@var{key} and an exact positive integer (the hash modulus), and returns
+an exact non-negative integer that is less than the second argument.
+Examples: @code{string-hash-mod}, @code{symbol-hash-mod}.
+@findex string-hash-mod
+@findex symbol-hash-mod
+
+@item key=?
+A equivalence predicate that accepts two @var{key} arguments and is true
+if they are the same key.  Examples: @code{eq?}, @code{string=?}.
+@findex eq?
+@findex string=?
+
+@item make-entry
+A procedure that accepts a @var{key} and a @var{datum} as arguments and
+returns an entry.  Typically @code{cons} or @code{weak-cons}.
+@findex cons
+@findex weak-cons
+
+@item entry-valid?
+A procedure that accepts an entry and returns @code{#f} only if the
+entry's @var{key} has been reclaimed by the garbage collector.  For
+example, if entries are weak pairs, this should be
+@code{weak-pair/car?}.  Instead of a procedure, this may be @code{#t},
+which is equivalent to @code{(lambda (entry) #t)}.
+@findex weak-pair/car?
+
+@item entry-key
+A procedure that accepts an entry as an argument and returns the entry's
+@var{key}.  Typically @code{car} or @code{weak-car}.
+@findex car
+@findex weak-car
+
+@item entry-value
+A procedure that accepts an entry as an argument and returns the entry's
+@var{datum}.  Typically @code{cdr} or @code{weak-cdr}.
+@findex cdr
+@findex weak-cdr
+
+@item set-entry-value!
+A procedure that accepts an entry and an object as arguments, modifies
+the entry's @var{datum} to be the object, and returns an unspecified
+result.  Typically @code{set-cdr!} or @code{weak-set-cdr!}.
+@findex set-cdr!
+@findex weak-set-cdr!
+@end table
+@end deffn
+
+@deffn {procedure+} hash-table/key-hash hash-table
+@deffnx {procedure+} hash-table/key=? hash-table
+@deffnx {procedure+} hash-table/make-entry hash-table
+@deffnx {procedure+} hash-table/entry-valid? hash-table
+@deffnx {procedure+} hash-table/entry-key hash-table
+@deffnx {procedure+} hash-table/entry-value hash-table
+@deffnx {procedure+} hash-table/set-entry-value! hash-table
+Each of these procedures corresponds to the respective argument of
+@code{hash-table/constructor}.  When called, these procedures return the
+value of the argument that was used to construct @var{hash-table}.
+@end deffn
+
+Two parameters control the growth of a hash table, the @dfn{rehash
+threshold} and the @dfn{rehash size}.
+
+@cindex rehash threshold, of hash table (defn)
+@cindex usable size, of hash table (defn)
+@cindex physical size, of hash table (defn)
+@cindex size, of hash table (defn)
+The @dfn{rehash threshold} is a real number, between zero exclusive and
+one inclusive, that specifies how full the hash table can get before it
+must grow.  In other words it is the ratio between a hash table's
+@dfn{usable size} and its @dfn{physical size}.  If the number of entries
+in the table exceeds this fraction of the table's physical size, the
+table is grown to a larger size.  The default rehash threshold of a
+newly constructed hash table is @code{1}, but this can be changed with
+@code{set-hash-table/rehash-threshold!}.
+
+@deffn {procedure+} hash-table/rehash-threshold hash-table
+Returns the rehash threshold of @var{hash-table}.
+@end deffn
+
+@deffn {procedure+} set-hash-table/rehash-threshold! hash-table x
+@var{X} must be a real number between zero exclusive and one inclusive.
+Sets the rehash threshold of @var{hash-table} to @var{x} and returns an
+unspecified result.
+@end deffn
+
+@cindex rehash size, of hash table (defn)
+The @dfn{rehash size} specifies how much to increase the usable size of
+the hash table when it becomes full.  It is either an exact positive
+integer, or a real number greater than one.  If it is an integer, the
+new size is the sum of the old size and the rehash size.  Otherwise, it
+is a real number, and the new size is the product of the old size and
+the rehash size.  The default rehash size of a newly constructed hash
+table is @code{2.0}, but this can be changed with
+@code{set-hash-table/rehash-size!}.
+
+@deffn {procedure+} hash-table/rehash-size hash-table
+Returns the rehash size of @var{hash-table}.
+@end deffn
+
+@deffn {procedure+} set-hash-table/rehash-size! hash-table x
+@var{X} must be either an exact positive integer, or a real number that
+is greater than one.  Sets the rehash size of @var{hash-table} to
+@var{x} and returns an unspecified result.
+@end deffn
+
+@deffn {procedure+} hash-table/size hash-table
+Returns the usable size of @var{hash-table} as an exact positive
+integer.  This is the number of entries that @var{hash-table} can hold
+before it must grow.
+@end deffn
+
+@deffn {procedure+} hash-table/count hash-table
+Returns the number of entries in @var{hash-table} as an exact
+non-negative integer.  This is always less than or equal to the usable
+size of @var{hash-table}.
+@end deffn
+
+@node Hashing,  , Hash Tables, Associations
+@section Hashing
+
+@cindex object hashing
+@cindex hashing, of object
+The MIT Scheme object-hashing facility provides a mechanism for
+generating a unique hash number for an arbitrary object.  This hash
+number, unlike an object's address, is unchanged by garbage collection.
+The object-hashing facility is useful in conjunction with hash tables,
+but it may be used for other things as well.  In particular, it is used
+in the generation of the written representation for some objects
+(@pxref{Custom Output}).
+
+@deffn {procedure+} object-hash object
+@deffnx {procedure+} object-unhash k
+@findex eq?
+@code{object-hash} associates an exact non-negative integer with
+@var{object} and returns that integer.  If @code{object-hash} was
+previously called with @var{object} as its argument, the integer
+returned is the same as was returned by the previous call.
+@code{object-hash} guarantees that distinct objects (in the sense of
+@code{eq?}) are associated with distinct integers.
+
+@code{object-unhash} takes an exact non-negative integer @var{k} and
+returns the object associated with that integer.  If there is no object
+associated with @var{k}, @code{#f} is returned.  In other words, if
+@code{object-hash} previously returned @var{k} for some object, that
+object is the value of the call to @code{object-unhash}.
+
+An object that is passed to @code{object-hash} as an argument is not
+protected from being garbage-collected.  If all other references to that
+object are eliminated, the object will be garbage-collected.
+Subsequently calling @code{object-unhash} with the hash number of the
+(garbage-collected) object will return @code{#f}.
+
+@example
+@group
+(define x (cons 0 0))                   @result{}  @r{unspecified}
+(object-hash x)                         @result{}  77
+(eqv? (object-hash x) (object-hash x))  @result{}  #t
+(define x 0)                            @result{}  @r{unspecified}
+(gc-flip)                               @r{;force a garbage collection}
+(object-unhash 77)                      @result{}  #f
+@end group
+@end example
+
+@findex hash
+@findex unhash
+Note: @code{hash} is a synonym for @code{object-hash} and @code{unhash}
+is a synonym for @code{object-unhash}.  These synonyms are obsolete and
+should not be used.
+@end deffn
+
+@node Procedures, Environments, Associations, Top
+@chapter Procedures
+
+@cindex procedure
+@cindex primitive procedure (defn)
+@cindex built-in procedure
+@findex lambda
+@cindex application hook (defn)
+@cindex hook, application (defn)
+Procedures are created by evaluating @code{lambda} expressions
+(@pxref{Lambda Expressions}); the @code{lambda} may either be explicit
+or may be implicit as in a ``procedure @code{define}''
+(@pxref{Definitions}).  Also there are special built-in procedures,
+called @dfn{primitive procedures}, such as @code{car}; these procedures
+are not written in Scheme but in the language used to implement the
+Scheme system.  MIT Scheme also provides @dfn{application hooks}, which
+support the construction of data structures that act like procedures.
+
+@cindex procedure, type
+@cindex procedure, primitive
+@cindex procedure, interpreted
+@cindex procedure, compiled
+@cindex type, of procedure
+@cindex primitive, procedure type
+@cindex interpreted, procedure type
+@cindex compiled, procedure type
+@cindex external representation, for procedure
+In MIT Scheme, the written representation of a procedure tells you
+the type of the procedure (compiled, interpreted, or primitive):
+
+@example
+@group
+pp
+     @result{}  #[compiled-procedure 56 ("pp" #x2) #x10 #x307578]
+(lambda (x) x)
+     @result{}  #[compound-procedure 57]
+(define (foo x) x)
+foo
+     @result{}  #[compound-procedure 58 foo]
+car
+     @result{}  #[primitive-procedure car]
+(call-with-current-continuation (lambda (x) x))
+     @result{}  #[continuation 59]
+@end group
+@end example
+
+@noindent
+@cindex compound procedure
+@cindex procedure, compound
+Note that interpreted procedures are called ``compound'' procedures
+(strictly speaking, compiled procedures are also compound procedures).
+The written representation makes this distinction for historical
+reasons, and may eventually change.
+
+@menu
+* Procedure Operations::        Procedure Operations
+* Primitive Procedures::        Primitive Procedures
+* Continuations::               Continuations
+* Application Hooks::           Application Hooks
+@end menu
+
+@node Procedure Operations, Primitive Procedures, Procedures, Procedures
+@section Procedure Operations
+
+@deffn procedure apply procedure object object @dots{}
+@cindex application, of procedure
+Calls @var{procedure} with the elements of the following list as
+arguments:
+
+@example
+(cons* @var{object} @var{object} @dots{})
+@end example
+
+@noindent
+The initial @var{object}s may be any objects, but the last @var{object}
+(there must be at least one @var{object}) must be a list.
+
+@example
+@group
+(apply + (list 3 4 5 6))                @result{}  18
+(apply + 3 4 '(5 6))                    @result{}  18
+
+(define compose
+  (lambda (f g)
+    (lambda args
+      (f (apply g args)))))
+((compose sqrt *) 12 75)                @result{}  30
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} procedure? object
+@cindex type predicate, for procedure
+Returns @code{#t} if @var{object} is a procedure; otherwise returns
+@code{#f}.  If @code{#t} is returned, exactly one of the following
+predicates is satisfied by @var{object}: @code{compiled-procedure?},
+@code{compound-procedure?}, or @code{primitive-procedure?}.
+@end deffn
+
+@deffn {procedure+} compiled-procedure? object
+@cindex type predicate, for compiled procedure
+Returns @code{#t} if @var{object} is a compiled procedure; otherwise
+returns @code{#f}.
+@end deffn
+
+@deffn {procedure+} compound-procedure? object
+@cindex type predicate, for compound procedure
+Returns @code{#t} if @var{object} is a compound (i.e.@: interpreted)
+procedure; otherwise returns @code{#f}.
+@end deffn
+
+@deffn {procedure+} primitive-procedure? object
+@cindex type predicate, for primitive procedure
+Returns @code{#t} if @var{object} is a primitive procedure; otherwise
+returns @code{#f}.
+@end deffn
+
+@deffn {procedure+} procedure-arity-valid? procedure k
+Returns @code{#t} if @var{procedure} accepts @var{k} arguments;
+otherwise returns @code{#f}.
+@end deffn
+
+@deffn {procedure+} procedure-arity procedure
+Returns a description of the number of arguments that @var{procedure}
+accepts.  The result is a newly allocated pair whose car field is the
+minimum number of arguments, and whose cdr field is the maximum
+number of arguments.  The minimum is an exact non-negative integer.  The
+maximum is either an exact non-negative integer, or @code{#f} meaning
+that the procedure has no maximum number of arguments.
+
+@example
+@group
+(procedure-arity (lambda () 3))         @result{}  (0 . 0)
+(procedure-arity (lambda (x) x))        @result{}  (1 . 1)
+(procedure-arity car)                   @result{}  (1 . 1)
+(procedure-arity (lambda x x))          @result{}  (0 . #f)
+(procedure-arity (lambda (x . y) x))    @result{}  (1 . #f)
+(procedure-arity (lambda (x #!optional y) x))
+                                        @result{}  (1 . 2)
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} procedure-environment procedure
+Returns the closing environment of @var{procedure}.  Signals an error if
+@var{procedure} is a primitive procedure, or if @var{procedure} is a
+compiled procedure for which the debugging information is unavailable.
+@end deffn
+
+@node Primitive Procedures, Continuations, Procedure Operations, Procedures
+@section Primitive Procedures
+
+@deffn {procedure+} make-primitive-procedure name [arity]
+@var{Name} must be a symbol.  @var{Arity} must be an exact non-negative
+integer, @code{-1}, @code{#f}, or @code{#t}; if not supplied it defaults
+to @code{#f}.  Returns the primitive procedure called @var{name}.  May
+perform further actions depending on @var{arity}:
+
+@table @asis
+@item @code{#f}
+If the primitive procedure is not implemented, signals an error.
+
+@item @code{#t}
+If the primitive procedure is not implemented, returns @code{#f}.
+
+@item integer
+If the primitive procedure is implemented, signals an error if its arity
+is not equal to @var{arity}.  If the primitive procedure is not
+implemented, returns an unimplemented primitive procedure object that
+accepts @var{arity} arguments.  An @var{arity} of @code{-1} means it
+accepts any number of arguments.
+@end table
+@end deffn
+
+@deffn {procedure+} primitive-procedure-name primitive-procedure
+Returns the name of @var{primitive-procedure}, a symbol.
+
+@example
+(primitive-procedure-name car)          @result{}  car
+@end example
+@end deffn
+
+@deffn {procedure+} implemented-primitive-procedure? primitive-procedure
+Returns @code{#t} if @var{primitive-procedure} is implemented; otherwise
+returns @code{#f}.  Useful because the code that implements a particular
+primitive procedure is not necessarily linked into the executable Scheme
+program.
+@end deffn
+
+@node Continuations, Application Hooks, Primitive Procedures, Procedures
+@section Continuations
+
+@deffn procedure call-with-current-continuation procedure
+@cindex continuation
+@cindex construction, of continuation
+@cindex procedure, escape (defn)
+@cindex escape procedure (defn)
+@var{Procedure} must be a procedure of one argument.  Packages up the
+current continuation (see below) as an @dfn{escape procedure} and passes
+it as an argument to @var{procedure}.  The escape procedure is a Scheme
+procedure of one argument that, if it is later passed a value, will
+ignore whatever continuation is in effect at that later time and will
+give the value instead to the continuation that was in effect when the
+escape procedure was created.  The escape procedure created by
+@code{call-with-current-continuation} has unlimited extent just like any
+other procedure in Scheme.  It may be stored in variables or data
+structures and may be called as many times as desired.
+
+The following examples show only the most common uses of this procedure.
+If all real programs were as simple as these examples, there would be no
+need for a procedure with the power of
+@code{call-with-current-continuation}.
+
+@example
+@group
+(call-with-current-continuation
+  (lambda (exit)
+    (for-each (lambda (x)
+                (if (negative? x)
+                    (exit x)))
+              '(54 0 37 -3 245 19))
+    #t))                                @result{}  -3
+
+(define list-length
+  (lambda (obj)
+    (call-with-current-continuation
+      (lambda (return)
+        (letrec ((r
+                  (lambda (obj)
+                    (cond ((null? obj) 0)
+                          ((pair? obj) (+ (r (cdr obj)) 1))
+                          (else (return #f))))))
+          (r obj))))))
+(list-length '(1 2 3 4))                @result{}  4
+(list-length '(a b . c))                @result{}  #f
+@end group
+@end example
+
+@cindex non-local exit
+@cindex exit, non-local
+A common use of @code{call-with-current-continuation} is for structured,
+non-local exits from loops or procedure bodies, but in fact
+@code{call-with-current-continuation} is quite useful for implementing a
+wide variety of advanced control structures.
+
+Whenever a Scheme expression is evaluated a continuation exists that
+wants the result of the expression.  The continuation represents an
+entire (default) future for the computation.  If the expression is
+evaluated at top level, for example, the continuation will take the
+result, print it on the screen, prompt for the next input, evaluate it,
+and so on forever.  Most of the time the continuation includes actions
+specified by user code, as in a continuation that will take the result,
+multiply it by the value stored in a local variable, add seven, and give
+the answer to the top-level continuation to be printed.  Normally these
+ubiquitous continuations are hidden behind the scenes and programmers
+don't think much about them.  On the rare occasions that you may need to
+deal explicitly with continuations,
+@code{call-with-current-continuation} lets you do so by creating a
+procedure that acts just like the current continuation.
+@end deffn
+
+@deffn {procedure+} continuation? object
+@cindex type predicate, for continuation
+Returns @code{#t} if @var{object} is a continuation; otherwise returns
+@code{#f}.
+@end deffn
+
+@deffn {procedure+} within-continuation continuation thunk
+@cindex continuation, alternate invocation
+@cindex escape procedure, alternate invocation
+@var{Continuation} must be a continuation produced by
+@code{call-with-current-continuation}.
+@var{Thunk} must be a procedure of no arguments.
+Conceptually, @code{within-continuation} invokes @code{continuation} on
+the result of invoking @code{thunk}, but @code{thunk} is executed in the
+dynamic context of @code{continuation}.  In other words, the ``current''
+continuation is abandoned before @code{thunk} is invoked.
+@end deffn
+
+@deffn {procedure+} dynamic-wind before-thunk action-thunk after-thunk
+@cindex unwind protect
+@findex unwind-protect
+This facility is a generalization of Common Lisp @code{unwind-protect},
+designed to take into account the fact that continuations produced by
+@code{call-with-current-continuation} may be reentered.  The arguments
+@var{before-thunk}, @var{action-thunk}, and @var{after-thunk} must all
+be procedures of no arguments (thunks).
+
+@code{dynamic-wind} behaves as follows.  First @var{before-thunk} is
+called.  Then @var{action-thunk} is called.  Finally, @var{after-thunk}
+is called.  The value returned by @var{action-thunk} is returned as the
+result of @code{dynamic-wind}.  @var{After-thunk} is also called if
+@var{action-thunk} escapes from its continuation.  If @var{action-thunk}
+captures its continuation as an escape procedure, escapes from it, then
+escapes back to it, @var{after-thunk} is invoked when escaping away, and
+@var{before-thunk} is invoked when escaping back.
+
+@cindex locks, and dynamic-wind
+@code{dynamic-wind} is useful, for example, for ensuring the proper
+maintenance of locks: locking would occur in the @var{before-thunk},
+protected code would appear in the @var{action-thunk}, and unlocking
+would occur in the @var{after-thunk}.
+@end deffn
+
+The following two procedures support multiple values.  A future revision
+of the Scheme standard will support a facility similar to, but almost
+certainly different from, this one.
+
+@deffn {procedure+} with-values thunk procedure
+@cindex multiple values, from procedure
+@cindex values, multiple
+@var{Thunk} must be a procedure of no arguments, and @var{procedure}
+must be a procedure.  @var{Thunk} is invoked with a continuation that
+expects to receive multiple values; specifically, the continuation
+expects to receive the same number of values that @var{procedure}
+accepts as arguments.  @var{Thunk} must return multiple values using the
+@code{values} procedure.  Then @var{procedure} is called with the
+multiple values as its arguments.  The result yielded by @var{procedure}
+is returned as the result of @code{with-values}.
+@end deffn
+
+@deffn {procedure+} values object @dots{}
+Returns multiple values.  The continuation in effect when this procedure
+is called must be a multiple-value continuation that was created by
+@code{with-values}.  Furthermore it must accept as many values as there
+are @var{object}s.
+@end deffn
+
+@node Application Hooks,  , Continuations, Procedures
+@section Application Hooks
+
+@cindex application hook (defn)
+@cindex procedure, of application hook
+@cindex extra object, of application hook
+@dfn{Application hooks} are objects that can be applied like procedures.
+Each application hook has two parts: a @dfn{procedure} that specifies
+what to do when the application hook is applied, and an arbitrary
+object, called @dfn{extra}.  Often the procedure uses the extra object
+to determine what to do.
+
+@cindex apply hook (defn)
+@cindex entity (defn)
+There are two kinds of application hooks, which differ in what arguments
+are passed to the procedure.  When an @dfn{apply hook} is applied, the
+procedure is passed exactly the same arguments that were passed to the
+apply hook.  When an @dfn{entity} is applied, the entity itself is
+passed as the first argument, followed by the other arguments that were
+passed to the entity.
+
+Both apply hooks and entities satisfy the predicate @code{procedure?}.
+Each satisfies either @code{compiled-procedure?},
+@code{compound-procedure?}, or @code{primitive-procedure?}, depending on
+its procedure component.  An apply hook is considered to accept the same
+number of arguments as its procedure, while an entity is considered to
+accept one less argument than its procedure.
+
+@deffn {procedure+} make-apply-hook procedure object
+Returns a newly allocated apply hook with a procedure component of
+@var{procedure} and an extra component of @var{object}.
+@end deffn
+
+@deffn {procedure+} apply-hook? object
+@cindex type predicate, for apply hook
+Returns @code{#t} if @var{object} is an apply hook; otherwise returns
+@code{#f}.
+@end deffn
+
+@deffn {procedure+} apply-hook-procedure apply-hook
+Returns the procedure component of @var{apply-hook}.
+@end deffn
+
+@deffn {procedure+} set-apply-hook-procedure! apply-hook procedure
+Changes the procedure component of @var{apply-hook} to be
+@var{procedure}.  Returns an unspecified value.
+@end deffn
+
+@deffn {procedure+} apply-hook-extra apply-hook
+Returns the extra component of @var{apply-hook}.
+@end deffn
+
+@deffn {procedure+} set-apply-hook-extra! apply-hook object
+Changes the extra component of @var{apply-hook} to be @var{object}.
+Returns an unspecified value.
+@end deffn
+
+@deffn {procedure+} make-entity procedure object
+Returns a newly allocated entity with a procedure component of
+@var{procedure} and an extra component of @var{object}.
+@end deffn
+
+@deffn {procedure+} entity? object
+@cindex type predicate, for entity
+Returns @code{#t} if @var{object} is an entity; otherwise returns
+@code{#f}.
+@end deffn
+
+@deffn {procedure+} entity-procedure entity
+Returns the procedure component of @var{entity}.
+@end deffn
+
+@deffn {procedure+} set-entity-procedure! entity procedure
+Changes the procedure component of @var{entity} to be @var{procedure}.
+Returns an unspecified value.
+@end deffn
+
+@deffn {procedure+} entity-extra entity
+Returns the extra component of @var{entity}.
+@end deffn
+
+@deffn {procedure+} set-entity-extra! entity object
+Changes the extra component of @var{entity} to be @var{object}.  Returns
+an unspecified value.
+@end deffn
+
+@node Environments, Input/Output, Procedures, Top
+@chapter Environments
+
+@menu
+* Environment Operations::      Environment Operations
+* Environment Variables::       Environment Variables
+* REPL Environment::            REPL Environment
+* Interpreter Environments::    Interpreter Environments
+@end menu
+
+@node Environment Operations, Environment Variables, Environments, Environments
+@section Environment Operations
+
+Environments are first-class objects in MIT Scheme.  An environment
+consists of some bindings and possibly a parent environment, from which
+other bindings are inherited.  The operations in this section reveal the
+frame-like structure of environments by permitting you to examine the
+bindings of a particular environment separately from those of its
+parent.
+
+@deffn {procedure+} environment? object
+@cindex type predicate, for environment
+Returns @code{#t} if @var{object} is an environment; otherwise returns
+@code{#f}.
+@end deffn
+
+@deffn {procedure+} environment-has-parent? environment
+Returns @code{#t} if @var{environment} has a parent environment;
+otherwise returns @code{#f}.
+@end deffn
+
+@deffn {procedure+} environment-parent environment
+Returns the parent environment of @var{environment}.  It is an error if
+@var{environment} has no parent.
+@end deffn
+
+@deffn {procedure+} environment-bound-names environment
+Returns a newly allocated list of the names (symbols) that are bound by
+@var{environment}.  This does not include the names that are bound by
+the parent environment of @var{environment}.
+@end deffn
+
+@deffn {procedure+} environment-bindings environment
+Returns a newly allocated list of the bindings of @var{environment};
+does not include the bindings of the parent environment.
+Each element of this list takes one of two forms: @code{(@var{name})}
+indicates that @var{name} is bound but unassigned, while
+@code{(@var{name} @var{object})} indicates that @var{name} is bound, and
+its value is @var{object}.
+@end deffn
+
+@deffn {procedure+} environment-bound? environment symbol
+Returns @code{#t} if @var{symbol} is bound in @var{environment} or one
+of its ancestor environments; otherwise returns @code{#f}.
+@end deffn
+
+@deffn {procedure+} environment-lookup environment symbol
+@var{Symbol} must be bound in @var{environment} or one of its ancestor
+environments.  Returns the value to which it is bound.  Signals an error
+if @var{symbol} is unassigned.
+@end deffn
+
+@deffn {procedure+} environment-assignable? environment symbol
+@var{Symbol} must be bound in @var{environment} or one of its ancestor
+environments.  Returns @code{#t} if the binding may be modified by side
+effect.
+@end deffn
+
+@deffn {procedure+} environment-assign! environment symbol object
+@var{Symbol} must be bound in @var{environment} or one of its ancestor
+environments, and must be assignable.  Modifies the binding to have
+@var{object} as its value, and returns an unspecified result.
+@end deffn
+
+@deffn {procedure+} eval expression environment
+@cindex s-expression
+@cindex evaluation, of s-expression
+Evaluates @var{expression}, a list-structure representation (sometimes
+called s-expression representation) of a Scheme expression, in
+@var{environment}.  You rarely need @code{eval} in ordinary programs; it
+is useful mostly for evaluating expressions that have been created ``on
+the fly'' by a program.  @code{eval} is relatively expensive because it
+must convert @var{expression} to an internal form before it is executed.
+
+@example
+@group
+(define foo (list '+ 1 2))
+(eval foo (the-environment))            @result{}  3
+@end group
+@end example
+@end deffn
+
+@node Environment Variables, REPL Environment, Environment Operations, Environments
+@section Environment Variables
+
+@findex define
+The @code{user-initial-environment} is where the top-level
+read-eval-print (@sc{rep}) loop evaluates expressions and stores
+definitions.  It is a child of the @code{system-global-environment},
+which is where all of the Scheme system definitions are stored.  All of
+the bindings in @code{system-global-environment} are available when the
+current environment is @code{user-initial-environment}.  However, any
+new bindings that you create in the @sc{rep} loop (with @code{define}
+forms or by loading files containing @code{define} forms) occur in
+@code{user-initial-environment}.
+
+@defvr {variable+} system-global-environment
+The variable @code{system-global-environment} is bound to the
+environment that's the parent of the @code{user-initial-environment}.
+Primitives and system procedures are bound (and sometimes closed) in
+this environment.
+@end defvr
+
+@defvr {variable+} user-initial-environment
+The variable @code{user-initial-environment} is bound to the default
+environment in which typed expressions are evaluated by the top-level
+@sc{rep} loop.
+
+Although all bindings in @code{system-global-environment} are visible to
+the @sc{rep} loop, definitions that are typed at, or loaded by, the
+@sc{rep} loop occur in the @code{user-initial-environment}.  This is
+partly a safety measure: if you enter a definition that happens to have
+the same name as a critical system procedure, your definition will be
+visible only to the procedures you define in the
+@code{user-initial-environment}; the MIT Scheme system procedures,
+which are defined ("closed") in the @code{system-global-environment},
+will continue to see the original definition.
+@end defvr
+
+@node REPL Environment, Interpreter Environments, Environment Variables, Environments
+@section REPL Environment
+
+@deffn {procedure+} nearest-repl/environment
+@findex user-initial-environment
+Returns the current @sc{rep} loop environment (i.e.@: the current
+environment of the closest enclosing @sc{rep} loop).  When Scheme first
+starts up, this is the same as @code{user-initial-environment}.
+@end deffn
+
+@deffn {procedure+} ge environment
+Changes the current @sc{rep} loop environment to @var{environment}.
+@var{Environment} can be either an environment or a procedure object.
+If it's a procedure, the environment in which that procedure was closed
+is the new environment.
+@end deffn
+
+@node Interpreter Environments,  , REPL Environment, Environments
+@section Interpreter Environments
+
+The operations in this section return environments that are constructed
+by the interpreter.  These operations should not be used lightly, as
+they will significantly degrade the performance of compiled code.  In
+particular, they force the current environment to represented in a form
+suitable for use by the interpreter.  This prevents the compiler from
+performing many useful optimizations on such environments, and forces
+the use of the interpreter for variable references in them.  However,
+because all top-level environments (such as
+@code{user-initial-environment}) are already interpreter environments,
+it does no harm to use such operations on them.
+
+@deffn {special form+} make-environment expression @dots{}
+@cindex construction, of environment
+Produces a new environment that is a child of the environment in which
+it is executed, evaluates the @var{expression}s sequentially in the new
+environment, and returns the new environment.  Note that
+
+@example
+(make-environment @var{expression} @dots{})
+@end example
+
+@noindent
+is equivalent to:
+
+@example
+(let ()
+  @var{expression} @dots{}
+  (the-environment))
+@end example
+@end deffn
+
+@deffn {special form+} the-environment
+Returns the current environment.
+@end deffn
+
+@deffn {procedure+} interpreter-environment? object
+@cindex type predicate, for interpreter environment
+Returns @code{#t} if @var{object} is an interpreter environment;
+otherwise returns @code{#f}.
+@end deffn
+
+@node Input/Output, File-System Interface, Environments, Top
+@chapter Input/Output
+
+@cindex input
+@cindex output
+@cindex port
+This chapter describes the procedures that are used for input and output
+(@sc{i/o}).  The chapter first describes @dfn{ports} and how they are
+manipulated, then describes the @sc{i/o} operations.  Finally, some
+low-level procedures are described that permit the implementation of
+custom ports and high-performance @sc{i/o}.
+
+@menu
+* Ports::                       Ports
+* File Ports::                  File Ports
+* String Ports::                String Ports
+* Input Procedures::            Input Procedures
+* Output Procedures::           Output Procedures
+* Format::                      Format
+* Custom Output::               Custom Output
+* Port Primitives::             Port Primitives
+@end menu
+
+@node Ports, File Ports, Input/Output, Input/Output
+@section Ports
+
+@cindex port (defn)
+Scheme uses ports for @sc{i/o}.  A @dfn{port}, which can be treated like
+any other Scheme object, serves as a source or sink for data.  A port
+must be open before it can be read from or written to.  The standard
+@sc{i/o} ports, the keyboard and the terminal screen, are opened
+automatically when you start Scheme.  When you use a file for input or
+output, you need to explicitly open and close a port to the file (with
+procedures described in this chapter).  Additional procedures let you
+open ports to strings.
+
+@cindex current input port (defn)
+@cindex input port, current (defn)
+@cindex port, current
+@findex read-char
+@findex read
+Many input procedures, such as @code{read-char} and @code{read}, read
+data from the current input port by default, or from a port that you
+specify.  The current input port is initially the keyboard, but Scheme
+provides procedures that let you change the current input port to be a
+file or string.
+
+@cindex current output port (defn)
+@cindex output port, current (defn)
+@findex write-char
+@findex display
+Similarly, many output procedures, such as @code{write-char} and
+@code{display}, write data to the current output port by default, or to
+a port that you specify.  The current output port is initially the
+terminal screen, but Scheme provides procedures that let you change the
+current output port to be a file or string.
+
+Most ports read or write only @sc{ascii} characters.  However, it is
+possible to create ports that will read and write arbitrary characters.
+The limitation to @sc{ascii} characters is imposed entirely by the port,
+not by the @sc{i/o} operations.
+
+@deffn procedure input-port? object
+@deffnx procedure output-port? object
+@cindex type predicate, for input port
+@cindex type predicate, for output port
+Returns @code{#t} if @var{object} is an input port or output port
+respectively, otherwise returns @code{#f}.  Any object satisfying one of
+these predicates also satisfies @code{vector?}.
+@end deffn
+
+@deffn {procedure+} guarantee-input-port object
+@deffnx {procedure+} guarantee-output-port object
+These procedures check the type of @var{object}, signalling an error if it
+is not an input port or output port, respectively.  Otherwise they return
+@var{object}.
+@end deffn
+
+@deffn procedure current-input-port
+@findex console-input-port
+Returns the current input port.  Initially, @code{current-input-port}
+returns the value of @code{console-input-port}.
+@end deffn
+
+@deffn procedure current-output-port
+@findex console-output-port
+Returns the current output port.  Initially, @code{current-output-port}
+returns the value of @code{console-output-port}.
+@end deffn
+
+@deffn {procedure+} with-input-from-port input-port thunk
+@var{Thunk} must be a procedure of no arguments.
+@code{with-input-from-port} binds the current input port to
+@var{input-port}, calls @var{thunk} with no arguments, restores the
+current input port to its original value, and returns the result that
+was returned by @var{thunk}.  This temporary binding is performed the
+same way as fluid binding of a variable, including the behavior in the
+presence of continuations (@pxref{Fluid Binding}).
+@end deffn
+
+@deffn {procedure+} with-output-to-port output-port thunk
+@var{Thunk} must be a procedure of no arguments.
+@code{with-output-to-port} binds the current output port to
+@var{output-port}, calls @var{thunk} with no arguments, restores the
+current output port to its original value, and returns the result that
+was returned by @var{thunk}.  This temporary binding is performed the
+same way as fluid binding of a variable, including the behavior in the
+presence of continuations (@pxref{Fluid Binding}).
+@end deffn
+
+@defvr {variable+} console-input-port
+@cindex port, console
+@cindex input port, console
+@cindex console, input port
+@code{console-input-port} is an input port that reads from the terminal
+keyboard (in unix, standard input).
+@end defvr
+
+@defvr {variable+} console-output-port
+@cindex output port, console
+@cindex console, output port
+@code{console-output-port} is an output port that writes to the terminal
+screen (in unix, standard output).
+@end defvr
+
+@deffn procedure close-input-port input-port
+@cindex closing, of port
+Closes @var{input-port} and returns an unspecified value.  If
+@var{input-port} is a file port, the file is closed.
+@end deffn
+
+@deffn procedure close-output-port output-port
+Closes @var{output-port} and returns an unspecified value.  If
+@var{output-port} is a file port, the file is closed.
+@end deffn
+
+@node File Ports, String Ports, Ports, Input/Output
+@section File Ports
+
+@cindex file, input and output ports
+@cindex port, file
+@cindex input port, file
+@cindex output port, file
+@cindex I/O, to files
+@findex close-input-port
+@findex close-output-port
+Before Scheme can access a file for reading or writing, it is necessary
+to open a port to the file.  This section describes procedures used to
+open ports to files.  Such ports are closed (like any other port) by
+@code{close-input-port} or @code{close-output-port}, depending on their
+type.
+
+@findex canonicalize-input-filename
+@findex canonicalize-output-filename
+Before opening an input file, by whatever method, the @var{filename}
+argument is converted to canonical form by the procedure
+@code{canonicalize-input-filename}.  Similarly, the @var{filename}
+argument used to open an output file is converted using
+@code{canonicalize-output-filename}.  See those procedures' definitions
+for details on the canonicalization process.  For naive purposes, the
+following guidelines can be used: @var{filename} is a character string
+that is the name of the file; relative filenames (on unix, those not
+beginning with @samp{/}) are interpreted relative to the directory in
+which MIT Scheme was started.
+
+Implementation notes:
+
+@itemize @bullet
+@item
+On unix systems, opening an output file that already exists causes the
+existing file to be removed and a new one opened in its place.  However,
+if the user does not have permission to write in the file's directory,
+the file is truncated to zero length and overwritten.
+
+@item
+File input ports always deliver @sc{ascii} characters, and file
+output ports only accept @sc{ascii} characters.  This will change if
+someone ports MIT Scheme to a non-@sc{ascii} operating system.
+@end itemize
+
+Here are the specific operations for file ports:
+
+@deffn procedure open-input-file filename
+@cindex construction, of file input port
+Takes a filename referring to an existing file and returns an input port
+capable of delivering characters from the file.  If the file cannot be
+opened, an error is signalled.
+
+@findex close-input-port
+Use the procedure @code{close-input-port} to close the port opened by
+this procedure.  If an input port returned by this procedure is
+reclaimed by the garbage collector, it is automatically closed.
+@end deffn
+
+@deffn procedure open-output-file filename
+@cindex construction, of file output port
+Takes a filename referring to an output file to be created and returns
+an output port capable of writing characters to a new file by that name.
+If the file cannot be opened, an error is signalled.  If a file with the
+given name already exists, if possible it will be deleted and a new file
+opened in its place, or failing that the existing file will be truncated
+and overwritten.
+
+@findex close-output-port
+Use the procedure @code{close-output-port} to close the port opened by
+this procedure.  If an output port returned by this procedure is
+reclaimed by the garbage collector, it is automatically closed.
+@end deffn
+
+@deffn {procedure+} close-all-open-files
+@cindex closing, of file port
+This procedure closes all file ports (input and output) that are open at
+the time that it is called.
+@end deffn
+
+@deffn procedure call-with-input-file filename procedure
+@deffnx procedure call-with-output-file filename procedure
+@var{Procedure} must be a procedure of one argument.  For
+@code{call-with-input-file} the file specified by @var{filename} must
+already exist; for @code{call-with-output-file}, if the file exists, if
+possible it will be deleted and a new file opened in its place, or
+failing that the existing file will be truncated and overwritten.
+
+These procedures call @var{procedure} with one argument: the port
+obtained by opening the named file for input or output.  If the file
+cannot be opened, an error is signalled.  If @var{procedure} returns,
+then the port is closed automatically and the value yielded by
+@var{procedure} is returned.  If @var{procedure} does not return, then
+the port will not be closed automatically unless it is reclaimed by the
+garbage collector.@footnote{Because Scheme's escape procedures have
+unlimited extent, it is possible to escape from the current continuation
+but later to escape back in.  If implementations were permitted to close
+the port on any escape from the current continuation, then it would be
+impossible to write portable code using both
+@code{call-with-current-continuation} and @code{call-with-input-file} or
+@code{call-with-output-file}.}
+@end deffn
+
+@deffn procedure with-input-from-file filename thunk
+@deffnx procedure with-output-to-file filename thunk
+@cindex current input port, rebinding
+@cindex current output port, rebinding
+@var{Thunk} must be a procedure of no arguments.  For
+@code{with-input-from-file} the file specified by @var{filename} must
+already exist; for @code{with-output-to-file}, if the file exists, if
+possible it will be deleted and a new file opened in its place, or
+failing that the existing file will be truncated and overwritten.
+
+@findex current-input-port
+@findex current-output-port
+The file is opened for input or output, an input or output port
+connected to it is made the default value returned by
+@code{current-input-port} or @code{current-output-port}, and the
+@var{thunk} is called with no arguments.  When the @var{thunk} returns,
+the port is closed and the previous default is restored.
+@code{with-input-from-file} and @code{with-output-to-file} return the
+value yielded by @var{thunk}.  If an escape procedure is used to escape
+from the continuation of these procedures, their behavior is
+implementation-dependent; in that situation MIT Scheme closes the port.
+@end deffn
+
+@node String Ports, Input Procedures, File Ports, Input/Output
+@section String Ports
+
+@cindex string, input and output ports
+@cindex port, string
+@cindex input port, string
+@cindex output port, string
+@cindex I/O, to strings
+This section describes the simplest kinds of ports: input ports that
+read their input from given strings, and output ports that accumulate
+their output and return it as a string.  It also describes
+``truncating'' output ports, that can limit the length of the resulting
+string to a given value.
+
+String input ports always deliver @sc{ascii} characters, and string
+output ports only accept @sc{ascii} characters.  This will change if
+someone ports MIT Scheme to a non-@sc{ascii} operating system.
+
+@deffn {procedure+} with-input-from-string string thunk
+@cindex current input port, rebinding
+Creates a new input port that reads from @var{string}, makes that port
+the current input port, and calls @var{thunk}.  When @var{thunk}
+returns, @code{with-input-from-string} restores the previous current
+input port and returns the result returned by @var{thunk}.
+
+@example
+(with-input-from-string "(a b c) (d e f)" read)  @result{}  (a b c)
+@end example
+
+Note: this procedure is equivalent to:
+
+@example
+(with-input-from-port (string->input-port @var{string}) @var{thunk})
+@end example
+@end deffn
+
+@deffn {procedure+} string->input-port string
+@cindex string, converting to input port
+@cindex construction, of string input port
+Returns a new string port that delivers characters from @var{string}.
+@end deffn
+
+@deffn {procedure+} with-output-to-string thunk
+@cindex current output port, rebinding
+@cindex construction, of string output port
+@findex current-output-port
+@var{Thunk} must be a procedure of no arguments.  Creates a new output
+port that accumulates output, makes that port the default value returned
+by @code{current-output-port}, and calls @var{thunk} with no arguments.
+When @var{thunk} returns, @code{with-output-to-string} restores the
+previous default and returns the accumulated output as a newly allocated
+string.
+
+@example
+(with-output-to-string
+  (lambda ()
+    (write 'abc)))                    @result{}  "abc"
+@end example
+@end deffn
+
+@deffn {procedure+} with-output-to-truncated-string k thunk
+Similar to @code{with-output-to-string}, except that the output is
+limited to @var{k} characters.  If @var{thunk} attempts to write more
+than @var{k} characters, it will be aborted by invoking an escape
+procedure that returns from @code{with-output-to-truncated-string}.
+
+The value of this procedure is a pair; the car of the pair is @code{#t}
+if @var{thunk} attempted to write more than @var{k} characters, and
+@code{#f} otherwise.  The cdr of the pair is a newly allocated string
+containing the accumulated output.
+
+This procedure is helpful for displaying circular lists, as shown in this
+example:
+
+@example
+@group
+(define inf (list 'inf))
+(with-output-to-truncated-string 40
+  (lambda ()
+    (write inf)))                       @result{}  (#f . "(inf)")
+(set-cdr! inf inf)
+(with-output-to-truncated-string 40
+  (lambda ()
+    (write inf)))
+        @result{}  (#t . "(inf inf inf inf inf inf inf inf inf inf")
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} write-to-string object [k]
+@findex with-output-to-truncated-string
+Writes @var{object} to a string output port, and returns the resulting
+newly allocated string.  If @var{k} is supplied and not @code{#f}, the
+output is truncated after @var{k} characters.  Unlike
+@code{with-output-to-truncated-string}, if @var{k} is specified, this
+procedure always returns a string.  There is no sure way to find out
+whether or not the returned string was truncated.
+@end deffn
+
+@node Input Procedures, Output Procedures, String Ports, Input/Output
+@section Input Procedures
+@cindex input operations
+
+This section describes the procedures that read input.  Input procedures
+can read either from the current input port or from a particular port.
+Remember that to read from a file, you must first open a port to the
+file.@footnote{Previous implementations of MIT Scheme treated
+interactive ports specially: when certain of these procedures were
+called, the input editor was temporarily enabled or disabled or the port
+was temporarily switched between blocking and non-blocking modes.  In
+the current implementation, these procedures have no effect on the input
+editor or the blocking mode.}
+
+All optional arguments called @var{input-port}, if not supplied, default
+to the current input port.
+
+@deffn procedure read-char [input-port]
+@cindex character, input from port
+Returns the next character available from @var{input-port}, updating
+@var{input-port} to point to the following character.  If no more
+characters are available, an end-of-file object is returned.
+
+In MIT Scheme, if @var{input-port} is an interactive input port and no
+characters are immediately available, @code{read-char} will hang waiting
+for input.
+@end deffn
+
+@deffn procedure peek-char [input-port]
+Returns the next character available from @var{input-port},
+@emph{without} updating @var{input-port} to point to the following
+character.  If no more characters are available, an end-of-file object
+is returned.@footnote{The value returned by a call to @code{peek-char}
+is the same as the value that would have been returned by a call to
+@code{read-char} on the same port.  The only difference is that the very
+next call to @code{read-char} or @code{peek-char} on that
+@var{input-port} will return the value returned by the preceding call to
+@code{peek-char}.  In particular, a call to @code{peek-char} on an
+interactive port will hang waiting for input whenever a call to
+@code{read-char} would have hung.}
+
+In MIT Scheme, if @var{input-port} is an interactive input port and no
+characters are immediately available, @code{peek-char} will hang waiting
+for input.
+@end deffn
+
+@deffn procedure char-ready? [input-port]
+@findex read-char
+Returns @code{#t} if a character is ready on @var{input-port} and
+returns @code{#f} otherwise.  If @code{char-ready?} returns @code{#t}
+then the next @code{read-char} operation on @var{input-port} is
+guaranteed not to hang.  If @var{input-port} is a file port at end of
+file then @code{char-ready?} returns
+@code{#t}.@footnote{@code{char-ready?} exists to make it possible for a
+program to accept characters from interactive ports without getting
+stuck waiting for input.  Any input editors associated with such ports
+must make sure that characters whose existence has been asserted by
+@code{char-ready?} cannot be rubbed out.  If @code{char-ready?} were to
+return @code{#f} at end of file, a port at end of file would be
+indistinguishable from an interactive port that has no ready
+characters.}
+@end deffn
+
+@deffn procedure read [input-port]
+@cindex expression, input from port
+@cindex external representation, parsing
+@cindex parsing, of external representation
+Converts external representations of Scheme objects into the objects
+themselves.  @code{read} returns the next object parsable from
+@var{input-port}, updating @var{input-port} to point to the first
+character past the end of the written representation of the object.  If
+an end of file is encountered in the input before any characters are
+found that can begin an object, @code{read} returns an end-of-file
+object.  The @var{input-port} remains open, and further attempts to read
+will also return an end-of-file object.  If an end of file is
+encountered after the beginning of an object's written representation,
+but the written representation is incomplete and therefore not parsable,
+an error is signalled.
+@end deffn
+
+@deffn procedure eof-object? object
+@cindex type predicate, for EOF object
+@cindex EOF object, predicate for
+@cindex end of file object (see EOF object)
+@cindex file, end-of-file marker (see EOF object)
+Returns @code{#t} if @var{object} is an end-of-file object; otherwise
+returns @code{#f}.
+@end deffn
+
+@deffn {procedure+} read-char-no-hang [input-port]
+If @var{input-port} can deliver a character without blocking, this
+procedure acts exactly like @code{read-char}, immediately returning that
+character.  Otherwise, @code{#f} is returned, unless @var{input-port} is
+a file port at end of file, in which case an end-of-file object is
+returned.  In no case will this procedure block waiting for input.
+@end deffn
+
+@deffn {procedure+} read-string char-set [input-port]
+@cindex string, input from port
+Reads characters from @var{input-port} until it finds a terminating
+character that is a member of @var{char-set} (@pxref{Character Sets}) or
+encounters end of file.  The port is updated to point to the terminating
+character, or to end of file if no terminating character was found.
+@code{read-string} returns the characters, up to but excluding the
+terminating character, as a newly allocated string.  However, if end of
+file was encountered before any characters were read, @code{read-string}
+returns an end-of-file object.
+
+@findex read-char
+On many input ports, this operation is significantly faster than the
+following equivalent code using @code{peek-char} and @code{read-char}:
+
+@example
+@group
+(define (read-string char-set input-port)
+  (let ((char (peek-char input-port)))
+    (if (eof-object? char)
+        char
+        (list->string
+         (let loop ((char char))
+           (if (or (eof-object? char)
+                   (char-set-member? char-set char))
+               '()
+               (begin
+                 (read-char input-port)
+                 (cons char (loop (peek-char input-port))))))))))
+@end group
+@end example
+@end deffn
+
+@node Output Procedures, Format, Input Procedures, Input/Output
+@section Output Procedures
+@cindex output procedures
+
+All optional arguments called @var{output-port}, if not supplied,
+default to the current output port.
+
+@deffn procedure write-char char [output-port]
+@cindex character, output to port
+Writes @var{char} (the character itself, not a written representation of
+the character) to @var{output-port}, and returns an unspecified
+value.
+@end deffn
+
+@deffn procedure display object [output-port]
+@cindex external representation, generating
+@cindex generating, external representation
+Writes a representation of @var{object} to @var{output-port}.  Strings
+that appear in the written representation are not enclosed in
+doublequotes, and no characters are escaped within those strings.
+Character objects appear in the representation as if written by
+@code{write-char} instead of by @code{write}.  @code{display} returns an
+unspecified value.@footnote{@code{write} is intended for producing
+machine-readable output and @code{display} is for producing
+human-readable output.}
+@end deffn
+
+@deffn procedure write object [output-port]
+@cindex expression, output to port
+Writes a written representation of @var{object} to @var{output-port},
+and returns an unspecified value.  If @var{object} has a standard
+external representation, then the written representation generated by
+@code{write} shall be parsable by @code{read} into an equivalent object.
+Thus strings that appear in the written representation are enclosed in
+doublequotes, and within those strings backslash and doublequote are
+escaped by backslashes.  @code{write} returns an unspecified value.
+@end deffn
+
+@deffn procedure newline [output-port]
+@cindex newline character, output to port
+Writes an end of line to @var{output-port} and returns an unspecified
+value.  Equivalent to @code{(write-char #\newline @var{output-port})}.
+@end deffn
+
+@deffn {procedure+} write-line object [output-port]
+Like @code{write}, except that it writes an end of line to
+@var{output-port} before writing @var{object}'s representation.  Returns
+an unspecified value.
+@end deffn
+
+@deffn {procedure+} write-string string [output-port]
+@cindex string, output to port
+Writes @var{string} to @var{output-port} and returns an unspecified
+value.  This is equivalent to writing the contents of string, one
+character at a time using @code{write-char}, except that it is usually
+much faster.
+
+@code{(write-string @var{string})} is the same as @code{(display
+@var{string})} except that it is faster.  Use @code{write-string} when you
+know the argument is a string, and @code{display} when you don't.
+@end deffn
+
+@deffn {procedure+} beep [output-port]
+@cindex console, ringing the bell
+@cindex ringing the console bell
+@cindex bell, ringing on console
+Performs a ``beep'' operation on @var{output-port} and returns an
+unspecified value.  On the console output port, this usually causes the
+terminal bell to beep, but more sophisticated interactive ports may take
+other actions, such as flashing the screen.  On most output ports, e.g.@:
+file and string output ports, this does nothing.
+@end deffn
+
+@deffn {procedure+} clear [output-port]
+@cindex console, clearing
+@cindex display, clearing
+@cindex screen, clearing
+@cindex terminal screen, clearing
+@cindex clearing the console screen
+``Clears the screen'' of @var{output-port} and returns an unspecified
+value.  On a terminal or window, this has a well-defined effect.  On
+other output ports, e.g.@: file and string output ports, this is
+equivalent to @code{(write-char #\page @var{output-port})}.
+@end deffn
+
+@deffn {procedure+} pp object [output-port [as-code?]]
+@cindex pretty printer
+@code{pp} prints @var{object} in a visually appealing and structurally
+revealing manner on @var{output-port}.  If object is a procedure,
+@code{pp} attempts to print the source text.  If the optional argument
+@var{as-code?} is true, @code{pp} prints lists as Scheme code, providing
+appropriate indentation; by default this argument is false.  @code{pp}
+returns an unspecified value.
+@end deffn
+
+@node Format, Custom Output, Output Procedures, Input/Output
+@section Format
+
+@comment **** begin CLTL ****
+
+The procedure @code{format} is very useful for producing nicely
+formatted text, producing good-looking messages, and so on.  MIT
+Scheme's implementation of @code{format} is similar to that of Common
+Lisp, except that Common Lisp defines many more
+directives.@footnote{This description of @code{format} is adapted from
+@cite{Common Lisp, The Language}, second edition, section 22.3.3.}
+
+@cindex run-time-loadable option
+@cindex option, run-time-loadable
+@code{format} is a run-time-loadable option.  To use it, execute
+
+@example
+(load-option 'format)
+@end example
+@findex load-option
+
+@noindent
+once before calling it.
+
+@deffn {procedure+} format destination control-string argument @dots{}
+@findex write-string
+@cindex format directive (defn)
+@cindex directive, format (defn)
+Writes the characters of @var{control-string} to @var{destination},
+except that a tilde (@code{~}) introduces a @dfn{format directive}.  The
+character after the tilde, possibly preceded by prefix parameters and
+modifiers, specifies what kind of formatting is desired.  Most
+directives use one or more @var{argument}s to create their output; the
+typical directive puts the next @var{argument} into the output,
+formatted in some special way.  It is an error if no argument remains
+for a directive requiring an argument, but it is not an error if one or
+more arguments remain unprocessed by a directive.
+
+The output is sent to @var{destination}.  If @var{destination} is
+@code{#f}, a string is created that contains the output; this string is
+returned as the value of the call to @code{format}.  In all other cases
+@code{format} returns an unspecified value.  If @var{destination} is
+@code{#t}, the output is sent to the current output port.  Otherwise,
+@var{destination} must be an output port, and the output is sent there.
+
+A @code{format} directive consists of a tilde (@code{~}), optional
+prefix parameters separated by commas, optional colon (@code{:}) and
+at-sign (@code{@@}) modifiers, and a single character indicating what
+kind of directive this is.  The alphabetic case of the directive
+character is ignored.  The prefix parameters are generally integers,
+notated as optionally signed decimal numbers.  If both the colon and
+at-sign modifiers are given, they may appear in either order.
+
+@cindex V as format parameter
+@cindex # as format parameter
+In place of a prefix parameter to a directive, you can put the letter
+@samp{V} (or @samp{v}), which takes an @var{argument} for use as a
+parameter to the directive.  Normally this should be an exact integer.
+This feature allows variable-width fields and the like.  You can also
+use the character @samp{#} in place of a parameter; it represents the
+number of arguments remaining to be processed.
+
+It is an error to give a format directive more parameters than it is
+described here as accepting.  It is also an error to give colon or
+at-sign modifiers to a directive in a combination not specifically
+described here as being meaningful.
+
+@table @code
+@item ~A
+The next @var{argument}, which may be any object, is printed as if by
+@code{display}.  @code{~@var{mincol}A} inserts spaces on the right, if
+necessary, to make the width at least @var{mincol} columns.  The
+@code{@@} modifier causes the spaces to be inserted on the left rather
+than the right.
+
+@item ~S
+The next @var{argument}, which may be any object, is printed as if by
+@code{write}.  @code{~@var{mincol}S} inserts spaces on the right, if
+necessary, to make the width at least @var{mincol} columns.  The
+@code{@@} modifier causes the spaces to be inserted on the left rather
+than the right.
+
+@item ~%
+This outputs a @code{#\newline} character.  @code{~@var{n}%} outputs
+@var{n} newlines.  No @var{argument} is used.  Simply putting a newline
+in @var{control-string} would work, but @code{~%} is often used because
+it make the control string look nicer in the middle of a program.
+
+@item ~~
+This outputs a tilde.  @code{~@var{n}~} outputs @var{n} tildes.
+
+@item ~@var{newline}
+Tilde immediately followed by a newline ignores the newline and any
+following non-newline whitespace characters.  With an @code{@@}, the
+newline is left in place, but any following whitespace is ignored.  This
+directive is typically used when @var{control-string} is too long to fit
+nicely into one line of the program:
+
+@example
+@group
+(define (type-clash-error procedure arg spec actual)
+  (format #t
+          "~%Procedure ~S~%requires its %A argument ~
+           to be of type ~S,~%but it was called with ~
+           an argument of type ~S.~%"
+          procedure arg spec actual))
+@end group
+@end example
+
+@code{(type-clash-error 'vector-ref "first" 'integer 'vector)} prints:
+
+@example
+@group
+Procedure vector-ref
+requires its first argument to be of type integer,
+but it was called with an argument of type vector.
+@end group
+@end example
+
+@noindent
+Note that in this example newlines appear in the output only as
+specified by the @code{~%} directives; the actual newline characters in
+the control string are suppressed because each is preceded by a tilde.
+@end table
+@end deffn
+
+@comment **** end CLTL ****
+
+@node Custom Output, Port Primitives, Format, Input/Output
+@section Custom Output
+
+MIT Scheme provides hooks for specifying that certain kinds of objects
+have special written representations.  There are no restrictions on the
+written representations, but only a few kinds of objects may have custom
+representation specified for them, specifically: records
+(@pxref{Records}), vectors that have special tags in their zero-th
+elements (@pxref{Vectors}), and pairs that have special tags in their
+car fields (@pxref{Lists}).  There is a different procedure for
+specifying the written representation of each of these types.
+
+@deffn {procedure+} set-record-type-unparser-method! record-type unparser-method
+Changes the unparser method of the type represented by @var{record-type}
+to be @var{unparser-method}, and returns an unspecified value.
+Subsequently, when the unparser encounters a record of this type, it
+will invoke @var{unparser-method} to generate the written
+representation.
+@end deffn
+
+@deffn {procedure+} unparser/set-tagged-vector-method! tag unparser-method
+Changes the unparser method of the vector type represented by @var{tag}
+to be @var{unparser-method}, and returns an unspecified value.
+Subsequently, when the unparser encounters a vector with @var{tag} as
+its zero-th element, it will invoke @var{unparser-method} to generate
+the written representation.
+@end deffn
+
+@deffn {procedure+} unparser/set-tagged-pair-method! tag unparser-method
+Changes the unparser method of the pair type represented by @var{tag} to
+be @var{unparser-method}, and returns an unspecified value.
+Subsequently, when the unparser encounters a pair with @var{tag} in its
+car field, it will invoke @var{unparser-method} to generate the written
+representation.
+@end deffn
+
+@cindex unparser method (defn)
+@cindex method, unparser (defn)
+An @dfn{unparser method} is a procedure that is invoked with two
+arguments: first, an unparser state, and second, an object.  An unparser
+method generates a written representation for the object, writing it to
+the output port specified by the unparser state.  The value yielded by
+an unparser method is ignored.  Note that an unparser state is not an
+output port, rather it is an object that contains an output port as one
+of its components.  Application programs generally do not construct or
+examine unparser state objects, but just pass them along.
+
+There are two ways to create an unparser method (which is then
+registered by one of the above procedures).  The first, and easiest, is
+to use @code{unparser/standard-method}.  The second is to define your
+own method using the procedures @code{unparse-char},
+@code{unparse-string}, and @code{unparse-object}.  We encourage the use
+of the first method, as it results in a more uniform appearance for
+objects.  Many predefined datatypes, for example procedures and
+environments, already have this appearance.
+
+@deffn {procedure+} unparser/standard-method name [procedure]
+Returns a standard unparser method.  @var{Name} may be any object, and
+is used as the name of the type with which the unparser method is
+associated; @var{name} is usually a symbol.  @var{Procedure}, if
+supplied, must be @code{#f} or a procedure of two arguments.
+
+@cindex #[ as external representation
+If @var{procedure} is not supplied, or is @code{#f}, the returned method
+generates an external representation of this form:
+
+@example
+#[@var{name} @var{hash}]
+@end example
+
+@noindent
+@findex display
+@findex object-hash
+Here @var{name} is the external representation of the argument
+@var{name}, as generated by @code{display}, and @var{hash} is the
+external representation of an exact non-negative integer unique to the
+object being printed (specifically, it is the result of calling
+@code{object-hash} on the object).  Subsequently, the expression
+
+@example
+#@@@var{hash}
+@end example
+
+@noindent
+is notation for the object.
+
+If @var{procedure} is supplied, the returned method generates a slightly
+different external representation:
+
+@example
+#[@var{name} @var{hash} @var{output}]
+@end example
+
+@noindent
+Here @var{name} and @var{hash} are as above, and @var{output} is the
+output generated by @var{procedure}.  The representation is constructed
+in three stages:
+
+@enumerate
+@item
+The first part of the format (up to @var{output}) is written to the
+output port specified by the unparser state.  This includes the space
+between @var{hash} and @var{output}.
+
+@item
+@var{Procedure} is invoked on two arguments: the unparser state and the
+object.
+
+@item
+The closing bracket is written to the output port.
+@end enumerate
+@end deffn
+
+The following three procedures are useful when writing unparser methods.
+
+@deffn {procedure+} unparse-char unparser-state char
+@findex write-char
+Writes @var{char} to the output-port component of @var{unparser-state},
+and returns an unspecified value.  Similar to @code{write-char}.
+@end deffn
+
+@deffn {procedure+} unparse-string unparser-state string
+@findex write-string
+Writes @var{string} to the output-port component of
+@var{unparser-state}, and returns an unspecified value.  Similar to
+@code{write-string}.
+@end deffn
+
+@deffn {procedure+} unparse-object unparser-state object
+@findex display
+@findex write
+Writes @var{object} to the output-port component of
+@var{unparser-state}, and returns an unspecified value.  @var{Object} is
+generated either as if by @code{display} or as if by @code{write},
+depending on other components of @var{unparser-state}.
+@end deffn
+
+@node Port Primitives,  , Custom Output, Input/Output
+@section Port Primitives
+@cindex port primitives
+
+This section describes the low-level operations that can be used to
+build and manipulate @sc{i/o} ports.
+
+The purpose of these operations is twofold: to allow programmers to
+construct new kinds of @sc{i/o} ports, and to provide faster @sc{i/o}
+operations than those supplied by the standard high level procedures.
+The latter is useful because the standard @sc{i/o} operations provide
+defaulting and error checking, and sometimes other features, which are
+often unnecessary.  This interface provides the means to bypass such
+features, thus improving performance.
+
+@findex eq?
+The abstract model of an @sc{i/o} port, as implemented here, is a
+combination of a set of named operations and a state.  The state is an
+arbitrary object, the meaning of which is determined by the operations.
+The operations are defined by a mapping from names to procedures.
+Typically the names are symbols, but any object that can be
+discriminated by @code{eq?} may be used.
+
+The operations are divided into two classes:
+
+@table @asis
+@item Standard operations
+There is a specific set of standard operations for input ports, and a
+different set for output ports.  Applications can assume that the
+appropriate set of operations is implemented for every port.
+@cindex standard operations, on port
+
+@item Custom operations
+Some ports support additional operations.  For example, ports that
+implement output to terminals (or windows) may define an operation named
+@code{y-size} that returns the height of the terminal in characters.
+Because only some ports will implement these operations, programs that
+use custom operations must test each port for their existence, and be
+prepared to deal with ports that do not implement them.
+@cindex custom operations, on port
+@findex y-size
+@end table
+
+@menu
+* Input Port Primitives::       Input Port Primitives
+* Output Port Primitives::      Output Port Primitives
+@end menu
+
+@node Input Port Primitives, Output Port Primitives, Port Primitives, Port Primitives
+@subsection Input Port Primitives
+@cindex input port primitives
+
+@deffn {procedure+} make-input-port operations object
+@cindex construction, of input port
+Operations must be a list; each element is a list of two elements, the
+name of the operation and the procedure that implements it.  A new input
+port is returned with the given operations and a state component of
+@var{object}.  @var{Operations} need not contain definitions for all of
+the standard operations.  @code{make-input-port} will provide defaults
+for any standard operations that are not defined.  At a minimum, the
+operations @code{read-char}, @code{peek-char}, and @code{char-ready?}
+must be defined.
+@end deffn
+
+@deffn {procedure+} input-port/copy input-port object
+@cindex copying, of input port
+Returns a new copy of @var{input-port}, identical to the original except
+that its state component is @var{object}.  @var{Input-port} is not
+modified.
+
+@code{input-port/copy} is normally used to speed up creation of input
+ports.  This is done by creating a template using
+@code{make-input-port}; a dummy state component is supplied for the
+template.  Then @code{input-port/copy} is used to make a copy of the
+template, supplying the copy with the correct state.  This is useful
+because @code{make-input-port} is somewhat slow, as it must parse the
+@var{operations} list, provide defaulting for missing operations, etc.
+@end deffn
+
+@deffn {procedure+} input-port/state input-port
+Returns the state component of @var{input-port}.
+@end deffn
+
+@deffn {procedure+} set-input-port/state! input-port object
+Changes the state component of @var{input-port} to be @var{object}.
+Returns an unspecified value.
+@end deffn
+
+@deffn {procedure+} input-port/operation input-port name
+Returns the procedure that implements the operation called @var{name},
+or @code{#f} if @var{input-port} has no such operation.
+@end deffn
+
+@deffn {procedure+} input-port/custom-operation input-port name
+Returns the procedure that implements the custom operation called
+@var{name}.  If @var{name} names a standard operation, or if
+@var{input-port} has no such custom operation, @code{#f} is returned.
+This is faster than @code{input-port/operation} if @var{name} is known
+to be the name of a custom operation.
+@end deffn
+
+@deffn {procedure+} make-eof-object input-port
+@cindex EOF object, construction
+@cindex construction, of EOF object
+@findex eof-object?
+Returns an object that satisfies the predicate @code{eof-object?}.  This
+is sometimes useful when building input ports.
+@end deffn
+
+The following are the standard operations on input ports.
+
+@defop {operation+} input-port read-char input-port
+@cindex character, input from port
+Removes the next character available from @var{input-port} and returns
+it.  If @var{input-port} has no more characters and will never have any
+(e.g.@: at the end of an input file), this operation returns an
+end-of-file object.  If @var{input-port} has no more characters but will
+eventually have some more (e.g.@: a terminal where nothing has been typed
+recently), and it is in non-blocking mode, @code{#f} is returned;
+otherwise the operation hangs until input is available.
+@end defop
+
+@defop {operation+} input-port peek-char input-port
+Reads the next character available from @var{input-port} and returns it.
+The character is @emph{not} removed from @var{input-port}, and a
+subsequent attempt to read from the port will get that character again.
+In other respects this operation behaves like @code{read-char}.
+@end defop
+
+@defop {operation+} input-port discard-char input-port
+Discards the next character available from @var{input-port} and returns
+an unspecified value.  In other respects this operation behaves like
+@code{read-char}.
+@end defop
+
+@defop {operation+} input-port char-ready? input-port k
+@code{char-ready?} returns @code{#t} if at least one character is
+available to be read from @var{input-port}.  If no characters are
+available, the operation waits up to @var{k} milliseconds before
+returning @code{#f}, returning immediately if any characters become
+available while it is waiting.
+@end defop
+
+@defop {operation+} input-port read-string input-port char-set
+@defopx {operation+} input-port discard-chars input-port char-set
+@cindex string, input from port
+These operations are like @code{read-char} and @code{discard-char},
+except that they read or discard multiple characters at once.  This can
+have a marked performance improvement on buffered input ports.  All
+characters up to, but excluding, the first character in @var{char-set}
+(or end of file) are read from @var{input-port}.  @code{read-string}
+returns these characters as a newly allocated string, while
+@code{discard-chars} discards them and returns an unspecified value.
+These operations hang until sufficient input is available, even if
+@var{input-port} is in non-blocking mode.  If end of file is encountered
+before any input characters, @code{read-string} returns an end-of-file
+object.
+@end defop
+
+@deffn {procedure+} input-port/operation/read-char input-port
+@deffnx {procedure+} input-port/operation/peek-char input-port
+@deffnx {procedure+} input-port/operation/discard-char input-port
+@deffnx {procedure+} input-port/operation/char-ready? input-port
+@deffnx {procedure+} input-port/operation/read-string input-port
+@deffnx {procedure+} input-port/operation/discard-chars input-port
+Each of these procedures returns the procedure that implements the
+respective operation for @var{input-port}.  Each is equivalent to, but
+faster than, @code{input-port/operation} on the respective operation
+name:
+
+@example
+@group
+(input-port/operation/read-char @var{input-port})
+(input-port/operation @var{input-port} 'read-char)
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} input-port/read-char input-port
+@deffnx {procedure+} input-port/peek-char input-port
+@deffnx {procedure+} input-port/discard-char input-port
+@deffnx {procedure+} input-port/char-ready? input-port k
+@deffnx {procedure+} input-port/read-string input-port char-set
+@deffnx {procedure+} input-port/discard-chars input-port char-set
+Each of these procedures invokes the respective operation on
+@var{input-port}.  For example, the following are equivalent:
+
+@example
+@group
+(input-port/read-string @var{input-port} @var{char-set})
+((input-port/operation/read-string @var{input-port}) @var{input-port} @var{char-set})
+@end group
+@end example
+@end deffn
+
+@node Output Port Primitives,  , Input Port Primitives, Port Primitives
+@subsection Output Port Primitives
+@cindex output port primitives
+
+@deffn {procedure+} make-output-port operations object
+@cindex construction, of output port
+Operations must be a list; each element is a list of two elements, the
+name of the operation and the procedure that implements it.  A new
+output port is returned with the given operations and a state component
+of @var{object}.  @var{Operations} need not contain definitions for all
+of the standard operations.  @code{make-output-port} will provide
+defaults for any standard operations that are not defined.  At a
+minimum, the operation @code{write-char} must be defined.
+@end deffn
+
+@deffn {procedure+} output-port/copy output-port object
+@cindex copying, of output port
+Returns a new copy of @var{output-port}, identical to the original except
+that its state component is @var{object}.  @var{Output-port} is not
+modified.
+
+@code{output-port/copy} is normally used to speed up creation of output
+ports.  This is done by creating a template using
+@code{make-output-port}; a dummy state component is supplied for the
+template.  Then @code{output-port/copy} is used to make a copy of the
+template, supplying the copy with the correct state.  This is useful
+because @code{make-output-port} is somewhat slow, as it must parse the
+@var{operations} list, provide defaulting for missing operations, etc.
+@end deffn
+
+@deffn {procedure+} output-port/state output-port
+Returns the state component of @var{output-port}.
+@end deffn
+
+@deffn {procedure+} set-output-port/state! output-port object
+Changes the state component of @var{output-port} to be @var{object}.
+Returns an unspecified value.
+@end deffn
+
+@deffn {procedure+} output-port/operation output-port name
+Returns the procedure that implements the operation called @var{name},
+or @code{#f} if @var{output-port} has no such operation.
+@end deffn
+
+@deffn {procedure+} output-port/custom-operation output-port name
+Returns the procedure that implements the custom operation called
+@var{name}.  If @var{name} names a standard operation, or if
+@var{output-port} has no such custom operation, @code{#f} is returned.
+This is faster than @code{output-port/operation} if @var{name} is known
+to be the name of a custom operation.
+@end deffn
+
+The following are the standard operations on output ports.
+
+@defop {operation+} output-port write-char output-port char
+@cindex character, output to port
+Writes @var{char} to @var{output-port} and returns an unspecified value.
+@end defop
+
+@defop {operation+} output-port write-string output-port string
+@cindex string, output to port
+Writes @var{string} to @var{output-port} and returns an unspecified
+value.  Equivalent to writing the characters of @var{string}, one by
+one, to @var{output-port}, but is often implemented more efficiently.
+@end defop
+
+@defop {operation+} output-port flush-output output-port
+If @var{output-port} is buffered, this causes its buffer to be written
+out.  Otherwise it has no effect.  Returns an unspecified value.
+@end defop
+
+@deffn {procedure+} output-port/operation/write-char output-port
+@deffnx {procedure+} output-port/operation/write-string output-port
+@deffnx {procedure+} output-port/operation/flush-output output-port
+Each of these procedures returns the procedure that implements the
+respective operation for @var{output-port}.  Each is equivalent to, but
+faster than, @code{output-port/operation} on the respective operation
+name:
+
+@example
+@group
+(output-port/operation/write-char @var{output-port})
+(output-port/operation @var{output-port} 'write-char)
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} output-port/write-char output-port char
+@deffnx {procedure+} output-port/write-string output-port string
+@deffnx {procedure+} output-port/flush-output output-port
+Each of these procedures invokes the respective operation on
+@var{output-port}.  For example, the following are equivalent:
+
+@example
+@group
+(output-port/write-char @var{output-port} @var{char})
+((output-port/operation/write-char @var{output-port}) @var{output-port} @var{char})
+@end group
+@end example
+@end deffn
+
+The custom operation @code{x-size} is so useful that we provide a
+procedure to call it:
+
+@deffn {procedure+} output-port/x-size output-port
+This procedure invokes the custom operation whose name is the symbol
+@code{x-size}, if it exists.  If the @code{x-size} operation is both
+defined and returns a value other than @code{#f}, that value is returned
+as the result of this procedure.  Otherwise, @code{output-port/x-size}
+returns a default value (currently 79).
+
+@code{output-port/x-size} is useful for programs that tailor their
+output to the width of the display (a fairly common practice).  If the
+output device is not a display, such programs normally want some
+reasonable default width to work with, and this procedure provides
+exactly that.
+@end deffn
+
+@defop {operation+} output-port x-size output-port
+Returns an exact positive integer that is the width of @var{output-port}
+in characters.  If @var{output-port} has no natural width, e.g.@: if it is
+a file port, @code{#f} is returned.
+@end defop
+
+@node File-System Interface, Error System, Input/Output, Top
+@chapter File-System Interface
+@cindex file-system interface
+
+The Scheme standard provides a simple mechanism for reading and writing
+files: file ports.  MIT Scheme provides additional tools for
+dealing with other aspects of the file system:
+
+@itemize @bullet
+@item
+@dfn{Pathnames} are a reasonably operating system independent tool for
+manipulating the component parts of file names.  This can be useful for
+implementing defaulting of file name components.
+@cindex pathname
+
+@item
+Control over the @dfn{current working directory}: the place in the file
+system from which relative file names are interpreted.
+@cindex current working directory
+
+@item
+Procedures that rename, copy, delete, and test for the existence of
+files.  Also, procedures that return detailed information about a
+particular file, such as its type (directory, link, etc.) or length.
+
+@item
+A facility for reading the contents of a directory.
+@end itemize
+
+@menu
+* Pathnames::                   Pathnames
+* Working Directory::           Working Directory
+* File Manipulation::           File Manipulation
+* Directory Reader::            Directory Reader
+@end menu
+
+@node Pathnames, Working Directory, File-System Interface, File-System Interface
+@section Pathnames
+
+@comment **** begin CLTL ****
+@cindex file name
+MIT Scheme programs need to use names to designate files.  The main
+difficulty in dealing with names of files is that different file systems
+have different naming formats for files.  For example, here is a table
+of several file systems (actually, operating systems that provide file
+systems) and what equivalent file names might look like for each one:
+
+@example
+@group
+System          File Name
+------          ---------
+TOPS-20         <LISPIO>FORMAT.FASL.13
+TOPS-10         FORMAT.FAS[1,4]
+ITS             LISPIO;FORMAT FASL
+MULTICS         >udd>LispIO>format.fasl
+TENEX           <LISPIO>FORMAT.FASL;13
+VAX/VMS         [LISPIO]FORMAT.FAS;13
+UNIX            /usr/lispio/format.fasl
+@end group
+@end example
+
+@cindex filename (defn)
+@cindex pathname (defn)
+It would be impossible for each program that deals with file names to
+know about each different file name format that exists; a new operating
+system to which Scheme was ported might use a format different from any
+of its predecessors.  Therefore, MIT Scheme provides @emph{two}
+ways to represent file names: @dfn{filenames}, which are strings in the
+implementation-dependent form customary for the file system, and
+@dfn{pathnames}, which are special abstract data objects that represent
+file names in an implementation-independent way.  Procedures are
+provided to convert between these two representations, and all
+manipulations of files can be expressed in machine-independent terms by
+using pathnames.
+
+@cindex host, in filename
+In order to allow MIT Scheme programs to operate in a network
+environment that may have more than one kind of file system, the
+pathname facility allows a file name to specify which file system is to
+be used.  In this context, each file system is called a @dfn{host}, in
+keeping with the usual networking terminology.@footnote{This
+introduction is adapted from @cite{Common Lisp, The Language}, second
+edition, section 23.1.}
+@comment **** end CLTL ****
+
+Note that the examples given in this section are specific to unix
+pathnames.  Pathnames for other operating systems have different
+external representations.
+
+@menu
+* Filenames and Pathnames::     Filenames and Pathnames
+* Components of Pathnames::     Components of Pathnames
+* Operations on Pathnames::     Operations on Pathnames
+@end menu
+
+@node Filenames and Pathnames, Components of Pathnames, Pathnames, Pathnames
+@subsection Filenames and Pathnames
+
+Pathname objects are usually created by parsing filenames (character
+strings) into component parts.  MIT Scheme provides operations that
+convert filenames into pathnames and vice versa.  In addition,
+@code{->pathname} will convert other objects, such as symbols, into
+pathnames.
+
+@deffn {procedure+} ->pathname object
+@cindex construction, of pathname
+Returns a pathname that is the equivalent of @var{object}.
+@var{Object} must be a pathname, a string, or a symbol.  If @var{object}
+is a pathname, it is returned.  If @var{object} is a string, this
+procedure acts like @code{string->pathname}.  If @var{object} is a
+symbol, it is converted to a string, passed to @code{string->pathname},
+and the result returned.
+
+@example
+@group
+(->pathname "foo")              @result{}  #[pathname 65 "foo"]
+(->pathname '/usr/morris)       @result{}  #[pathname 66 "/usr/morris"]
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} string->pathname string
+@cindex string, converting to pathname
+Returns the pathname that corresponds to the filename @var{string}.
+This operation is the inverse of @code{pathname->string}.
+@end deffn
+
+@deffn {procedure+} pathname->string pathname
+@findex string->pathname
+Returns a newly allocated string that is the filename corresponding to
+@var{pathname}.  This operation is the inverse of
+@code{string->pathname}.
+
+@example
+@group
+(pathname->string (string->pathname "/usr/morris/foo"))
+     @result{}  "/usr/morris/foo"
+@end group
+@end example
+@end deffn
+
+@node Components of Pathnames, Operations on Pathnames, Filenames and Pathnames, Pathnames
+@subsection Components of Pathnames
+@cindex components, of pathname
+@cindex pathname components
+
+@comment **** begin CLTL ****
+A pathname object always has six components, described below.  These
+components are the common interface that allows programs to work the
+same way with different file systems; the mapping of the pathname
+components into the concepts peculiar to each file system is taken care
+of by the Scheme implementation.
+
+@table @var
+@item host
+The name of the file system on which the file resides.  In the current
+implementation of MIT Scheme, this component is not used and should
+always be @code{#f}.
+@cindex host, pathname component
+
+@item device
+Corresponds to the ``device'' or ``file structure'' concept in many host
+file systems: the name of a (logical or physical) device containing
+files.  In the current implementation of MIT Scheme, this component
+is not used and should always be @code{#f}.
+@cindex device, pathname component
+
+@item directory
+Corresponds to the ``directory'' concept in many host file systems: the
+name of a group of related files (typically those belonging to a single
+user or project).
+@cindex directory, pathname component
+
+@item name
+The name of a group of files that can be thought of as conceptually the
+``same'' file.
+@cindex name, pathname component
+
+@item type
+Corresponds to the ``filetype'' or ``extension'' concept in many host
+file systems.  This says what kind of file this is.  Files with the same
+name but different type are usually related in some specific way, such
+as one being a source file, another the compiled form of that source,
+and a third the listing of error messages from the compiler.
+@cindex type, pathname component
+
+@item version
+Corresponds to the ``version number'' concept in many host file systems.
+Typically this is a number that is incremented every time the file is
+modified.  In the current implementation of MIT Scheme, this
+component is not used and should always be @code{#f}.
+@cindex version, pathname component
+@end table
+
+Note that a pathname is not necessarily the name of a specific file.
+Rather, it is a specification (possibly only a partial specification) of
+how to access a file.  A pathname need not correspond to any file that
+actually exists, and more than one pathname can refer to the same file.
+For example, the pathname with a version of @code{newest} may refer to
+the same file as a pathname with the same components except a certain
+number as the version.  Indeed, a pathname with version @code{newest}
+may refer to different files as time passes, because the meaning of such
+a pathname depends on the state of the file system.  In file systems
+with such facilities as ``links'', multiple file names, logical devices,
+and so on, two pathnames that look quite different may turn out to
+address the same file.  To access a file given a pathname, one must do a
+file-system operation such as @code{open-input-file}.@footnote{This
+description is adapted from @cite{Common Lisp, The Language}, second
+edition, section 23.1.1.}
+@comment **** end CLTL ****
+
+Each component in a pathname is typically one of the following (with
+some exceptions that will be described below):
+
+@table @asis
+@item a string
+This is a @dfn{literal component}.  It is considered to be fully
+specified.
+@cindex literal component, of pathname
+@cindex pathname component, literal
+@cindex component, of pathname, literal
+
+@item @code{#f}
+This is a @dfn{missing component}.  It is considered to be unspecified.
+@cindex #f, as pathname component
+@cindex missing component, of pathname
+@cindex pathname component, missing
+@cindex component, of pathname, missing
+
+@item @code{wild}
+This is a @dfn{wildcard component}.  It is useful only when the pathname
+is being used with the directory reader, where it means that the
+pathname component matches anything.
+@cindex wild, as pathname component
+@cindex wildcard component, of pathname
+@cindex pathname component, wildcard
+@cindex component, of pathname, wildcard
+
+@item @code{unspecific}
+This is an @dfn{unspecifiable component}.  It is treated the same as a
+missing component except that it is not considered to be missing for
+purposes of merging or defaulting components.
+@cindex unspecifiable component, of pathname
+@cindex unspecific, as pathname component
+@cindex component, of pathname, unspecific
+@end table
+
+The directory and version pathname components are exceptions to these
+rules in that they may never be strings, although the values @code{#f},
+@code{wild}, and @code{unspecific} are allowed with their usual
+meanings.  Here are the other values allowed for these components:
+
+@itemize @bullet
+@item
+A directory, if it is not one of the above values, must be a non-empty
+list, which represents a @dfn{directory path}: a sequence of
+directories, each of which has a name in the previous directory, the
+last of which is the directory specified by the entire path.  Each
+element in such a path specifies the name of the directory relative to
+the directory specified by the elements to its left.  If the first
+element in the list is the symbol @code{root}, then the directory
+component (and subsequently the pathname) is @dfn{absolute}; the first
+component in the sequence is to be found at the ``root'' of the file
+system.  Otherwise, the directory is @dfn{relative}, meaning that the
+first component is to be found in some as yet unspecified directory;
+typically this is later specified to be the @dfn{current working
+directory}.
+@cindex root, as pathname component
+@cindex directory path (defn)
+@cindex path, directory (defn)
+
+@cindex self, as pathname component
+@cindex up, as pathname component
+@cindex parent, of directory
+Aside from the special case of @code{root}, which may only appear as the
+first element of the list (if it appears at all), each element in the
+list is either a string or the symbol @code{wild} (each with the same
+meaning as described above), or one of these symbols: @code{self}, which
+means the next directory in the sequence is the same as the previous
+one, or @code{up}, which means the next directory is the ``parent'' of
+the previous one.  @code{self} and @code{up} correspond to the files
+@file{.} and @file{..} in unix file systems.
+
+In file systems that do not have ``heirarchical'' structure, a specified
+directory component will always be a list whose first element is
+@code{root}.  If the system does not support directories other than a
+single global directory, the list will have no other elements.  If the
+system supports ``flat'' directories, i.e.@: a global set of directories
+with no subdirectories, then the list will contain a second element,
+whiich is either a string or @code{wild}.  In other words, a
+non-heirarchical file system is treated as if it were heirarchical, but
+the heirarchical features are unused.  This representation is somewhat
+inconvenient for such file systems, but it discourages programmers from
+making code depend on the lack of a file heirarchy.  Fortunately few
+such file systems are in common use today.
+
+@item
+A version component may take the following values: an exact positive
+integer, which is a literal component; the symbol @code{newest}, which
+means to choose the largest available version number for that file; or
+the symbol @code{oldest}, which means to choose the smallest version
+number.  In the future some other possible values may be added, e.g.@:
+@code{installed}.  Note that in the current implementation this
+component is not used and should be @code{#f}.
+@cindex newest, as pathname component
+@cindex oldest, as pathname component
+@cindex installed, as pathname component
+@end itemize
+
+@deffn {procedure+} make-pathname host device directory name type version
+@cindex construction, of pathname
+Returns a pathname object whose components are the respective arguments.
+Each argument must satisfy the restrictions for the corresponding
+component, which were outlined above.
+
+@example
+@group
+(make-pathname #f #f '(root "usr" "morris") "foo" "scm" #f)
+     @result{}  #[pathname 67 "/usr/morris/foo.scm"]
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} pathname-host pathname
+@deffnx {procedure+} pathname-device pathname
+@deffnx {procedure+} pathname-directory pathname
+@deffnx {procedure+} pathname-name pathname
+@deffnx {procedure+} pathname-type pathname
+@deffnx {procedure+} pathname-version pathname
+Returns a particular component of @var{pathname}.
+
+@example
+@group
+(define x (->pathname "/usr/morris/foo.scm"))
+(pathname-host x)       @result{}  #f
+(pathname-device x)     @result{}  #f
+(pathname-directory x)  @result{}  (root "usr" "morris")
+(pathname-name x)       @result{}  "foo"
+(pathname-type x)       @result{}  "scm"
+(pathname-version x)    @result{}  #f
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} pathname-components pathname receiver
+Calls @var{receiver} with the six components of @var{pathname}, and
+returns the result yielded by @var{receiver}.
+
+@example
+@group
+(pathname-components (->pathname "/usr/morris/foo.scm") list)
+     @result{}  (#f #f (root "usr" "morris") "foo" "scm" #f)
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} pathname-new-host pathname host
+@deffnx {procedure+} pathname-new-device pathname device
+@deffnx {procedure+} pathname-new-directory pathname directory
+@deffnx {procedure+} pathname-new-name pathname name
+@deffnx {procedure+} pathname-new-type pathname type
+@deffnx {procedure+} pathname-new-version pathname version
+Returns a new copy of @var{pathname} with the respective component
+replaced by the second argument.  @var{Pathname} is unchanged.
+
+@example
+@group
+(define p (->pathname "/usr/blisp/rel15"))
+p
+     @result{}  #[pathname 71 "/usr/blisp/rel15"]
+(pathname-new-name p "rel100")
+     @result{}  #[pathname 72 "/usr/blisp/rel100"]
+(pathname-new-directory p '("test" "morris"))
+     @result{}  #[pathname 73 "test/morris/rel15"]
+p
+     @result{}  #[pathname 71 "/usr/blisp/rel15"]
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} pathname-name-path pathname
+Extracts the name, type, and version components of @var{pathname} and
+returns a pathname with just these components.  For example,
+
+@example
+@group
+(pathname-name-path (->pathname "/usr/blisp/rel5"))
+     @result{}  #[pathname 69 "rel5"]
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} pathname-directory-path pathname
+Extracts the host, device, and directory components of @var{pathname}
+and returns a pathname with just these components.
+
+@example
+@group
+(pathname-directory-path (->pathname "/usr/blisp/rel5"))
+     @result{}  #[pathname 70 "/usr/blisp/"]
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} pathname-as-directory pathname
+@cindex directory, converting pathname to
+Returns a pathname that is equivalent to pathname, but in which any file
+components have been converted to a directory component.  If
+@var{pathname} does not have name, type, or version components, it is
+returned.  Otherwise, these file components are converted into a string,
+and the string is added to the end of the list of directory components.
+Note the difference between this procedure and
+@code{pathname-directory-path}.
+
+@example
+@group
+(pathname-as-directory (->pathname "/usr/blisp/rel5"))
+     @result{}  #[pathname "/usr/blisp/rel5/"]
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} pathname-name-string pathname
+Extracts the name, type, and version components of @var{pathname} and
+returns a newly allocated filename (string) with just these components.
+For example,
+
+@example
+@group
+(pathname-name-string (->pathname "/usr/blisp/rel5"))
+     @result{}  "rel5"
+@end group
+@end example
+
+@code{pathname-name-string} could have been defined as follows:
+
+@example
+@group
+(define (pathname-name-string pathname)
+  (pathname->string (pathname-name-path pathname)))
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} pathname-directory-string pathname
+Extracts the host, device, and directory components of @var{pathname}
+and returns a newly allocated filename (string) with just these
+components.
+
+@example
+@group
+(pathname-directory-string (->pathname "/usr/blisp/rel5"))
+     @result{}  "/usr/blisp/"
+@end group
+@end example
+
+@code{pathname-directory-string} could have been defined as follows:
+
+@example
+@group
+(define (pathname-directory-string pathname)
+  (pathname->string (pathname-directory-path pathname)))
+@end group
+@end example
+@end deffn
+
+@node Operations on Pathnames,  , Components of Pathnames, Pathnames
+@subsection Operations on Pathnames
+
+@deffn {procedure+} pathname? object
+@cindex type predicate, for pathname
+Returns @code{#t} if @var{object} is a pathname; otherwise returns
+@code{#f}.
+@end deffn
+
+@deffn {procedure+} merge-pathnames pathname1 pathname2
+@cindex merging, of pathnames
+@cindex defaulting, of pathname
+Returns a pathname whose components are obtained by combining those of
+@var{pathname1} and @var{pathname2}.  The pathnames are combined by
+components: if @var{pathname1} has a non-missing component, that is the
+resulting component, otherwise the component from @var{pathname2} is
+used.  The directory component is handled specially: if both pathnames
+have directory components that are lists, and the directory component
+from @var{pathname1} is relative (i.e.@: does not start with @code{root}),
+the the resulting directory component is formed by appending
+@var{pathname1}'s component to @var{pathname2}'s component.  For
+example:
+
+@example
+@group
+(define path1 (->pathname "scheme/foo.scm"))
+(define path2 (->pathname "/usr/morris"))
+path1
+     @result{}  #[pathname 74 "scheme/foo.scm"]
+path2
+     @result{}  #[pathname 75 "/usr/morris"]
+(merge-pathnames path1 path2)
+     @result{}  #[pathname 76 "/usr/scheme/foo.scm"]
+(merge-pathnames path2 path1)
+     @result{}  #[pathname 77 "/usr/morris.scm"]
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} pathname-default-host pathname host
+@deffnx {procedure+} pathname-default-device pathname device
+@deffnx {procedure+} pathname-default-directory pathname directory
+@deffnx {procedure+} pathname-default-name pathname name
+@deffnx {procedure+} pathname-default-type pathname type
+@deffnx {procedure+} pathname-default-version pathname version
+These operations are similar to the @code{pathname-new-@var{component}}
+operations, except that they only change the specified @var{component}
+if it has the value @code{#f} in @var{pathname}.
+@end deffn
+
+@deffn {procedure+} pathname-default pathname host device directory name type version
+This procedure defaults all of the components of @var{pathname}
+simultaneously.  It could have been defined by:
+
+@example
+@group
+(define (pathname-default pathname
+                          host device directory
+                          name type version)
+  (make-pathname (or (pathname-host pathname) host)
+                 (or (pathname-device pathname) device)
+                 (or (pathname-directory pathname) directory)
+                 (or (pathname-name pathname) name)
+                 (or (pathname-type pathname) type)
+                 (or (pathname-version pathname) version)))
+@end group
+@end example
+@end deffn
+
+@node Working Directory, File Manipulation, Pathnames, File-System Interface
+@section Working Directory
+
+@cindex absolute pathname (defn)
+@cindex pathname, absolute (defn)
+@cindex relative pathname (defn)
+@cindex pathname, relative (defn)
+@cindex directory, current working (defn)
+@cindex current working directory (defn)
+@cindex working directory (see current working directory)
+A pathname may be absolute or relative.  An @dfn{absolute pathname} is a
+complete path from the top level of the file system to the destination
+resource (under unix, a filename corresponding to an absolute pathname
+begins with the slash character, @samp{/}).  A @dfn{relative pathname}
+is a partial path that's interpreted relative to the current working
+directory.  When MIT Scheme is started, the @dfn{current working
+directory} (or simply, @dfn{working directory}) is initialized in an
+operating-system dependent manner; usually, it is the directory in which
+Scheme was invoked.  The working directory can be determined from within
+Scheme by calling the @code{pwd} procedure, and changed by calling the
+@code{cd} procedure.
+
+@deffn {procedure+} working-directory-pathname
+@deffnx {procedure+} pwd
+Returns the current working directory as a pathname that has no name,
+type, or version components, just host, device, and directory
+components.  @code{pwd} is an alias for
+@code{working-directory-pathname}.  The long name is intended for
+programs and the short name for interactive use.
+@end deffn
+
+@deffn {procedure+} set-working-directory-pathname! filename
+@deffnx {procedure+} cd filename
+@findex ->pathname
+@findex pathname->absolute-pathname
+@findex pathname-as-directory
+Makes @var{filename} the current working directory and returns the new
+current working directory as a pathname.  @var{Filename} is coerced
+using @code{->pathname}, @code{pathname->absolute-pathname}, and
+@code{pathname-as-directory}.  @code{cd} is an alias for
+@code{set-working-directory-pathname!}.  The long name is intended for
+programs and the short name for interactive use.
+
+@example
+@group
+(set-working-directory-pathname! "/usr/morris/blisp")
+     @result{}  #[pathname "/usr/morris/blisp/"]
+(set-working-directory-pathname! "~")
+     @result{}  #[pathname "/usr/morris/"]
+@end group
+@end example
+
+This procedure signals an error if @var{filename} does not refer to an
+actual directory in the file system.
+
+If @var{filename} describes a relative rather than absolute pathname,
+this procedure interprets it as relative to the current working
+directory, before changing the working directory.
+
+@example
+@group
+(working-directory-pathname)
+     @result{}  #[pathname "/usr/morris/"]
+(set-working-directory-pathname! "foo")
+     @result{}  #[pathname "/usr/morris/foo/"]
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} with-working-directory-pathname filename thunk
+This procedure temporarily rebinds the current working directory to
+@var{filename}, invokes @var{thunk} (a procedure of no arguments), then
+restores the previous working directory and returns the value yielded by
+@var{thunk}.  @var{Filename} is canonicalized in exactly as does
+@code{set-working-directory-pathname!}.  The binding is performed in
+exactly the same way as fluid binding of a variable (@pxref{Fluid
+Binding}).
+@end deffn
+
+@deffn {procedure+} pathname->absolute-pathname pathname
+Converts @var{pathname} into an absolute pathname.  If @var{pathname} is
+relative, it is converted to absolute form starting at the current
+working directory.  If @var{pathname} is already an absolute pathname,
+it is returned.
+@end deffn
+
+@deffn {procedure+} pathname-absolute? pathname
+Returns @code{#t} if @var{pathname} is an absolute rather than relative
+pathname object; otherwise returns @code{#f}.  All pathnames are either
+absolute or relative, so if this procedure returns @code{#f}, the
+argument is a relative pathname.
+@end deffn
+
+@node File Manipulation, Directory Reader, Working Directory, File-System Interface
+@section File Manipulation
+
+@deffn {procedure+} file-exists? filename
+@cindex existence, testing of file
+Returns @code{#t} if @var{filename} is an existing file or directory;
+otherwise returns @code{#f}.  If the file is a symbolic link, this
+procedure tests the existence of the file linked to, not the link
+itself.
+@end deffn
+
+@deffn {procedure+} copy-file source-filename target-filename
+@cindex copying, of file
+Makes a copy of the file named by @var{source-filename}.  The copy is
+performed by creating a new file called @var{target-filename}, and
+filling it with the same data as @var{source-filename}.  If
+@var{target-filename} exists prior to this procedure's invocation, it is
+deleted before the new output file is created.
+@end deffn
+
+@deffn {procedure+} rename-file source-filename target-filename
+@cindex renaming, of file
+@cindex name, of file
+Changes the name of @var{source-filename} to be @var{target-filename}.
+In the unix implementation, this will not rename across file systems.
+@end deffn
+
+@deffn {procedure+} delete-file filename
+@cindex deletion, of file
+Deletes the file named @var{filename}.
+@end deffn
+
+@deffn {procedure+} canonicalize-input-filename filename
+@cindex canonicalization, of filename
+If @var{filename} refers to an existing file or directory, returns as a
+string the absolute pathname of the file (or directory).  If
+@var{filename} doesn't refer to an existing file or directory, an error
+is signalled.
+@end deffn
+
+@deffn {procedure+} canonicalize-output-filename filename
+Returns as a string the absolute pathname of @var{filename}, whether or
+not the file or directory that @var{filename} refers to exists.
+
+@example
+@group
+(pwd)
+     @result{}  #[pathname "/usr/morris/"]
+(canonicalize-output-filename "foo")
+     @result{}  "/usr/morris/foo"
+@end group
+@end example
+@end deffn
+
+@deffn {procedure+} pathname->input-truename pathname
+@cindex truename, of input file
+Converts @var{pathname} into the corresponding absolute pathname.  If
+pathname doesn't exist, returns @code{#f}.
+@end deffn
+
+@deffn {procedure+} pathname->output-truename pathname
+@cindex truename, of output file
+Converts @var{pathname} into the corresponding absolute pathname.
+@end deffn
+
+@deffn {procedure+} file-modification-time filename
+@cindex modification time, of file
+Returns the modification time of @var{filename} as an exact integer.
+The result may be compared to other modification times using ordinary
+integer arithmetic.  If @var{filename} names a file that does not exist,
+returns @code{#f}.  If @var{filename} names a symbolic link, this
+returns the modification time of the file linked to, not the link
+itself.
+@end deffn
+
+@deffn {procedure+} file-directory? filename
+@cindex directory, predicate for
+Returns @code{#t} if the file named @var{filename} exists and is a
+directory.  Otherwise returns @code{#f}.  If @var{filename} names a
+symbolic link, this examines the file linked to, not the link itself.
+@end deffn
+
+@deffn {procedure+} file-symbolic-link? filename
+@cindex symbolic link, predicate for
+If the file named @var{filename} exists and is a symbolic link, this
+procedure returns the contents of the symbolic link as a newly allocated
+string.  The returned value is the name of the file that the symbolic
+link points to and must be interpreted relative to the directory of
+@var{filename}.  If @var{filename} either does not exist or is not a
+symbolic link, this procedure returns @code{#f}.
+@end deffn
+
+@deffn {procedure+} file-attributes filename
+@cindex attribute, of file
+This procedure determines if the file named @var{filename} exists, and
+returns information about it if so; if the file does not exist, it
+returns @code{#f}.  The information returned is a vector of 10 items:
+
+@enumerate
+@item
+The file type: @code{#t} if the file is a directory, a character string
+(the name linked to) if a symbolic link, or @code{#f} for all other
+types of file.
+
+@item
+The number of links to the file.
+
+@item
+The user id of the file's owner, an exact non-negative integer.
+
+@item
+The group id of the file's group, an exact non-negative integer.
+
+@item
+The last access time of the file, an exact non-negative integer.
+
+@item
+The last modification time of the file, an exact non-negative integer.
+
+@item
+The last change time of the file, an exact non-negative integer.
+
+@item
+The size of the file in bytes.
+
+@item
+The mode string of the file.  This is a newly allocated string showing
+the file's mode bits.
+
+@item
+The inode number of the file, an exact non-negative integer.
+@end enumerate
+@end deffn
+
+@node Directory Reader,  , File Manipulation, File-System Interface
+@section Directory Reader
+@cindex directory, reading
+
+@deffn {procedure+} directory-read directory [sort?]
+@var{Directory} must be an object that can be converted into a pathname
+by @code{->pathname}.  The directory specified by @var{directory} is
+read, and the contents of the directory is returned as a newly allocated
+list of absolute pathnames.  The result is sorted according to the usual
+sorting conventions for directories, unless @var{sort?} is specified as
+@code{#f}.  If @var{directory} has name, type, or version components,
+the returned list contains only those pathnames whose name, type, and
+version components match those of @var{directory}; @code{wild} or
+@code{#f} as one of these components means ``match anything''.
+@end deffn
+
+@node Error System, Graphics, File-System Interface, Top
+@chapter Error System
+
+@findex error
+The Scheme error system provides a uniform mechanism for the signalling of
+errors and other exceptional conditions.  For most purposes, the only part
+of the error system that is needed is the special form @code{error}, which
+is used to signal simple errors, specifying a message and some irritant
+objects (@pxref{Simple Errors}).  In addition, an option to @code{error}
+permits users to do simple formatting of their error messages (@pxref{Error
+Messages}).
+
+More demanding applications require more powerful facilities.  To give a
+concrete example, suppose you want floating-point division to return a very
+large number whenever the denominator is zero.  This behavior can be
+implemented using the error system.
+
+The Scheme arithmetic system can signal many different kinds of errors,
+including floating-point divide by zero.  In our example, we would like to
+handle this particular condition specially, allowing the system to handle
+other arithmetic errors in its usual way.
+
+The error system supports this kind of application by providing
+mechanisms for distinguishing different types of error conditions and
+for the specification of where control should be transferred should a
+given condition arise.  In this example, there is a specific object
+that represents the ``floating-point divide by zero'' condition type,
+and it is possible to dynamically specify an arbitrary Scheme procedure
+to be executed when a condition of that type is signalled.  This
+procedure then finds the stack frame containing the call to the division
+operator, and returns the appropriate value from that frame.
+
+Another kind of behavior that is useful is the ability to specify uniform
+handling for related classes of conditions.  For example, it might be
+desirable, when opening a file for input, to gracefully handle a variety of
+different conditions associated with the file system.  One such condition
+might be that the file does not exist, in which case the program will try
+some other action, perhaps opening a different file instead.  Another
+related condition is that the file exists, but is read protected, so it
+cannot be opened for input.  If these or any other related conditions
+occur, the program would like to skip this operation and move on to
+something else.
+
+At the same time, errors unrelated to the file system should be treated in
+their usual way.  For example, calling @code{car} on the argument @code{3}
+should signal an error.  Or perhaps the name given for the file is
+syntactically incorrect, a condition that probably wants to be handled
+differently from the case of the file not existing.
+
+@cindex taxonomical link, of condition type (defn)
+@cindex specialization, of condition types (defn)
+@cindex generalization, of condition types (defn)
+To facilitate the handling of classes of conditions, the error system
+taxonomically organizes all condition types.  The types are related to one
+another by @dfn{taxonomical links}, which specify that one type is a ``kind
+of'' another type.  If two types are linked this way, one is considered to
+be a @dfn{specialization} of the other; or vice-versa, the second is a
+@dfn{generalization} of the first.  In our example, all of the errors
+associated with opening an input file would be specializations of the
+condition type ``cannot open input file''.
+
+The taxonomy of condition types imposes a partial order on the types,
+because each type is allowed to have multiple generalizations.  This is
+allowed because some condition types can be generalized in several
+different ways.  An example of this is ``floating-point divide by zero'',
+which can be generalized to either a ``floating-point overflow'' or a
+``divide by zero''.  The latter generalization, ``divide by zero'', cannot
+be a specialization of the former, because it can also be signalled by
+arithmetic on numbers other than floating-point.
+
+To summarize, the error system provides facilities for the following tasks.
+The sections that follow will describe these facilities in more
+detail.
+
+@table @asis
+@item Signalling conditions
+Conditions may be signalled in a number of different ways.  Simple
+errors may be signalled, without explicitly defining a condition type,
+using @code{error}.  The @code{signal-condition} procedure provides the
+most general signalling mechanism.
+
+@item Handling conditions
+The programmer can dynamically specify handlers for particular condition
+types or for classes of condition types, by means of the
+@code{bind-condition-handler} procedure.  Individual handlers have
+complete control over the handling of a condition, and additionally may
+decide not to handle a particular condition, passing it on to
+previously bound handlers.
+
+@item Classification of conditions
+Each condition has a type, which is represented by a
+@code{condition-type} object.  Each condition type may be a
+specialization of some other condition types.  A group of types that
+share a common generalization can be handled uniformly by specifying a
+handler for the generalization.
+
+@item Packaging condition state
+Each condition is represented by an explicit object.  Condition objects
+contain information about the nature of the condition as well as
+information that describes the state of the computation from which the
+condition arose.
+@end table
+
+@menu
+* Simple Errors::               Simple Errors
+* Error Handler::               Error Handler
+* Error Messages::              Error Messages
+* Condition Types::             Condition Types
+* Condition Instances::         Condition Instances
+* Condition Signalling::        Condition Signalling
+* Condition Handling::          Condition Handling
+* Predefined Errors::           Predefined Errors
+@end menu
+
+@node Simple Errors, Error Handler, Error System, Error System
+@section Simple Errors
+
+@cindex irritants, of error (defn)
+The simplest error-signalling mechanism is the special form
+@code{error}.  It allows the programmer to signal errors by specifying
+an error message and providing a list of some objects (@dfn{irritants})
+that are relevant to the error.
+
+@deffn {special form+} error message irritant @dots{}
+Signals an error.  This special form expands into the following code:
+
+@example
+(error-procedure @var{message} (list @var{irritant} @dots{}) (the-environment))
+@end example
+
+@noindent
+@findex the-environment
+The use of @code{the-environment} would normally force the environment
+in which it appears to be an interpreter environment.  However, the
+compiler treats @code{error} expressions specially so that errors signalled
+from compiled code do not supply the environment argument to
+@code{error-procedure}.
+@end deffn
+
+@deffn {procedure+} error-procedure message irritants environment
+Signals an error.  @var{Message} is normally a short string that
+summarizes the error, and @var{irritants} is a list of objects that
+contain interesting information about the error.  @var{Environment} is
+the environment in which the error occurred.
+
+Normally, the message and irritants are used to build a condition whose
+type is @code{error-type:vanilla}, @var{environment} is attached to that
+condition, and then the condition is signalled.  However, if
+@var{message} is a @code{condition-type} object, then that object is
+used (instead of @code{error-type:vanilla}) to build the condition.
+
+The argument @var{environment} is used by the standard error handler.
+Currently there is no mechanism to retrieve this information.
+@end deffn
+
+@defvr {condition type+} error-type:vanilla
+This is the error type used by @code{error-procedure} when it signals
+anonymous errors.  Do not use this type for signalling new errors, as some
+of the system code expects to find the message in a special place for
+errors of this type.  This object is made public solely so that condition
+handlers can be bound to it.
+@end defvr
+
+@deffn {procedure+} warn message irritant @dots{}
+This procedure takes arguments just like @code{error}, formats and prints a
+message in the usual way, but does not signal an exception.  The output
+goes to the output-port of the nearest @code{cmdl} object.  In the future
+this may be made customizable in some ways, such as allowing conditional
+error signalling based on a flag.
+@end deffn
+
+@node Error Handler, Error Messages, Simple Errors, Error System
+@section Error Handler
+
+@cindex standard error handler
+@cindex error handler, standard
+In the absence of more specific handling, errors invoke the
+@dfn{standard error handler}.  This handler normally prints an error
+message and enters a new @sc{rep} loop.
+
+@deffn {procedure+} standard-error-handler condition
+This procedure is used to handle error conditions that are not otherwise
+taken care of.  It can be useful when building custom error
+handlers.
+@end deffn
+
+While the standard error handler is executing, the following procedures
+provide useful information.
+
+@deffn {procedure+} error-condition
+This procedure returns the condition that was passed to the standard
+error handler as its argument.  If the standard error handler is not
+executing, this procedure returns @code{#f}.
+@end deffn
+
+@deffn {procedure+} error-message
+@deffnx {procedure+} error-irritants
+@deffnx {procedure+} error-continuation
+These procedures extract standard components from @code{(error-condition)}.
+@code{error-continuation} returns @code{#f} if @code{error-condition}
+does.
+@end deffn
+
+@node Error Messages, Condition Types, Error Handler, Error System
+@section Error Messages
+
+The error system provides a simple formatting language that allows the
+programmer to have some control over the printing of error messages.  The
+basic idea is as follows.
+
+@findex display
+@findex write
+Error messages typically consist of a string describing the error,
+followed by some irritant objects.  The string is printed using
+@code{display}, and the irritants are printed using @code{write},
+typically with a space between each irritant.  To allow simple
+formatting, we introduce a @dfn{noise} object, which is printed using
+@code{display}.  The irritant list may contain ordinary objects
+interspersed with noise objects.  Each noise object is printed using
+@code{display}, with no extra whitespace, while each normal object is
+printed using @code{write}, prefixed by a single space character.
+
+Here is an example:
+
+@example
+@group
+(define (error-within-procedure message irritant procedure)
+  (error message
+         irritant
+         (error-irritant/noise #\newline)    
+         (error-irritant/noise "within procedure")      
+         procedure))
+@end group
+@end example
+
+This would format as follows:
+
+@example
+@group
+(error-within-procedure "bad widget" 'widget-32 'invert-widget) @error{}
+
+bad widget widget-32
+within procedure invert-widget
+@end group
+@end example
+
+Note the use of a separate noise object for the newline.  In general, for
+characters such as newline or formfeed (i.e.@: non-graphic characters), this
+is desirable since it makes it easier for the formatter to notice
+formatting characters with special meanings and handle them specially
+should it be necessary.
+
+Here are the operations supporting error messages:
+
+@deffn {procedure+} format-error-message message irritants port
+@var{Message} must be a string, @var{irritants} a list of irritant
+objects, and @var{port} an output port.  Formats @var{message} and
+@var{irritants} to @var{port} in the standard way.  Note that, during
+the formatting process, the depth and breadth to which lists are printed
+are each limited to small numbers, to guarantee that the output from
+each irritant is not arbitrarily large.
+@end deffn
+
+@deffn {procedure+} error-irritant/noise value
+Creates and returns a noise object whose value is @var{value}.
+@end deffn
+
+@deffn {procedure+} error-irritant/noise? object
+Returns @code{#t} if @var{object} was created by
+@code{error-irritant/noise}; otherwise returns @code{#f}.
+@end deffn
+
+@deffn {procedure+} error-irritant/noise-value noise
+Returns the value of the noise object @var{noise}.  This is the object that
+was passed to @code{error-irritant/noise} as an argument when @var{noise}
+was created.
+@end deffn
+
+@deffn {procedure+} error-irritants/sans-noise
+@findex error-irritants
+This returns the value of @code{error-irritants} with the noise objects
+removed.  It could have been written:
+
+@example
+@group
+(define (error-irritants/sans-noise)
+  (list-transform-negative (error-irritants)
+    error-irritant/noise?))
+@end group
+@end example
+@end deffn
+
+@node Condition Types, Condition Instances, Error Messages, Error System
+@section Condition Types
+
+@cindex condition type
+@cindex type, of condition
+Each condition has a @dfn{condition type} object associated with it.
+These objects are used as a means of focusing on related classes of
+conditions, first by concentrating all of the information about a
+specific class of condition in a single place, and second by specifying
+inheritance relationships between types.
+
+Condition types are defined by the following operations.  Any argument
+called @var{condition-type} is assumed to be a condition type
+object.
+
+@deffn {procedure+} make-condition-type generalizations reporter
+This procedure creates and returns a new condition type.
+@var{Generalizations} must be a list of condition types; the resulting
+condition type will be a specialization of each of these types.
+@var{Reporter} is a procedure of two arguments, a condition instance and
+an output port, which will write a concise description of the condition
+on the output port.  As a special option, @var{reporter} may be a
+string, in which case a standard error message will be printed using
+that string.
+@end deffn
+
+@deffn {procedure+} condition-type? object
+@cindex type predicate, for condition type
+Returns @code{#t} if @var{object} is a condition type; otherwise returns
+@code{#f}.
+@end deffn
+
+@deffn {procedure+} guarantee-condition-type object
+Signals an error if @var{object} is not a condition type.  Returns
+@var{object} as its value otherwise.
+@end deffn
+
+@deffn {procedure+} condition-type/generalizations condition-type
+Returns the generalizations of @var{condition-type}.  This is the reflexive
+and transitive closure of the @var{generalizations} argument to
+@code{make-condition-type}, i.e.@: all of the members of
+@var{generalizations} plus all of their generalizations as well.  This list
+always contains @var{condition-type}.
+@end deffn
+
+@deffn {procedure+} condition-type/reporter condition-type
+Returns the report procedure for @var{condition-type}.
+@end deffn
+
+@deffn {procedure+} condition-type/properties condition-type
+Each condition type contains a 1D table for associating arbitrary
+properties with the condition type.  This operation returns the table
+associated with @var{condition-type}.
+@end deffn
+
+@deffn {procedure+} condition-type/error? condition-type
+@cindex error type (defn)
+@cindex type, of error (defn)
+This predicate is true only of condition types that are considered to be
+errors.  Condition types satisfying this predicate are treated specially
+under certain cirumstances, and are sometimes referred to as @dfn{error
+types}.
+
+The following two expressions are equivalent (as predicates):
+
+@example
+@group
+(condition-type/error? x)
+(memq condition-type:error (condition-type/generalizations x))
+@end group
+@end example
+@end deffn
+
+@defvr {condition type+} condition-type:error
+The value of this variable a condition type with no generalizations that
+is used to mark condition types as being errors.
+@end defvr
+
+@deffn {procedure+} make-error-type generalizations reporter
+@findex make-condition-type
+This operation is like @code{make-condition-type}, except that if none of
+@var{generalizations} satisfies @code{condition-type/error?}, it adds
+@code{condition-type:error} to the set of generalizations.
+@end deffn
+
+@deffn {procedure+} error-type? object
+@cindex type predicate, for error type
+Returns @code{#t} if @var{object} is a condition type that satisfies
+@code{condition-type/error?}; otherwise returns @code{#f}.
+@end deffn
+
+@node Condition Instances, Condition Signalling, Condition Types, Error System
+@section Condition Instances
+
+@cindex condition (defn)
+@cindex condition instance (defn)
+@cindex instance, of condition (defn)
+A @dfn{condition}, in addition to the information associated with its
+type, usually contains other information that is not shared with other
+conditions of the same type.  For example, the condition type associated
+with unbound variable errors does not specify the name of the variable
+that was unbound.  The additional information is captured in
+@dfn{condition} objects, also called @dfn{condition instances}.
+
+In addition to information that is specific to a given type of condition
+(such as the variable name for ``unbound variable'' conditions), every
+condition instance also contains a continuation that encapsulates the
+state of the computation in which the condition occurred.  This
+continuation is used when condition handlers want to restart the
+computation in some way, or sometimes for analyzing the computation to
+learn more about the context in which the condition occurred.
+
+The following operations define the condition datatype.  Any argument
+called @var{condition} is assumed to be a condition object.
+
+@deffn {procedure+} make-condition condition-type irritants continuation
+Makes a new condition instance, with a type of @var{condition-type}.
+@var{Irritants} is a list of arbitrary objects, and @var{continuation}
+must be a continuation, normally the continuation of the computation
+which caused the condition.
+@end deffn
+
+@deffn {procedure+} condition? object
+@cindex type predicate, for condition instance
+Returns true iff @var{object} is a condition instance.
+@end deffn
+
+@deffn {procedure+} error? object
+@cindex type predicate, for error instance
+@findex condition-type/error?
+Returns @code{#t} if @var{object} is a condition instance that satisfies
+@code{condition/error?}; otherwise returns @code{#f}.
+@end deffn
+
+@deffn {procedure+} guarantee-condition object
+Signals an error if @var{object} is not a condition instance.  Returns
+@var{object} otherwise.
+@end deffn
+
+@deffn {procedure+} condition/type condition
+Returns the condition type associated with @var{condition}.
+@end deffn
+
+@deffn {procedure+} condition/irritants condition
+Returns the irritants associated with @var{condition}.
+@end deffn
+
+@deffn {procedure+} condition/continuation condition
+Returns the continuation associated with @var{condition}.
+@end deffn
+
+@deffn {procedure+} condition/write-report condition [output-port]
+Writes a concise description of @var{condition} to @var{output-port},
+which defaults to the current output port.
+@end deffn
+
+@deffn {procedure+} condition/report-string condition
+Returns a newly allocated string that is a concise description of
+@var{condition}.
+@end deffn
+
+@deffn {procedure+} condition/properties condition
+Each condition instance contains a 1D table for associating arbitrary
+properties with the condition.  This procedure returns the table
+associated with @var{condition}.
+@end deffn
+
+@deffn {procedure+} condition/internal? condition
+This predicate is true of certain conditions that normally should not be
+handled by user code.  Condition handlers that handle ``all'' conditions
+should ignore conditions satisfying this predicate, unless the handler's
+writer has a good understanding of internal conditions.
+@end deffn
+
+@deffn {procedure+} condition/generalizations condition
+@deffnx {procedure+} condition/error? condition
+@deffnx {procedure+} condition/reporter condition
+These operations access the corresponding components in the type of
+@var{condition}.  For example, the following expressions are
+equivalent:
+
+@example
+(condition/generalizations condition)
+(condition-type/generalizations (condition/type condition))
+@end example
+
+@cindex error condition (defn)
+@cindex condition, error (defn)
+Note that condition instances satisfying the predicate
+@code{condition/error?} are sometimes referred to as @dfn{error
+conditions}, or even @dfn{errors}.
+@end deffn
+
+@node Condition Signalling, Condition Handling, Condition Instances, Error System
+@section Condition Signalling
+
+@cindex condition signalling (defn)
+@cindex signalling, of condition (defn)
+@findex make-condition
+Once a condition instance has been created using @code{make-condition}, it
+can be @dfn{signalled}.  The act of signalling a condition is separated
+from the act of creating the condition to allow more flexibility in how
+conditions are handled.  For example, a condition instance could be
+returned as the value of a procedure, indicating that something unusual has
+happened, to allow the caller to clean up some state.  The caller could
+then signal the condition once it is ready.
+
+A more important reason for having a separate condition signalling
+mechanism is that it allows @emph{resignalling}.  When a signalled
+condition has been caught by a particular handler, and the handler decides
+that it doesn't want to process that particular condition, it can signal
+the condition again.  This is one way to allow other handlers to get a
+chance to see the condition.
+
+There is a single procedure responsible for signalling conditions.  All
+other signalling mechanisms go through this procedure:
+
+@deffn {procedure+} signal-condition condition [default-handler]
+Signals @var{condition}.  @var{Default-handler}, if given, must be a
+procedure of one argument.  The signalling procedure attempts to find a
+handler for the condition, using the following rules:
+
+@itemize @bullet
+@item
+The set of condition handlers is searched, until it finds one that will
+handle any of the condition types specified by the generalizations of
+@var{condition}.  Each handler specifies, at the time it is bound, a set of
+condition types it will handle; if the intersection of that set and
+@var{condition}'s generalizations is not empty, the handler is
+selected.
+@cindex condition handler
+@cindex handler, of condition
+
+If a handler is found, it is invoked on @var{condition}.  If it returns
+@code{#f}, that means the handler has declined to handle the condition
+and the search continues.  Otherwise the handler's value is returned as
+the value of @code{signal-condition}.
+
+@item
+If no condition handler is found, and the argument @var{default-handler} is
+supplied, it is invoked on @var{condition}; its value is returned as the
+value of @code{signal-condition}.
+
+@item
+Otherwise, @code{#f} is returned, indicating that no handler could be
+found.
+@end itemize
+@end deffn
+
+@deffn {procedure+} signal-error condition
+@findex standard-error-handler
+Signals @var{condition}, which must be a condition instance.  If this
+condition is not otherwise handled, the standard error handler is
+invoked.  Equivalent to @code{(signal-condition @var{condition}
+standard-error-handler)}.
+@end deffn
+
+@node Condition Handling, Predefined Errors, Condition Signalling, Error System
+@section Condition Handling
+
+@cindex condition handling (defn)
+@cindex handling, of condition (defn)
+@dfn{Condition handling} refers to the act of defining the behavior of a
+signalled condition.  This is controlled by the binding of
+@dfn{condition handlers}.
+
+@cindex condition handler (defn)
+@cindex handler, of condition (defn)
+@findex signal-condition
+A @dfn{condition handler} is a procedure of one argument.  When a handler
+is invoked by @code{signal-condition}, a condition is supplied to
+the handler as its argument.  The handler may return a value: if the value
+is @code{#f}, this indicates that the handler has decided not to handle
+this particular condition.  In that case, @code{signal-condition} continues
+its search for another handler.  Otherwise the value returned by the
+handler is returned as the value of @code{signal-condition}.
+
+@cindex resignalling, of condition (defn)
+Often, though, the handler will not return a value.  Usually a condition
+handler will exit by invoking some continuation.  Sometimes it will
+signal a different condition instead, or signal the same condition
+again.  This latter action, @dfn{resignalling} the same condition, is
+equivalent to returning @code{#f} from the handler.  This is because
+when the handler is invoked, the set of condition-handler bindings is
+unwound to the point at which the handler was bound.  In other words,
+when a condition handler is bound, the set of condition handlers that is
+in effect at the time of binding is the set that will be in effect when
+the handler is invoked.
+
+@cindex binding, of condition handler (defn)
+@cindex condition handler, binding (defn)
+A condition handler is @dfn{bound} by specifying that it will handle a
+condition whose generalizations intersect a given set of condition types.
+Condition handlers are bound using a mechanism very similar to fluid
+binding of variables.  A condition handler binding has a dynamic extent
+rather than a lexical scope, that is, it is effective for a specified time
+segment rather than for a specified code segment.
+
+The order in which the bindings are searched (by @code{signal-condition})
+is the opposite from the order in which they are bound.  Thus, more
+recently bound handlers appear earlier in the search order.
+
+@deffn {procedure+} bind-condition-handler condition-types handler thunk
+@findex condition/internal?
+Executes @var{thunk}, handling any condition whose generalizations
+intersect @var{condition-types} by passing it to @var{handler}.
+@var{Condition-types} must be a list of condition-type objects.  If
+@var{condition-types} is the empty list, it means @var{handler} should
+handle @emph{all} conditions, regardless of their type; such handlers
+should ignore conditions satisfying the predicate
+@code{condition/internal?}.
+@end deffn
+
+@node Predefined Errors,  , Condition Handling, Error System
+@section Predefined Errors
+
+@defvr {condition type+} error-type:wrong-type-argument
+Signalled when the argument to a procedure is determined to have an
+incorrect type.  For example, this error is signalled by @code{car} if
+its argument is not a pair.  This is a specialization of
+@code{error-type:illegal-argument}.
+@end defvr
+
+@deffn {procedure+} error:illegal-datum object [procedure-name]
+Signals @code{error-type:wrong-type-argument}.  @var{Object} is the
+argument in question, and @code{procedure-name}, if supplied, is the
+name of the procedure that determined the argument's incorrectness.
+@end deffn
+
+@defvr {condition type+} error-type:bad-range-argument
+Signalled when the argument to a procedure is determined to have the
+correct type but is not in the acceptable range.  For example, this
+error is signalled by @code{vector-ref} if its second argument is an
+exact negative integer.  This is a specialization of
+@code{error-type:illegal-argument}.
+@end defvr
+
+@deffn {procedure+} error:datum-out-of-range object [procedure-name]
+Signals @code{error-type:bad-range-argument}.  @var{Object} is the
+argument in question, and @code{procedure-name}, if supplied, is the
+name of the procedure that determined the argument's incorrectness.
+@end deffn
+
+@defvr {condition type+} error-type:illegal-argument
+This type is not signalled -- one of its specializations is signalled
+when the argument to a procedure is determined to be incorrect in some
+fashion.
+@end defvr
+
+@defvr {condition type+} error-type:open-file
+Signalled if an error occurs while trying to open a file for input or
+output.
+@end defvr
+
+@defvr {condition type+} error-type:file
+This type is not signalled -- one of its specializations is signalled
+when any @sc{i/o} error occurs.  The name of this type is a misnomer; it
+can be signalled by any @sc{i/o} operation, whether or not it involves
+files.
+@end defvr
+
+@node Graphics, Procedure Index, Error System, Top
+@chapter Graphics
+@cindex graphics
+
+MIT Scheme has a simple two-dimensional line-graphics interface
+that is suitable for many graphics applications.  In particular it is
+often used for plotting data points from experiments.  The interface is
+generic in that it can support different types of graphics devices in a
+uniform manner.  At the present time only two types of graphics device
+are implemented.
+
+Procedures are available for drawing points, lines, and text; defining
+the coordinate system; clipping graphics output; controlling some of the
+drawing characteristics; and controlling the output buffer (for devices
+that perform buffering).  Additionally, devices may support custom
+operations, such as control of colors.
+
+@menu
+* Opening and Closing of Graphics Devices::  Opening and Closing of Graphics Devices
+* Coordinates for Graphics::    Coordinates for Graphics
+* Drawing Graphics::            Drawing Graphics
+* Characteristics of Graphics Output::  Characteristics of Graphics Output
+* Buffering of Graphics Output::  Buffering of Graphics Output
+* Clipping of Graphics Output::  Clipping of Graphics Output
+* Custom Graphics Operations::  Custom Graphics Operations
+* X Graphics::                  X Graphics
+* Starbase Graphics::           Starbase Graphics
+@end menu
+
+@node Opening and Closing of Graphics Devices, Coordinates for Graphics, Graphics, Graphics
+@section Opening and Closing of Graphics Devices
+@cindex graphics, opening and closing devices
+
+@deffn {procedure+} graphics-type-available? graphics-device-type
+This predicate returns @code{#t} if @var{graphics-device-type} is
+implemented by the Scheme system.  Otherwise it returns @code{#f}, in
+which case it is an error to attempt to make a graphics device using
+@var{graphics-device-type}.  This is useful because a given graphics
+device type may exist as an object in the Scheme runtime environment
+even though the primitive procedures required to support that type do
+not.  This predicate determines when full support is available.
+@end deffn
+
+@deffn {procedure+} make-graphics-device graphics-device-type object @dots{}
+This operation creates a graphics device object.  The first argument is
+a graphics device type, and both the number and the meaning of the
+remaining arguments is determined by that type (see the description of
+each device type for details).  This procedure opens and initializes the
+device, which remains valid until explicitly closed by the procedure
+@code{graphics-close}.  In the current implementation of MIT
+Scheme, if this object is garbage-collected, the graphics device remains
+open, and any resources it is using are not released.  In the future the
+garbage collector may be changed to automatically close such devices.
+@end deffn
+
+@deffn {procedure+} graphics-close graphics-device
+Closes @var{graphics-device}, releasing its resources.  Subsequently it
+is an error to use @var{graphics-device}.
+@end deffn
+
+@node Coordinates for Graphics, Drawing Graphics, Opening and Closing of Graphics Devices, Graphics
+@section Coordinates for Graphics
+@cindex graphics, coordinate systems
+
+@cindex coordinates, graphics
+@cindex device coordinates, graphics (defn)
+@cindex graphics, device coordinates (defn)
+@cindex virtual coordinates, graphics (defn)
+@cindex graphics, virtual coordinates (defn)
+Each graphics device has two different coordinate systems associated
+with it: @dfn{device coordinates} and @dfn{virtual coordinates}.  Device
+coordinates are generally defined by low-level characteristics of the
+device itself, and often cannot be changed.  Most device coordinate
+systems are defined in terms of pixels, and usually the upper-left-hand
+corner is the origin of the coordinate system, with x coordinates
+increasing to the right and y coordinates increasing downwards.
+
+In contrast, virtual coordinates are more flexible in the units
+employed, the position of the origin, and even the direction in which
+the coordinates increase.  A virtual coordinate system is defined by
+assigning coordinates to the edges of a device.  Because these edge
+coordinates are arbitrary real numbers, any Cartesian coordinate system
+can be defined.
+
+All graphics procedures that use coordinates are defined on virtual
+coordinates.  Thus, to draw a line at a particular place on a device,
+the virtual coordinates for the endpoints of that line are given.
+
+When a graphics device is initialized, its virtual coordinate system is
+reset so that the left edge corresponds to an x-coordinate of @code{-1},
+the right edge to x-coordinate @code{1}, the bottom edge to y-coordinate
+@code{-1}, and the top edge to y-coordinate @code{1}.
+
+@deffn {procedure+} graphics-device-coordinate-limits graphics-device
+Returns (as multiple values) the device coordinate limits for
+@var{graphics-device}.  The values, which are exact non-negative
+integers, are: @var{x-left}, @var{y-bottom}, @var{x-right}, and
+@var{y-top}.
+@end deffn
+
+@deffn {procedure+} graphics-coordinate-limits graphics-device
+Returns (as multiple values) the virtual coordinate limits for
+@var{graphics-device}.  The values, which are real numbers, are:
+@var{x-left}, @var{y-bottom}, @var{x-right}, and @var{y-top}.
+@end deffn
+
+@deffn {procedure+} graphics-set-coordinate-limits graphics-device x-left y-bottom x-right y-top
+Changes the virtual coordinate limits of @var{graphics-device} to the
+given arguments.  @var{X-left}, @var{y-bottom}, @var{x-right}, and
+@var{y-top} must be real numbers.  Subsequent calls to
+@code{graphics-coordinate-limits} will return the new limits.  This
+operation has no effect on the device's displayed contents.
+
+Note: This operation usually resets the clip rectangle, although it is
+not guaranteed to do so.  If a clip rectangle is in effect when this
+procedure is called, it is necessary to redefine the clip rectangle
+afterwards.
+@end deffn
+
+@node Drawing Graphics, Characteristics of Graphics Output, Coordinates for Graphics, Graphics
+@section Drawing Graphics
+@cindex graphics, drawing
+
+The procedures in this section provide the basic drawing capabilities of
+Scheme's graphics system.
+
+@deffn {procedure+} graphics-clear graphics-device
+Clears the display of @var{graphics-device}.  It is unaffected by the
+current drawing mode.
+@end deffn
+
+@deffn {procedure+} graphics-draw-point graphics-device x y
+Draws a single point on @var{graphics-device} at the virtual coordinates
+given by @var{x} and @var{y}, using the current drawing mode.
+@end deffn
+
+@deffn {procedure+} graphics-erase-point graphics-device x y
+Erases a single point on @var{graphics-device} at the virtual
+coordinates given by @var{x} and @var{y}.  It is unaffected by the
+current drawing mode.
+
+This is equivalent to
+
+@example
+(lambda (device x y)
+  (graphics-bind-drawing-mode device 0
+    (lambda ()
+      (graphics-draw-point device x y))))
+@end example
+@end deffn
+
+@deffn {procedure+} graphics-draw-line graphics-device x-start y-start x-end y-end
+@var{X-start}, @var{y-start}, @var{x-end}, and @var{y-end} must be real
+numbers.  Draws a line on @var{graphics-device} that connects the points
+(@var{x-start}, @var{y-start}) and (@var{x-end}, @var{y-end}).  The line
+is drawn using the current drawing mode and line style.
+@end deffn
+
+@deffn {procedure+} graphics-draw-text graphics-device x y string
+Draws the characters of @var{string} at the point (@var{x}, @var{y}) on
+@var{graphics-device}, using the current drawing mode.  The
+characteristics of the characters drawn are device-dependent, but all
+devices are initialized so that the characters are drawn upright, from
+left to right, with the leftmost edge of the leftmost character at
+@var{x}, and the baseline of the characters at @var{y}.
+@end deffn
+
+@cindex graphics, cursor (defn)
+@cindex cursor, graphics (defn)
+The following two procedures provide an alternate mechanism for drawing
+lines, which is more akin to using a plotter.  They maintain a
+@dfn{cursor}, which can be positioned to a particular point and then
+dragged to another point, producing a line.  Sequences of connected line
+segments can be drawn by dragging the cursor from point to point.
+
+Many graphics operations have an unspecified effect on the cursor.  The
+following exceptions are guaranteed to leave the cursor unaffected:
+
+@example
+@group
+graphics-device-coordinate-limits
+graphics-coordinate-limits
+graphics-enable-buffering
+graphics-disable-buffering
+graphics-flush
+graphics-bind-drawing-mode
+graphics-set-drawing-mode
+graphics-bind-line-style
+graphics-set-line-style
+@end group
+@end example
+
+The initial state of the cursor is unspecified.
+
+@deffn {procedure+} graphics-move-cursor graphics-device x y
+Moves the cursor for @var{graphics-device} to the point (@var{x},
+@var{y}).  The contents of the device's display are unchanged.
+@end deffn
+
+@deffn {procedure+} graphics-drag-cursor graphics-device x y
+Draws a line from @var{graphics-device}'s cursor to the point (@var{x},
+@var{y}), simultaneously moving the cursor to that point.  The line is
+drawn using the current drawing mode and line style.
+@end deffn
+
+@node Characteristics of Graphics Output, Buffering of Graphics Output, Drawing Graphics, Graphics
+@section Characteristics of Graphics Output
+
+@cindex graphics, output characteristics
+Two characteristics of graphics output are so useful that they are
+supported uniformly by all graphics devices: @dfn{drawing mode} and
+@dfn{line style}.  A third characteristic, @dfn{color}, is equally
+useful (if not more so), but implementation restrictions prohibit a
+uniform interface.
+
+@cindex drawing mode, graphics (defn)
+@cindex graphics, drawing mode (defn)
+The @dfn{drawing mode}, an exact integer in the range 0 to 15 inclusive,
+determines how the figure being drawn is combined with the background
+over which it is drawn to generate the final result.  Initially the
+drawing mode is set to ``source'', so that the new output overwrites
+whatever appears in that place.  Useful alternative drawing modes can,
+for example, erase what was already there, or invert it.
+
+Altogether 16 boolean operations are available for combining the source
+(what is being drawn) and the destination (what is being drawn over).
+The source and destination are combined by the device on a
+pixel-by-pixel basis as follows:
+
+@example
+@group
+Mode    Meaning
+----    -------
+0       ZERO @r{[erase; use background color]}
+1       source AND destination
+2       source AND (NOT destination)
+3       source
+4       (NOT source) AND destination
+5       destination
+6       source XOR destination
+7       source OR destination
+8       NOT (source OR destination)
+9       NOT (source XOR destination)
+10      NOT destination
+11      source OR (NOT destination)
+12      NOT source
+13      (NOT source) OR destination
+14      (NOT source) OR (NOT destination)
+15      ONE @r{[use foreground color]}
+@end group
+@end example
+
+@cindex line style, graphics (defn)
+@cindex graphics, line style (defn)
+The @dfn{line style}, an exact integer in the range 0 to 7 inclusive,
+determines which parts of a line are drawn in the foreground color, and
+which in the background color.  The default line style, ``solid'', draws
+the entire line in the foreground color.  Alternatively, the ``dash''
+style alternates between foreground and background colors to generate a
+dashed line.  This capability is useful for plotting several things on
+the same graph.
+
+Here is a table showing the name and approximate pattern of the
+different styles.  A @samp{1} in the pattern represents a foreground
+pixel, while a @samp{-} represents a background pixel.  Note that the
+precise output for each style will vary from device to device.  The only
+style that is guaranteed to be the same for every device is ``solid''.
+
+@example
+@group
+Style   Name                    Pattern
+-----   -------                 -------
+0       solid                   1111111111111111
+1       dash                    11111111--------
+2       dot                     1-1-1-1-1-1-1-1-
+3       dash dot                1111111111111-1-
+4       dash dot dot            11111111111-1-1-
+5       long dash               11111111111-----
+6       center dash             111111111111-11-
+7       center dash dash        111111111-11-11-
+@end group
+@end example
+
+@deffn {procedure+} graphics-bind-drawing-mode graphics-device drawing-mode thunk
+@deffnx {procedure+} graphics-bind-line-style graphics-device line-style thunk
+These procedures bind the drawing mode or line style, respectively, of
+@var{graphics-device}, invoke the procedure @var{thunk} with no
+arguments, then undo the binding when @var{thunk} returns.  The value of
+each procedure is the value returned by @var{thunk}.  Graphics
+operations performed during @var{thunk}'s dynamic extent will see the
+newly bound mode or style as current.
+@end deffn
+
+@deffn {procedure+} graphics-set-drawing-mode graphics-device drawing-mode
+@deffnx {procedure+} graphics-set-line-style graphics-device line-style
+These procedures change the drawing mode or line style, respectively, of
+@var{graphics-device}.  The mode or style will remain in effect until
+subsequent changes or bindings.
+@end deffn
+
+@node Buffering of Graphics Output, Clipping of Graphics Output, Characteristics of Graphics Output, Graphics
+@section Buffering of Graphics Output
+@cindex buffering, of graphics output
+@cindex graphics, buffering of output
+
+To improve performance of graphics output, most graphics devices provide
+some form of buffering.  By default, Scheme's graphics procedures flush
+this buffer after every drawing operation.  The procedures in this
+section allow the user to control the flushing of the output
+buffer.
+
+@deffn {procedure+} graphics-enable-buffering graphics-device
+Enables buffering for @var{graphics-device}.  In other words, after this
+procedure is called, graphics operations are permitted to buffer their
+drawing requests.  This usually means that the drawing is delayed until
+the buffer is flushed explicitly by the user, or until it fills up and
+is flushed by the system.
+@end deffn
+
+@deffn {procedure+} graphics-disable-buffering graphics-device
+Disables buffering for @var{graphics-device}.  By default, all graphics
+devices are initialized with buffering disabled.  After this procedure
+is called, all drawing operations perform their output immediately,
+before returning.
+
+Note: @code{graphics-disable-buffering} flushes the output buffer if
+necessary.
+@end deffn
+
+@deffn {procedure+} graphics-flush graphics-device
+Flushes the graphics output buffer for @var{graphics-device}.  It has no
+effect for devices that do not support buffering, or if buffering is
+disabled for the device.
+@end deffn
+
+@node Clipping of Graphics Output, Custom Graphics Operations, Buffering of Graphics Output, Graphics
+@section Clipping of Graphics Output
+@cindex graphics, clipping
+@cindex clipping, of graphics
+
+@cindex clip rectangle, graphics (defn)
+Scheme provides a rudimentary mechanism for restricting graphics output
+to a given rectangular subsection of a graphics device.  By default,
+graphics output that is drawn anywhere within the device's virtual
+coordinate limits will appear on the device.  When a @dfn{clip
+rectangle} is specified, however, output that would have appeared
+outside the clip rectangle is not drawn.
+
+Note that changing the virtual coordinate limits for a device will
+usually reset the clip rectangle for that device, as will any operation
+that affects the size of the device (such as a window resizing
+operation).  However, programs should not depend on this.
+
+@deffn {procedure+} graphics-set-clip-rectangle graphics-device x-left y-bottom x-right y-top
+Specifies the clip rectangle for @var{graphics-device} in virtual
+coordinates.  @var{X-left}, @var{y-bottom}, @var{x-right}, and
+@var{y-top} must be real numbers.  Subsequent graphics output is clipped
+to the intersection of this rectangle and the device's virtual
+coordinate limits.
+@end deffn
+
+@deffn {procedure+} graphics-reset-clip-rectangle graphics-device
+Eliminates the clip rectangle for @var{graphics-device}.  Subsequent
+graphics output is clipped to the virtual coordinate limits of the
+device.
+@end deffn
+
+@node Custom Graphics Operations, X Graphics, Clipping of Graphics Output, Graphics
+@section Custom Graphics Operations
+@cindex custom operations, on graphics device
+@cindex graphics, custom operations
+
+In addition to the standard operations, a graphics device may support
+@dfn{custom operations}.  For example, most devices have custom
+operations to control color.  @code{graphics-operation} is used to
+invoke custom operations.
+
+@deffn {procedure+} graphics-operation graphics-device name object @dots{}
+Invokes the graphics operation on @var{graphics-device} whose name is
+the symbol @var{name}, passing it the remaining arguments.  This
+procedure can be used to invoke the standard operations, as well as
+custom operations that are specific to a particular graphics device
+type.  The names of the standard graphics operations are formed by
+removing the @code{graphics-} prefix from the corresponding procedure.
+For example, the following are equivalent:
+
+@example
+(graphics-draw-point device x y)
+(graphics-operation device 'draw-point x y)
+@end example
+
+For information on the custom operations for a particular device, see
+the documentation for its type.
+@end deffn
+
+@node X Graphics, Starbase Graphics, Custom Graphics Operations, Graphics
+@section X Graphics
+@cindex X graphics
+
+@cindex X window system
+Scheme supports graphics in the X window system (version 11).  Arbitrary
+numbers of displays may be opened, and arbitrary numbers of graphics
+windows may be created for each display.  A variety of operations is
+available to manipulate various aspects of the windows, to control their
+size, position, colors, and mapping.
+
+@menu
+* X Graphics Type::             X Graphics Type
+* Utilities for X Graphics::    Utilities for X Graphics
+* Custom Operations on X Graphics Devices::  Custom Operations on X Graphics Devices
+@end menu
+
+@node X Graphics Type, Utilities for X Graphics, X Graphics, X Graphics
+@subsection X Graphics Type
+
+@defvr {variable+} x-graphics-device-type
+This is the graphics device type for X windows.  X windows are opened as
+follows:
+
+@example
+(make-graphics-device x-graphics-device-type
+                      @var{display}
+                      @var{geometry}
+                      #!optional @var{suppress-map?})
+@end example
+
+@noindent
+where @var{display} is either a display object, @code{#f}, or a string;
+@var{geometry} is either @code{#f} or a string; and @var{suppress-map?}
+is a boolean.  A new window is created on the appropriate display, and a
+graphics device representing that window is returned.
+
+@findex x-open-display
+@var{Display} specifies which X display the window is to be opened on;
+if it is @code{#f} or a string, it is passed as an argument to
+@code{x-open-display}, and the value returned by that procedure is used
+in place of the original argument.  @var{Geometry} is an X geometry
+string, or @code{#f} which means to use the default geometry (which is
+specified as a resource).  @var{Suppress-map?}, if given and not
+@code{#f}, prevents the window from being mapped after it is
+created.
+
+@cindex resources, X graphics
+@cindex X resources, graphics
+The window is initialized using the resource name
+@code{"scheme-graphics"}, and is sensitive to the following resource
+properties:
+
+@example
+@group
+Property        Class           Default
+--------        -----           -------
+geometry        Geometry        @r{[none]}
+font            Font            9x15
+borderWidth     BorderWidth     2
+internalBorder  BorderWidth     @r{[border width]}
+background      Background      white
+foreground      Foreground      black
+borderColor     BorderColor     @r{[foreground color]}
+pointerColor    Foreground      @r{[foreground color]}
+@end group
+@end example
+
+The window is created with a @code{backing_store} attribute of
+@code{Always}.  The window's name and icon name are initialized to
+@code{"scheme-graphics"}.
+@end defvr
+
+@node Utilities for X Graphics, Custom Operations on X Graphics Devices, X Graphics Type, X Graphics
+@subsection Utilities for X Graphics
+
+@deffn {procedure+} x-open-display display-name
+@cindex display, X graphics
+@cindex X display, graphics
+Opens a connection to the display whose name is @var{display-name},
+returning a display object.  If unable to open a connection, @code{#f}
+is returned.  @var{Display-name} is normally a string, which is the
+usual X display name; however, @code{#f} is also allowed, meaning to use
+the value of the unix environment variable @code{DISPLAY}.
+@end deffn
+
+@deffn {procedure+} x-close-display display
+Closes @var{display}; after calling this procedure, it is an error to
+use @var{display} for any purpose.  Any windows that were previously
+opened on @var{display} are destroyed and their resources returned to
+the operating system.
+@end deffn
+
+@deffn {procedure+} x-close-all-displays
+Closes all open connections to X displays.  Equivalent to calling
+@code{x-close-display} on all open displays.
+@end deffn
+
+@deffn {procedure+} x-geometry-string x y width height
+@cindex geometry string, X graphics
+@cindex X geometry string, graphics
+This procedure creates and returns a standard X geometry string from the
+given arguments.  @var{X} and @var{y} must be either exact integers or
+@code{#f}, while @var{width} and @var{height} must be either exact
+non-negative integers or @code{#f}.  Usually either @var{x} and @var{y}
+are both specified or both @code{#f}; similarly for @var{width} and
+@var{height}.  If only one of the elements of such a pair is specified,
+it is ignored.
+
+Examples:
+
+@example
+(x-geometry-string #f #f 100 200) @result{} "100x200"
+(x-geometry-string 2 -3 100 200) @result{} "100x200+2-3"
+(x-geometry-string 2 -3 #f #f) @result{} "+2-3"
+@end example
+
+Note that the @var{x} and @var{y} arguments cannot distinguish between
+@code{+0} and @code{-0}, even though those have different meanings in X.
+If either of those arguments is @code{0}, it means @code{+0} in X
+terminology.  If you need to distinguish these two cases you must create
+your own geometry string using Scheme's string and number primitives.
+@end deffn
+
+@node Custom Operations on X Graphics Devices,  , Utilities for X Graphics, X Graphics
+@subsection Custom Operations on X Graphics Devices
+
+Custom operations are invoked using the procedure
+@code{graphics-operation}.  For example,
+
+@example
+(graphics-operation device 'set-foreground-color "blue")
+@end example
+
+@defop {operation+} x-graphics-device set-background-color color-name
+@defopx {operation+} x-graphics-device set-foreground-color color-name
+@defopx {operation+} x-graphics-device set-border-color color-name
+@defopx {operation+} x-graphics-device set-mouse-color color-name
+@findex graphics-clear
+These operations change the colors associated with a window.
+@var{Color-name} must be a string, which is the X server's name for the
+desired color.  @code{set-border-color} and @code{set-mouse-color}
+immediately change the border and mouse-cursor colors.
+@code{set-background-color} and @code{set-foreground-color} change the
+colors to be used when drawing, but have no effect on anything drawn
+prior to their invocation.  Because changing the background color
+affects the entire window, we recommend calling @code{graphics-clear} on
+the window's device afterwards.
+@end defop
+
+@defop {operation+} x-graphics-device set-border-width width
+@defopx {operation+} x-graphics-device set-internal-border-width width
+@findex graphics-clear
+These operations change the external and internal border widths of a
+window.  @var{Width} must be an exact non-negative integer.  The change
+takes place immediately.  Note that changing the internal border width
+can cause displayed graphics to be garbled; we recommend calling
+@code{graphics-clear} on the window's device after doing so.
+@end defop
+
+@defop {operation+} x-graphics-device set-font font-name
+Changes the font used when drawing text in a window.  @var{Font-name}
+must be a string that is a font name known to the X server.  This
+operation does not affect text drawn prior to its invocation.
+@end defop
+
+@defop {operation+} x-graphics-device font-structure font-name
+Returns a Scheme equivalent of the X font structure for the font named
+@var{font-name}.  If the string @var{Font-name} does not name a font
+known to the X server, or names a 16-bit font, the function returns
+false.
+@end defop
+
+@defop {operation+} x-graphics-device set-mouse-shape shape-number
+Changes the shape of the mouse cursor.  @var{Shape-number} is an exact
+non-negative integer that is used as an index into the mouse-shape font;
+when multiplied by 2 this number corresponds to an index in the file
+@file{/usr/include/X11/cursorfont.h}.
+@end defop
+
+@defop {operation+} x-graphics-device map-window
+@defopx {operation+} x-graphics-device unmap-window
+These operations control the mapping of windows.  They correspond
+directly to the Xlib procedures @code{XMapWindow} and
+@code{XUnmapWindow}.
+@end defop
+
+@defop {operation+} x-graphics-device resize-window width height
+Changes the size of a window.  @var{Width} and @var{height} must be
+exact non-negative integers.  The operation corresponds directly to the
+Xlib procedure @code{XResizeWindow}.
+
+This operation resets the virtual coordinate system and the clip
+rectangle.
+@end defop
+
+@defop {operation+} x-graphics-device move-window x y
+Changes the position of a window on the display.  @var{X} and @var{y}
+must be exact integers.  The operation corresponds directly to the Xlib
+procedure @code{XMoveWindow}.  Note that the coordinates @var{x} and
+@var{y} do not take the external border into account, and therefore will
+not position the window as you might like.  The only reliable way to
+position a window is to ask a window manager to do it for you.
+@end defop
+
+@defop {operation+} x-graphics-device get-default resource property
+This operation corresponds directly to the Xlib procedure
+@code{XGetDefault}.  @var{Resource} and @var{property} must be strings.
+The operation returns the character string corresponding to the
+association of @var{resource} and @var{property}; if no such association
+exists, @code{#f} is returned.
+@end defop
+
+@defop {operation+} x-graphics-device starbase-filename
+On Hewlett-Packard computers that support Starbase graphics, this
+operation returns a character string that can be used to open the
+device's window as a Starbase graphics device using the ``sox11''
+driver.  Note that the default distribution of Scheme for HP computers
+does not include support for Starbase --- you must rebuild the microcode
+to get this support.
+@end defop
+
+@node Starbase Graphics,  , X Graphics, Graphics
+@section Starbase Graphics
+@cindex starbase graphics
+
+On Hewlett-Packard computers under the HP-UX operating system, Scheme
+supports graphics through the Starbase graphics library.  Note that the
+default distribution of Scheme for HP computers does not include support
+for Starbase --- you must rebuild the microcode to get this support.
+
+@defvr {variable+} starbase-graphics-device-type
+This is the device type for Starbase graphics devices.  A Starbase
+device is opened as follows:
+
+@example
+(make-graphics-device starbase-graphics-device-type
+                      @var{device-name}
+                      @var{driver-name})
+@end example
+
+where @var{device-name} and @var{driver-name} are strings that are used
+as the device and driver arguments to the Starbase @code{gopen} call.
+The device is opened with kind @code{OUTDEV} and mode @code{0}.  The
+device is initialized to have a mapping mode of @code{DISTORT}, and a
+line color index of @code{1}.
+@end defvr
+
+@defop {operation+} starbase-graphics-device write-image-file filename invert?
+This operation writes an image of the Starbase device's display in the
+file specified by @var{filename}.  The image is formatted to print on an
+HP Laserjet printer.  Normally pixels with a color index of 0 are not
+drawn by the printer, and all other pixels are; this results in the
+background being white and the foreground being black in the printed
+image.  If @var{invert?} is not @code{#f}, this is reversed: the
+background is printed as black and the foreground is not printed.
+@end defop
+
+@defop {operation+} starbase-graphics-device color-map-size
+Returns, as an exact non-negative integer, the number of entries in the
+color map for the device.
+@end defop
+
+@defop {operation+} starbase-graphics-device define-color color-index red green blue
+Defines the color associated with the color-map index @var{color-index}.
+@var{Color-index} must be an exact non-negative integer strictly less
+than the number of entries in the color map.  @var{Red}, @var{green},
+and @var{blue} must be real numbers in the range 0 to 1 inclusive, which
+define the color to be put in the map.
+@end defop
+
+@defop {operation+} starbase-graphics-device set-line-color color-index
+Changes the foreground color used in graphics operations for this
+device.  @var{Color-index} must be an exact non-negative integer
+strictly less than the number of entries in the color map.  Graphics
+drawn after this operation is invoked will appear in this new color.
+@end defop
+
+The text drawn by a Starbase device is controlled by the following
+characteristics:
+
+@table @asis
+@item Aspect
+The @dfn{aspect} of a character is its height-to-width ratio, a real
+number.  By default, this has the value @code{1}.
+@cindex aspect, of graphics character (defn)
+
+@item Height
+The @dfn{height} of a character in virtual device coordinates, a real
+number.  This is measured along the ``up vector'', which is defined by
+the slant of the character.  By default, the height is @code{.1}.
+@cindex height, of graphics character (defn)
+
+@item Rotation
+The @dfn{rotation} of a character defines the direction in which the
+characters are drawn.  It is specified as a real number in degrees, but
+only 4 values have any meaning: @code{0}, @code{90}, @code{180}, and
+@code{270}.  @code{0} draws left-to-right with upright characters;
+@code{90} draws top-to-bottom with characters on their right side;
+@code{180} draws right-to-left with upside-down characters; @code{270}
+draws bottom-to-top with characters on their left side.  The default
+rotation is @code{0}.
+@cindex rotation, of graphics character (defn)
+
+@item Slant
+The @dfn{slant} of a character defines the ``up vector''; it is a real
+number which is the tangent of the angle between the character's
+``vertical'' (defined by the rotation), and the ``up vector'', measured
+clockwise.  The default slant is @code{0}.
+@cindex slant, of graphics character (defn)
+@end table
+
+@defop {operation+} starbase-graphics-device text-aspect
+@defopx {operation+} starbase-graphics-device text-height
+@defopx {operation+} starbase-graphics-device text-rotation
+@defopx {operation+} starbase-graphics-device text-slant
+These operations return the current values of the text
+characteristics.
+@end defop
+
+@defop {operation+} starbase-graphics-device set-text-aspect aspect
+@defopx {operation+} starbase-graphics-device set-text-height height
+@defopx {operation+} starbase-graphics-device set-text-rotation rotation
+@defopx {operation+} starbase-graphics-device set-text-slant slant
+These operations alter the current values of the text characteristics.
+They have no effect on text drawn prior to their invocation.
+@end defop
+
+@node Procedure Index, Concept Index, Graphics, Top
+@unnumbered Index of Procedures, Special Forms, and Variables
+@printindex fn
+
+@node Concept Index,  , Procedure Index, Top
+@unnumbered Index of Concepts
+@printindex cp
+
+@summarycontents
+@contents
+\f
+@c Local Variables:
+@c eval: (auto-save-mode -1)
+@c End:
+
+@bye
diff --git a/v7/doc/user-manual/user.texinfo b/v7/doc/user-manual/user.texinfo
new file mode 100644 (file)
index 0000000..8658852
--- /dev/null
@@ -0,0 +1,2028 @@
+\input texinfo @c -*-Texinfo-*-
+@tex
+\special{twoside}
+@end tex
+@c %**start of header
+@setfilename user.info
+@settitle MIT Scheme User's Manual
+@c %**end of header
+@setchapternewpage odd
+@synindex vr fn
+
+@ifinfo
+This file documents the use of MIT Scheme.
+
+Copyright @copyright{} 1991 Massachusetts Institute of Technology
+
+This material was developed by the Scheme project at the Massachusetts
+Institute of Technology, Department of Electrical Engineering and Computer
+Science.  Permission to copy this document, to redistribute it, and to use
+it for any purpose is granted, subject to the following restrictions and
+understandings.
+
+@enumerate
+@item
+Any copy made of this document must include this copyright notice in
+full.
+
+@item
+Users of this document agree to make their best efforts (a) to return to
+the MIT Scheme project any improvements or extensions that they make, so
+that these may be included in future releases; and (b) to inform MIT of
+noteworthy uses of this document.
+
+@item
+All materials developed as a consequence of the use of this document shall
+duly acknowledge such use, in accordance with the usual standards of
+acknowledging credit in academic research.
+
+@item
+MIT has made no warrantee or representation that the contents of this
+document will be error-free, and MIT is under no obligation to provide any
+services, by way of maintenance, update, or otherwise.
+
+@item
+In conjunction with products arising from the use of this material, there
+shall be no use of the name of the Massachusetts Institute of Technology
+nor of any adaptation thereof in any advertising, promotional, or sales
+literature without prior written consent from MIT in each case.
+@end enumerate
+@end ifinfo
+
+@titlepage
+@title{MIT Scheme User's Manual}
+@subtitle Edition 0.9
+@subtitle for Scheme Release 7.1
+@subtitle DRAFT: @today{}
+@author by Chris Hanson
+
+@page
+
+@vskip 0pt plus 1filll
+Copyright @copyright{} 1991 Massachusetts Institute of Technology
+
+This material was developed by the Scheme project at the Massachusetts
+Institute of Technology, Department of Electrical Engineering and Computer
+Science.  Permission to copy this document, to redistribute it, and to use
+it for any purpose is granted, subject to the following restrictions and
+understandings.
+
+@enumerate
+@item
+Any copy made of this document must include this copyright notice in
+full.
+
+@item
+Users of this document agree to make their best efforts (a) to return to
+the MIT Scheme project any improvements or extensions that they make, so
+that these may be included in future releases; and (b) to inform MIT of
+noteworthy uses of this document.
+
+@item
+All materials developed as a consequence of the use of this document shall
+duly acknowledge such use, in accordance with the usual standards of
+acknowledging credit in academic research.
+
+@item
+MIT has made no warrantee or representation that the contents of this
+document will be error-free, and MIT is under no obligation to provide any
+services, by way of maintenance, update, or otherwise.
+
+@item
+In conjunction with products arising from the use of this material, there
+shall be no use of the name of the Massachusetts Institute of Technology
+nor of any adaptation thereof in any advertising, promotional, or sales
+literature without prior written consent from MIT in each case.
+@end enumerate
+@end titlepage
+
+@node Top, Running Scheme, (dir), (dir)
+
+@menu
+* Running Scheme::              Running Scheme
+* REPL::                        The Read-Eval-Print Loop
+* Debugging::                   Debugging
+* Loading Files::               Loading Files
+* World Images::                World Images
+* Compiling Files::             Compiling Files
+* GNU Emacs Interface::         GNU Emacs Interface
+* Edwin::                       Edwin
+* Variable Index::              Variable, Declaration, and Option Index
+* Key Index::                   Key Index
+* Concept Index::               Concept Index
+
+ --- The Detailed Node Listing ---
+
+Running Scheme
+
+* Basics of Starting Scheme::   Basics of Starting Scheme
+* Command-Line Options::        Command-Line Options
+* Environment Variables::       Environment Variables
+* Leaving Scheme::              Leaving Scheme
+
+The Read-Eval-Print Loop
+
+* The Prompt and Level Number::  The Prompt and Level Number
+* Interrupting::                Interrupting
+* Proceeding::                  Proceeding
+* The Current REPL Environment::  The Current REPL Environment
+
+Debugging
+
+* Subproblems and Reductions::  Subproblems and Reductions
+* Debugger::                    The Debugger
+
+Compiling Files
+
+* Compilation Procedures::      Compilation Procedures
+* Declarations::                Declarations
+
+Declarations
+
+* Standard Names::              Standard Names
+* In-line Coding::              In-line Coding
+* Operator Reduction::          Operator Reduction
+@end menu
+
+@node Running Scheme, REPL, Top, Top
+@chapter Running Scheme
+
+This chapter describes how to run MIT Scheme on a unix system.  It also
+describes the command-line options and environment variables that affect
+how Scheme runs.
+
+@menu
+* Basics of Starting Scheme::   Basics of Starting Scheme
+* Command-Line Options::        Command-Line Options
+* Environment Variables::       Environment Variables
+* Leaving Scheme::              Leaving Scheme
+@end menu
+
+@node Basics of Starting Scheme, Command-Line Options, Running Scheme, Running Scheme
+@section Basics of Starting Scheme
+
+Usually, MIT Scheme is invoked by typing
+
+@example
+scheme
+@end example
+
+@noindent
+at your operating system's command interpreter.  Scheme will load
+itself, clear the screen, and print something like this:
+
+@example
+Scheme saved on Monday December 10, 1990 at 9:55:37 PM
+  Release 7.1.0 (beta)
+  Microcode 11.59
+  Runtime 14.104
+@end example
+
+@noindent
+This information, which can be printed again by evaluating
+
+@findex identify-world
+@lisp
+(identify-world)
+@end lisp
+
+@cindex release number
+@cindex microcode, version
+@cindex runtime system, version
+@cindex version numbers
+@noindent
+tells you the following version information.  ``Release'' is the release
+number for the entire Scheme system.  This number is changed each time a
+new version of Scheme is released.  An ``(alpha)'' or ``(beta)''
+following the release number indicates that this is a alpha- or
+beta-test release.  ``Microcode'' is the version number for the part of
+the system that is written in C.  ``Runtime'' is the version number for
+the part of the system that is written in Scheme.
+
+@cindex subsystem versions
+@cindex SF, version
+@cindex compiler, version
+@cindex Edwin, version
+@cindex student package, version
+@cindex compatibility package, version
+Following this there may be additional version numbers for specific
+subsystems.  @samp{SF} refers to the scode optimization program
+@code{sf}, @samp{Liar} is the native-code compiler, @samp{Edwin} is the
+Emacs-like text editor, and @samp{Student} is the S&ICP compatibility
+package.
+
+@cindex compiler, starting
+If the compiler is supported for your machine, you can invoke it by
+giving Scheme the @samp{-compiler} option:
+
+@example
+scheme -compiler
+@end example
+
+@noindent
+This option causes Scheme to use a larger constant space and heap, and
+to load the world image containing the compiler.
+
+@cindex init file
+Scheme supports @dfn{init files}: if the file @file{~/.scheme.init}
+exists, it is loaded immediately after the identification banner, and
+before the input prompt is printed.  The @code{-no-init-file} command
+line option causes Scheme to ignore the @file{~/.scheme.init} file (see
+@xref{Command-Line Options}).
+
+@node Command-Line Options, Environment Variables, Basics of Starting Scheme, Running Scheme
+@section Command-Line Options
+
+Scheme accepts the following command-line options.  The options may
+appear in any order, but they must all appear before any other
+arguments on the command line.  (At present, any arguments other than
+these options will generate a warning message when Scheme starts.  In
+the future, there will be an advertised mechanism by which the extra
+arguments can be handled by user code.)
+
+@table @code
+
+@item -band @var{filename}
+@findex -band
+@findex MITSCHEME_BAND
+@cindex world image
+@cindex band
+Specifies the initial world image file (@dfn{band}) to be loaded.
+Searches for @var{filename} in the working directory and the library
+directories, using the full pathname of the first readable file of that
+name.  If @var{filename} is an absolute pathname (on unix, this means it
+starts with @samp{/}), then no search occurs --- @var{filename} is
+tested for readability and then used directly.  If this option isn't
+given, the filename is the value of the environment variable
+@code{MITSCHEME_BAND}, or if that isn't defined, @file{runtime.com}; in
+these cases the library directories are searched, but not the working
+directory.
+
+@item -compiler
+@findex -compiler
+@findex MITSCHEME_COMPILER_BAND
+This option specifies defaults appropriate for loading the compiler.  It
+specifies the use of large sizes, exactly like @code{-large}.  If the
+@code{-band} option is also specified, that is the only effect of this
+option.  Otherwise, the default band's filename is the value of the
+environment variable @code{MITSCHEME_COMPILER_BAND}, if defined, or
+@file{compiler.com}; the library directories are searched to locate this
+file.  Note that the @code{-compiler} option is available only on
+machines with compiled-code support.
+
+@item -edwin
+@findex -edwin
+@findex MITSCHEME_EDWIN_BAND
+This option specifies defaults appropriate for loading the editor.  It
+specifies the use of large sizes, exactly like @code{-large}.  If the
+@code{-band} option is also specified, that is the only effect of this
+option.  Otherwise, the default band's filename is the value of the
+environment variable @code{MITSCHEME_EDWIN_BAND}, if defined, or
+@file{edwin.com}; the library directories are searched to locate this
+file.  Note that the @code{-edwin} option is available only on machines
+with compiled-code support.
+
+@item -no-init-file
+@findex -no-init-file
+This option causes Scheme to ignore the @file{~/.scheme.init} file,
+normally loaded automatically when Scheme starts (if it exists).
+
+@item -eval
+@findex -eval
+This option causes Scheme to evaluate the expressions following it on
+the command line, up to (but not including) the next option that starts
+with a hyphen.  The expressions are evaluated in the
+@code{user-initial-environment}.
+
+@item -load
+@findex -load
+This option causes Scheme to load the files (or lists of files)
+following it on the command line, up to (but not including) the next
+option that starts with a hyphen.  The files are loaded in the
+@code{user-initial-environment} using the default syntax table.
+
+@item -large
+@findex -large
+Specifies that large heap, constant, and stack sizes should be used.
+These are specified by the environment variables
+
+@group
+@findex MITSCHEME_LARGE_HEAP
+@findex MITSCHEME_LARGE_CONSTANT
+@findex MITSCHEME_LARGE_STACK
+@example
+MITSCHEME_LARGE_HEAP
+MITSCHEME_LARGE_CONSTANT
+MITSCHEME_LARGE_STACK
+@end example
+@end group
+
+@noindent
+If this option isn't given, the small sizes are used, specified by the
+environment variables
+
+@group
+@findex MITSCHEME_SMALL_HEAP
+@findex MITSCHEME_SMALL_CONSTANT
+@findex MITSCHEME_SMALL_STACK
+@example
+MITSCHEME_SMALL_HEAP
+MITSCHEME_SMALL_CONSTANT
+MITSCHEME_SMALL_STACK
+@end example
+@end group
+
+@noindent
+There are reasonable built-in defaults for all of these environment
+variables, should any of them be undefined.  Note that any or all of the
+defaults can be individually overridden by the @code{-heap},
+@code{-constant}, and @code{-stack} options.
+
+@findex print-gc-statistics
+Note: the Scheme procedure @code{(print-gc-statistics)} shows how much
+heap and constant space is available and in use.
+
+@item -heap @var{blocks}
+@findex -heap
+Specifies the size of the heap in 1024-word blocks.  Overrides any
+default.  Normally two such heaps are allocated; @code{bchscheme}
+allocates only one, and uses a disk file for the other.
+
+@item -constant @var{blocks}
+@findex -constant
+Specifies the size of constant space in 1024-word blocks.  Overrides any
+default.  Constant space holds the compiled code for the runtime system
+and other subsystems.
+
+@item -stack @var{blocks}
+@findex -stack
+Specifies the size of the stack in 1024-word blocks.  Overrides any
+default.  This is Scheme's stack, NOT the unix stack used by C programs.
+
+@item -option-summary
+@findex -option-summary
+Causes Scheme to write an option summary to standard error.  This shows
+the values of all of the settable option variables.
+
+@item -emacs
+@findex -emacs
+Specifies that Scheme is running as a subprocess of GNU Emacs.  This
+option is automatically supplied by GNU Emacs, and should not be given
+under other circumstances.
+
+@item -interactive
+@findex -interactive
+If this option isn't specified, and Scheme's standard @sc{i/o} is not a
+terminal, Scheme will detach itself from its controlling terminal.  This
+will prevent it from getting signals sent to the process group of that
+terminal.  If this option is specified, Scheme will not detach itself
+from the controlling terminal.
+
+This detaching behavior is useful for running Scheme as a background
+job.  For example, using the C shell in unix, the following will run
+Scheme as a background job, redirecting its input and output to files,
+and preventing it from being killed by keyboard interrupts or by logging
+out:
+
+@example
+scheme < /usr/cph/foo.in >& /usr/cph/foo.out &
+@end example
+
+@item -nocore
+@findex -nocore
+Specifies that Scheme should not generate a core dump under any
+circumstances.  If this option is not given, and Scheme terminates
+abnormally, you will be prompted to decide whether a core dump should be
+generated.
+
+@item -library @var{path}
+@findex -library
+@findex MITSCHEME_LIBRARY_PATH
+Sets the library search path to @var{path}.  This is a colon-separated
+list of directories that is searched to find various library files, such
+as bands.  If this option is not given, the value of the environment
+variable @code{MITSCHEME_LIBRARY_PATH} is used; if that isn't defined,
+@file{/usr/local/lib/mit-scheme} is used.
+
+@item -utabmd @var{filename}
+@item -utab @var{filename}
+@findex -utabmd
+@findex -utab
+@findex MITSCHEME_UTABMD_FILE
+Specifies that @var{filename} contains the microcode tables (the
+microcode tables are information that informs the runtime system about
+the microcode's structure).  @var{Filename} is searched for in the
+working directory and the library directories.  If this option isn't
+given, the filename is the value of the environment variable
+@code{MITSCHEME_UTABMD_FILE}, or if that isn't defined,
+@file{utabmd.bin}; in these cases the library directories are searched,
+but not the working directory.
+
+@code{-utab} is an alternate name for the @code{-utabmd} option.  At
+most one of these options may be given.
+
+@item -fasl @var{filename}
+@findex -fasl
+Specifies that a @dfn{cold load} should be performed, using
+@var{filename} as the initial file to be loaded.  If this option isn't
+given, a normal load is performed instead.  This option may not be used
+together with the @code{-band} option.  This option is useful only for
+maintainance and development of the MIT Scheme runtime system.
+
+@item -gc-directory @var{directory}
+@findex -gc-directory
+@findex MITSCHEME_GC_DIRECTORY
+Specifies that @var{directory} should be used to create files for
+garbage collection.  This option is recognized only by @code{bchscheme}.
+If the option is not given, the value of environment variable
+@code{MITSCHEME_GC_DIRECTORY} is used instead, and if that is not
+defined, @file{/tmp} is used.
+
+@item -gc-drone @var{program}
+@findex -gc-drone
+@findex MITSCHEME_GC_DRONE
+Specifies that @var{program} should be used as the drone program for
+overlapped I/O during garbage collection.  This option is recognized
+only by @code{bchscheme}.  If the option is not given, the value of
+environment variable @code{MITSCHEME_GC_DRONE} is used instead, and if
+that is not defined, @file{gcdrone} is used.
+
+@item -gc-end-position @var{number}
+@findex -gc-end-position
+@findex MITSCHEME_GC_END_POSITION
+This option is recognized only by @code{bchscheme}.  It specifies the
+last byte position in @code{-gc-file} at which this invocation of scheme
+can write.  If the option is not given, the value of environment
+variable @code{MITSCHEME_GC_END_POSITION} is used instead, and if that
+is not defined, it is computed from the start position (as provided with
+-gc-start-position) and the heap size.  The area of the file used (and
+locked if possible) is the region between @code{-gc-start-position} and
+@code{-gc-end-position}.
+
+@item -gc-file @var{filename}
+@item -gcfile
+@findex -gc-file
+@findex -gcfile
+@findex MITSCHEME_GC_FILE
+Specifies that @var{filename} should be used for garbage collection.
+This option is recognized only by @code{bchscheme}.  If the option is
+not given, the value of environment variable @code{MITSCHEME_GC_FILE} is
+used, and if this is not defined, a unique filename is generated in the
+directory specified with @code{-gc-directory}.
+
+@code{-gcfile} is an alias for @code{-gc-file}.  At most one of these
+options should be specified.
+
+@item -gc-keep
+@findex -gc-keep
+Specifies that the gc file used for garbage collection should not be
+deleted when scheme terminates.  This option is recognized only by
+@code{bchscheme}.  The gc file is deleted only if the file was created
+by this invocation of scheme, and this option is not set.
+
+@item -gc-read-overlap @var{N}
+@findex -gc-read-overlap
+@findex MITSCHEME_GC_READ_OVERLAP
+Specifies that scheme should delegate at most @var{N} simultaneous disk
+read operations during garbage collection.  This option is recognized
+only by @code{bchscheme}.  If the option is not given, the value of
+environment variable @code{MITSCHEME_GC_READ_OVERLAP} is used instead,
+and if that is not defined, 0 is used, disabling overlapped reads.
+
+@item -gc-start-position @var{number}
+@findex -gc-start-position
+@findex MITSCHEME_GC_START_POSITION
+This option is recognized only by @code{bchscheme}.  It specifies the
+first byte position in @code{-gc-file} at which this invocation of
+scheme can write.  If the option is not given, the value of environment
+variable @code{MITSCHEME_GC_START_POSITION} is used instead, and if that
+is not defined, 0 is used, meaning the beginning of the file.  The area
+of the file used (and locked if possible) is the region between
+@code{-gc-start-position} and @code{-gc-end-position}.
+
+@item -gc-window-size @var{blocks}
+@findex -gc-window-size
+@findex MITSCHEME_GC_WINDOW_SIZE
+Specifies the size of the windows into new space during garbage
+collection.  This option is recognized only by @code{bchscheme}.
+If this option is not given, the value of environment variable
+@code{MITSCHEME_GC_WINDOW_SIZE} is used instead, and if that is not
+defined, the value 16 is used.
+
+@item -gc-write-overlap @var{N}
+@findex -gc-write-overlap
+@findex MITSCHEME_GC_WRITE_OVERLAP
+Specifies that scheme should delegate at most @var{N} simultaneous disk
+write operations during garbage collection.  This option is recognized
+only by @code{bchscheme}.  If the option is not given, the value of
+environment variable @code{MITSCHEME_GC_WRITE_OVERLAP} is used instead,
+and if that is not defined, 0 is used, disabling overlapped writes.
+@end table
+
+@node Environment Variables, Leaving Scheme, Command-Line Options, Running Scheme
+@section Environment Variables
+
+This is a summary of the environment variables that are specific to MIT
+Scheme.
+
+@table @asis
+
+@item @code{MITSCHEME_BAND} (default: @file{runtime.com})
+@findex MITSCHEME_BAND
+The initial band to be loaded.  Overridden by @code{-band},
+@code{-compiler}, or @code{-edwin}.
+
+@item @code{MITSCHEME_COMPILER_BAND} (default: @file{compiler.com})
+@findex MITSCHEME_COMPILER_BAND
+The initial band to be loaded if the @code{-compiler} option is given.
+Overridden by @code{-band}.
+
+@item @code{MITSCHEME_EDWIN_BAND} (default: @file{edwin.com})
+@findex MITSCHEME_EDWIN_BAND
+The initial band to be loaded if the @code{-edwin} option is given.
+Overridden by @code{-band}.
+
+@item @code{MITSCHEME_LARGE_CONSTANT} (default: @samp{1000})
+@findex MITSCHEME_LARGE_CONSTANT
+The size of constant space, in 1024-word blocks, if the @code{-large},
+@code{-compiler}, or @code{-edwin} options are given.  Overridden by
+@code{-constant}.  Note: default is somewhat larger on RISC machines.
+
+@item @code{MITSCHEME_LARGE_HEAP} (default: @samp{1000})
+@findex MITSCHEME_LARGE_HEAP
+The size of the heap, in 1024-word blocks, if the @code{-large},
+@code{-compiler}, or @code{-edwin} options are given.  Overridden by
+@code{-heap}.
+
+@item @code{MITSCHEME_LARGE_STACK} (default: @samp{100})
+@findex MITSCHEME_LARGE_STACK
+The size of the stack, in 1024-word blocks, if the @code{-large},
+@code{-compiler}, or @code{-edwin} options are given.  Overridden by
+@code{-stack}.
+
+@item @code{MITSCHEME_LIBRARY_PATH} (default: @file{/usr/local/lib/mit-scheme})
+@findex MITSCHEME_LIBRARY_PATH
+A colon-separated list of directories.  These directories are searched,
+left to right, to find bands and various other files.
+
+@item @code{MITSCHEME_SMALL_CONSTANT} (default: @samp{400})
+@findex MITSCHEME_SMALL_CONSTANT
+The size of constant space, in 1024-word blocks, if the size options are
+not given.  Overridden by @code{-constant}, @code{-large},
+@code{-compiler}, or @code{-edwin}.  Note: default is somewhat larger on
+RISC machines.
+
+@item @code{MITSCHEME_SMALL_HEAP} (default: @samp{250})
+@findex MITSCHEME_SMALL_HEAP
+The size of the heap, in 1024-word blocks, if the size options are not
+given.  Overridden by @code{-heap}, @code{-large}, @code{-compiler}, or
+@code{-edwin}.
+
+@item @code{MITSCHEME_SMALL_STACK} (default: @samp{100})
+@findex MITSCHEME_SMALL_STACK
+The size of the stack, in 1024-word blocks, if the size options are not
+given.  Overridden by @code{-stack}, @code{-large}, @code{-compiler}, or
+@code{-edwin}.
+
+@item @code{MITSCHEME_UTABMD_FILE} (default: @file{utabmd.bin})
+@findex MITSCHEME_UTABMD_FILE
+The file containing the microcode tables.  Overridden by @code{-utabmd}
+and @code{-utab}.
+
+@item @code{MITSCHEME_GC_DIRECTORY} (default: @file{/tmp})
+@findex MITSCHEME_GC_DIRECTORY
+The directory where to write gc files.  Overriden by @code{-gc-directory}.
+
+@item @code{MITSCHEME_GC_DRONE} (default: @file{gcdrone})
+@findex MITSCHEME_GC_DRONE
+The program to use as the I/O drone during garbage collection.
+Overriden by @code{-gc-drone}.
+
+@item @code{MITSCHEME_GC_END_POSITION} (default: start-position + heap-size)
+@findex MITSCHEME_GC_END_POSITION
+The last position in the gc file to use.  Overriden by
+@code{-gc-end-position}.
+
+@item @code{MITSCHEME_GC_FILE} (default: @file{GCXXXXXX})
+@findex MITSCHEME_GC_FILE
+The name of the file to use for garbage collection.  If it ends in 6 Xs,
+the Xs are replaced by a letter and process id of the scheme process,
+thus generating a unique name.  Overriden by @code{-gc-file}.
+
+@item @code{MITSCHEME_GC_READ_OVERLAP} (default: 0)
+@findex MITSCHEME_GC_READ_OVERLAP
+The maximum number of simultaneous read operations.  Overriden by
+@code{-gc-read-overlap}.
+
+@item @code{MITSCHEME_GC_START_POSITION} (default: 0)
+@findex MITSCHEME_GC_START_POSITION
+The first position in the gc file to use.  Overriden by
+@code{-gc-start-position}.
+
+@item @code{MITSCHEME_GC_WINDOW_SIZE} (default: 16)
+@findex MITSCHEME_GC_WINDOW_SIZE
+The size in blocks of windows into new space (in the gc file).
+Overriden by @code{-gc-window-size}.
+
+@item @code{MITSCHEME_GC_WRITE_OVERLAP} (default: 0)
+@findex MITSCHEME_GC_WRITE_OVERLAP
+The maximum number of simultaneous write operations.  Overriden by
+@code{-gc-write-overlap}.
+@end table
+
+@node Leaving Scheme,  , Environment Variables, Running Scheme
+@section Leaving Scheme
+
+There are two ways you can leave Scheme.  The first is to evaluate
+
+@findex exit
+@lisp
+(exit)
+@end lisp
+
+@noindent
+which will halt the Scheme system, after first requesting confirmation.
+Any information that was in the environment is lost, so this should not
+be done lightly.
+
+The second way to leave Scheme is to suspend it; when this is done you
+may later restart where you left off.  Unfortunately this is not
+possible in all operating systems --- currently it is known to work on
+BSD Unix, Ultrix, SunOS, HP-UX (version 6.5 or later).  It does NOT work
+on AT&T Unix.  (Specifically, for unix or POSIX systems, suspension is
+available if the system supports job control.)
+
+Scheme is suspended by evaluating
+
+@findex quit
+@lisp
+(quit)
+@end lisp
+
+@noindent
+If your system supports suspension, this will cause Scheme to stop, and
+you will be returned to the operating system's command interpreter.
+Scheme remains stopped, and can be continued using the job-control
+commands of your command interpreter.  If your system doesn't support
+suspension, this procedure does nothing.
+
+@node REPL, Debugging, Running Scheme, Top
+@chapter The Read-Eval-Print Loop
+
+@cindex REPL
+When you first start up Scheme, you will be typing at a program called
+the @dfn{Read-Eval-Print Loop} (abbreviated @dfn{REPL}).  It displays a
+prompt at the left hand side of the screen whenever it is waiting for
+input.  You then type an expression (terminating it with @key{RET}).
+Scheme evaluates the expression, prints the result, and gives you
+another prompt.
+
+@menu
+* The Prompt and Level Number::  The Prompt and Level Number
+* Interrupting::                Interrupting
+* Proceeding::                  Proceeding
+* The Current REPL Environment::  The Current REPL Environment
+@end menu
+
+@node The Prompt and Level Number, Interrupting, REPL, REPL
+@section The Prompt and Level Number
+
+@cindex prompt, REPL
+The @sc{repl} @dfn{prompt} normally has the form
+
+@example
+1 ]=>
+@end example
+
+@cindex level number, REPL
+@noindent
+The @samp{1} in the prompt is a @dfn{level number}, which is always a
+positive integer.  This number is incremented under certain
+circumstances, the most common being an error.  For example, here is
+what you will see if you type @kbd{f o o @key{RET}} after starting
+Scheme:
+
+@example
+1 ]=> foo
+
+Unbound variable foo
+
+2 Error->
+@end example
+
+@noindent
+In this case, the level number has been incremented to @samp{2}, which
+indicates that a new @sc{repl} has been started (also the prompt string
+has been changed to remind you that the @sc{repl} was started because of
+an error).  The @samp{2} means that this new @sc{repl} is ``over'' the
+old one.  The original @sc{repl} still exists, and is waiting for you to
+return to it.  Furthermore, if an error occurs while you are in this
+@sc{repl}, yet another @sc{repl} will be started, and the level number
+will be increased to @samp{3}.  This can continue ad infinitum, but
+normally it is rare to use more than a few levels.
+
+The normal way to get out of an error @sc{repl} and back to the top
+level @sc{repl} is to use the @kbd{C-g} interrupt.  This is a
+single-keystroke command executed by holding down the @key{CTRL} key and
+pressing the @key{G} key.  @kbd{C-g} always terminates whatever is
+running and returns you to the top level @sc{repl} immediately.
+
+Note: The appearance of the @samp{Error->} prompt does not mean that
+Scheme is in some weird inconsistent state that you should avoid.  It is
+merely a reminder that your program was in error: an illegal operation
+was attempted, but it was detected and avoided.  Often the best way to
+find out what is in error is to do some poking around in the error
+@sc{repl}.  If you abort out of it, the context of the error will be
+destroyed, and you may not be able to find out what happened.
+
+@node Interrupting, Proceeding, The Prompt and Level Number, REPL
+@section Interrupting
+
+@kindex C-g
+@kindex C-c
+Scheme has two interrupt keys under unix (other systems may have more
+than two): @kbd{C-g} and @kbd{C-c}.  The @kbd{C-g} key stops any Scheme
+evaluation that is running and returns you to the top level @sc{repl}.
+@kbd{C-c} prompts you for another character and performs some action
+based on that character.  It is not necessary to type @key{RET} after
+@kbd{C-g} or @kbd{C-c}, nor is it needed after the character that
+@kbd{C-c} will ask you for.
+
+Here are the more common options for @kbd{C-c}.
+
+@table @kbd
+
+@item C-c i
+@kindex C-c i
+Ignore the interrupt.  Type this if you made a mistake and didn't
+really mean to type @kbd{C-c}.
+
+@item C-c ?
+@kindex C-c ?
+Print help information.  This will describe any other options not
+documented here.
+
+@item C-c q
+@kindex C-c q
+@findex exit
+Similar to typing @code{(exit)} at the @sc{repl}, except that it works
+even if Scheme is running an evaluation, and does not request
+confirmation.
+
+@item C-c z
+@kindex C-c z
+@findex quit
+Similar to typing @code{(quit)} at the @sc{repl}, except that it works
+even if Scheme is running an evaluation.
+
+@item C-c C-c
+@kindex C-c C-c
+Identical to typing @kbd{C-g}.  If no evaluation is running, this is
+equivalent to evaluating
+
+@findex cmdl-interrupt/abort-top-level
+@lisp
+(cmdl-interrupt/abort-top-level)
+@end lisp
+
+@noindent
+@kindex C-c C-g
+@kindex C-c g
+The options @kbd{C-c C-g} and @kbd{C-c g}, supplied for compatibility
+with older implementations, are equivalent to @kbd{C-c C-c}.
+
+@item C-c C-x
+@kindex C-c C-x
+Abort whatever Scheme evaluation is currently running and return to the
+``current'' @sc{repl}.  If no evaluation is running, this is equivalent
+to evaluating
+
+@findex cmdl-interrupt/abort-nearest
+@lisp
+(cmdl-interrupt/abort-nearest)
+@end lisp
+
+@kindex C-c x
+The option @kbd{C-c x}, supplied for compatibility with older
+implementations, is equivalent to @kbd{C-c C-x}.
+
+@item C-c C-u
+@kindex C-c C-u
+Abort whatever Scheme evaluation is running and go up one level.  If you
+are already at level number 1, it just aborts the evaluation, leaving
+you at level 1.  If no evaluation is running, this is equivalent to
+evaluating
+
+@findex cmdl-interrupt/abort-previous
+@lisp
+(cmdl-interrupt/abort-previous)
+@end lisp
+
+@kindex C-c u
+The option @kbd{C-c u}, supplied for compatibility with older
+implementations, is equivalent to @kbd{C-c C-u}.
+
+@item C-c C-b
+@kindex C-c C-b
+@cindex breakpoint
+Suspend whatever Scheme evaluation is running and start a
+@dfn{breakpoint} @sc{repl}.  The evaluation can be resumed by evaluating
+
+@findex proceed
+@lisp
+(proceed)
+@end lisp
+
+@noindent
+in that @sc{repl} at any time.
+
+@kindex C-c b
+The option @kbd{C-c b}, supplied for compatibility with older
+implementations, is equivalent to @kbd{C-c C-b}.
+@end table
+
+@node Proceeding, The Current REPL Environment, Interrupting, REPL
+@section Proceeding
+
+Another way of exiting a @sc{repl} is to use the @code{proceed}
+procedure:
+
+@deffn {procedure+} proceed [value]
+@cindex error REPL, proceeding from
+There are two ways to use this procedure from an error @sc{repl} (usage
+from other kinds of @sc{repl} is not necessarily the same).  If
+@var{value} is not given, @code{proceed} retries the expression that
+caused the error.  Unless you have done something to fix the error
+condition, this will just cause the error to happen all over again.  If,
+for example, you are in an error @sc{repl} caused by evaluating an
+unbound variable, the proper way to use @code{proceed} is to first
+define a value for the variable, then to evaluate @code{(proceed)}.
+Your program should continue from that point normally.
+
+One caveat: when you get an unbound variable error, the environment for
+the error @sc{repl} is the environment in which you looked up the
+variable, which is not necessarily the environment in which the variable
+should be defined.  It is best to use the @code{ge} procedure to
+guarantee that your definition goes into the right place.
+
+If @var{value} is given, @code{proceed} returns it in place of the
+expression that caused the error.  Thus, if you cannot easily fix a
+particular bug, but you know a correct value for the erring expression,
+you can continue the computation this way.
+@end deffn
+
+@node The Current REPL Environment,  , Proceeding, REPL
+@section The Current REPL Environment
+
+@cindex current REPL environment
+@findex user-initial-environment
+@findex system-global-environment
+Every @sc{repl} has a @dfn{current environment}, which is the place
+where expressions are evaluated and definitions are stored.  When Scheme
+is started, this environment is the value of the variable
+@code{user-initial-environment}.  There are a number of other
+environments in the system, for example
+@code{system-global-environment}, where the runtime system's bindings
+are stored.
+
+You can get the current @sc{repl} environment by evaluating
+
+@findex nearest-repl/environment
+@lisp
+(nearest-repl/environment)
+@end lisp
+
+There are several other ways to obtain environments.  For example, if
+you have a procedure object, you can get a pointer to the environment in
+which it was closed by evaluating
+
+@findex procedure-environment
+@lisp
+(procedure-environment @var{procedure})
+@end lisp
+
+Your programs create new environments whenever a procedure is called.
+When an error occurs, the error @sc{repl} that is created is usually
+initialized so that its current environment is the one in which the
+error occurred.  When it is not possible to supply the error's
+environment, the following message is printed:
+
+@lisp
+There is no environment available;
+using the current REPL environment
+@end lisp
+
+@noindent
+This message tells you that the error @sc{repl} is using the same
+environment as the @sc{repl} whose level number is one less than the
+error @sc{repl}'s.
+
+Here is the procedure that changes the @sc{repl}'s environment:
+
+@deffn {procedure+} ge environment
+Changes the current @sc{repl} environment to be @var{environment}
+(@code{ge} stands for ``Goto Environment'').  @var{Environment} is
+allowed to be a procedure as well as an environment object.  If it is a
+procedure, then the closing environment of that procedure is used in its
+place.
+@end deffn
+
+@deffn {procedure+} gst syntax-table
+In addition to the current environment, each @sc{repl} maintains a
+current @dfn{syntax table}.  The current syntax table tells the
+@sc{repl} which keywords are used to identify special forms (e.g.
+@code{if}, @code{lambda}).  If you write macros, often you will want to
+make your own syntax table, in which case it is useful to be able to
+make that syntax table be the current one.  @code{Gst} allows you to do
+that.
+@end deffn
+
+@node Debugging, Loading Files, REPL, Top
+@chapter Debugging
+
+This chapter is adapted from @cite{Don't Panic: A 6.001 User's Guide to
+the Chipmunk System}, by Arthur A. Gleckler.
+
+@cindex bugs
+@cindex debugging
+Even computer software that has been planned carefully and written well
+may not always work correctly.  Mysterious creatures called @dfn{bugs}
+may creep in and wreak havoc, leaving the programmer to clean up the
+mess.  Some have theorized that a program fails only because its author
+made a mistake, but experienced computer programmers know that bugs are
+always to blame.  This is why the task of fixing broken computer
+software is called @dfn{debugging}.
+
+It is impossible to prove the correctness of any non-trivial program;
+hence the Cynic's First Law of Debugging:
+
+@quotation
+Programs don't become more reliable as they are debugged; the bugs just
+get harder to find.
+@end quotation
+
+@cindex breakpoints
+Scheme is equipped with a variety of special software for finding and
+removing bugs.  The debugging tools include facilities for tracing a
+program's use of specified procedures, for examining Scheme
+environments, and for setting @dfn{breakpoints}, places where the
+program will pause for inspection.
+
+@cindex error
+Many bugs are detected when programs try to do something which is
+impossible, like adding a number to a symbol, or using a variable which
+does not exist; this type of mistake is called an @dfn{error}.
+Whenever an error occurs, Scheme prints an error message and starts a
+new @sc{repl}.  For example, using a nonexistent variable @code{foo} will
+cause Scheme to respond
+
+@example
+1 ]=> foo
+
+Unbound variable foo
+;Package: (user)
+
+2 Error->
+@end example
+
+Sometimes, a bug will never cause an error, but will still cause the
+program to operate incorrectly.  For instance,
+
+@lisp
+(prime? 7)   @result{}   #f
+@end lisp
+
+In this situation, Scheme does not know that the program is misbehaving.
+The programmer must notice the problem and, if necessary, start the
+debugging tools manually.
+
+There are several approaches to finding bugs in a Scheme program:
+
+@itemize @bullet
+@item
+Inspect the original Scheme program.
+
+@item
+Use the debugging tools to follow your program's progress.
+
+@item
+Edit the program to insert checks and breakpoints.
+@end itemize
+
+@noindent
+Only experience can teach how to debug programs, so be sure to
+experiment with all these approaches while doing your own debugging.
+Planning ahead is the best way to ward off bugs, but when bugs do
+appear, be prepared to attack them with all the tools available.
+
+@menu
+* Subproblems and Reductions::  Subproblems and Reductions
+* Debugger::                    The Debugger
+@end menu
+
+@node Subproblems and Reductions, Debugger, Debugging, Debugging
+@section Subproblems and Reductions
+
+@cindex subproblem
+@cindex reduction
+@cindex subexpression
+Understanding the concepts of @dfn{reduction} and @dfn{subproblem} is
+essential to good use of the debugging tools.  The Scheme interpreter
+evaluates an expression by @dfn{reducing} it to a simpler expression.
+In general, Scheme's evaluation rules designate that evaluation proceeds
+from one expression to the next by either starting to work on a
+@dfn{subexpression} of the given expression, or by reducing the entire
+expression to a new (simpler, or reduced) form.  Thus, a history of the
+successive forms processed during the evaluation of an expression will
+show a sequence of subproblems, where each subproblem may consist of a
+sequence of reductions.
+
+For example, both @code{(+ 5 6)} and @code{(+ 7 9)} are subproblems of
+the following combination:
+
+@lisp
+(* (+ 5 6) (+ 7 9))
+@end lisp
+
+If @code{(prime? n)} is true, then @code{(cons 'prime n)} is a reduction
+for the following expression:
+
+@lisp
+(if (prime? n)
+    (cons 'prime n)
+    (cons 'not-prime n))
+@end lisp
+
+This is because the entire subproblem of the @code{if} combination can
+be reduced to the problem @code{(cons 'prime n)}, once we know that
+@code{(prime?  n)} is true; the @code{(cons 'not-prime n)} can be
+ignored, because it will never be needed.  On the other hand, if
+@code{(prime? n)} were false, then @code{(cons 'not-prime n)} would be
+the reduction for the @code{if} combination.
+
+The @emph{subproblem level} is a number representing how far back in the
+history of the current computation a particular evaluation is.  Consider
+@code{factorial}:
+
+@lisp
+(define (factorial n)
+  (if (< n 2)
+      1
+      (* n (factorial (- n 1)))))
+@end lisp
+
+@noindent
+If we stop @code{factorial} in the middle of evaluating @code{(- n 1)},
+the @code{(- n 1)} is at subproblem level 0.  Following the history of
+the computation ``upwards,'' @code{(factorial (- n 1))} is at subproblem
+level 1, and @code{(* n (factorial (- n 1)))} is at subproblem level 2.
+These expressions all have @emph{reduction number} 0.  Continuing
+upwards, the @code{if} combination has reduction number 1.
+
+Moving backwards in the history of a computation, subproblem levels and
+reduction numbers increase, starting from zero at the expression
+currently being evaluated.  Reduction numbers increase until the next
+subproblem, where they start over at zero.  The best way to get a feel
+for subproblem levels and reduction numbers is to experiment with the
+debugging tools, especially @code{debug}.
+
+@node Debugger,  , Subproblems and Reductions, Debugging
+@section The Debugger
+
+@cindex debugger
+@cindex continuation Browser
+@cindex browser, Continuation
+@findex debug
+The @dfn{debugger}, called @code{debug}, is the tool you should use when
+Scheme signals an error and you want to find out what caused the error.
+When Scheme signals an error, it records all the information necessary
+to continue running the Scheme program that caused the error; the
+debugger provides you with the means to inspect this information.  For
+this reason, the debugger is sometimes called a @dfn{continuation
+browser}.
+
+Here is the transcript of a typical Scheme session, showing a user
+evaluating the expression @code{(fib 10)}, Scheme responding with an
+unbound variable error for the variable @code{fob}, and the user
+starting the debugger:
+
+@example
+1 ]=> (fib 10)
+
+Unbound variable fob
+
+2 Error-> (debug)
+
+There are 8 subproblems on the stack.
+
+Subproblem level: 0 (this is the lowest subproblem level)
+Expression (from stack):
+    fob
+Environment created by the procedure: fib
+ applied to: (10)
+The execution history for this subproblem contains 1 reduction.
+You are now in the debugger.  Type q to quit, ? for commands.
+
+3 Debug--> 
+@end example
+
+@noindent
+@cindex execution history
+This tells us that the error occurred while trying to evaluate the
+expression @code{fob} while running @code{(fib 10)}.  It also tells us
+this is subproblem level 0, the first of 8 subproblems that are
+available for us to examine.  The expression shown is marked ``(from
+stack)'', which tells us that this expression was reconstructed from the
+interpreter's internal data structures.  Another source of information
+is the @dfn{execution history}, which keeps a record of expressions
+evaluated by the interpreter.  The debugger informs us that the
+execution history has recorded some information for this subproblem,
+specifically a description of one reduction.
+
+@node Loading Files, World Images, Debugging, Top
+@chapter Loading Files
+
+To load files of Scheme code, use the procedure @code{load}:
+
+@deffn {procedure} load filename [environment [syntax-table]]
+@var{Filename} may be a string naming a file, or a list of strings
+naming many files.  @var{Environment}, if given, is the environment to
+evaluate the file in; if not given the current @sc{repl} environment is
+used.  Likewise @var{syntax-table} is the syntax table to use.
+
+@findex pathname-type
+@code{Load} determines whether the file to be loaded is binary or source
+code, and performs the appropriate action.  By convention, files of
+source code have a pathname type of @code{"scm"}, and files of binary
+SCode have pathname type @code{"bin"}.  Native-code binaries have
+pathname type @code{"com"}.  (See the description of
+@code{pathname-type} in the reference manual.)
+@end deffn
+
+@defvr {variable+} load-noisily?
+If @code{load-noisily?} is set to @code{#t}, @code{load} will print the
+value of each expression in the file as it is evaluated.  Otherwise,
+nothing is printed except for the value of the last expression in the
+file.  (Note: the noisy loading feature is implemented for source-code
+files only.)
+@end defvr
+
+@defvr {variable+} load/default-types
+This variable is a list of strings that are the pathname types to look
+for, in that order, if @code{load} is given a pathname that has no type.
+The initial value of this variable is
+
+@lisp
+("com" "bin" "scm")
+@end lisp
+@end defvr
+
+@cindex working directory
+@findex pwd
+@findex cd
+All pathnames are interpreted relative to a working directory, which is
+initialized when Scheme is started.  The working directory can be
+obtained from the procedure @code{pwd} or modified by the procedure
+@code{cd}; see the reference manual for details.
+
+@node World Images, Compiling Files, Loading Files, Top
+@chapter World Images
+
+@cindex world image
+@cindex band
+A @dfn{world image} is a file that contains a complete Scheme system,
+perhaps additionally including user application code.  Scheme provides
+two methods for saving and restoring world images.  The first method
+writes a file containing all of the Scheme code in the world, which is
+called a @dfn{band}.  The file @file{runtime.com} that is loaded by the
+microcode is just such a band.  To make your own band, use the procedure
+@code{disk-save}:
+
+@deffn {procedure+} disk-save filename [identify]
+Causes a band to be written to the file specified by @var{filename}.
+The optional argument @var{identify} controls what happens when that
+band is restored, as follows:
+
+@table @asis
+@item not specified
+Start up in the top-level @sc{repl}, identifying the world in the normal
+way.
+
+@item a string
+Do the same thing except print that string instead of @samp{Scheme} when
+restarting.
+
+@item the constant @code{#t}
+Restart exactly where you were when the call to @code{disk-save} was
+performed.  This is especially useful for saving your state when an
+error has occurred and you are not in the top-level @sc{repl}.
+
+@item the constant @code{#f}
+Just like @code{#t}, except that the runtime system will not perform
+normal restart initializations; in particular, it will not load your
+init file.
+@end table
+@end deffn
+
+@findex disk-restore
+To restore a saved band, give the @code{-band} option when starting
+Scheme.  Alternatively, evaluate @code{(disk-restore @var{filename})}
+from a running Scheme, which will destroy the current world, replacing
+it with the saved world.  The argument to @code{disk-restore} may be
+omitted, in which case it defaults to the filename from which the
+current world was last restored.
+
+Note: when restoring a saved band, the Scheme executable must be
+configured with a large enough constant space and heap to hold the
+band's contents.  If you attempt to restore a band using the
+@code{-band} option, and the band is too large, Scheme will write an
+error message that tells you the appropriate command-line options needed
+to load that band.  If you attempt restore a too-large band using
+@code{disk-restore}, Scheme will signal an error, but will not provide
+the configuration information.  In general, the configuration that was
+used to save a band is sufficiently large to restore it.
+
+@findex dump-world
+Another method for saving the world is the @code{dump-world} procedure,
+which accepts the same arguments as @code{disk-save} and works in much
+the same way.  However, rather than dumping a band, @code{dump-world}
+saves an executable image, which is started just like any other program.
+This has the advantage of being considerably faster to start on some
+systems, but the image file is typically much larger than the
+corresponding band.  However, @code{dump-world} is only supported for a
+few operating systems, and is not built in to the distributed executable
+files --- if you wish to use @code{dump-world}, you must build your own
+executable file from the source code.
+
+@node Compiling Files, GNU Emacs Interface, World Images, Top
+@chapter Compiling Files
+
+Note: the procedures described in this section are only available in the
+@file{compiler.com} world image.  Furthermore, @code{cf} is only
+available on machines that support native-code compilation.
+
+@menu
+* Compilation Procedures::      Compilation Procedures
+* Declarations::                Declarations
+@end menu
+
+@node Compilation Procedures, Declarations, Compiling Files, Compiling Files
+@section Compilation Procedures
+
+@deffn {procedure+} cf filename [destination]
+This is the program that transforms a source-code file into native-code
+binary form.  If @var{destination} is not given, as in
+
+@lisp
+(cf "foo")
+@end lisp
+
+@noindent
+@code{cf} compiles the file @file{foo.scm}, producing the file
+@file{foo.com} (incidentally it will also produce @file{foo.bin},
+@file{foo.binf}, and possibly @file{foo.ext}).  If you later evaluate
+
+@lisp
+(load "foo")
+@end lisp
+
+@noindent
+@file{foo.com} will be loaded rather than @file{foo.scm}.
+
+If @var{destination} is given, it says where the output files should go.
+If this argument is a directory, they go in that directory, e.g.:
+
+@lisp
+(cf "foo" "../bar/")
+@end lisp
+
+@noindent
+will take @file{foo.scm} and generate the file @file{../bar/foo.com}.
+If @var{destination} is not a directory, it is the root name of the
+output:
+
+@lisp
+(cf "foo" "bar")
+@end lisp
+
+@noindent
+takes @file{foo.scm} and generates @file{bar.com}.
+
+About the @file{.binf} files: these files contain the debugging
+information that Scheme uses when you call @code{debug} to examine
+compiled code.  When you load a @file{.com} file, Scheme remembers where
+it was loaded from, and when the debugger looks at the compiled code
+from that file, it attempts to find the @file{.binf} file in the same
+directory from which the @file{.com} file was loaded.  Thus it is a good
+idea to leave these files together.
+
+Another useful thing contained in the @file{.binf} file is the symbol
+table produced by the assembler.  If you have both the @file{foo.com}
+and @file{foo.binf} files, you can generate an assembly listing in
+@file{foo.lap} by evaluating:
+
+@findex compiler:write-lap-file
+@lisp
+(compiler:write-lap-file "foo")
+@end lisp
+@end deffn
+
+Unfortunately, the @file{.binf} files are somewhat large in the current
+implementation.  If you wish to save space, these files may be deleted;
+if Scheme tries to find one and cannot, it will still permit debugging,
+but will be unable to produce much information about your program.
+
+@deffn {procedure+} sf filename [destination]
+@code{sf} is the program that transforms a source-code file into binary
+SCode form; it is used on machines that do not support native-code
+compilation.  It performs numerous optimizations that can make your
+programs run considerably faster than unoptimized interpreted code.
+Also, the binary files that it generates load very quickly compared to
+source-code files.
+
+The simplest way to use @code{sf} is just to say:
+
+@lisp
+(sf @var{filename})
+@end lisp
+
+@noindent
+This will cause your file to be transformed, and the resulting binary
+file to be written out with the same name, but with @code{pathname-type}
+@code{"bin"}.  If you do not specify a @code{pathname-type} on the input
+file, @code{"scm"} is assumed.
+
+Like @code{load}, the first argument to @code{sf} may be a list of
+filenames rather than a single filename.
+
+@code{sf} takes an optional second argument, which is the filename of
+the output file.  If this argument is a directory, then the output file
+has its normal name but is put in that directory instead.
+@end deffn
+
+@node Declarations,  , Compilation Procedures, Compiling Files
+@section Declarations
+@cindex declarations
+
+Several declarations can be added to your programs to help @code{cf} and
+@code{sf} make them more efficient.
+
+@menu
+* Standard Names::              Standard Names
+* In-line Coding::              In-line Coding
+* Operator Reduction::          Operator Reduction
+@end menu
+
+@node Standard Names, In-line Coding, Declarations, Declarations
+@subsection Standard Names
+
+Normally, all files have a line
+
+@findex usual-integrations
+@lisp
+(declare (usual-integrations))
+@end lisp
+
+@noindent
+near their beginning, which tells the compiler that free variables whose
+names are defined in @code{system-global-environment} will not be
+shadowed by other definitions when the program is loaded.  If you
+redefine some global name in your code, for example @code{car},
+@code{cdr}, and @code{cons}, you should indicate it in the declaration:
+
+@lisp
+(declare (usual-integrations car cdr cons))
+@end lisp
+
+You can obtain an alphabetically-sorted list of the names that the
+@code{usual-integrations} declaration affects by evaluating the
+following expression:
+
+@lisp
+(eval '(sort (append usual-integrations/constant-names
+                     usual-integrations/expansion-names)
+             (lambda (x y)
+               (string<=? (symbol->string x)
+                          (symbol->string y))))
+      (->environment '(scode-optimizer)))
+@end lisp
+
+@node In-line Coding, Operator Reduction, Standard Names, Declarations
+@subsection In-line Coding
+
+Another useful facility is the ability to in-line code procedure
+definitions.  In fact, the compiler will perform full beta conversion,
+with automatic renaming, if you request it.  Here are the relevant
+declarations:
+
+@deffn {declaration+} integrate name @dots{}
+The variables @var{name}s should be defined in the same file as this
+declaration.  Any reference to one of the named variables that appears
+in the same block as the declaration, or one of its descendant blocks,
+will be replaced by the corresponding definition's value expression.
+@end deffn
+
+@deffn {declaration+} integrate-operator name @dots{}
+Similar to the @code{integrate} declaration, except that it only
+substitutes for references that appear in the operator position of a
+combination.  All other references are ignored.
+@end deffn
+
+@deffn {declaration+} integrate-external filename
+Causes the compiler to use the top-level integrations provided by
+@var{filename}.  @var{filename} should not specify a file type, and the
+source-code file that it names must have been previously processed by
+the compiler.
+
+If @var{filename} is a relative filename (the normal case), it is
+interpreted as being relative to the file in which the declaration
+appears.  Thus if the declaration appears in file @file{/usr/cph/foo.scm},
+then the compiler looks for a file called @file{/usr/cph/@var{filename}.ext}.
+
+Note: When the compiler finds top-level integrations, it collects them
+and outputs them into an auxiliary file with extension @file{.ext}.
+This @file{.ext} file is what the @code{integrate-external} declaration
+refers to.
+@end deffn
+
+@findex define-integrable
+@findex define
+Note that the most common use of this facility, in-line coding of
+procedure definitions, requires a somewhat complicated use of these
+declarations.  Because this is so common, there is a special form,
+@code{define-integrable}, which is like @code{define} but performs the
+appropriate declarations.  For example:
+
+@lisp
+(define-integrable (foo-bar foo bar)
+  (vector-ref (vector-ref foo bar) 3))
+@end lisp
+
+Here is how you do the same thing without this special form: there
+should be an @code{integrate-operator} declaration for the procedure's
+name, and (internal to the procedure's definition) an @code{integrate}
+declaration for each of the procedure's parameters, like this:
+
+@lisp
+(declare (integrate-operator foo-bar))
+
+(define foo-bar
+  (lambda (foo bar)
+    (declare (integrate foo bar))
+    (vector-ref (vector-ref foo bar) 3)))
+@end lisp
+
+The reason for this complication is as follows: the
+@code{integrate-operator} declaration finds all the references to
+@code{foo-bar} and replaces them with the lambda expression from the
+definition.  Then, the @code{integrate} declarations take effect because
+the combination in which the reference to @code{foo-bar} occurred
+supplies code which is substituted throughout the body of the procedure
+definition.  For example:
+
+@lisp
+(foo-bar (car baz) (cdr baz))
+@end lisp
+
+@noindent
+First use the @code{integrate-operator} declaration:
+
+@group
+@lisp
+((lambda (foo bar)
+   (declare (integrate foo bar))
+   (vector-ref (vector-ref foo bar) 3))
+ (car baz)
+ (cdr baz))
+@end lisp
+@end group
+
+@noindent
+Next use the internal @code{integrate} declaration:
+
+@group
+@lisp
+((lambda (foo bar)
+   (vector-ref (vector-ref (car baz) (cdr baz)) 3))
+ (car baz)
+ (cdr baz))
+@end lisp
+@end group
+
+@noindent
+Next notice that the variables @code{foo} and @code{bar} are not used,
+and eliminate them:
+
+@group
+@lisp
+((lambda ()
+   (vector-ref (vector-ref (car baz) (cdr baz)) 3)))
+@end lisp
+@end group
+
+@noindent
+Finally, remove the @code{((lambda () @dots{}))} to produce
+
+@lisp
+(vector-ref (vector-ref (car baz) (cdr baz)) 3)
+@end lisp
+
+@node Operator Reduction,  , In-line Coding, Declarations
+@subsection Operator Reduction
+
+@findex reduce-operator
+The @code{reduce-operator} declaration is provided to inform the
+compiler that certain names are n-ary versions of binary operators.
+Here are some examples:
+
+@noindent
+Declaration:
+
+@group
+@lisp
+(declare (reduce-operator (cons* cons)))
+@end lisp
+@end group
+
+@noindent
+Replacements:
+
+@group
+@lisp
+(cons* @var{x} @var{y} @var{z} @var{w}) @expansion{} (cons @var{x} (cons @var{y} (cons @var{z} @var{w}))),
+(cons* @var{x} @var{y}) @expansion{} (cons @var{x} @var{y})
+(cons* @var{x}) @expansion{} @var{x}
+(cons*) @error{} too few arguments
+@end lisp
+@end group
+
+@noindent
+Declaration:
+
+@group
+@lisp
+(declare (reduce-operator (list cons (null-value '() any))))
+@end lisp
+@end group
+
+@noindent
+Replacements:
+
+@group
+@lisp
+(list @var{x} @var{y} @var{z} @var{w}) @expansion{} (cons @var{x} (cons @var{y} (cons @var{z} (cons @var{w} '()))))
+(list @var{x} @var{y}) @expansion{} (cons @var{x} (cons @var{y} '()))
+(list @var{x}) @expansion{} (cons @var{x} '())
+(list) @expansion{} '()
+@end lisp
+@end group
+
+@noindent
+Declaration:
+
+@group
+@lisp
+(declare (reduce-operator (- %- (null-value 0 single) (group left))))
+@end lisp
+@end group
+
+@noindent
+Replacements:
+
+@group
+@lisp
+(- @var{x} @var{y} @var{z} @var{w}) @expansion{} (%- (%- (%- @var{x} @var{y}) @var{z}) @var{w})
+(- @var{x} @var{y}) @expansion{} (%- @var{x} @var{y})
+(- @var{x}) @expansion{} (%- 0 @var{x})
+(-) @expansion{} 0
+@end lisp
+@end group
+
+@noindent
+Declaration:
+
+@group
+@lisp
+(declare (reduce-operator (+ %+ (null-value 0 none) (group right))))
+@end lisp
+@end group
+
+@noindent
+Replacements:
+
+@group
+@lisp
+(+ @var{x} @var{y} @var{z} @var{w}) @expansion{} (%+ @var{x} (%+ @var{y} (%+ @var{z} @var{w})))
+(+ @var{x} @var{y}) @expansion{} (%+ @var{x} @var{y})
+(+ @var{x}) @expansion{} @var{x}
+(+) @expansion{} 0
+@end lisp
+@end group
+
+Note: This declaration does not cause an appropriate definition of
+@code{+} (in the last example) to appear in your code.  It merely
+informs the compiler that certain optimizations can be performed on
+calls to @code{+} by replacing them with calls to @code{%+}.  You should
+provide a definition of @code{+} as well, although it is not required.
+
+The general format of the declaration is (brackets denote optional
+elements):
+
+@group
+@lisp
+(reduce-operator
+ (@var{name}
+  @var{binop}
+  @r{[}(group @var{ordering})@r{]}
+  @r{[}(null-value @var{value} @var{null-option})@r{]}
+  @r{[}(singleton @var{unop})@r{]}
+  @r{[}(wrapper @var{wrap})@r{]}
+  ))
+@end lisp
+@end group
+
+@noindent
+where
+
+@itemize @bullet
+
+@item
+@var{name} is a symbol.
+
+@item
+@var{binop}, @var{value}, @var{unop}, and @var{wrap} are simple
+expressions in one of these forms:
+
+@table @code
+
+@item '@var{constant}
+A constant.
+
+@item @var{variable}
+A variable.
+
+@item (primitive @var{primitive-name} @r{[}@var{arity}@r{]})
+The primitive procedure named @var{primitive-name}.  The optional
+element @var{arity} specifies the number of arguments that the primitive
+accepts.
+@end table
+
+@item
+@var{null-option} is either @code{always}, @code{any}, @code{one},
+@code{single}, @code{none}, or @code{empty}.
+
+@item
+@var{ordering} is either @code{left}, @code{right}, or
+@code{associative}.
+@end itemize
+
+The meaning of these fields is:
+
+@itemize @bullet
+
+@item
+@var{name} is the name of the n-ary operation to be reduced.
+
+@item
+@var{binop} is the binary operation into which the n-ary operation is to
+be reduced.
+
+@item
+The @code{group} option specifies whether @var{name} associates to the
+right or left.
+
+@item
+The @code{null-value} option specifies a value to use in the following
+cases:
+
+@table @code
+
+@item none
+@itemx empty
+When no arguments are supplied to @var{name}, @var{value} is returned.
+
+@item one
+@itemx single
+When a single argument is provided to @var{name}, @var{value} becomes
+the second argument to @var{binop}.
+
+@item any
+@itemx always
+@var{binop} is used on the ``last'' argument, and @var{value} provides
+the remaining argument to @var{binop}.
+@end table
+
+In the above options, when @var{value} is supplied to @var{binop}, it is
+supplied on the left if grouping to the left, otherwise it is supplied
+on the right.
+
+@item
+The @code{singleton} option specifies a function, @var{unop}, to be
+invoked on the single argument left.  This option supersedes the
+@code{null-value} option, which can only take the value @code{none}.
+
+@item
+The @code{wrapper} option specifies a function, @var{wrap}, to be
+invoked on the result of the outermost call to @var{binop} after the
+expansion.
+@end itemize
+
+@node GNU Emacs Interface, Edwin, Compiling Files, Top
+@chapter GNU Emacs Interface
+
+There is an interface library, called @code{xscheme}, distributed with
+MIT Scheme and GNU Emacs, which facilitates running Scheme as a
+subprocess of Emacs.  If you wish to use this interface, please install
+the version of @file{xscheme.el} that comes with MIT Scheme, as it is
+guaranteed to be correct for your version of Scheme.
+
+@findex run-scheme
+@findex -emacs
+To invoke Scheme from Emacs, use @kbd{M-x run-scheme}, which is defined
+when either of the libraries @file{scheme} or @file{xscheme} is loaded.
+You may give @code{run-scheme} a prefix argument, in which case it will
+allow you to edit the command line that is used to invoke Scheme.
+@emph{Do not} remove the @code{-emacs} option!
+
+@findex scheme-interaction-mode
+Scheme will be started up as a subprocess in a buffer called
+@code{*scheme*}.  This buffer will be in @code{scheme-interaction-mode}
+and all output from the Scheme process will go there.  The mode line for
+the @code{*scheme*} buffer will have this form:
+
+@example
+-----Scheme: 1 [Evaluator]           (Scheme Interaction: input)------
+@end example
+
+@noindent
+@cindex level number, REPL
+The first field, showing @samp{1} in this example, is the level number.
+
+@noindent
+The second field, showing @samp{[Evaluator]} in this example, describes
+the type of @sc{repl} that is running.  Other values include:
+
+@example
+[Debugger]
+[Where]
+@end example
+
+@noindent
+The @dfn{mode} after @samp{Scheme Interaction} is one of:
+
+@table @samp
+@item input
+Scheme is waiting for input.
+
+@item run
+Scheme is running an evaluation.
+
+@item gc
+Scheme is garbage collecting.
+@end table
+
+@findex scheme-mode
+When @code{xscheme} is loaded, @code{scheme-mode} is extended to include
+commands for evaluating expressions (do @kbd{C-h m} in any
+@code{scheme-mode} buffer for the most up-to-date information):
+
+@table @kbd
+
+@item @key{ESC} o
+@kindex @key{ESC} o
+@findex xscheme-send-buffer
+Evaluates the current buffer (@code{xscheme-send-buffer}).
+
+@item @key{ESC} z
+@kindex @key{ESC} z
+@findex xscheme-send-definition
+Evaluates the current definition (@code{xscheme-send-definition}).  This
+is also bound to @kbd{@key{ESC} C-x}.
+
+@item @key{ESC} C-z
+@kindex @key{ESC} C-z
+@findex xscheme-send-region
+Evaluates the current region (@code{xscheme-send-region}).
+
+@item C-x C-e
+@kindex C-x C-e
+@findex xscheme-send-previous-expression
+Evaluates the expression to the left of point
+(@code{xscheme-send-previous-expression}).  This is also bound to
+@kbd{@key{ESC} @key{RET}}.
+
+@item C-c C-s
+@kindex C-c C-s
+@findex xscheme-select-process-buffer
+Selects the @code{*scheme*} buffer and places you at its end
+(@code{xscheme-select-process-buffer}).
+
+@item C-c C-y
+@kindex C-c C-y
+@findex xscheme-yank-previous-send
+Yanks the most recently evaluated expression, placing it at point
+(@code{xscheme-yank-previous-send}).  This works only in the
+@code{*scheme*} buffer.
+@end table
+
+The following commands provide interrupt capability:
+
+@table @kbd
+
+@item C-c C-c
+@kindex C-c C-c
+@findex xscheme-send-control-g-interrupt
+Like typing @kbd{C-g} when running Scheme without Emacs
+(@code{xscheme-send-control-g-interrupt}).
+
+@item C-c C-x
+@kindex C-c C-x
+@findex xscheme-send-control-x-interrupt
+Like typing @kbd{C-c C-x} when running Scheme without Emacs
+(@code{xscheme-send-control-x-interrupt}).
+
+@item C-c C-u
+@kindex C-c C-u
+@findex xscheme-send-control-u-interrupt
+Like typing @kbd{C-c C-u} when running Scheme without Emacs
+(@code{xscheme-send-control-u-interrupt}).
+
+@item C-c C-b
+@kindex C-c C-b
+@findex xscheme-send-breakpoint-interrupt
+Like typing @kbd{C-c C-b} when running Scheme without Emacs
+(@code{xscheme-send-breakpoint-interrupt}).
+
+@item C-c C-p
+@kindex C-c C-p
+@findex xscheme-send-proceed
+Like evaluating @code{(proceed)} (@code{xscheme-send-proceed}).
+@end table
+
+@node Edwin, Variable Index, GNU Emacs Interface, Top
+@chapter Edwin
+
+This chapter describes how to start Edwin, the MIT Scheme text editor.
+Edwin is very similar to GNU Emacs --- you should refer to the GNU Emacs
+manual for information about Edwin's commands and key bindings ---
+except that Edwin's extension language is MIT Scheme, while GNU Emacs
+extensions are written in Emacs Lisp.  This manual does not discuss
+customization of Edwin.
+
+To use Edwin, start Scheme with a world image containing Edwin (for
+example by giving the @code{-edwin} command-line option), then call the
+procedure @code{edit}:
+
+@deffn {procedure+} edit
+Enter the Edwin text editor.  If entering for the first time, the editor
+is initialized (by calling @code{create-editor} with no arguments).
+Otherwise, the previously-initialized editor is reentered.
+
+@findex edwin
+The procedure @code{edwin} is an alias for @code{edit}.
+@end deffn
+
+@defvr {variable+} inhibit-editor-init-file?
+When Edwin is first initialized, it loads your init file (called
+@file{~/.edwin}) if you have one.  If the Scheme variable
+@code{inhibit-editor-init-file?} is true, however, your init file will
+not be loaded even if it exists.  By default, this variable is false.
+@end defvr
+
+@deffn {procedure+} create-editor arg @dots{}
+Initializes Edwin, or reinitializes it if already initialized.
+@code{Create-editor} is normally invoked automatically by @code{edit}.
+
+If no @var{arg}s are given, the value of @code{create-editor-args} is
+used instead.  In other words, the following are equivalent:
+
+@lisp
+(create-editor)
+(apply create-editor create-editor-args)
+@end lisp
+
+@noindent
+On the other hand, if @var{arg}s are given, they are used to update
+@code{create-editor-args}, making the following equivalent:
+
+@lisp
+(apply create-editor @var{args})
+(begin (set! create-editor-args @var{args}) (create-editor))
+@end lisp
+@end deffn
+
+@defvr {variable+} create-editor-args
+This variable controls the initialization of Edwin.  The following
+values are defined:
+
+@table @code
+
+@item (console)
+This says to run Edwin on Scheme's console, or in unix terminology, the
+standard input and output.  If the console is not a terminal device, or
+is not powerful enough to run Edwin, an error will be signalled at
+initialization time.
+
+@item (x)
+@findex DISPLAY
+This says to create an X window and run Edwin on it.  This requires the
+@code{DISPLAY} environment variable to have been set to the appropriate
+value before Scheme was started.
+
+@item (x @var{geometry})
+This is like @code{(x)} except that @var{geometry} specifies the
+window's geometry in the usual way.  @var{Geometry} must be a character
+string whose contents is an X geometry specification.
+
+@item (#f)
+This is the default.  It says to try running Edwin on Scheme's console,
+and failing that, to create an X window and run Edwin on that.  This
+signals an error if neither the console nor the X display is usable.
+@end table
+@end defvr
+
+Once Edwin has been entered, it can be exited in the following ways:
+
+@table @kbd
+
+@item C-x z
+@kindex C-x z
+@findex suspend-edwin
+Stop Edwin and return to Scheme (@code{suspend-edwin}).  The call to the
+procedure @code{edit} that entered Edwin returns normally.  A subsequent
+call to @code{edit} will resume Edwin where it was stopped.
+
+@item C-x c
+@kindex C-x c
+@findex save-buffers-kill-edwin
+Offer to save any modified buffers, then kill Edwin, returning to Scheme
+(@code{save-buffers-kill-edwin}).  This is like the @code{suspend-edwin}
+command, except that a subsequent call to @code{edit} will reinitialize
+the editor.
+
+@item C-x C-z
+@kindex C-x C-z
+@findex suspend-scheme
+Stop Edwin and suspend Scheme, returning control to the operating
+system's command interpreter (@code{suspend-scheme}).  When Scheme is
+resumed (using the command interpreter's job-control commands), Edwin is
+automatically restarted where it was stopped.  This command is identical
+to the @kbd{C-x C-z} command of GNU Emacs.
+
+@item C-x C-c
+@kindex C-x C-c
+@findex save-buffers-kill-scheme
+Offer to save any modified buffers, then kill both Edwin and Scheme
+(@code{save-buffers-kill-scheme}).  Control is returned to the operating
+system's command interpreter, and the Scheme process is terminated.
+This command is identical to the @kbd{C-x C-c} command of GNU Emacs.
+@end table
+
+The following Scheme procedures are useful for recovering from bugs in
+Edwin's implementation.  All of them are designed for use when Edwin is
+@emph{not} running --- they should not be used when Edwin is running.
+These procedures are designed to help Edwin's implementors deal with
+bugs during the implementation of the editor; they are not intended for
+casual use, but as a means of recovering from bugs that would otherwise
+require reloading the editor's world image from the disk.
+
+@deffn {procedure+} save-editor-files
+Examines Edwin, offering to save any unsaved buffers.  This is useful if
+some bug caused Edwin to die while there were unsaved buffers, and you
+want to save the information without restarting the editor.
+@end deffn
+
+@deffn {procedure+} reset-editor
+Resets Edwin, causing it to be reinitialized the next time that
+@code{edit} is called.  If you encounter a fatal bug in Edwin, a good
+way to recover is to first call @code{save-editor-files}, and then to
+call @code{reset-editor}.  That should completely reset the editor to
+its initial state.
+@end deffn
+
+@deffn {procedure+} reset-editor-windows
+Resets Edwin's display structures, without affecting any of the buffers
+or their contents.  This is useful if a bug in the display code causes
+Edwin's internal display data structures to get into an inconsistent
+state that prevents Edwin from running.
+@end deffn
+\f
+@node Variable Index, Key Index, Edwin, Top
+@unnumbered Variable, Declaration, and Option Index
+@printindex fn
+
+@node Key Index, Concept Index, Variable Index, Top
+@unnumbered Key Index
+@printindex ky
+
+@node Concept Index,  , Key Index, Top
+@unnumbered Concept Index
+@printindex cp
+
+@contents
+@bye
+
+@c Local Variables:
+@c selective-display: t
+@c truncate-lines: t
+@c End: