summaryrefslogtreecommitdiff
path: root/support/vvcode/doc
diff options
context:
space:
mode:
authorNorbert Preining <norbert@preining.info>2019-09-02 13:46:59 +0900
committerNorbert Preining <norbert@preining.info>2019-09-02 13:46:59 +0900
commite0c6872cf40896c7be36b11dcc744620f10adf1d (patch)
tree60335e10d2f4354b0674ec22d7b53f0f8abee672 /support/vvcode/doc
Initial commit
Diffstat (limited to 'support/vvcode/doc')
-rw-r--r--support/vvcode/doc/texinfo.tex3229
-rw-r--r--support/vvcode/doc/vvcode.tex255
-rw-r--r--support/vvcode/doc/vvfiles.tex1287
-rw-r--r--support/vvcode/doc/vvinstal.tex17
-rw-r--r--support/vvcode/doc/vvintro.tex483
-rw-r--r--support/vvcode/doc/vvport.tex704
-rw-r--r--support/vvcode/doc/vvtest.tex432
-rw-r--r--support/vvcode/doc/vvuser.tex200
8 files changed, 6607 insertions, 0 deletions
diff --git a/support/vvcode/doc/texinfo.tex b/support/vvcode/doc/texinfo.tex
new file mode 100644
index 0000000000..32eec25962
--- /dev/null
+++ b/support/vvcode/doc/texinfo.tex
@@ -0,0 +1,3229 @@
+%% TeX macros to handle texinfo files
+
+% Copyright (C) 1985, 1986, 1988, 1990, 1991 Free Software Foundation, Inc.
+
+%This texinfo.tex file is free software; you can redistribute it and/or
+%modify it under the terms of the GNU General Public License as
+%published by the Free Software Foundation; either version 2, or (at
+%your option) any later version.
+
+%This texinfo.tex file is distributed in the hope that it will be
+%useful, but WITHOUT ANY WARRANTY; without even the implied warranty
+%of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+%General Public License for more details.
+
+%You should have received a copy of the GNU General Public License
+%along with this texinfo.tex file; see the file COPYING. If not, write
+%to the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139,
+%USA.
+
+
+%In other words, you are welcome to use, share and improve this program.
+%You are forbidden to forbid anyone else to use, share and improve
+%what you give them. Help stamp out software-hoarding!
+
+\def\texinfoversion{2.65}
+\message{Loading texinfo package [Version \texinfoversion]:}
+\message{}
+
+% Print the version number if in a .fmt file.
+\everyjob{\message{[Texinfo version \texinfoversion]}\message{}}
+
+% Save some parts of plain tex whose names we will redefine.
+
+\let\ptexlbrace=\{
+\let\ptexrbrace=\}
+\let\ptexdots=\dots
+\let\ptexdot=\.
+\let\ptexstar=\*
+\let\ptexend=\end
+\let\ptexbullet=\bullet
+\let\ptexb=\b
+\let\ptexc=\c
+\let\ptexi=\i
+\let\ptext=\t
+\let\ptexl=\l
+\let\ptexL=\L
+
+\def\tie{\penalty 10000\ } % Save plain tex definition of ~.
+
+\message{Basics,}
+\chardef\other=12
+
+\hyphenation{ap-pen-dix}
+\hyphenation{mini-buf-fer mini-buf-fers}
+\hyphenation{eshell}
+
+% Margin to add to right of even pages, to left of odd pages.
+\newdimen \bindingoffset \bindingoffset=0pt
+\newdimen \normaloffset \normaloffset=\hoffset
+\newdimen\pagewidth \newdimen\pageheight
+\pagewidth=\hsize \pageheight=\vsize
+
+%---------------------Begin change-----------------------
+%
+%%%% For @cropmarks command.
+% Dimensions to add cropmarks at corners Added by P. A. MacKay, 12 Nov. 1986
+%
+\newdimen\cornerlong \newdimen\cornerthick
+\newdimen \topandbottommargin
+\newdimen \outerhsize \newdimen \outervsize
+\cornerlong=1pc\cornerthick=.3pt % These set size of cropmarks
+\outerhsize=7in
+%\outervsize=9.5in
+% Alternative @smallbook page size is 9.25in
+\outervsize=9.25in
+\topandbottommargin=.75in
+%
+%---------------------End change-----------------------
+
+% \onepageout takes a vbox as an argument. Note that \pagecontents
+% does insertions itself, but you have to call it yourself.
+\chardef\PAGE=255 \output={\onepageout{\pagecontents\PAGE}}
+\def\onepageout#1{\hoffset=\normaloffset
+\ifodd\pageno \advance\hoffset by \bindingoffset
+\else \advance\hoffset by -\bindingoffset\fi
+{\escapechar=`\\\relax % makes sure backslash is used in output files.
+\shipout\vbox{{\let\hsize=\pagewidth \makeheadline} \pagebody{#1}%
+{\let\hsize=\pagewidth \makefootline}}}%
+\advancepageno \ifnum\outputpenalty>-20000 \else\dosupereject\fi}
+
+%%%% For @cropmarks command %%%%
+
+% Here is a modification of the main output routine for Near East Publications
+% This provides right-angle cropmarks at all four corners.
+% The contents of the page are centerlined into the cropmarks,
+% and any desired binding offset is added as an \hskip on either
+% site of the centerlined box. (P. A. MacKay, 12 November, 1986)
+%
+\def\croppageout#1{\hoffset=0pt % make sure this doesn't mess things up
+ \shipout
+ \vbox to \outervsize{\hsize=\outerhsize
+ \vbox{\line{\ewtop\hfill\ewtop}}
+ \nointerlineskip
+ \line{\vbox{\moveleft\cornerthick\nstop}
+ \hfill
+ \vbox{\moveright\cornerthick\nstop}}
+ \vskip \topandbottommargin
+ \centerline{\ifodd\pageno\hskip\bindingoffset\fi
+ \vbox{
+ {\let\hsize=\pagewidth \makeheadline}
+ \pagebody{#1}
+ {\let\hsize=\pagewidth \makefootline}}
+ \ifodd\pageno\else\hskip\bindingoffset\fi}
+ \vskip \topandbottommargin plus1fill minus1fill
+ \boxmaxdepth\cornerthick
+ \line{\vbox{\moveleft\cornerthick\nsbot}
+ \hfill
+ \vbox{\moveright\cornerthick\nsbot}}
+ \nointerlineskip
+ \vbox{\line{\ewbot\hfill\ewbot}}
+ }
+ \advancepageno
+ \ifnum\outputpenalty>-20000 \else\dosupereject\fi}
+%
+% Do @cropmarks to get crop marks
+\def\cropmarks{\let\onepageout=\croppageout }
+
+\def\pagebody#1{\vbox to\pageheight{\boxmaxdepth=\maxdepth #1}}
+{\catcode`\@ =11
+\gdef\pagecontents#1{\ifvoid\topins\else\unvbox\topins\fi
+\dimen@=\dp#1 \unvbox#1
+\ifvoid\footins\else\vskip\skip\footins\footnoterule \unvbox\footins\fi
+\ifr@ggedbottom \kern-\dimen@ \vfil \fi}
+}
+
+%
+% Here are the rules for the cropmarks. Note that they are
+% offset so that the space between them is truly \outerhsize or \outervsize
+% (P. A. MacKay, 12 November, 1986)
+%
+\def\ewtop{\vrule height\cornerthick depth0pt width\cornerlong}
+\def\nstop{\vbox
+ {\hrule height\cornerthick depth\cornerlong width\cornerthick}}
+\def\ewbot{\vrule height0pt depth\cornerthick width\cornerlong}
+\def\nsbot{\vbox
+ {\hrule height\cornerlong depth\cornerthick width\cornerthick}}
+
+% Parse an argument, then pass it to #1.
+% The argument can be delimited with [...] or with "..." or braces
+% or it can be a whole line.
+% #1 should be a macro which expects
+% an ordinary undelimited TeX argument.
+
+\def\parsearg #1{\let\next=#1\begingroup\obeylines\futurelet\temp\parseargx}
+
+\def\parseargx{%
+\ifx \obeyedspace\temp \aftergroup\parseargdiscardspace \else%
+\aftergroup \parseargline %
+\fi \endgroup}
+
+{\obeyspaces %
+\gdef\parseargdiscardspace {\begingroup\obeylines\futurelet\temp\parseargx}}
+
+\gdef\obeyedspace{\ }
+
+\def\parseargline{\begingroup \obeylines \parsearglinex}
+{\obeylines %
+\gdef\parsearglinex #1^^M{\endgroup \next {#1}}}
+
+\def\flushcr{\ifx\par\lisppar \def\next##1{}\else \let\next=\relax \fi \next}
+
+%% These are used to keep @begin/@end levels from running away
+%% Call \inENV within environments (after a \begingroup)
+\newif\ifENV \ENVfalse \def\inENV{\ifENV\relax\else\ENVtrue\fi}
+\def\ENVcheck{%
+\ifENV\errmessage{Still within an environment. Type Return to continue.}
+\endgroup\fi} % This is not perfect, but it should reduce lossage
+
+% @begin foo is the same as @foo, for now.
+\newhelp\EMsimple{Type <Return> to continue}
+
+\outer\def\begin{\parsearg\beginxxx}
+
+\def\beginxxx #1{%
+\expandafter\ifx\csname #1\endcsname\relax
+{\errhelp=\EMsimple \errmessage{Undefined command @begin #1}}\else
+\csname #1\endcsname\fi}
+
+%% @end foo executes the definition of \Efoo.
+%% foo can be delimited by doublequotes or brackets.
+
+\def\end{\parsearg\endxxx}
+
+\def\endxxx #1{%
+\expandafter\ifx\csname E#1\endcsname\relax
+\expandafter\ifx\csname #1\endcsname\relax
+\errmessage{Undefined command @end #1}\else
+\errorE{#1}\fi\fi
+\csname E#1\endcsname}
+\def\errorE#1{
+{\errhelp=\EMsimple \errmessage{@end #1 not within #1 environment}}}
+
+% Single-spacing is done by various environments.
+
+\newskip\singlespaceskip \singlespaceskip = \baselineskip
+\def\singlespace{%
+{\advance \baselineskip by -\singlespaceskip
+\kern \baselineskip}%
+\baselineskip=\singlespaceskip
+}
+
+%% Simple single-character @ commands
+
+% @@ prints an @
+% Kludge this until the fonts are right (grr).
+\def\@{{\tt \char '100}}
+
+% Define @` and @' to be the same as ` and '
+% but suppressing ligatures.
+\def\`{{`}}
+\def\'{{'}}
+
+% Used to generate quoted braces.
+
+\def\mylbrace {{\tt \char '173}}
+\def\myrbrace {{\tt \char '175}}
+\let\{=\mylbrace
+\let\}=\myrbrace
+
+% @: forces normal size whitespace following.
+\def\:{\spacefactor=1000 }
+
+% @* forces a line break.
+\def\*{\hfil\break\hbox{}\ignorespaces}
+
+% @. is an end-of-sentence period.
+\def\.{.\spacefactor=3000 }
+
+% @w prevents a word break
+\def\w #1{\hbox{#1}}
+
+% @group ... @end group forces ... to be all on one page.
+
+\def\group{\begingroup% \inENV ???
+\ifnum\catcode13=\active \else
+\errmessage{@group invalid in context where filling is enabled}\fi
+\def \Egroup{\egroup\endgroup}
+\vbox\bgroup}
+
+% @need space-in-mils
+% forces a page break if there is not space-in-mils remaining.
+
+\newdimen\mil \mil=0.001in
+
+\def\need{\parsearg\needx}
+
+\def\needx #1{\par %
+% This method tries to make TeX break the page naturally
+% if the depth of the box does not fit.
+{\baselineskip=0pt%
+\vtop to #1\mil{\vfil}\kern -#1\mil\penalty 10000
+\prevdepth=-1000pt
+}}
+
+% @br forces paragraph break
+
+\let\br = \par
+
+% @dots{} output some dots
+
+\def\dots{$\ldots$}
+
+% @page forces the start of a new page
+
+\def\page{\par\vfill\supereject}
+
+% @exdent text....
+% outputs text on separate line in roman font, starting at standard page margin
+
+\def\exdent{\errmessage{@exdent in filled text}}
+ % @lisp, etc, define \exdent locally from \internalexdent
+
+{\obeyspaces
+\gdef\internalexdent{\parsearg\exdentzzz}}
+
+\def\exdentzzz #1{{\advance \leftskip by -\lispnarrowing
+\advance \hsize by -\leftskip
+\advance \hsize by -\rightskip
+\leftline{{\rm#1}}}}
+
+% @include file insert text of that file as input.
+
+\def\include{\parsearg\includezzz}
+\def\includezzz #1{{\def\thisfile{#1}\input #1
+}}
+
+\def\thisfile{}
+
+% @center line outputs that line, centered
+
+\def\center{\parsearg\centerzzz}
+\def\centerzzz #1{{\advance\hsize by -\leftskip
+\advance\hsize by -\rightskip
+\centerline{#1}}}
+
+% @sp n outputs n lines of vertical space
+
+\def\sp{\parsearg\spxxx}
+\def\spxxx #1{\par \vskip #1\baselineskip}
+
+% @comment ...line which is ignored...
+% @c is the same as @comment
+% @ignore ... @end ignore is another way to write a comment
+
+\def\comment{\catcode 64=\other \catcode 123=\other \catcode 125=\other%
+\parsearg \commentxxx}
+
+\def\commentxxx #1{\catcode 64=0 \catcode 123=1 \catcode 125=2 }
+
+\let\c=\comment
+
+% Prevent errors for section commands.
+% Used in @ignore and in failing conditionals.
+\def\ignoresections{%
+\let\chapter=\relax
+\let\unnumbered=\relax
+\let\top=\relax
+\let\unnumberedsec=\relax
+\let\unnumberedsection=\relax
+\let\unnumberedsubsec=\relax
+\let\unnumberedsubsection=\relax
+\let\unnumberedsubsubsec=\relax
+\let\unnumberedsubsubsection=\relax
+\let\section=\relax
+\let\subsec=\relax
+\let\subsubsec=\relax
+\let\subsection=\relax
+\let\subsubsection=\relax
+\let\appendix=\relax
+\let\appendixsec=\relax
+\let\appendixsection=\relax
+\let\appendixsubsec=\relax
+\let\appendixsubsection=\relax
+\let\appendixsubsubsec=\relax
+\let\appendixsubsubsection=\relax
+\let\contents=\relax
+\let\smallbook=\relax
+\let\titlepage=\relax
+}
+
+\def\ignore{\begingroup\ignoresections
+% Make sure that spaces turn into tokens that match what \ignorexxx wants.
+\catcode32=10
+\ignorexxx}
+\long\def\ignorexxx #1\end ignore{\endgroup\ignorespaces}
+
+\def\direntry{\begingroup\direntryxxx}
+\long\def\direntryxxx #1\end direntry{\endgroup\ignorespaces}
+
+% Conditionals to test whether a flag is set.
+
+\def\ifset{\begingroup\ignoresections\parsearg\ifsetxxx}
+
+\def\ifsetxxx #1{\endgroup
+\expandafter\ifx\csname IF#1\endcsname\relax \let\temp=\ifsetfail
+\else \let\temp=\relax \fi
+\temp}
+\def\Eifset{}
+\def\ifsetfail{\begingroup\ignoresections\ifsetfailxxx}
+\long\def\ifsetfailxxx #1\end ifset{\endgroup\ignorespaces}
+
+\def\ifclear{\begingroup\ignoresections\parsearg\ifclearxxx}
+
+\def\ifclearxxx #1{\endgroup
+\expandafter\ifx\csname IF#1\endcsname\relax \let\temp=\relax
+\else \let\temp=\ifclearfail \fi
+\temp}
+\def\Eifclear{}
+\def\ifclearfail{\begingroup\ignoresections\ifclearfailxxx}
+\long\def\ifclearfailxxx #1\end ifclear{\endgroup\ignorespaces}
+
+% @set foo to set the flag named foo.
+% @clear foo to clear the flag named foo.
+\def\set{\parsearg\setxxx}
+\def\setxxx #1{
+\expandafter\let\csname IF#1\endcsname=\set}
+
+\def\clear{\parsearg\clearxxx}
+\def\clearxxx #1{
+\expandafter\let\csname IF#1\endcsname=\relax}
+
+% Some texinfo constructs that are trivial in tex
+
+\def\iftex{}
+\def\Eiftex{}
+\def\ifinfo{\begingroup\ignoresections\ifinfoxxx}
+\long\def\ifinfoxxx #1\end ifinfo{\endgroup\ignorespaces}
+
+\long\def\menu #1\end menu{}
+\def\asis#1{#1}
+
+% @math means output in math mode.
+% We don't use $'s directly in the definition of \math because control
+% sequences like \math are expanded when the toc file is written. Then,
+% we read the toc file back, the $'s will be normal characters (as they
+% should be, according to the definition of Texinfo). So we must use a
+% control sequence to switch into and out of math mode.
+%
+% This isn't quite enough for @math to work properly in indices, but it
+% seems unlikely it will ever be needed there.
+%
+\let\implicitmath = $
+\def\math#1{\implicitmath #1\implicitmath}
+
+\def\node{\ENVcheck\parsearg\nodezzz}
+\def\nodezzz#1{\nodexxx [#1,]}
+\def\nodexxx[#1,#2]{\gdef\lastnode{#1}}
+\let\lastnode=\relax
+
+\def\donoderef{\ifx\lastnode\relax\else
+\expandafter\expandafter\expandafter\setref{\lastnode}\fi
+\let\lastnode=\relax}
+
+\def\unnumbnoderef{\ifx\lastnode\relax\else
+\expandafter\expandafter\expandafter\unnumbsetref{\lastnode}\fi
+\let\lastnode=\relax}
+
+\def\appendixnoderef{\ifx\lastnode\relax\else
+\expandafter\expandafter\expandafter\appendixsetref{\lastnode}\fi
+\let\lastnode=\relax}
+
+\let\refill=\relax
+
+% @setfilename is done at the beginning of every texinfo file.
+% So open here the files we need to have open while reading the input.
+% This makes it possible to make a .fmt file for texinfo.
+\def\setfilename{%
+ \readauxfile
+ \opencontents
+ \openindices
+ \fixbackslash % Turn off hack to swallow `\input texinfo'.
+ \global\let\setfilename=\comment % Ignore extra @setfilename cmds.
+ \comment % Ignore the actual filename.
+}
+
+\outer\def\bye{\pagealignmacro\tracingstats=1\ptexend}
+
+\def\inforef #1{\inforefzzz #1,,,,**}
+\def\inforefzzz #1,#2,#3,#4**{See Info file \file{\losespace#3{}},
+ node \samp{\losespace#1{}}}
+\def\losespace #1{#1}
+
+\message{fonts,}
+
+% Font-change commands.
+
+% Texinfo supports the sans serif font style, which plain TeX does not.
+% So we set up a \sf analogous to plain's \rm, etc.
+\newfam\sffam
+\def\sf{\fam=\sffam \tensf}
+\let\li = \sf % Sometimes we call it \li, not \sf.
+
+%% Try out Computer Modern fonts at \magstephalf
+\let\mainmagstep=\magstephalf
+
+\ifx\bigger\relax
+\let\mainmagstep=\magstep1
+\font\textrm=cmr12
+\font\texttt=cmtt12
+\else
+\font\textrm=cmr10 scaled \mainmagstep
+\font\texttt=cmtt10 scaled \mainmagstep
+\fi
+% Instead of cmb10, you many want to use cmbx10.
+% cmbx10 is a prettier font on its own, but cmb10
+% looks better when embedded in a line with cmr10.
+\font\textbf=cmb10 scaled \mainmagstep
+\font\textit=cmti10 scaled \mainmagstep
+\font\textsl=cmsl10 scaled \mainmagstep
+\font\textsf=cmss10 scaled \mainmagstep
+\font\textsc=cmcsc10 scaled \mainmagstep
+\font\texti=cmmi10 scaled \mainmagstep
+\font\textsy=cmsy10 scaled \mainmagstep
+
+% A few fonts for @defun, etc.
+\font\defbf=cmbx10 scaled \magstep1 %was 1314
+\font\deftt=cmtt10 scaled \magstep1
+\def\df{\let\tentt=\deftt \let\tenbf = \defbf \bf}
+
+% Fonts for indices and small examples.
+% We actually use the slanted font rather than the italic,
+% because texinfo normally uses the slanted fonts for that.
+% Do not make many font distinctions in general in the index, since they
+% aren't very useful.
+\font\ninett=cmtt9
+\font\indrm=cmr9
+\font\indit=cmsl9
+\let\indsl=\indit
+\let\indtt=\ninett
+\let\indsf=\indrm
+\let\indbf=\indrm
+\let\indsc=\indrm
+\font\indi=cmmi9
+\font\indsy=cmsy9
+
+% Fonts for headings
+\font\chaprm=cmbx12 scaled \magstep2
+\font\chapit=cmti12 scaled \magstep2
+\font\chapsl=cmsl12 scaled \magstep2
+\font\chaptt=cmtt12 scaled \magstep2
+\font\chapsf=cmss12 scaled \magstep2
+\let\chapbf=\chaprm
+\font\chapsc=cmcsc10 scaled\magstep3
+\font\chapi=cmmi12 scaled \magstep2
+\font\chapsy=cmsy10 scaled \magstep3
+
+\font\secrm=cmbx12 scaled \magstep1
+\font\secit=cmti12 scaled \magstep1
+\font\secsl=cmsl12 scaled \magstep1
+\font\sectt=cmtt12 scaled \magstep1
+\font\secsf=cmss12 scaled \magstep1
+\font\secbf=cmbx12 scaled \magstep1
+\font\secsc=cmcsc10 scaled\magstep2
+\font\seci=cmmi12 scaled \magstep1
+\font\secsy=cmsy10 scaled \magstep2
+
+% \font\ssecrm=cmbx10 scaled \magstep1 % This size an font looked bad.
+% \font\ssecit=cmti10 scaled \magstep1 % The letters were too crowded.
+% \font\ssecsl=cmsl10 scaled \magstep1
+% \font\ssectt=cmtt10 scaled \magstep1
+% \font\ssecsf=cmss10 scaled \magstep1
+
+%\font\ssecrm=cmb10 scaled 1315 % Note the use of cmb rather than cmbx.
+%\font\ssecit=cmti10 scaled 1315 % Also, the size is a little larger than
+%\font\ssecsl=cmsl10 scaled 1315 % being scaled magstep1.
+%\font\ssectt=cmtt10 scaled 1315
+%\font\ssecsf=cmss10 scaled 1315
+
+%\let\ssecbf=\ssecrm
+
+\font\ssecrm=cmbx12 scaled \magstephalf
+\font\ssecit=cmti12 scaled \magstephalf
+\font\ssecsl=cmsl12 scaled \magstephalf
+\font\ssectt=cmtt12 scaled \magstephalf
+\font\ssecsf=cmss12 scaled \magstephalf
+\font\ssecbf=cmbx12 scaled \magstephalf
+\font\ssecsc=cmcsc10 scaled \magstep1
+\font\sseci=cmmi12 scaled \magstephalf
+\font\ssecsy=cmsy10 scaled \magstep1
+% The smallcaps and symbol fonts should actually be scaled \magstep1.5,
+% but that is not a standard magnification.
+
+% Fonts for title page:
+\font\titlerm = cmbx12 scaled \magstep3
+\let\authorrm = \secrm
+
+% In order for the font changes to affect most math symbols and letters,
+% we have to define the \textfont of the standard families. Since
+% texinfo doesn't allow for producing subscripts and superscripts, we
+% don't bother to reset \scriptfont and \scriptscriptfont (which would
+% also require loading a lot more fonts).
+%
+\def\resetmathfonts{%
+ \textfont0 = \tenrm \textfont1 = \teni \textfont2 = \tensy
+ \textfont\itfam = \tenit \textfont\slfam = \tensl \textfont\bffam = \tenbf
+ \textfont\ttfam = \tentt \textfont\sffam = \tensf
+}
+
+
+% The font-changing commands redefine the meanings of \tenSTYLE, instead
+% of just \STYLE. We do this so that font changes will continue to work
+% in math mode, where it is the current \fam that is relevant in most
+% cases, not the current. Plain TeX does, for example,
+% \def\bf{\fam=\bffam \tenbf} By redefining \tenbf, we obviate the need
+% to redefine \bf itself.
+\def\textfonts{%
+ \let\tenrm=\textrm \let\tenit=\textit \let\tensl=\textsl
+ \let\tenbf=\textbf \let\tentt=\texttt \let\smallcaps=\textsc
+ \let\tensf=\textsf \let\teni=\texti \let\tensy=\textsy
+ \resetmathfonts}
+\def\chapfonts{%
+ \let\tenrm=\chaprm \let\tenit=\chapit \let\tensl=\chapsl
+ \let\tenbf=\chapbf \let\tentt=\chaptt \let\smallcaps=\chapsc
+ \let\tensf=\chapsf \let\teni=\chapi \let\tensy=\chapsy
+ \resetmathfonts}
+\def\secfonts{%
+ \let\tenrm=\secrm \let\tenit=\secit \let\tensl=\secsl
+ \let\tenbf=\secbf \let\tentt=\sectt \let\smallcaps=\secsc
+ \let\tensf=\secsf \let\teni=\seci \let\tensy=\secsy
+ \resetmathfonts}
+\def\subsecfonts{%
+ \let\tenrm=\ssecrm \let\tenit=\ssecit \let\tensl=\ssecsl
+ \let\tenbf=\ssecbf \let\tentt=\ssectt \let\smallcaps=\ssecsc
+ \let\tensf=\ssecsf \let\teni=\sseci \let\tensy=\ssecsy
+ \resetmathfonts}
+\def\indexfonts{%
+ \let\tenrm=\indrm \let\tenit=\indit \let\tensl=\indsl
+ \let\tenbf=\indbf \let\tentt=\indtt \let\smallcaps=\indsc
+ \let\tensf=\indsf \let\teni=\indi \let\tensy=\indsy
+ \resetmathfonts}
+
+% Set up the default fonts, so we can use them for creating boxes.
+%
+\textfonts
+
+% Count depth in font-changes, for error checks
+\newcount\fontdepth \fontdepth=0
+
+% Fonts for short table of contents.
+\font\shortcontrm=cmr12
+\font\shortcontbf=cmbx12
+\font\shortcontsl=cmsl12
+
+%% Add scribe-like font environments, plus @l for inline lisp (usually sans
+%% serif) and @ii for TeX italic
+
+% \smartitalic{ARG} outputs arg in italics, followed by an italic correction
+% unless the following character is such as not to need one.
+\def\smartitalicx{\ifx\next,\else\ifx\next-\else\ifx\next.\else\/\fi\fi\fi}
+\def\smartitalic#1{{\sl #1}\futurelet\next\smartitalicx}
+
+\let\i=\smartitalic
+\let\var=\smartitalic
+\let\dfn=\smartitalic
+\let\emph=\smartitalic
+\let\cite=\smartitalic
+
+\def\b#1{{\bf #1}}
+\let\strong=\b
+
+\def\t#1{{\tt \exhyphenpenalty=10000\rawbackslash \frenchspacing #1}\null}
+\let\ttfont = \t
+%\def\samp #1{`{\tt \rawbackslash \frenchspacing #1}'\null}
+\def\samp #1{`\tclose{#1}'\null}
+\def\key #1{{\tt \exhyphenpenalty=10000\uppercase{#1}}\null}
+\def\ctrl #1{{\tt \rawbackslash \hat}#1}
+
+\let\file=\samp
+
+% @code is a modification of @t,
+% which makes spaces the same size as normal in the surrounding text.
+\newdimen\tclosesave
+\newdimen\tcloserm
+\def\tclose#1{{\rm \tcloserm=\fontdimen2\font \tt \tclosesave=\fontdimen2\font
+\fontdimen2\font=\tcloserm
+% prevent breaking lines at hyphens.
+\exhyphenpenalty=10000
+\def\ {{\fontdimen2\font=\tclosesave{} }}%
+ \rawbackslash \frenchspacing #1\fontdimen2\font=\tclosesave}\null}
+\let\code=\tclose
+%\let\exp=\tclose %Was temporary
+
+% @kbd is like @code, except that if the argument is just one @key command,
+% then @kbd has no effect.
+
+\def\xkey{\key}
+\def\kbdfoo#1#2#3\par{\def\one{#1}\def\three{#3}\def\threex{??}%
+\ifx\one\xkey\ifx\threex\three \key{#2}%
+\else\tclose{\look}\fi
+\else\tclose{\look}\fi}
+
+% Typeset a dimension, e.g., `in' or `pt'. The only reason for the
+% argument is to make the input look right: @dmn{pt} instead of
+% @dmn{}pt.
+%
+\def\dmn#1{\thinspace #1}
+
+\def\kbd#1{\def\look{#1}\expandafter\kbdfoo\look??\par}
+
+\def\l#1{{\li #1}\null} %
+
+\def\r#1{{\rm #1}} % roman font
+% Use of \lowercase was suggested.
+\def\sc#1{{\smallcaps#1}} % smallcaps font
+\def\ii#1{{\it #1}} % italic font
+
+\message{page headings,}
+
+\newskip\titlepagetopglue \titlepagetopglue = 1.5in
+\newskip\titlepagebottomglue \titlepagebottomglue = 2pc
+
+% First the title page. Must do @settitle before @titlepage.
+\def\titlefont#1{{\titlerm #1}}
+
+\newtoks\realeverypar
+\newif\ifseenauthor
+\newif\iffinishedtitlepage
+
+\def\titlepage{\begingroup \parindent=0pt \textfonts
+ \let\subtitlerm=\tenrm
+% I deinstalled the following change because \cmr12 is undefined.
+% This change was not in the ChangeLog anyway. --rms.
+% \let\subtitlerm=\cmr12
+ \def\subtitlefont{\subtitlerm \normalbaselineskip = 13pt \normalbaselines}%
+ %
+ \def\authorfont{\authorrm \normalbaselineskip = 16pt \normalbaselines}%
+ %
+ % Leave some space at the very top of the page.
+ \vglue\titlepagetopglue
+ %
+ % Now you can print the title using @title.
+ \def\title{\parsearg\titlezzz}%
+ \def\titlezzz##1{\leftline{\titlefont{##1}}
+ % print a rule at the page bottom also.
+ \finishedtitlepagefalse
+ \vskip4pt \hrule height 4pt \vskip4pt}%
+ % No rule at page bottom unless we print one at the top with @title.
+ \finishedtitlepagetrue
+ %
+ % Now you can put text using @subtitle.
+ \def\subtitle{\parsearg\subtitlezzz}%
+ \def\subtitlezzz##1{{\subtitlefont \rightline{##1}}}%
+ %
+ % @author should come last, but may come many times.
+ \def\author{\parsearg\authorzzz}%
+ \def\authorzzz##1{\ifseenauthor\else\vskip 0pt plus 1filll\seenauthortrue\fi
+ {\authorfont \leftline{##1}}}%
+ %
+ % Most title ``pages'' are actually two pages long, with space
+ % at the top of the second. We don't want the ragged left on the second.
+ \let\oldpage = \page
+ \def\page{%
+ \iffinishedtitlepage\else
+ \finishtitlepage
+ \fi
+ \oldpage
+ \let\page = \oldpage
+ \hbox{}}%
+% \def\page{\oldpage \hbox{}}
+}
+
+\def\Etitlepage{%
+ \iffinishedtitlepage\else
+ \finishtitlepage
+ \fi
+ % It is important to do the page break before ending the group,
+ % because the headline and footline are only empty inside the group.
+ % If we use the new definition of \page, we always get a blank page
+ % after the title page, which we certainly don't want.
+ \oldpage
+ \endgroup
+ \HEADINGSon
+}
+
+\def\finishtitlepage{%
+ \vskip4pt \hrule height 2pt
+ \vskip\titlepagebottomglue
+ \finishedtitlepagetrue
+}
+
+%%% Set up page headings and footings.
+
+\let\thispage=\folio
+
+\newtoks \evenheadline % Token sequence for heading line of even pages
+\newtoks \oddheadline % Token sequence for heading line of odd pages
+\newtoks \evenfootline % Token sequence for footing line of even pages
+\newtoks \oddfootline % Token sequence for footing line of odd pages
+
+% Now make Tex use those variables
+\headline={{\textfonts\rm \ifodd\pageno \the\oddheadline
+ \else \the\evenheadline \fi}}
+\footline={{\textfonts\rm \ifodd\pageno \the\oddfootline
+ \else \the\evenfootline \fi}\HEADINGShook}
+\let\HEADINGShook=\relax
+
+% Commands to set those variables.
+% For example, this is what @headings on does
+% @evenheading @thistitle|@thispage|@thischapter
+% @oddheading @thischapter|@thispage|@thistitle
+% @evenfooting @thisfile||
+% @oddfooting ||@thisfile
+
+\def\evenheading{\parsearg\evenheadingxxx}
+\def\oddheading{\parsearg\oddheadingxxx}
+\def\everyheading{\parsearg\everyheadingxxx}
+
+\def\evenfooting{\parsearg\evenfootingxxx}
+\def\oddfooting{\parsearg\oddfootingxxx}
+\def\everyfooting{\parsearg\everyfootingxxx}
+
+{\catcode`\@=0 %
+
+\gdef\evenheadingxxx #1{\evenheadingyyy #1@|@|@|@|\finish}
+\gdef\evenheadingyyy #1@|#2@|#3@|#4\finish{%
+\global\evenheadline={\rlap{\centerline{#2}}\line{#1\hfil#3}}}
+
+\gdef\oddheadingxxx #1{\oddheadingyyy #1@|@|@|@|\finish}
+\gdef\oddheadingyyy #1@|#2@|#3@|#4\finish{%
+\global\oddheadline={\rlap{\centerline{#2}}\line{#1\hfil#3}}}
+
+\gdef\everyheadingxxx #1{\everyheadingyyy #1@|@|@|@|\finish}
+\gdef\everyheadingyyy #1@|#2@|#3@|#4\finish{%
+\global\evenheadline={\rlap{\centerline{#2}}\line{#1\hfil#3}}
+\global\oddheadline={\rlap{\centerline{#2}}\line{#1\hfil#3}}}
+
+\gdef\evenfootingxxx #1{\evenfootingyyy #1@|@|@|@|\finish}
+\gdef\evenfootingyyy #1@|#2@|#3@|#4\finish{%
+\global\evenfootline={\rlap{\centerline{#2}}\line{#1\hfil#3}}}
+
+\gdef\oddfootingxxx #1{\oddfootingyyy #1@|@|@|@|\finish}
+\gdef\oddfootingyyy #1@|#2@|#3@|#4\finish{%
+\global\oddfootline={\rlap{\centerline{#2}}\line{#1\hfil#3}}}
+
+\gdef\everyfootingxxx #1{\everyfootingyyy #1@|@|@|@|\finish}
+\gdef\everyfootingyyy #1@|#2@|#3@|#4\finish{%
+\global\evenfootline={\rlap{\centerline{#2}}\line{#1\hfil#3}}
+\global\oddfootline={\rlap{\centerline{#2}}\line{#1\hfil#3}}}
+%
+}% unbind the catcode of @.
+
+% @headings double turns headings on for double-sided printing.
+% @headings single turns headings on for single-sided printing.
+% @headings off turns them off.
+% @headings on same as @headings double, retained for compatibility.
+% @headings after turns on double-sided headings after this page.
+% @headings doubleafter turns on double-sided headings after this page.
+% @headings singleafter turns on single-sided headings after this page.
+% By default, they are off.
+
+\def\headings #1 {\csname HEADINGS#1\endcsname}
+
+\def\HEADINGSoff{
+\global\evenheadline={\hfil} \global\evenfootline={\hfil}
+\global\oddheadline={\hfil} \global\oddfootline={\hfil}}
+\HEADINGSoff
+% When we turn headings on, set the page number to 1.
+% For double-sided printing, put current file name in lower left corner,
+% chapter name on inside top of right hand pages, document
+% title on inside top of left hand pages, and page numbers on outside top
+% edge of all pages.
+\def\HEADINGSdouble{
+%\pagealignmacro
+\global\pageno=1
+\global\evenfootline={\hfil}
+\global\oddfootline={\hfil}
+\global\evenheadline={\line{\folio\hfil\thistitle}}
+\global\oddheadline={\line{\thischapter\hfil\folio}}
+}
+% For single-sided printing, chapter title goes across top left of page,
+% page number on top right.
+\def\HEADINGSsingle{
+%\pagealignmacro
+\global\pageno=1
+\global\evenfootline={\hfil}
+\global\oddfootline={\hfil}
+\global\evenheadline={\line{\thischapter\hfil\folio}}
+\global\oddheadline={\line{\thischapter\hfil\folio}}
+}
+\def\HEADINGSon{\HEADINGSdouble}
+
+\def\HEADINGSafter{\let\HEADINGShook=\HEADINGSdoublex}
+\let\HEADINGSdoubleafter=\HEADINGSafter
+\def\HEADINGSdoublex{%
+\global\evenfootline={\hfil}
+\global\oddfootline={\hfil}
+\global\evenheadline={\line{\folio\hfil\thistitle}}
+\global\oddheadline={\line{\thischapter\hfil\folio}}
+}
+
+\def\HEADINGSsingleafter{\let\HEADINGShook=\HEADINGSsinglex}
+\def\HEADINGSsinglex{%
+\global\evenfootline={\hfil}
+\global\oddfootline={\hfil}
+\global\evenheadline={\line{\thischapter\hfil\folio}}
+\global\oddheadline={\line{\thischapter\hfil\folio}}
+}
+
+% Subroutines used in generating headings
+% Produces Day Month Year style of output.
+\def\today{\number\day\space
+\ifcase\month\or
+January\or February\or March\or April\or May\or June\or
+July\or August\or September\or October\or November\or December\fi
+\space\number\year}
+
+% Use this if you want the Month Day, Year style of output.
+%\def\today{\ifcase\month\or
+%January\or February\or March\or April\or May\or June\or
+%July\or August\or September\or October\or November\or December\fi
+%\space\number\day, \number\year}
+
+% @settitle line... specifies the title of the document, for headings
+% It generates no output of its own
+
+\def\thistitle{No Title}
+\def\settitle{\parsearg\settitlezzz}
+\def\settitlezzz #1{\gdef\thistitle{#1}}
+
+\message{tables,}
+
+% @tabs -- simple alignment
+
+% These don't work. For one thing, \+ is defined as outer.
+% So these macros cannot even be defined.
+
+%\def\tabs{\parsearg\tabszzz}
+%\def\tabszzz #1{\settabs\+#1\cr}
+%\def\tabline{\parsearg\tablinezzz}
+%\def\tablinezzz #1{\+#1\cr}
+%\def\&{&}
+
+% Tables -- @table, @ftable, @item(x), @kitem(x), @xitem(x).
+
+% default indentation of table text
+\newdimen\tableindent \tableindent=.8in
+% default indentation of @itemize and @enumerate text
+\newdimen\itemindent \itemindent=.3in
+% margin between end of table item and start of table text.
+\newdimen\itemmargin \itemmargin=.1in
+
+% used internally for \itemindent minus \itemmargin
+\newdimen\itemmax
+
+% Note @table and @ftable define @item, @itemx, etc., with these defs.
+% They also define \itemindex
+% to index the item name in whatever manner is desired (perhaps none).
+
+\def\internalBitem{\smallbreak \parsearg\itemzzz}
+\def\internalBitemx{\par \parsearg\itemzzz}
+
+\def\internalBxitem "#1"{\def\xitemsubtopix{#1} \smallbreak \parsearg\xitemzzz}
+\def\internalBxitemx "#1"{\def\xitemsubtopix{#1} \par \parsearg\xitemzzz}
+
+\def\internalBkitem{\smallbreak \parsearg\kitemzzz}
+\def\internalBkitemx{\par \parsearg\kitemzzz}
+
+\def\kitemzzz #1{\dosubind {kw}{\code{#1}}{for {\bf \lastfunction}}%
+ \itemzzz {#1}}
+
+\def\xitemzzz #1{\dosubind {kw}{\code{#1}}{for {\bf \xitemsubtopic}}%
+ \itemzzz {#1}}
+
+\def\itemzzz #1{\begingroup %
+ \advance\hsize by -\rightskip
+ \advance\hsize by -\tableindent
+ \setbox0=\hbox{\itemfont{#1}}%
+ \itemindex{#1}%
+ \nobreak % This prevents a break before @itemx.
+ %
+ % Be sure we are not still in the middle of a paragraph.
+ \parskip=0in
+ \par
+ %
+ % If the item text does not fit in the space we have, put it on a line
+ % by itself, and do not allow a page break either before or after that
+ % line. We do not start a paragraph here because then if the next
+ % command is, e.g., @kindex, the whatsit would get put into the
+ % horizontal list on a line by itself, resulting in extra blank space.
+ \ifdim \wd0>\itemmax
+ \setbox0=\hbox{\hskip \leftskip \hskip -\tableindent \unhbox0}\box0
+ \nobreak
+ \else
+ % The item text fits into the space. Start a paragraph, so that the
+ % following text (if any) will end up on the same line. Since that
+ % text will be indented by \tableindent, we make the item text be in
+ % a zero-width box.
+ \noindent
+ \rlap{\hskip -\tableindent\box0}%
+ \fi
+ \endgroup
+}
+
+\def\item{\errmessage{@item while not in a table}}
+\def\itemx{\errmessage{@itemx while not in a table}}
+\def\kitem{\errmessage{@kitem while not in a table}}
+\def\kitemx{\errmessage{@kitemx while not in a table}}
+\def\xitem{\errmessage{@xitem while not in a table}}
+\def\xitemx{\errmessage{@xitemx while not in a table}}
+
+%% Contains a kludge to get @end[description] to work
+\def\description{\tablez{\dontindex}{1}{}{}{}{}}
+
+\def\table{\begingroup\inENV\obeylines\obeyspaces\tablex}
+{\obeylines\obeyspaces%
+\gdef\tablex #1^^M{%
+\tabley\dontindex#1 \endtabley}}
+
+\def\ftable{\begingroup\inENV\obeylines\obeyspaces\ftablex}
+{\obeylines\obeyspaces%
+\gdef\ftablex #1^^M{%
+\tabley\fnitemindex#1 \endtabley
+\def\Eftable{\endgraf\endgroup\afterenvbreak}%
+\let\Etable=\relax}}
+
+\def\dontindex #1{}
+\def\fnitemindex #1{\doind {fn}{\code{#1}}}%
+
+{\obeyspaces %
+\gdef\tabley#1#2 #3 #4 #5 #6 #7\endtabley{\endgroup%
+\tablez{#1}{#2}{#3}{#4}{#5}{#6}}}
+
+\def\tablez #1#2#3#4#5#6{%
+\aboveenvbreak %
+\begingroup %
+\def\Edescription{\Etable}% Neccessary kludge.
+\let\itemindex=#1%
+\ifnum 0#3>0 \advance \leftskip by #3\mil \fi %
+\ifnum 0#4>0 \tableindent=#4\mil \fi %
+\ifnum 0#5>0 \advance \rightskip by #5\mil \fi %
+\def\itemfont{#2}%
+\itemmax=\tableindent %
+\advance \itemmax by -\itemmargin %
+\advance \leftskip by \tableindent %
+\parindent = 0pt
+\parskip = \smallskipamount
+\ifdim \parskip=0pt \parskip=2pt \fi%
+\def\Etable{\endgraf\endgroup\afterenvbreak}%
+\let\item = \internalBitem %
+\let\itemx = \internalBitemx %
+\let\kitem = \internalBkitem %
+\let\kitemx = \internalBkitemx %
+\let\xitem = \internalBxitem %
+\let\xitemx = \internalBxitemx %
+}
+
+% This is the counter used by @enumerate, which is really @itemize
+
+\newcount \itemno
+
+\def\itemize{\parsearg\itemizezzz}
+
+\def\itemizezzz #1{%
+ \begingroup % ended by the @end itemsize
+ \itemizey {#1}{\Eitemize}
+}
+
+\def\itemizey #1#2{%
+\aboveenvbreak %
+\itemmax=\itemindent %
+\advance \itemmax by -\itemmargin %
+\advance \leftskip by \itemindent %
+\parindent = 0pt %
+\parskip = \smallskipamount %
+\ifdim \parskip=0pt \parskip=2pt \fi%
+\def#2{\endgraf\endgroup\afterenvbreak}%
+\def\itemcontents{#1}%
+\let\item=\itemizeitem}
+
+\def\bullet{$\ptexbullet$}
+\def\minus{$-$}
+
+% Set sfcode to normal for the chars that usually have another value.
+% These are `.?!:;,'
+\def\frenchspacing{\sfcode46=1000 \sfcode63=1000 \sfcode33=1000
+ \sfcode58=1000 \sfcode59=1000 \sfcode44=1000 }
+
+% \splitoff TOKENS\endmark defines \first to be the first token in
+% TOKENS, and \rest to be the remainder.
+%
+\def\splitoff#1#2\endmark{\def\first{#1}\def\rest{#2}}%
+
+% Allow an optional argument of an uppercase letter, lowercase letter,
+% or number, to specify the first label in the enumerated list. No
+% argument is the same as `1'.
+%
+\def\enumerate{\parsearg\enumeratezzz}
+\def\enumeratezzz #1{\enumeratey #1 \endenumeratey}
+\def\enumeratey #1 #2\endenumeratey{%
+ \begingroup % ended by the @end enumerate
+ %
+ % If we were given no argument, pretend we were given `1'.
+ \def\thearg{#1}%
+ \ifx\thearg\empty \def\thearg{1}\fi
+ %
+ % Detect if the argument is a single token. If so, it might be a
+ % letter. Otherwise, the only valid thing it can be is a number.
+ % (We will always have one token, because of the test we just made.
+ % This is a good thing, since \splitoff doesn't work given nothing at
+ % all -- the first parameter is undelimited.)
+ \expandafter\splitoff\thearg\endmark
+ \ifx\rest\empty
+ % Only one token in the argument. It could still be anything.
+ % A ``lowercase letter'' is one whose \lccode is nonzero.
+ % An ``uppercase letter'' is one whose \lccode is both nonzero, and
+ % not equal to itself.
+ % Otherwise, we assume it's a number.
+ %
+ % We need the \relax at the end of the \ifnum lines to stop TeX from
+ % continuing to look for a <number>.
+ %
+ \ifnum\lccode\expandafter`\thearg=0\relax
+ \numericenumerate % a number (we hope)
+ \else
+ % It's a letter.
+ \ifnum\lccode\expandafter`\thearg=\expandafter`\thearg\relax
+ \lowercaseenumerate % lowercase letter
+ \else
+ \uppercaseenumerate % uppercase letter
+ \fi
+ \fi
+ \else
+ % Multiple tokens in the argument. We hope it's a number.
+ \numericenumerate
+ \fi
+}
+
+% An @enumerate whose labels are integers. The starting integer is
+% given in \thearg.
+%
+\def\numericenumerate{%
+ \itemno = \thearg
+ \startenumeration{\the\itemno}%
+}
+
+% The starting (lowercase) letter is in \thearg.
+\def\lowercaseenumerate{%
+ \itemno = \expandafter`\thearg
+ \startenumeration{%
+ % Be sure we're not beyond the end of the alphabet.
+ \ifnum\itemno=0
+ \errmessage{No more lowercase letters in @enumerate; get a bigger
+ alphabet}%
+ \fi
+ \char\lccode\itemno
+ }%
+}
+
+% The starting (uppercase) letter is in \thearg.
+\def\uppercaseenumerate{%
+ \itemno = \expandafter`\thearg
+ \startenumeration{%
+ % Be sure we're not beyond the end of the alphabet.
+ \ifnum\itemno=0
+ \errmessage{No more uppercase letters in @enumerate; get a bigger
+ alphabet}
+ \fi
+ \char\uccode\itemno
+ }%
+}
+
+% Call itemizey, adding a period to the first argument and supplying the
+% common last two arguments. Also subtract one from the initial value in
+% \itemno, since @item increments \itemno.
+%
+\def\startenumeration#1{%
+ \advance\itemno by -1
+ \itemizey{#1.}\Eenumerate\flushcr
+}
+
+% @alphaenumerate and @capsenumerate are abbreviations for giving an arg
+% to @enumerate.
+%
+\def\alphaenumerate{\enumerate{a}}
+\def\capsenumerate{\enumerate{A}}
+\def\Ealphaenumerate{\Eenumerate}
+\def\Ecapsenumerate{\Eenumerate}
+
+% Definition of @item while inside @itemize.
+
+\def\itemizeitem{%
+\advance\itemno by 1
+{\let\par=\endgraf \smallbreak}%
+\ifhmode \errmessage{\in hmode at itemizeitem}\fi
+{\parskip=0in \hskip 0pt
+\hbox to 0pt{\hss \itemcontents\hskip \itemmargin}%
+\vadjust{\penalty 1200}}%
+\flushcr}
+
+\message{indexing,}
+% Index generation facilities
+
+% Define \newwrite to be identical to plain tex's \newwrite
+% except not \outer, so it can be used within \newindex.
+{\catcode`\@=11
+\gdef\newwrite{\alloc@7\write\chardef\sixt@@n}}
+
+% \newindex {foo} defines an index named foo.
+% It automatically defines \fooindex such that
+% \fooindex ...rest of line... puts an entry in the index foo.
+% It also defines \fooindfile to be the number of the output channel for
+% the file that accumulates this index. The file's extension is foo.
+% The name of an index should be no more than 2 characters long
+% for the sake of vms.
+
+\def\newindex #1{
+\expandafter\newwrite \csname#1indfile\endcsname% Define number for output file
+\openout \csname#1indfile\endcsname \jobname.#1 % Open the file
+\expandafter\xdef\csname#1index\endcsname{% % Define \xxxindex
+\noexpand\doindex {#1}}
+}
+
+% @defindex foo == \newindex{foo}
+
+\def\defindex{\parsearg\newindex}
+
+% Define @defcodeindex, like @defindex except put all entries in @code.
+
+\def\newcodeindex #1{
+\expandafter\newwrite \csname#1indfile\endcsname% Define number for output file
+\openout \csname#1indfile\endcsname \jobname.#1 % Open the file
+\expandafter\xdef\csname#1index\endcsname{% % Define \xxxindex
+\noexpand\docodeindex {#1}}
+}
+
+\def\defcodeindex{\parsearg\newcodeindex}
+
+% @synindex foo bar makes index foo feed into index bar.
+% Do this instead of @defindex foo if you don't want it as a separate index.
+\def\synindex #1 #2 {%
+\expandafter\let\expandafter\synindexfoo\expandafter=\csname#2indfile\endcsname
+\expandafter\let\csname#1indfile\endcsname=\synindexfoo
+\expandafter\xdef\csname#1index\endcsname{% % Define \xxxindex
+\noexpand\doindex {#2}}%
+}
+
+% @syncodeindex foo bar similar, but put all entries made for index foo
+% inside @code.
+\def\syncodeindex #1 #2 {%
+\expandafter\let\expandafter\synindexfoo\expandafter=\csname#2indfile\endcsname
+\expandafter\let\csname#1indfile\endcsname=\synindexfoo
+\expandafter\xdef\csname#1index\endcsname{% % Define \xxxindex
+\noexpand\docodeindex {#2}}%
+}
+
+% Define \doindex, the driver for all \fooindex macros.
+% Argument #1 is generated by the calling \fooindex macro,
+% and it is "foo", the name of the index.
+
+% \doindex just uses \parsearg; it calls \doind for the actual work.
+% This is because \doind is more useful to call from other macros.
+
+% There is also \dosubind {index}{topic}{subtopic}
+% which makes an entry in a two-level index such as the operation index.
+
+\def\doindex#1{\edef\indexname{#1}\parsearg\singleindexer}
+\def\singleindexer #1{\doind{\indexname}{#1}}
+
+% like the previous two, but they put @code around the argument.
+\def\docodeindex#1{\edef\indexname{#1}\parsearg\singlecodeindexer}
+\def\singlecodeindexer #1{\doind{\indexname}{\code{#1}}}
+
+\def\indexdummies{%
+\def\_{{\realbackslash _}}%
+\def\w{\realbackslash w }%
+\def\bf{\realbackslash bf }%
+\def\rm{\realbackslash rm }%
+\def\sl{\realbackslash sl }%
+\def\sf{\realbackslash sf}%
+\def\tt{\realbackslash tt}%
+\def\gtr{\realbackslash gtr}%
+\def\less{\realbackslash less}%
+\def\hat{\realbackslash hat}%
+\def\char{\realbackslash char}%
+\def\TeX{\realbackslash TeX}%
+\def\dots{\realbackslash dots }%
+\def\copyright{\realbackslash copyright }%
+\def\tclose##1{\realbackslash tclose {##1}}%
+\def\code##1{\realbackslash code {##1}}%
+\def\samp##1{\realbackslash samp {##1}}%
+\def\t##1{\realbackslash r {##1}}%
+\def\r##1{\realbackslash r {##1}}%
+\def\i##1{\realbackslash i {##1}}%
+\def\b##1{\realbackslash b {##1}}%
+\def\cite##1{\realbackslash cite {##1}}%
+\def\key##1{\realbackslash key {##1}}%
+\def\file##1{\realbackslash file {##1}}%
+\def\var##1{\realbackslash var {##1}}%
+\def\kbd##1{\realbackslash kbd {##1}}%
+}
+
+% \indexnofonts no-ops all font-change commands.
+% This is used when outputting the strings to sort the index by.
+\def\indexdummyfont#1{#1}
+\def\indexdummytex{TeX}
+\def\indexdummydots{...}
+
+\def\indexnofonts{%
+\let\w=\indexdummyfont
+\let\t=\indexdummyfont
+\let\r=\indexdummyfont
+\let\i=\indexdummyfont
+\let\b=\indexdummyfont
+\let\emph=\indexdummyfont
+\let\strong=\indexdummyfont
+\let\cite=\indexdummyfont
+\let\sc=\indexdummyfont
+%Don't no-op \tt, since it isn't a user-level command
+% and is used in the definitions of the active chars like <, >, |...
+%\let\tt=\indexdummyfont
+\let\tclose=\indexdummyfont
+\let\code=\indexdummyfont
+\let\file=\indexdummyfont
+\let\samp=\indexdummyfont
+\let\kbd=\indexdummyfont
+\let\key=\indexdummyfont
+\let\var=\indexdummyfont
+\let\TeX=\indexdummytex
+\let\dots=\indexdummydots
+}
+
+% To define \realbackslash, we must make \ not be an escape.
+% We must first make another character (@) an escape
+% so we do not become unable to do a definition.
+
+{\catcode`\@=0 \catcode`\\=\other
+@gdef@realbackslash{\}}
+
+\let\indexbackslash=0 %overridden during \printindex.
+
+\def\doind #1#2{%
+{\count10=\lastpenalty %
+{\indexdummies % Must do this here, since \bf, etc expand at this stage
+\escapechar=`\\%
+{\let\folio=0% Expand all macros now EXCEPT \folio
+\def\rawbackslashxx{\indexbackslash}% \indexbackslash isn't defined now
+% so it will be output as is; and it will print as backslash in the indx.
+%
+% Now process the index-string once, with all font commands turned off,
+% to get the string to sort the index by.
+{\indexnofonts
+\xdef\temp1{#2}%
+}%
+% Now produce the complete index entry. We process the index-string again,
+% this time with font commands expanded, to get what to print in the index.
+\edef\temp{%
+\write \csname#1indfile\endcsname{%
+\realbackslash entry {\temp1}{\folio}{#2}}}%
+\temp }%
+}\penalty\count10}}
+
+\def\dosubind #1#2#3{%
+{\count10=\lastpenalty %
+{\indexdummies % Must do this here, since \bf, etc expand at this stage
+\escapechar=`\\%
+{\let\folio=0%
+\def\rawbackslashxx{\indexbackslash}%
+%
+% Now process the index-string once, with all font commands turned off,
+% to get the string to sort the index by.
+{\indexnofonts
+\xdef\temp1{#2 #3}%
+}%
+% Now produce the complete index entry. We process the index-string again,
+% this time with font commands expanded, to get what to print in the index.
+\edef\temp{%
+\write \csname#1indfile\endcsname{%
+\realbackslash entry {\temp1}{\folio}{#2}{#3}}}%
+\temp }%
+}\penalty\count10}}
+
+% The index entry written in the file actually looks like
+% \entry {sortstring}{page}{topic}
+% or
+% \entry {sortstring}{page}{topic}{subtopic}
+% The texindex program reads in these files and writes files
+% containing these kinds of lines:
+% \initial {c}
+% before the first topic whose initial is c
+% \entry {topic}{pagelist}
+% for a topic that is used without subtopics
+% \primary {topic}
+% for the beginning of a topic that is used with subtopics
+% \secondary {subtopic}{pagelist}
+% for each subtopic.
+
+% Define the user-accessible indexing commands
+% @findex, @vindex, @kindex, @cindex.
+
+\def\findex {\fnindex}
+\def\kindex {\kyindex}
+\def\cindex {\cpindex}
+\def\vindex {\vrindex}
+\def\tindex {\tpindex}
+\def\pindex {\pgindex}
+
+\def\cindexsub {\begingroup\obeylines\cindexsub}
+{\obeylines %
+\gdef\cindexsub "#1" #2^^M{\endgroup %
+\dosubind{cp}{#2}{#1}}}
+
+% Define the macros used in formatting output of the sorted index material.
+
+% This is what you call to cause a particular index to get printed.
+% Write
+% @unnumbered Function Index
+% @printindex fn
+
+\def\printindex{\parsearg\doprintindex}
+
+\def\doprintindex#1{%
+ \tex
+ \dobreak \chapheadingskip {10000}
+ \catcode`\%=\other\catcode`\&=\other\catcode`\#=\other
+ \catcode`\$=\other\catcode`\_=\other
+ \catcode`\~=\other
+ %
+ % The following don't help, since the chars were translated
+ % when the raw index was written, and their fonts were discarded
+ % due to \indexnofonts.
+ %\catcode`\"=\active
+ %\catcode`\^=\active
+ %\catcode`\_=\active
+ %\catcode`\|=\active
+ %\catcode`\<=\active
+ %\catcode`\>=\active
+ % %
+ \def\indexbackslash{\rawbackslashxx}
+ \indexfonts\rm \tolerance=9500 \advance\baselineskip -1pt
+ \begindoublecolumns
+ %
+ % See if the index file exists and is nonempty.
+ \openin 1 \jobname.#1s
+ \ifeof 1
+ % \enddoublecolumns gets confused if there is no text in the index,
+ % and it loses the chapter title and the aux file entries for the
+ % index. The easiest way to prevent this problem is to make sure
+ % there is some text.
+ (Index is nonexistent)
+ \else
+ %
+ % If the index file exists but is empty, then \openin leaves \ifeof
+ % false. We have to make TeX try to read something from the file, so
+ % it can discover if there is anything in it.
+ \read 1 to \temp
+ \ifeof 1
+ (Index is empty)
+ \else
+ \input \jobname.#1s
+ \fi
+ \fi
+ \closein 1
+ \enddoublecolumns
+ \Etex
+}
+
+% These macros are used by the sorted index file itself.
+% Change them to control the appearance of the index.
+
+% Same as \bigskipamount except no shrink.
+% \balancecolumns gets confused if there is any shrink.
+\newskip\initialskipamount \initialskipamount 12pt plus4pt
+
+\def\initial #1{%
+{\let\tentt=\sectt \let\tt=\sectt \let\sf=\sectt
+\ifdim\lastskip<\initialskipamount
+\removelastskip \penalty-200 \vskip \initialskipamount\fi
+\line{\secbf#1\hfill}\kern 2pt\penalty10000}}
+
+\def\entry #1#2{
+{\parfillskip=0in \parskip=0in \parindent=0in
+\hangindent=1in \hangafter=1%
+\noindent\hbox{#1}\indexdotfill #2\par
+}}
+
+% Like \dotfill except takes at least 1 em.
+\def\indexdotfill{\cleaders
+ \hbox{$\mathsurround=0pt \mkern1.5mu . \mkern1.5mu$}\hskip 1em plus 1fill}
+
+\def\primary #1{\line{#1\hfil}}
+
+\newskip\secondaryindent \secondaryindent=0.5cm
+
+\def\secondary #1#2{
+{\parfillskip=0in \parskip=0in
+\hangindent =1in \hangafter=1
+\noindent\hskip\secondaryindent\hbox{#1}\indexdotfill #2\par
+}}
+
+%% Define two-column mode, which is used in indexes.
+%% Adapted from the TeXBook, page 416
+\catcode `\@=11
+
+\newbox\partialpage
+
+\newdimen\doublecolumnhsize \doublecolumnhsize = 3.11in
+\newdimen\doublecolumnvsize \doublecolumnvsize = 19.1in
+\newdimen\availdimen@
+
+\def\begindoublecolumns{\begingroup
+ \output={\global\setbox\partialpage=
+ \vbox{\unvbox255\kern -\topskip \kern \baselineskip}}\eject
+ \output={\doublecolumnout}%
+ \hsize=\doublecolumnhsize \vsize=\doublecolumnvsize}
+\def\enddoublecolumns{\output={\balancecolumns}\eject
+ \endgroup \pagegoal=\vsize}
+
+\def\doublecolumnout{\splittopskip=\topskip \splitmaxdepth=\maxdepth
+ \dimen@=\pageheight \advance\dimen@ by-\ht\partialpage
+ \setbox0=\vsplit255 to\dimen@ \setbox2=\vsplit255 to\dimen@
+ \onepageout\pagesofar \unvbox255 \penalty\outputpenalty}
+\def\pagesofar{\unvbox\partialpage %
+ \hsize=\doublecolumnhsize % have to restore this since output routine
+% changes it to set cropmarks (P. A. MacKay, 12 Nov. 1986)
+ \wd0=\hsize \wd2=\hsize \hbox to\pagewidth{\box0\hfil\box2}}
+\def\balancecolumns{%
+% Unset the glue.
+ \setbox255=\vbox{\unvbox255}
+ \dimen@=\ht255
+ \advance\dimen@ by\topskip \advance\dimen@ by-\baselineskip
+ \divide\dimen@ by2
+ \availdimen@=\pageheight \advance\availdimen@ by-\ht\partialpage
+% If the remaining data is too big for one page,
+% output one page normally, then work with what remains.
+ \ifdim \dimen@>\availdimen@
+ {
+ \splittopskip=\topskip \splitmaxdepth=\maxdepth
+ \dimen@=\pageheight \advance\dimen@ by-\ht\partialpage
+ \setbox0=\vsplit255 to\dimen@ \setbox2=\vsplit255 to\dimen@
+ \onepageout\pagesofar
+ }
+% Recompute size of what remains, in case we just output some of it.
+ \dimen@=\ht255
+ \advance\dimen@ by\topskip \advance\dimen@ by-\baselineskip
+ \divide\dimen@ by2
+ \fi
+ \setbox0=\vbox{\unvbox255}
+ \splittopskip=\topskip
+ {\vbadness=10000 \loop \global\setbox3=\copy0
+ \global\setbox1=\vsplit3 to\dimen@
+ \ifdim\ht3>\dimen@ \global\advance\dimen@ by1pt \repeat}
+ \setbox0=\vbox to\dimen@{\unvbox1} \setbox2=\vbox to\dimen@{\unvbox3}
+ \pagesofar}
+
+\catcode `\@=\other
+\message{sectioning,}
+% Define chapters, sections, etc.
+
+\newcount \chapno
+\newcount \secno \secno=0
+\newcount \subsecno \subsecno=0
+\newcount \subsubsecno \subsubsecno=0
+
+% This counter is funny since it counts through charcodes of letters A, B, ...
+\newcount \appendixno \appendixno = `\@
+\def\appendixletter{\char\the\appendixno}
+
+\newwrite \contentsfile
+% This is called from \setfilename.
+\def\opencontents{\openout \contentsfile = \jobname.toc}
+
+% Each @chapter defines this as the name of the chapter.
+% page headings and footings can use it. @section does likewise
+
+\def\thischapter{} \def\thissection{}
+\def\seccheck#1{\if \pageno<0 %
+\errmessage{@#1 not allowed after generating table of contents}\fi
+%
+}
+
+\def\chapternofonts{%
+\let\rawbackslash=\relax%
+\let\frenchspacing=\relax%
+\def\TeX{\realbackslash TeX}
+\def\dots{\realbackslash dots}
+\def\copyright{\realbackslash copyright}
+\def\tt{\realbackslash tt}
+\def\bf{\realbackslash bf }
+\def\w{\realbackslash w}
+\def\less{\realbackslash less}
+\def\gtr{\realbackslash gtr}
+\def\hat{\realbackslash hat}
+\def\char{\realbackslash char}
+\def\tclose##1{\realbackslash tclose {##1}}
+\def\code##1{\realbackslash code {##1}}
+\def\samp##1{\realbackslash samp {##1}}
+\def\r##1{\realbackslash r {##1}}
+\def\b##1{\realbackslash b {##1}}
+\def\key##1{\realbackslash key {##1}}
+\def\file##1{\realbackslash file {##1}}
+\def\kbd##1{\realbackslash kbd {##1}}
+% These are redefined because @smartitalic wouldn't work inside xdef.
+\def\i##1{\realbackslash i {##1}}
+\def\cite##1{\realbackslash cite {##1}}
+\def\var##1{\realbackslash var {##1}}
+\def\emph##1{\realbackslash emph {##1}}
+\def\dfn##1{\realbackslash dfn {##1}}
+}
+
+\def\thischaptername{No Chapter Title}
+\outer\def\chapter{\parsearg\chapterzzz}
+\def\chapterzzz #1{\seccheck{chapter}%
+\secno=0 \subsecno=0 \subsubsecno=0
+\global\advance \chapno by 1 \message{Chapter \the\chapno}%
+\chapmacro {#1}{\the\chapno}%
+\gdef\thissection{#1}%
+\gdef\thischaptername{#1}%
+% We don't substitute the actual chapter name into \thischapter
+% because we don't want its macros evaluated now.
+\xdef\thischapter{Chapter \the\chapno: \noexpand\thischaptername}%
+{\chapternofonts%
+\edef\temp{{\realbackslash chapentry {#1}{\the\chapno}{\noexpand\folio}}}%
+\escapechar=`\\%
+\write \contentsfile \temp %
+\donoderef %
+\global\let\section = \numberedsec
+\global\let\subsection = \numberedsubsec
+\global\let\subsubsection = \numberedsubsubsec
+}}
+
+\outer\def\appendix{\parsearg\appendixzzz}
+\def\appendixzzz #1{\seccheck{appendix}%
+\secno=0 \subsecno=0 \subsubsecno=0
+\global\advance \appendixno by 1 \message{Appendix \appendixletter}%
+\chapmacro {#1}{Appendix \appendixletter}%
+\gdef\thissection{#1}%
+\gdef\thischaptername{#1}%
+\xdef\thischapter{Appendix \appendixletter: \noexpand\thischaptername}%
+{\chapternofonts%
+\edef\temp{{\realbackslash chapentry
+ {#1}{Appendix \appendixletter}{\noexpand\folio}}}%
+\escapechar=`\\%
+\write \contentsfile \temp %
+\appendixnoderef %
+\global\let\section = \appendixsec
+\global\let\subsection = \appendixsubsec
+\global\let\subsubsection = \appendixsubsubsec
+}}
+
+\outer\def\top{\parsearg\unnumberedzzz}
+\outer\def\unnumbered{\parsearg\unnumberedzzz}
+\def\unnumberedzzz #1{\seccheck{unnumbered}%
+\secno=0 \subsecno=0 \subsubsecno=0 \message{(#1)}
+\unnumbchapmacro {#1}%
+\gdef\thischapter{#1}\gdef\thissection{#1}%
+{\chapternofonts%
+\edef\temp{{\realbackslash unnumbchapentry {#1}{\noexpand\folio}}}%
+\escapechar=`\\%
+\write \contentsfile \temp %
+\unnumbnoderef %
+\global\let\section = \unnumberedsec
+\global\let\subsection = \unnumberedsubsec
+\global\let\subsubsection = \unnumberedsubsubsec
+}}
+
+\outer\def\numberedsec{\parsearg\seczzz}
+\def\seczzz #1{\seccheck{section}%
+\subsecno=0 \subsubsecno=0 \global\advance \secno by 1 %
+\gdef\thissection{#1}\secheading {#1}{\the\chapno}{\the\secno}%
+{\chapternofonts%
+\edef\temp{{\realbackslash secentry %
+{#1}{\the\chapno}{\the\secno}{\noexpand\folio}}}%
+\escapechar=`\\%
+\write \contentsfile \temp %
+\donoderef %
+\penalty 10000 %
+}}
+
+\outer\def\appendixsection{\parsearg\appendixsectionzzz}
+\outer\def\appendixsec{\parsearg\appendixsectionzzz}
+\def\appendixsectionzzz #1{\seccheck{appendixsection}%
+\subsecno=0 \subsubsecno=0 \global\advance \secno by 1 %
+\gdef\thissection{#1}\secheading {#1}{\appendixletter}{\the\secno}%
+{\chapternofonts%
+\edef\temp{{\realbackslash secentry %
+{#1}{\appendixletter}{\the\secno}{\noexpand\folio}}}%
+\escapechar=`\\%
+\write \contentsfile \temp %
+\appendixnoderef %
+\penalty 10000 %
+}}
+
+\outer\def\unnumberedsec{\parsearg\unnumberedseczzz}
+\def\unnumberedseczzz #1{\seccheck{unnumberedsec}%
+\plainsecheading {#1}\gdef\thissection{#1}%
+{\chapternofonts%
+\edef\temp{{\realbackslash unnumbsecentry{#1}{\noexpand\folio}}}%
+\escapechar=`\\%
+\write \contentsfile \temp %
+\unnumbnoderef %
+\penalty 10000 %
+}}
+
+\outer\def\numberedsubsec{\parsearg\numberedsubseczzz}
+\def\numberedsubseczzz #1{\seccheck{subsection}%
+\gdef\thissection{#1}\subsubsecno=0 \global\advance \subsecno by 1 %
+\subsecheading {#1}{\the\chapno}{\the\secno}{\the\subsecno}%
+{\chapternofonts%
+\edef\temp{{\realbackslash subsecentry %
+{#1}{\the\chapno}{\the\secno}{\the\subsecno}{\noexpand\folio}}}%
+\escapechar=`\\%
+\write \contentsfile \temp %
+\donoderef %
+\penalty 10000 %
+}}
+
+\outer\def\appendixsubsec{\parsearg\appendixsubseczzz}
+\def\appendixsubseczzz #1{\seccheck{appendixsubsec}%
+\gdef\thissection{#1}\subsubsecno=0 \global\advance \subsecno by 1 %
+\subsecheading {#1}{\appendixletter}{\the\secno}{\the\subsecno}%
+{\chapternofonts%
+\edef\temp{{\realbackslash subsecentry %
+{#1}{\appendixletter}{\the\secno}{\the\subsecno}{\noexpand\folio}}}%
+\escapechar=`\\%
+\write \contentsfile \temp %
+\appendixnoderef %
+\penalty 10000 %
+}}
+
+\outer\def\unnumberedsubsec{\parsearg\unnumberedsubseczzz}
+\def\unnumberedsubseczzz #1{\seccheck{unnumberedsubsec}%
+\plainsecheading {#1}\gdef\thissection{#1}%
+{\chapternofonts%
+\edef\temp{{\realbackslash unnumbsubsecentry{#1}{\noexpand\folio}}}%
+\escapechar=`\\%
+\write \contentsfile \temp %
+\unnumbnoderef %
+\penalty 10000 %
+}}
+
+\outer\def\numberedsubsubsec{\parsearg\numberedsubsubseczzz}
+\def\numberedsubsubseczzz #1{\seccheck{subsubsection}%
+\gdef\thissection{#1}\global\advance \subsubsecno by 1 %
+\subsubsecheading {#1}
+ {\the\chapno}{\the\secno}{\the\subsecno}{\the\subsubsecno}%
+{\chapternofonts%
+\edef\temp{{\realbackslash subsubsecentry %
+ {#1}
+ {\the\chapno}{\the\secno}{\the\subsecno}{\the\subsubsecno}
+ {\noexpand\folio}}}%
+\escapechar=`\\%
+\write \contentsfile \temp %
+\donoderef %
+\penalty 10000 %
+}}
+
+\outer\def\appendixsubsubsec{\parsearg\appendixsubsubseczzz}
+\def\appendixsubsubseczzz #1{\seccheck{appendixsubsubsec}%
+\gdef\thissection{#1}\global\advance \subsubsecno by 1 %
+\subsubsecheading {#1}
+ {\appendixletter}{\the\secno}{\the\subsecno}{\the\subsubsecno}%
+{\chapternofonts%
+\edef\temp{{\realbackslash subsubsecentry{#1}%
+ {\appendixletter}
+ {\the\secno}{\the\subsecno}{\the\subsubsecno}{\noexpand\folio}}}%
+\escapechar=`\\%
+\write \contentsfile \temp %
+\appendixnoderef %
+\penalty 10000 %
+}}
+
+\outer\def\unnumberedsubsubsec{\parsearg\unnumberedsubsubseczzz}
+\def\unnumberedsubsubseczzz #1{\seccheck{unnumberedsubsubsec}%
+\plainsecheading {#1}\gdef\thissection{#1}%
+{\chapternofonts%
+\edef\temp{{\realbackslash unnumbsubsubsecentry{#1}{\noexpand\folio}}}%
+\escapechar=`\\%
+\write \contentsfile \temp %
+\unnumbnoderef %
+\penalty 10000 %
+}}
+
+% These are variants which are not "outer", so they can appear in @ifinfo.
+% Actually, they should now be obsolete; ordinary section commands should work.
+\def\infotop{\parsearg\unnumberedzzz}
+\def\infounnumbered{\parsearg\unnumberedzzz}
+\def\infounnumberedsec{\parsearg\unnumberedseczzz}
+\def\infounnumberedsubsec{\parsearg\unnumberedsubseczzz}
+\def\infounnumberedsubsubsec{\parsearg\unnumberedsubsubseczzz}
+
+\def\infoappendix{\parsearg\appendixzzz}
+\def\infoappendixsec{\parsearg\appendixseczzz}
+\def\infoappendixsubsec{\parsearg\appendixsubseczzz}
+\def\infoappendixsubsubsec{\parsearg\appendixsubsubseczzz}
+
+\def\infochapter{\parsearg\chapterzzz}
+\def\infosection{\parsearg\sectionzzz}
+\def\infosubsection{\parsearg\subsectionzzz}
+\def\infosubsubsection{\parsearg\subsubsectionzzz}
+
+% These macros control what the section commands do, according
+% to what kind of chapter we are in (ordinary, appendix, or unnumbered).
+% Define them by default for a numbered chapter.
+\global\let\section = \numberedsec
+\global\let\subsection = \numberedsubsec
+\global\let\subsubsection = \numberedsubsubsec
+
+% Define @majorheading, @heading and @subheading
+
+% NOTE on use of \vbox for chapter headings, section headings, and
+% such:
+% 1) We use \vbox rather than the earlier \line to permit
+% overlong headings to fold.
+% 2) \hyphenpenalty is set to 10000 because hyphenation in a
+% heading is obnoxious; this forbids it.
+% 3) Likewise, headings look best if no \parindent is used, and
+% if justification is not attempted. Hence \raggedright.
+
+
+\def\majorheading{\parsearg\majorheadingzzz}
+\def\majorheadingzzz #1{%
+{\advance\chapheadingskip by 10pt \chapbreak }%
+{\chapfonts \vbox{\hyphenpenalty=10000\tolerance=5000
+ \parindent=0pt\raggedright
+ \rm #1\hfill}}\bigskip \par\penalty 200}
+
+\def\chapheading{\parsearg\chapheadingzzz}
+\def\chapheadingzzz #1{\chapbreak %
+{\chapfonts \vbox{\hyphenpenalty=10000\tolerance=5000
+ \parindent=0pt\raggedright
+ \rm #1\hfill}}\bigskip \par\penalty 200}
+
+\def\heading{\parsearg\secheadingi}
+
+\def\subheading{\parsearg\subsecheadingi}
+
+\def\subsubheading{\parsearg\subsubsecheadingi}
+
+% These macros generate a chapter, section, etc. heading only
+% (including whitespace, linebreaking, etc. around it),
+% given all the information in convenient, parsed form.
+
+%%% Args are the skip and penalty (usually negative)
+\def\dobreak#1#2{\par\ifdim\lastskip<#1\removelastskip\penalty#2\vskip#1\fi}
+
+\def\setchapterstyle #1 {\csname CHAPF#1\endcsname}
+
+%%% Define plain chapter starts, and page on/off switching for it
+% Parameter controlling skip before chapter headings (if needed)
+
+\newskip \chapheadingskip \chapheadingskip = 30pt plus 8pt minus 4pt
+
+\def\chapbreak{\dobreak \chapheadingskip {-4000}}
+\def\chappager{\par\vfill\supereject}
+\def\chapoddpage{\chappager \ifodd\pageno \else \hbox to 0pt{} \chappager\fi}
+
+\def\setchapternewpage #1 {\csname CHAPPAG#1\endcsname}
+
+\def\CHAPPAGoff{
+\global\let\pchapsepmacro=\chapbreak
+\global\let\pagealignmacro=\chappager}
+
+\def\CHAPPAGon{
+\global\let\pchapsepmacro=\chappager
+\global\let\pagealignmacro=\chappager
+\global\def\HEADINGSon{\HEADINGSsingle}}
+
+\def\CHAPPAGodd{
+\global\let\pchapsepmacro=\chapoddpage
+\global\let\pagealignmacro=\chapoddpage
+\global\def\HEADINGSon{\HEADINGSdouble}}
+
+\CHAPPAGon
+
+\def\CHAPFplain{
+\global\let\chapmacro=\chfplain
+\global\let\unnumbchapmacro=\unnchfplain}
+
+\def\chfplain #1#2{%
+ \pchapsepmacro
+ {%
+ \chapfonts \vbox{\hyphenpenalty=10000\tolerance=5000
+ \parindent=0pt\raggedright
+ \rm #2\enspace #1}%
+ }%
+ \bigskip
+ \penalty5000
+}
+
+\def\unnchfplain #1{%
+\pchapsepmacro %
+{\chapfonts \vbox{\hyphenpenalty=10000\tolerance=5000
+ \parindent=0pt\raggedright
+ \rm #1\hfill}}\bigskip \par\penalty 10000 %
+}
+\CHAPFplain % The default
+
+\def\unnchfopen #1{%
+\chapoddpage {\chapfonts \vbox{\hyphenpenalty=10000\tolerance=5000
+ \parindent=0pt\raggedright
+ \rm #1\hfill}}\bigskip \par\penalty 10000 %
+}
+
+\def\chfopen #1#2{\chapoddpage {\chapfonts
+\vbox to 3in{\vfil \hbox to\hsize{\hfil #2} \hbox to\hsize{\hfil #1} \vfil}}%
+\par\penalty 5000 %
+}
+
+\def\CHAPFopen{
+\global\let\chapmacro=\chfopen
+\global\let\unnumbchapmacro=\unnchfopen}
+
+% Parameter controlling skip before section headings.
+
+\newskip \subsecheadingskip \subsecheadingskip = 17pt plus 8pt minus 4pt
+\def\subsecheadingbreak{\dobreak \subsecheadingskip {-500}}
+
+\newskip \secheadingskip \secheadingskip = 21pt plus 8pt minus 4pt
+\def\secheadingbreak{\dobreak \secheadingskip {-1000}}
+
+% @paragraphindent is defined for the Info formatting commands only.
+\let\paragraphindent=\comment
+
+% Section fonts are the base font at magstep2, which produces
+% a size a bit more than 14 points in the default situation.
+
+\def\secheading #1#2#3{\secheadingi {#2.#3\enspace #1}}
+\def\plainsecheading #1{\secheadingi {#1}}
+\def\secheadingi #1{{\advance \secheadingskip by \parskip %
+\secheadingbreak}%
+{\secfonts \vbox{\hyphenpenalty=10000\tolerance=5000
+ \parindent=0pt\raggedright
+ \rm #1\hfill}}%
+\ifdim \parskip<10pt \kern 10pt\kern -\parskip\fi \penalty 10000 }
+
+
+% Subsection fonts are the base font at magstep1,
+% which produces a size of 12 points.
+
+\def\subsecheading #1#2#3#4{\subsecheadingi {#2.#3.#4\enspace #1}}
+\def\subsecheadingi #1{{\advance \subsecheadingskip by \parskip %
+\subsecheadingbreak}%
+{\subsecfonts \vbox{\hyphenpenalty=10000\tolerance=5000
+ \parindent=0pt\raggedright
+ \rm #1\hfill}}%
+\ifdim \parskip<10pt \kern 10pt\kern -\parskip\fi \penalty 10000 }
+
+\def\subsubsecfonts{\subsecfonts} % Maybe this should change:
+ % Perhaps make sssec fonts scaled
+ % magstep half
+\def\subsubsecheading #1#2#3#4#5{\subsubsecheadingi {#2.#3.#4.#5\enspace #1}}
+\def\subsubsecheadingi #1{{\advance \subsecheadingskip by \parskip %
+\subsecheadingbreak}%
+{\subsubsecfonts \vbox{\hyphenpenalty=10000\tolerance=5000
+ \parindent=0pt\raggedright
+ \rm #1\hfill}}%
+\ifdim \parskip<10pt \kern 10pt\kern -\parskip\fi \penalty 10000}
+
+
+\message{toc printing,}
+
+% Finish up the main text and prepare to read what we've written
+% to \contentsfile.
+
+\newskip\contentsrightmargin \contentsrightmargin=1in
+\def\startcontents#1{%
+ \ifnum \pageno>0
+ \pagealignmacro
+ \immediate\closeout \contentsfile
+ \pageno = -1 % Request roman numbered pages.
+ \fi
+ % Don't need to put `Contents' or `Short Contents' in the headline.
+ % It is abundantly clear what they are.
+ \unnumbchapmacro{#1}\def\thischapter{}%
+ \begingroup % Set up to handle contents files properly.
+ \catcode`\\=0 \catcode`\{=1 \catcode`\}=2 \catcode`\@=11
+ \raggedbottom % Worry more about breakpoints than the bottom.
+ \advance\hsize by -\contentsrightmargin % Don't use the full line length.
+}
+
+
+% Normal (long) toc.
+\outer\def\contents{%
+ \startcontents{Table of Contents}%
+ \input \jobname.toc
+ \endgroup
+ \vfill \eject
+}
+
+% And just the chapters.
+\outer\def\summarycontents{%
+ \startcontents{Short Contents}%
+ %
+ \let\chapentry = \shortchapentry
+ \let\unnumbchapentry = \shortunnumberedentry
+ % We want a true roman here for the page numbers.
+ \secfonts
+ \let\rm=\shortcontrm \let\bf=\shortcontbf \let\sl=\shortcontsl
+ \rm
+ \advance\baselineskip by 1pt % Open it up a little.
+ \def\secentry ##1##2##3##4{}
+ \def\unnumbsecentry ##1##2{}
+ \def\subsecentry ##1##2##3##4##5{}
+ \def\unnumbsubsecentry ##1##2{}
+ \def\subsubsecentry ##1##2##3##4##5##6{}
+ \def\unnumbsubsubsecentry ##1##2{}
+ \input \jobname.toc
+ \endgroup
+ \vfill \eject
+}
+\let\shortcontents = \summarycontents
+
+% These macros generate individual entries in the table of contents.
+% The first argument is the chapter or section name.
+% The last argument is the page number.
+% The arguments in between are the chapter number, section number, ...
+
+% Chapter-level things, for both the long and short contents.
+\def\chapentry#1#2#3{\dochapentry{#2\labelspace#1}{#3}}
+
+% See comments in \dochapentry re vbox and related settings
+\def\shortchapentry#1#2#3{%
+ \vbox{\hyphenpenalty=10000\tolerance=5000
+ \parindent=0pt\strut\raggedright
+ {#2\labelspace #1}\dotfill\doshortpageno{#3}}%
+}
+
+\def\unnumbchapentry#1#2{\dochapentry{#1}{#2}}
+\def\shortunnumberedentry#1#2{%
+ \vbox{\hyphenpenalty=10000\tolerance=5000
+ \parindent=0pt\strut\raggedright
+ #1\dotfill\doshortpageno{#2}}%
+}
+
+% Sections.
+\def\secentry#1#2#3#4{\dosecentry{#2.#3\labelspace#1}{#4}}
+\def\unnumbsecentry#1#2{\dosecentry{#1}{#2}}
+
+% Subsections.
+\def\subsecentry#1#2#3#4#5{\dosubsecentry{#2.#3.#4\labelspace#1}{#5}}
+\def\unnumbsubsecentry#1#2{\dosubsecentry{#1}{#2}}
+
+% And subsubsections.
+\def\subsubsecentry#1#2#3#4#5#6{%
+ \dosubsubsecentry{#2.#3.#4.#5\labelspace#1}{#6}}
+\def\unnumbsubsubsecentry#1#2{\dosubsubsecentry{#1}{#2}}
+
+
+% This parameter controls the indentation of the various levels.
+\newdimen\tocindent \tocindent = 3pc
+
+% Now for the actual typesetting. In all these, #1 is the text and #2 is the
+% page number.
+%
+% If the toc has to be broken over pages, we would want to be at chapters
+% if at all possible; hence the \penalty.
+\def\dochapentry#1#2{%
+ \penalty-300 \vskip\baselineskip
+ % This \vbox (and similar ones in dosecentry etc.) used to be a
+ % \line; changed to permit linebreaks for long headings. See
+ % comments above \majorheading. Here we also use \strut to
+ % keep the top end of the vbox from jamming up against the previous
+ % entry in the table of contents.
+ \vbox{\chapentryfonts
+ \hyphenpenalty=10000\tolerance=5000 % this line and next introduced
+ \parindent=0pt\strut\raggedright % with \line -> \vbox change
+ #1\dotfill
+ \dopageno{#2}}%
+ \nobreak\vskip .25\baselineskip
+}
+
+\def\dosecentry#1#2{%
+ \vbox{\secentryfonts \leftskip=\tocindent
+ \hyphenpenalty=10000\tolerance=5000
+ \parindent=0pt\strut\raggedright #1\dotfill
+ \dopageno{#2}}%
+}
+
+\def\dosubsecentry#1#2{%
+ \vbox{\subsecentryfonts \leftskip=2\tocindent
+ \hyphenpenalty=10000\tolerance=5000
+ \parindent=0pt\strut\raggedright #1\dotfill
+ \dopageno{#2}}%
+}
+
+\def\dosubsubsecentry#1#2{%
+ \vbox{\subsubsecentryfonts \leftskip=3\tocindent
+ \hyphenpenalty=10000\tolerance=5000
+ \parindent=0pt\strut\raggedright #1\dotfill
+ \dopageno{#2}}%
+}
+
+% Space between chapter (or whatever) number and the title.
+\def\labelspace{\hskip1em \relax}
+
+\def\dopageno#1{{\rm #1}}
+\def\doshortpageno#1{{\rm #1}}
+
+\def\chapentryfonts{\secfonts \rm}
+\def\secentryfonts{\textfonts}
+\let\subsecentryfonts = \textfonts
+\let\subsubsecentryfonts = \textfonts
+
+
+\message{environments,}
+
+% Since these characters are used in examples, it should be an even number of
+% \tt widths. Each \tt character is 1en, so two makes it 1em.
+% Furthermore, these definitions must come after we define our fonts.
+\newbox\dblarrowbox \newbox\longdblarrowbox
+\newbox\pushcharbox \newbox\bullbox
+\newbox\equivbox \newbox\errorbox
+
+\let\ptexequiv = \equiv
+
+%{\tentt
+%\global\setbox\dblarrowbox = \hbox to 1em{\hfil$\Rightarrow$\hfil}
+%\global\setbox\longdblarrowbox = \hbox to 1em{\hfil$\mapsto$\hfil}
+%\global\setbox\pushcharbox = \hbox to 1em{\hfil$\dashv$\hfil}
+%\global\setbox\equivbox = \hbox to 1em{\hfil$\ptexequiv$\hfil}
+% Adapted from the manmac format (p.420 of TeXbook)
+%\global\setbox\bullbox = \hbox to 1em{\kern.15em\vrule height .75ex width .85ex
+% depth .1ex\hfil}
+%}
+
+\def\point{$\star$}
+
+\def\result{\leavevmode\raise.15ex\hbox to 1em{\hfil$\Rightarrow$\hfil}}
+\def\expansion{\leavevmode\raise.1ex\hbox to 1em{\hfil$\mapsto$\hfil}}
+\def\print{\leavevmode\lower.1ex\hbox to 1em{\hfil$\dashv$\hfil}}
+
+\def\equiv{\leavevmode\lower.1ex\hbox to 1em{\hfil$\ptexequiv$\hfil}}
+
+% Adapted from the TeXbook's \boxit.
+{\tentt \global\dimen0 = 3em}% Width of the box.
+\dimen2 = .55pt % Thickness of rules
+% The text. (`r' is open on the right, `e' somewhat less so on the left.)
+\setbox0 = \hbox{\kern-.75pt \tensf error\kern-1.5pt}
+
+\global\setbox\errorbox=\hbox to \dimen0{\hfil
+ \hsize = \dimen0 \advance\hsize by -5.8pt % Space to left+right.
+ \advance\hsize by -2\dimen2 % Rules.
+ \vbox{
+ \hrule height\dimen2
+ \hbox{\vrule width\dimen2 \kern3pt % Space to left of text.
+ \vtop{\kern2.4pt \box0 \kern2.4pt}% Space above/below.
+ \kern3pt\vrule width\dimen2}% Space to right.
+ \hrule height\dimen2}
+ \hfil}
+
+% The @error{} command.
+\def\error{\leavevmode\lower.7ex\copy\errorbox}
+
+% @tex ... @end tex escapes into raw Tex temporarily.
+% One exception: @ is still an escape character, so that @end tex works.
+% But \@ or @@ will get a plain tex @ character.
+
+\def\tex{\begingroup
+\catcode `\\=0 \catcode `\{=1 \catcode `\}=2
+\catcode `\$=3 \catcode `\&=4 \catcode `\#=6
+\catcode `\^=7 \catcode `\_=8 \catcode `\~=13 \let~=\tie
+\catcode `\%=14
+\catcode 43=12
+\catcode`\"=12
+\catcode`\==12
+\catcode`\|=12
+\catcode`\<=12
+\catcode`\>=12
+\escapechar=`\\
+%
+\let\{=\ptexlbrace
+\let\}=\ptexrbrace
+\let\.=\ptexdot
+\let\*=\ptexstar
+\let\dots=\ptexdots
+\def\@{@}%
+\let\bullet=\ptexbullet
+\let\b=\ptexb \let\c=\ptexc \let\i=\ptexi \let\t=\ptext \let\l=\ptexl
+\let\L=\ptexL
+%
+\let\Etex=\endgroup}
+
+% Define @lisp ... @endlisp.
+% @lisp does a \begingroup so it can rebind things,
+% including the definition of @endlisp (which normally is erroneous).
+
+% Amount to narrow the margins by for @lisp.
+\newskip\lispnarrowing \lispnarrowing=0.4in
+
+% This is the definition that ^M gets inside @lisp
+% phr: changed space to \null, to avoid overfull hbox problems.
+{\obeyspaces%
+\gdef\lisppar{\null\endgraf}}
+
+% Cause \obeyspaces to make each Space cause a word-separation
+% rather than the default which is that it acts punctuation.
+% This is because space in tt font looks funny.
+{\obeyspaces %
+\gdef\sepspaces{\def {\ }}}
+
+\newskip\aboveenvskipamount \aboveenvskipamount= 0pt
+\def\aboveenvbreak{{\advance\aboveenvskipamount by \parskip
+\endgraf \ifdim\lastskip<\aboveenvskipamount
+\removelastskip \penalty-50 \vskip\aboveenvskipamount \fi}}
+
+\def\afterenvbreak{\endgraf \ifdim\lastskip<\aboveenvskipamount
+\removelastskip \penalty-50 \vskip\aboveenvskipamount \fi}
+
+% \nonarrowing is a flag. If "set", @lisp etc don't narrow margins.
+\let\nonarrowing=\relax
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+% \cartouche: draw rectangle w/rounded corners around argument
+\font\circle=lcircle10
+\newdimen\circthick
+\newdimen\cartouter\newdimen\cartinner
+\newskip\normbskip\newskip\normpskip\newskip\normlskip
+\circthick=\fontdimen8\circle
+%
+\def\ctl{{\circle\char'013\hskip -6pt}}% 6pt from pl file: 1/2charwidth
+\def\ctr{{\hskip 6pt\circle\char'010}}
+\def\cbl{{\circle\char'012\hskip -6pt}}
+\def\cbr{{\hskip 6pt\circle\char'011}}
+\def\carttop{\hbox to \cartouter{\hskip\lskip
+ \ctl\leaders\hrule height\circthick\hfil\ctr
+ \hskip\rskip}}
+\def\cartbot{\hbox to \cartouter{\hskip\lskip
+ \cbl\leaders\hrule height\circthick\hfil\cbr
+ \hskip\rskip}}
+%
+\newskip\lskip\newskip\rskip
+
+\long\def\cartouche{%
+\begingroup
+ \lskip=\leftskip \rskip=\rightskip
+ \leftskip=0pt\rightskip=0pt %we want these *outside*.
+ \cartinner=\hsize \advance\cartinner by-\lskip
+ \advance\cartinner by-\rskip
+ \cartouter=\hsize
+ \advance\cartouter by 18pt % allow for 3pt kerns on either
+% side, and for 6pt waste from
+% each corner char
+ \normbskip=\baselineskip \normpskip=\parskip \normlskip=\lineskip
+ % Flag to tell @lisp, etc., not to narrow margin.
+ \let\nonarrowing=\comment
+ \vbox\bgroup
+ \baselineskip=0pt\parskip=0pt\lineskip=0pt
+ \carttop
+ \hbox\bgroup
+ \hskip\lskip
+ \vrule\kern3pt
+ \vbox\bgroup
+ \hsize=\cartinner
+ \kern3pt
+ \begingroup
+ \baselineskip=\normbskip
+ \lineskip=\normlskip
+ \parskip=\normpskip
+ \vskip -\parskip
+\def\Ecartouche{%
+ \endgroup
+ \kern3pt
+ \egroup
+ \kern3pt\vrule
+ \hskip\rskip
+ \egroup
+ \cartbot
+ \egroup
+\endgroup
+}}
+
+\def\lisp{\aboveenvbreak
+\begingroup\inENV % This group ends at the end of the @lisp body
+\hfuzz=12truept % Don't be fussy
+% Make spaces be word-separators rather than space tokens.
+\sepspaces %
+% Single space lines
+\singlespace %
+% The following causes blank lines not to be ignored
+% by adding a space to the end of each line.
+\let\par=\lisppar
+\def\Elisp{\endgroup\afterenvbreak}%
+\parskip=0pt
+% @cartouche defines \nonarrowing to inhibit narrowing
+% at next level down.
+\ifx\nonarrowing\relax
+\advance \leftskip by \lispnarrowing
+\let\nonarrowing=\relax
+\fi
+\parindent=0pt
+\let\exdent=\internalexdent
+\obeyspaces \obeylines \tt \rawbackslash
+\def\next##1{}\next}
+
+
+\let\example=\lisp
+\def\Eexample{\Elisp}
+
+\let\smallexample=\lisp
+\def\Esmallexample{\Elisp}
+
+% Macro for 9 pt. examples, necessary to print with 5" lines.
+% From Pavel@xerox. This is not really used unless the
+% @smallbook command is given.
+
+\def\smalllispx{\aboveenvbreak\begingroup\inENV
+% This group ends at the end of the @lisp body
+\hfuzz=12truept % Don't be fussy
+% Make spaces be word-separators rather than space tokens.
+\sepspaces %
+% Single space lines
+\singlespace %
+% The following causes blank lines not to be ignored
+% by adding a space to the end of each line.
+\let\par=\lisppar
+\def\Esmalllisp{\endgroup\afterenvbreak}%
+\parskip=0pt
+% @cartouche defines \nonarrowing to inhibit narrowing
+% at next level down.
+\ifx\nonarrowing\relax
+\advance \leftskip by \lispnarrowing
+\let\nonarrowing=\relax
+\fi
+\parindent=0pt
+\let\exdent=\internalexdent
+\obeyspaces \obeylines \ninett \indexfonts \rawbackslash
+\def\next##1{}\next}
+
+% This is @display; same as @lisp except use roman font.
+
+\def\display{\begingroup\inENV %This group ends at the end of the @display body
+\aboveenvbreak
+% Make spaces be word-separators rather than space tokens.
+\sepspaces %
+% Single space lines
+\singlespace %
+% The following causes blank lines not to be ignored
+% by adding a space to the end of each line.
+\let\par=\lisppar
+\def\Edisplay{\endgroup\afterenvbreak}%
+\parskip=0pt
+% @cartouche defines \nonarrowing to inhibit narrowing
+% at next level down.
+\ifx\nonarrowing\relax
+\advance \leftskip by \lispnarrowing
+\let\nonarrowing=\relax
+\fi
+\parindent=0pt
+\let\exdent=\internalexdent
+\obeyspaces \obeylines
+\def\next##1{}\next}
+
+% This is @format; same as @lisp except use roman font and don't narrow margins
+
+\def\format{\begingroup\inENV %This group ends at the end of the @format body
+\aboveenvbreak
+% Make spaces be word-separators rather than space tokens.
+\sepspaces %
+\singlespace %
+% The following causes blank lines not to be ignored
+% by adding a space to the end of each line.
+\let\par=\lisppar
+\def\Eformat{\endgroup\afterenvbreak}
+\parskip=0pt \parindent=0pt
+\obeyspaces \obeylines
+\def\next##1{}\next}
+
+% @flushleft and @flushright
+
+\def\flushleft{%
+\begingroup\inENV %This group ends at the end of the @format body
+\aboveenvbreak
+% Make spaces be word-separators rather than space tokens.
+\sepspaces %
+% The following causes blank lines not to be ignored
+% by adding a space to the end of each line.
+% This also causes @ to work when the directive name
+% is terminated by end of line.
+\let\par=\lisppar
+\def\Eflushleft{\endgroup\afterenvbreak}%
+\parskip=0pt \parindent=0pt
+\obeyspaces \obeylines
+\def\next##1{}\next}
+
+\def\flushright{%
+\begingroup\inENV %This group ends at the end of the @format body
+\aboveenvbreak
+% Make spaces be word-separators rather than space tokens.
+\sepspaces %
+% The following causes blank lines not to be ignored
+% by adding a space to the end of each line.
+% This also causes @ to work when the directive name
+% is terminated by end of line.
+\let\par=\lisppar
+\def\Eflushright{\endgroup\afterenvbreak}%
+\parskip=0pt \parindent=0pt
+\advance \leftskip by 0pt plus 1fill
+\obeyspaces \obeylines
+\def\next##1{}\next}
+
+% @quotation - narrow the margins.
+
+\def\quotation{%
+\begingroup\inENV %This group ends at the end of the @quotation body
+{\parskip=0pt % because we will skip by \parskip too, later
+\aboveenvbreak}%
+\singlespace
+\parindent=0pt
+\def\Equotation{\par\endgroup\afterenvbreak}%
+% @cartouche defines \nonarrowing to inhibit narrowing
+% at next level down.
+\ifx\nonarrowing\relax
+\advance \leftskip by \lispnarrowing
+\advance \rightskip by \lispnarrowing
+\let\nonarrowing=\relax
+\fi}
+
+\message{defuns,}
+% Define formatter for defuns
+% First, allow user to change definition object font (\df) internally
+\def\setdeffont #1 {\csname DEF#1\endcsname}
+
+\newskip\defbodyindent \defbodyindent=.4in
+\newskip\defargsindent \defargsindent=50pt
+\newskip\deftypemargin \deftypemargin=12pt
+\newskip\deflastargmargin \deflastargmargin=18pt
+
+\newcount\parencount
+% define \functionparens, which makes ( and ) and & do special things.
+% \functionparens affects the group it is contained in.
+\def\activeparens{%
+\catcode`\(=\active \catcode`\)=\active \catcode`\&=\active
+\catcode`\[=\active \catcode`\]=\active}
+{\activeparens % Now, smart parens don't turn on until &foo (see \amprm)
+\gdef\functionparens{\boldbrax\let&=\amprm\parencount=0 }
+\gdef\boldbrax{\let(=\opnr\let)=\clnr\let[=\lbrb\let]=\rbrb}
+
+% Definitions of (, ) and & used in args for functions.
+% This is the definition of ( outside of all parentheses.
+\gdef\oprm#1 {{\rm\char`\(}#1 \bf \let(=\opnested %
+\global\advance\parencount by 1 }
+%
+% This is the definition of ( when already inside a level of parens.
+\gdef\opnested{\char`\(\global\advance\parencount by 1 }
+%
+\gdef\clrm{% Print a paren in roman if it is taking us back to depth of 0.
+% also in that case restore the outer-level definition of (.
+\ifnum \parencount=1 {\rm \char `\)}\sl \let(=\oprm \else \char `\) \fi
+\global\advance \parencount by -1 }
+% If we encounter &foo, then turn on ()-hacking afterwards
+\gdef\amprm#1 {{\rm\&#1}\let(=\oprm \let)=\clrm\ }
+%
+\gdef\normalparens{\boldbrax\let&=\ampnr}
+} % End of definition inside \activeparens
+%% These parens (in \boldbrax) actually are a little bolder than the
+%% contained text. This is especially needed for [ and ]
+\def\opnr{{\sf\char`\(}} \def\clnr{{\sf\char`\)}} \def\ampnr{\&}
+\def\lbrb{{\bf\char`\[}} \def\rbrb{{\bf\char`\]}}
+
+% First, defname, which formats the header line itself.
+% #1 should be the function name.
+% #2 should be the type of definition, such as "Function".
+
+\def\defname #1#2{%
+% Get the values of \leftskip and \rightskip as they were
+% outside the @def...
+\dimen2=\leftskip
+\advance\dimen2 by -\defbodyindent
+\dimen3=\rightskip
+\advance\dimen3 by -\defbodyindent
+\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
+{% Adjust \hsize to exclude the ambient margins,
+% so that \rightline will obey them.
+\advance \hsize by -\dimen2 \advance \hsize by -\dimen3
+\rlap{\rightline{{\rm #2}\hskip \deftypemargin}}}%
+% Make all lines underfull and no complaints:
+\tolerance=10000 \hbadness=10000
+\advance\leftskip by -\defbodyindent
+{\df #1}\enskip % Generate function name
+}
+
+% Actually process the body of a definition
+% #1 should be the terminating control sequence, such as \Edefun.
+% #2 should be the "another name" control sequence, such as \defunx.
+% #3 should be the control sequence that actually processes the header,
+% such as \defunheader.
+
+\def\defparsebody #1#2#3{\begingroup\inENV% Environment for definitionbody
+\medbreak %
+% Define the end token that this defining construct specifies
+% so that it will exit this group.
+\def#1{\endgraf\endgroup\medbreak}%
+\def#2{\begingroup\obeylines\activeparens\spacesplit#3}%
+\parindent=0in
+\advance\leftskip by \defbodyindent \advance \rightskip by \defbodyindent
+\begingroup %
+\catcode 61=\active %
+\obeylines\activeparens\spacesplit#3}
+
+\def\defmethparsebody #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
+\advance\leftskip by \defbodyindent \advance \rightskip by \defbodyindent
+\begingroup\obeylines\activeparens\spacesplit{#3{#4}}}
+
+\def\defopparsebody #1#2#3#4#5 {\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 ##2 {\def#4{##1}%
+\begingroup\obeylines\activeparens\spacesplit{#3{##2}}}%
+\parindent=0in
+\advance\leftskip by \defbodyindent \advance \rightskip by \defbodyindent
+\begingroup\obeylines\activeparens\spacesplit{#3{#5}}}
+
+% These parsing functions are similar to the preceding ones
+% except that they do not make parens into active characters.
+% These are used for "variables" since they have no arguments.
+
+\def\defvarparsebody #1#2#3{\begingroup\inENV% Environment for definitionbody
+\medbreak %
+% Define the end token that this defining construct specifies
+% so that it will exit this group.
+\def#1{\endgraf\endgroup\medbreak}%
+\def#2{\begingroup\obeylines\spacesplit#3}%
+\parindent=0in
+\advance\leftskip by \defbodyindent \advance \rightskip by \defbodyindent
+\begingroup %
+\catcode 61=\active %
+\obeylines\spacesplit#3}
+
+\def\defvrparsebody #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\spacesplit{#3{##1}}}%
+\parindent=0in
+\advance\leftskip by \defbodyindent \advance \rightskip by \defbodyindent
+\begingroup\obeylines\spacesplit{#3{#4}}}
+
+\def\defopvarparsebody #1#2#3#4#5 {\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 ##2 {\def#4{##1}%
+\begingroup\obeylines\spacesplit{#3{##2}}}%
+\parindent=0in
+\advance\leftskip by \defbodyindent \advance \rightskip by \defbodyindent
+\begingroup\obeylines\spacesplit{#3{#5}}}
+
+% Split up #2 at the first space token.
+% call #1 with two arguments:
+% the first is all of #2 before the space token,
+% the second is all of #2 after that space token.
+% If #2 contains no space token, all of it is passed as the first arg
+% and the second is passed as empty.
+
+{\obeylines
+\gdef\spacesplit#1#2^^M{\endgroup\spacesplitfoo{#1}#2 \relax\spacesplitfoo}%
+\long\gdef\spacesplitfoo#1#2 #3#4\spacesplitfoo{%
+\ifx\relax #3%
+#1{#2}{}\else #1{#2}{#3#4}\fi}}
+
+% So much for the things common to all kinds of definitions.
+
+% Define @defun.
+
+% First, define the processing that is wanted for arguments of \defun
+% Use this to expand the args and terminate the paragraph they make up
+
+\def\defunargs #1{\functionparens \sl
+% Expand, preventing hyphenation at `-' chars.
+% Note that groups don't affect changes in \hyphenchar.
+\hyphenchar\tensl=0
+#1%
+\hyphenchar\tensl=45
+\ifnum\parencount=0 \else \errmessage{unbalanced parens in @def arguments}\fi%
+\interlinepenalty=10000
+\advance\rightskip by 0pt plus 1fil
+\endgraf\penalty 10000\vskip -\parskip\penalty 10000%
+}
+
+\def\deftypefunargs #1{%
+% Expand, preventing hyphenation at `-' chars.
+% Note that groups don't affect changes in \hyphenchar.
+\functionparens
+\code{#1}%
+\interlinepenalty=10000
+\advance\rightskip by 0pt plus 1fil
+\endgraf\penalty 10000\vskip -\parskip\penalty 10000%
+}
+
+% Do complete processing of one @defun or @defunx line already parsed.
+
+% @deffn Command forward-char nchars
+
+\def\deffn{\defmethparsebody\Edeffn\deffnx\deffnheader}
+
+\def\deffnheader #1#2#3{\doind {fn}{\code{#2}}%
+\begingroup\defname {#2}{#1}\defunargs{#3}\endgroup %
+\catcode 61=\other % Turn off change made in \defparsebody
+}
+
+% @defun == @deffn Function
+
+\def\defun{\defparsebody\Edefun\defunx\defunheader}
+
+\def\defunheader #1#2{\doind {fn}{\code{#1}}% Make entry in function index
+\begingroup\defname {#1}{Function}%
+\defunargs {#2}\endgroup %
+\catcode 61=\other % Turn off change made in \defparsebody
+}
+
+% @deftypefun int foobar (int @var{foo}, float @var{bar})
+
+\def\deftypefun{\defparsebody\Edeftypefun\deftypefunx\deftypefunheader}
+
+% #1 is the data type. #2 is the name and args.
+\def\deftypefunheader #1#2{\deftypefunheaderx{#1}#2 \relax}
+% #1 is the data type, #2 the name, #3 the args.
+\def\deftypefunheaderx #1#2 #3\relax{%
+\doind {fn}{\code{#2}}% Make entry in function index
+\begingroup\defname {\code{#1} #2}{Function}%
+\deftypefunargs {#3}\endgroup %
+\catcode 61=\other % Turn off change made in \defparsebody
+}
+
+% @deftypefn {Library Function} int foobar (int @var{foo}, float @var{bar})
+
+\def\deftypefn{\defmethparsebody\Edeftypefn\deftypefnx\deftypefnheader}
+
+% #1 is the classification. #2 is the data type. #3 is the name and args.
+\def\deftypefnheader #1#2#3{\deftypefnheaderx{#1}{#2}#3 \relax}
+% #1 is the classification, #2 the data type, #3 the name, #4 the args.
+\def\deftypefnheaderx #1#2#3 #4\relax{%
+\doind {fn}{\code{#3}}% Make entry in function index
+\begingroup\defname {\code{#2} #3}{#1}%
+\deftypefunargs {#4}\endgroup %
+\catcode 61=\other % Turn off change made in \defparsebody
+}
+
+% @defmac == @deffn Macro
+
+\def\defmac{\defparsebody\Edefmac\defmacx\defmacheader}
+
+\def\defmacheader #1#2{\doind {fn}{\code{#1}}% Make entry in function index
+\begingroup\defname {#1}{Macro}%
+\defunargs {#2}\endgroup %
+\catcode 61=\other % Turn off change made in \defparsebody
+}
+
+% @defspec == @deffn Special Form
+
+\def\defspec{\defparsebody\Edefspec\defspecx\defspecheader}
+
+\def\defspecheader #1#2{\doind {fn}{\code{#1}}% Make entry in function index
+\begingroup\defname {#1}{Special Form}%
+\defunargs {#2}\endgroup %
+\catcode 61=\other % Turn off change made in \defparsebody
+}
+
+% This definition is run if you use @defunx
+% anywhere other than immediately after a @defun or @defunx.
+
+\def\deffnx #1 {\errmessage{@deffnx in invalid context}}
+\def\defunx #1 {\errmessage{@defunx in invalid context}}
+\def\defmacx #1 {\errmessage{@defmacx in invalid context}}
+\def\defspecx #1 {\errmessage{@defspecx in invalid context}}
+\def\deftypefnx #1 {\errmessage{@deftypefnx in invalid context}}
+\def\deftypeunx #1 {\errmessage{@deftypeunx in invalid context}}
+
+% @defmethod, and so on
+
+% @defop {Funny Method} foo-class frobnicate argument
+
+\def\defop #1 {\def\defoptype{#1}%
+\defopparsebody\Edefop\defopx\defopheader\defoptype}
+
+\def\defopheader #1#2#3{%
+\dosubind {fn}{\code{#2}}{on #1}% Make entry in function index
+\begingroup\defname {#2}{\defoptype{} on #1}%
+\defunargs {#3}\endgroup %
+}
+
+% @defmethod == @defop Method
+
+\def\defmethod{\defmethparsebody\Edefmethod\defmethodx\defmethodheader}
+
+\def\defmethodheader #1#2#3{%
+\dosubind {fn}{\code{#2}}{on #1}% entry in function index
+\begingroup\defname {#2}{Method on #1}%
+\defunargs {#3}\endgroup %
+}
+
+% @defcv {Class Option} foo-class foo-flag
+
+\def\defcv #1 {\def\defcvtype{#1}%
+\defopvarparsebody\Edefcv\defcvx\defcvarheader\defcvtype}
+
+\def\defcvarheader #1#2#3{%
+\dosubind {vr}{\code{#2}}{of #1}% Make entry in var index
+\begingroup\defname {#2}{\defcvtype{} of #1}%
+\defvarargs {#3}\endgroup %
+}
+
+% @defivar == @defcv {Instance Variable}
+
+\def\defivar{\defvrparsebody\Edefivar\defivarx\defivarheader}
+
+\def\defivarheader #1#2#3{%
+\dosubind {vr}{\code{#2}}{of #1}% Make entry in var index
+\begingroup\defname {#2}{Instance Variable of #1}%
+\defvarargs {#3}\endgroup %
+}
+
+% These definitions are run if you use @defmethodx, etc.,
+% anywhere other than immediately after a @defmethod, etc.
+
+\def\defopx #1 {\errmessage{@defopx in invalid context}}
+\def\defmethodx #1 {\errmessage{@defmethodx in invalid context}}
+\def\defcvx #1 {\errmessage{@defcvx in invalid context}}
+\def\defivarx #1 {\errmessage{@defivarx in invalid context}}
+
+% Now @defvar
+
+% First, define the processing that is wanted for arguments of @defvar.
+% This is actually simple: just print them in roman.
+% This must expand the args and terminate the paragraph they make up
+\def\defvarargs #1{\normalparens #1%
+\interlinepenalty=10000
+\endgraf\penalty 10000\vskip -\parskip\penalty 10000}
+
+% @defvr Counter foo-count
+
+\def\defvr{\defvrparsebody\Edefvr\defvrx\defvrheader}
+
+\def\defvrheader #1#2#3{\doind {vr}{\code{#2}}%
+\begingroup\defname {#2}{#1}\defvarargs{#3}\endgroup}
+
+% @defvar == @defvr Variable
+
+\def\defvar{\defvarparsebody\Edefvar\defvarx\defvarheader}
+
+\def\defvarheader #1#2{\doind {vr}{\code{#1}}% Make entry in var index
+\begingroup\defname {#1}{Variable}%
+\defvarargs {#2}\endgroup %
+}
+
+% @defopt == @defvr {User Option}
+
+\def\defopt{\defvarparsebody\Edefopt\defoptx\defoptheader}
+
+\def\defoptheader #1#2{\doind {vr}{\code{#1}}% Make entry in var index
+\begingroup\defname {#1}{User Option}%
+\defvarargs {#2}\endgroup %
+}
+
+% @deftypevar int foobar
+
+\def\deftypevar{\defvarparsebody\Edeftypevar\deftypevarx\deftypevarheader}
+
+% #1 is the data type. #2 is the name.
+\def\deftypevarheader #1#2{%
+\doind {vr}{\code{#2}}% Make entry in variables index
+\begingroup\defname {\code{#1} #2}{Variable}%
+\interlinepenalty=10000
+\endgraf\penalty 10000\vskip -\parskip\penalty 10000
+\endgroup}
+
+% @deftypevr {Global Flag} int enable
+
+\def\deftypevr{\defvrparsebody\Edeftypevr\deftypevrx\deftypevrheader}
+
+\def\deftypevrheader #1#2#3{\doind {vr}{\code{#3}}%
+\begingroup\defname {\code{#2} #3}{#1}
+\interlinepenalty=10000
+\endgraf\penalty 10000\vskip -\parskip\penalty 10000
+\endgroup}
+
+% This definition is run if you use @defvarx
+% anywhere other than immediately after a @defvar or @defvarx.
+
+\def\defvrx #1 {\errmessage{@defvrx in invalid context}}
+\def\defvarx #1 {\errmessage{@defvarx in invalid context}}
+\def\defoptx #1 {\errmessage{@defoptx in invalid context}}
+\def\deftypevarx #1 {\errmessage{@deftypevarx in invalid context}}
+\def\deftypevrx #1 {\errmessage{@deftypevrx in invalid context}}
+
+% Now define @deftp
+% Args are printed in bold, a slight difference from @defvar.
+
+\def\deftpargs #1{\bf \defvarargs{#1}}
+
+% @deftp Class window height width ...
+
+\def\deftp{\defvrparsebody\Edeftp\deftpx\deftpheader}
+
+\def\deftpheader #1#2#3{\doind {tp}{\code{#2}}%
+\begingroup\defname {#2}{#1}\deftpargs{#3}\endgroup}
+
+% This definition is run if you use @deftpx, etc
+% anywhere other than immediately after a @deftp, etc.
+
+\def\deftpx #1 {\errmessage{@deftpx in invalid context}}
+
+\message{cross reference,}
+% Define cross-reference macros
+\newwrite \auxfile
+
+\newif\ifhavexrefs % True if xref values are known.
+\newif\ifwarnedxrefs % True if we warned once that they aren't known.
+
+% \setref{foo} defines a cross-reference point named foo.
+
+\def\setref#1{%
+%\dosetq{#1-title}{Ytitle}%
+\dosetq{#1-pg}{Ypagenumber}%
+\dosetq{#1-snt}{Ysectionnumberandtype}}
+
+\def\unnumbsetref#1{%
+%\dosetq{#1-title}{Ytitle}%
+\dosetq{#1-pg}{Ypagenumber}%
+\dosetq{#1-snt}{Ynothing}}
+
+\def\appendixsetref#1{%
+%\dosetq{#1-title}{Ytitle}%
+\dosetq{#1-pg}{Ypagenumber}%
+\dosetq{#1-snt}{Yappendixletterandtype}}
+
+% \xref, \pxref, and \ref generate cross-references to specified points.
+% For \xrefX, #1 is the node name, #2 the name of the Info
+% cross-reference, #3 the printed node name, #4 the name of the Info
+% file, #5 the name of the printed manual. All but the node name can be
+% omitted.
+%
+\def\pxref#1{see \xrefX[#1,,,,,,,]}
+\def\xref#1{See \xrefX[#1,,,,,,,]}
+\def\ref#1{\xrefX[#1,,,,,,,]}
+\def\xrefX[#1,#2,#3,#4,#5,#6]{\begingroup%
+\def\printedmanual{\ignorespaces #5}%
+\def\printednodename{\ignorespaces #3}%
+%
+\setbox1=\hbox{\printedmanual}%
+\setbox0=\hbox{\printednodename}%
+\ifdim \wd0=0pt%
+\def\printednodename{\ignorespaces #1}%
+%%% Uncommment the following line to make the actual chapter or section title
+%%% appear inside the square brackets.
+%\def\printednodename{#1-title}%
+\fi%
+%
+%
+% If we use \unhbox0 and \unhbox1 to print the node names, TeX does
+% not insert empty discretionaries after hyphens, which means that it
+% will not find a line break at a hyphen in a node names. Since some
+% manuals are best written with fairly long node names, containing
+% hyphens, this is a loss. Therefore, we simply give the text of
+% the node name again, so it is as if TeX is seeing it for the first
+% time.
+\ifdim \wd1>0pt
+section ``\printednodename'' in \cite{\printedmanual}%
+\else%
+\turnoffactive%
+\refx{#1-snt}{} [\printednodename], page\tie\refx{#1-pg}{}%
+\fi
+\endgroup}
+
+% \dosetq is the interface for calls from other macros
+
+% Use \turnoffactive so that punctuation chars such as underscore
+% work in node names.
+\def\dosetq #1#2{{\let\folio=0 \turnoffactive%
+\edef\next{\write\auxfile{\internalsetq {#1}{#2}}}%
+\next}}
+
+% \internalsetq {foo}{page} expands into
+% CHARACTERS 'xrdef {foo}{...expansion of \Ypage...}
+% When the aux file is read, ' is the escape character
+
+\def\internalsetq #1#2{'xrdef {#1}{\csname #2\endcsname}}
+
+% Things to be expanded by \internalsetq
+
+\def\Ypagenumber{\folio}
+
+\def\Ytitle{\thischapter}
+
+\def\Ynothing{}
+
+\def\Ysectionnumberandtype{%
+\ifnum\secno=0 Chapter\xreftie\the\chapno %
+\else \ifnum \subsecno=0 Section\xreftie\the\chapno.\the\secno %
+\else \ifnum \subsubsecno=0 %
+Section\xreftie\the\chapno.\the\secno.\the\subsecno %
+\else %
+Section\xreftie\the\chapno.\the\secno.\the\subsecno.\the\subsubsecno %
+\fi \fi \fi }
+
+\def\Yappendixletterandtype{%
+\ifnum\secno=0 Appendix\xreftie'char\the\appendixno{}%
+\else \ifnum \subsecno=0 Section\xreftie'char\the\appendixno.\the\secno %
+\else \ifnum \subsubsecno=0 %
+Section\xreftie'char\the\appendixno.\the\secno.\the\subsecno %
+\else %
+Section\xreftie'char\the\appendixno.\the\secno.\the\subsecno.\the\subsubsecno %
+\fi \fi \fi }
+
+\gdef\xreftie{'tie}
+
+% Use TeX 3.0's \inputlineno to get the line number, for better error
+% messages, but if we're using an old version of TeX, don't do anything.
+%
+\ifx\inputlineno\thisisundefined
+ \let\linenumber = \empty % Non-3.0.
+\else
+ \def\linenumber{\the\inputlineno:\space}
+\fi
+
+% Define \refx{NAME}{SUFFIX} to reference a cross-reference string named NAME.
+% If its value is nonempty, SUFFIX is output afterward.
+
+\def\refx#1#2{%
+ \expandafter\ifx\csname X#1\endcsname\relax
+ % If not defined, say something at least.
+ $\langle$un\-de\-fined$\rangle$%
+ \ifhavexrefs
+ \message{\linenumber Undefined cross reference `#1'.}%
+ \else
+ \ifwarnedxrefs\else
+ \global\warnedxrefstrue
+ \message{Cross reference values unknown; you must run TeX again.}%
+ \fi
+ \fi
+ \else
+ % It's defined, so just use it.
+ \csname X#1\endcsname
+ \fi
+ #2% Output the suffix in any case.
+}
+
+% Read the last existing aux file, if any. No error if none exists.
+
+% This is the macro invoked by entries in the aux file.
+\def\xrdef #1#2{
+{\catcode`\'=\other\expandafter \gdef \csname X#1\endcsname {#2}}}
+
+\def\readauxfile{%
+\begingroup
+\catcode `\^^@=\other
+\catcode `\=\other
+\catcode `\=\other
+\catcode `\^^C=\other
+\catcode `\^^D=\other
+\catcode `\^^E=\other
+\catcode `\^^F=\other
+\catcode `\^^G=\other
+\catcode `\^^H=\other
+\catcode `\ =\other
+\catcode `\^^L=\other
+\catcode `\=\other
+\catcode `\=\other
+\catcode `\=\other
+\catcode `\=\other
+\catcode `\=\other
+\catcode `\=\other
+\catcode `\=\other
+\catcode `\=\other
+\catcode `\=\other
+\catcode `\=\other
+\catcode `\=\other
+\catcode `\=\other
+\catcode 26=\other
+\catcode `\^^[=\other
+\catcode `\^^\=\other
+\catcode `\^^]=\other
+\catcode `\^^^=\other
+\catcode `\^^_=\other
+\catcode `\@=\other
+\catcode `\^=\other
+\catcode `\~=\other
+\catcode `\[=\other
+\catcode `\]=\other
+\catcode`\"=\other
+\catcode`\_=\other
+\catcode`\|=\other
+\catcode`\<=\other
+\catcode`\>=\other
+\catcode `\$=\other
+\catcode `\#=\other
+\catcode `\&=\other
+% the aux file uses ' as the escape.
+% Turn off \ as an escape so we do not lose on
+% entries which were dumped with control sequences in their names.
+% For example, 'xrdef {$\leq $-fun}{page ...} made by @defun ^^
+% Reference to such entries still does not work the way one would wish,
+% but at least they do not bomb out when the aux file is read in.
+\catcode `\{=1 \catcode `\}=2
+\catcode `\%=\other
+\catcode `\'=0
+\catcode `\\=\other
+\openin 1 \jobname.aux
+\ifeof 1 \else \closein 1 \input \jobname.aux \global\havexrefstrue
+\fi
+% Open the new aux file. Tex will close it automatically at exit.
+\openout \auxfile=\jobname.aux
+\endgroup}
+
+
+% Footnotes.
+
+\newcount \footnoteno
+
+\def\supereject{\par\penalty -20000\footnoteno =0 }
+
+% @footnotestyle is meaningful for info output only..
+\let\footnotestyle=\comment
+
+\let\ptexfootnote=\footnote
+
+{\catcode `\@=11
+\long\gdef\footnote #1{\global\advance \footnoteno by \@ne
+\unskip
+\edef\thisfootno{$^{\the\footnoteno}$}%
+\let\@sf\empty
+\ifhmode\edef\@sf{\spacefactor\the\spacefactor}\/\fi
+\thisfootno\@sf \footnotezzz{#1}}
+% \parsearg\footnotezzz}
+
+\long\gdef\footnotezzz #1{\insert\footins{
+\interlinepenalty\interfootnotelinepenalty
+\splittopskip\ht\strutbox % top baseline for broken footnotes
+\splitmaxdepth\dp\strutbox \floatingpenalty\@MM
+\leftskip\z@skip \rightskip\z@skip \spaceskip\z@skip \xspaceskip\z@skip
+\footstrut\parindent=\defaultparindent\hang\textindent{\thisfootno}#1\strut}}
+
+}%end \catcode `\@=11
+
+% End of control word definitions.
+
+\message{and turning on texinfo input format.}
+
+\def\openindices{%
+ \newindex{cp}%
+ \newcodeindex{fn}%
+ \newcodeindex{vr}%
+ \newcodeindex{tp}%
+ \newcodeindex{ky}%
+ \newcodeindex{pg}%
+}
+
+% Set some numeric style parameters, for 8.5 x 11 format.
+
+%\hsize = 6.5in
+\newdimen\defaultparindent \defaultparindent = 15pt
+\parindent = \defaultparindent
+\parskip 18pt plus 1pt
+\baselineskip 15pt
+\advance\topskip by 1.2cm
+
+% Prevent underfull vbox error messages.
+\vbadness=10000
+
+% Following George Bush, just get rid of widows and orphans.
+\widowpenalty=10000
+\clubpenalty=10000
+
+% Use TeX 3.0's \emergencystretch to help line breaking, but if we're
+% using an old version of TeX, don't do anything. We want the amount of
+% stretch added to depend on the line length, hence the dependence on
+% \hsize. This makes it come to about 9pt for the 8.5x11 format.
+%
+\ifx\emergencystretch\thisisundefined \else
+ \emergencystretch = \hsize
+ \divide\emergencystretch by 45
+\fi
+
+% Use @smallbook to reset parameters for 7x9.5 format (or else 7x9.25)
+\def\smallbook{
+\global\lispnarrowing = 0.3in
+\global\baselineskip 12pt
+\global\parskip 3pt plus 1pt
+\global\hsize = 5in
+\global\doublecolumnhsize=2.4in \global\doublecolumnvsize=15.0in
+\global\vsize=7.5in
+\global\tolerance=700
+\global\hfuzz=1pt
+\global\contentsrightmargin=0pt
+
+\global\pagewidth=\hsize
+\global\pageheight=\vsize
+
+\global\let\smalllisp=\smalllispx
+\global\let\smallexample=\smalllispx
+\global\def\Esmallexample{\Esmalllisp}
+}
+
+% Use @afourpaper to print on European A4 paper.
+\def\afourpaper{
+\global\tolerance=700
+\global\hfuzz=1pt
+\global\baselineskip=12pt
+\global\parskip 15pt plus 1pt
+
+\global\vsize= 53\baselineskip
+\advance\vsize by \topskip
+%\global\hsize= 5.85in % A4 wide 10pt
+\global\hsize= 6.5in
+\global\outerhsize=\hsize
+\global\advance\outerhsize by 0.5in
+\global\outervsize=\vsize
+\global\advance\outervsize by 0.6in
+\global\doublecolumnhsize=\hsize
+\global\divide\doublecolumnhsize by 2
+\global\advance\doublecolumnhsize by -0.1in
+\global\doublecolumnvsize=\vsize
+\global\multiply\doublecolumnvsize by 2
+\global\advance\doublecolumnvsize by 0.1in
+
+\global\pagewidth=\hsize
+\global\pageheight=\vsize
+}
+
+%% For a final copy, take out the rectangles
+%% that mark overfull boxes (in case you have decided
+%% that the text looks ok even though it passes the margin).
+\def\finalout{\overfullrule=0pt}
+
+% Define macros to output various characters with catcode for normal text.
+\catcode`\"=\other
+\catcode`\~=\other
+\catcode`\^=\other
+\catcode`\_=\other
+\catcode`\|=\other
+\catcode`\<=\other
+\catcode`\>=\other
+\catcode`\+=\other
+\def\normaldoublequote{"}
+\def\normaltilde{~}
+\def\normalcaret{^}
+\def\normalunderscore{_}
+\def\normalverticalbar{|}
+\def\normalless{<}
+\def\normalgreater{>}
+\def\normalplus{+}
+
+% This macro is used to make a character print one way in ttfont
+% where it can probably just be output, and another way in other fonts,
+% where something hairier probably needs to be done.
+%
+% #1 is what to print if we are indeed using \tt; #2 is what to print
+% otherwise. Since all the Computer Modern typewriter fonts have zero
+% interword stretch (and shrink), and it is reasonable to expect all
+% typewriter fonts to have this, we can check that font parameter.
+%
+\def\ifusingtt#1#2{\ifdim \fontdimen3\the\font=0pt #1\else #2\fi}
+
+% Turn off all special characters except @
+% (and those which the user can use as if they were ordinary).
+% Most of these we simply print from the \tt font, but for some, we can
+% use math or other variants that look better in normal text.
+
+\catcode`\"=\active
+\def\activedoublequote{{\tt \char '042}}
+\let"=\activedoublequote
+\catcode`\~=\active
+\def~{{\tt \char '176}}
+\chardef\hat=`\^
+\catcode`\^=\active
+\def^{{\tt \hat}}
+
+\catcode`\_=\active
+\def_{\ifusingtt\normalunderscore\_}
+% Subroutine for the previous macro.
+\def\_{\lvvmode \kern.06em \vbox{\hrule width.3em height.1ex}}
+
+% \lvvmode is equivalent in function to \leavevmode.
+% Using \leavevmode runs into trouble when written out to
+% an index file due to the expansion of \leavevmode into ``\unhbox
+% \voidb@x'' ---which looks to TeX like ``\unhbox \voidb\x'' due to our
+% magic tricks with @.
+\def\lvvmode{\vbox to 0pt{}}
+
+\catcode`\|=\active
+\def|{{\tt \char '174}}
+\chardef \less=`\<
+\catcode`\<=\active
+\def<{{\tt \less}}
+\chardef \gtr=`\>
+\catcode`\>=\active
+\def>{{\tt \gtr}}
+\catcode`\+=\active
+\def+{{\tt \char 43}}
+%\catcode 27=\active
+%\def^^[{$\diamondsuit$}
+
+% Used sometimes to turn off (effectively) the active characters
+% even after parsing them.
+\def\turnoffactive{\let"=\normaldoublequote
+\let~=\normaltilde
+\let^=\normalcaret
+\let_=\normalunderscore
+\let|=\normalverticalbar
+\let<=\normalless
+\let>=\normalgreater
+\let+=\normalplus}
+
+% Set up an active definition for =, but don't enable it most of the time.
+{\catcode`\==\active
+\global\def={{\tt \char 61}}}
+
+\catcode`\@=0
+
+% \rawbackslashxx output one backslash character in current font
+\global\chardef\rawbackslashxx=`\\
+%{\catcode`\\=\other
+%@gdef@rawbackslashxx{\}}
+
+% \rawbackslash redefines \ as input to do \rawbackslashxx.
+{\catcode`\\=\active
+@gdef@rawbackslash{@let\=@rawbackslashxx }}
+
+% \normalbackslash outputs one backslash in fixed width font.
+\def\normalbackslash{{\tt\rawbackslashxx}}
+
+% Say @foo, not \foo, in error messages.
+\escapechar=`\@
+
+% \catcode 17=0 % Define control-q
+\catcode`\\=\active
+
+% If a .fmt file is being used, we don't want the `\input texinfo' to show up.
+% That is what \eatinput is for; after that, the `\' should revert to printing
+% a backslash.
+%
+@gdef@eatinput input texinfo{@fixbackslash}
+@global@let\ = @eatinput
+
+% On the other hand, perhaps the file did not have a `\input texinfo'. Then
+% the first `\{ in the file would cause an error. This macro tries to fix
+% that, assuming it is called before the first `\' could plausibly occur.
+%
+@gdef@fixbackslash{@ifx\@eatinput @let\ = @normalbackslash @fi}
+
+%% These look ok in all fonts, so just make them not special. The @rm below
+%% makes sure that the current font starts out as the newly loaded cmr10
+@catcode`@$=@other @catcode`@%=@other @catcode`@&=@other @catcode`@#=@other
+
+@textfonts
+@rm
+@message{Setting default page type to A4.}
+@afourpaper
+
+@c Local variables:
+@c page-delimiter: "^\\\\message"
+@c End:
diff --git a/support/vvcode/doc/vvcode.tex b/support/vvcode/doc/vvcode.tex
new file mode 100644
index 0000000000..8a0ac20b6b
--- /dev/null
+++ b/support/vvcode/doc/vvcode.tex
@@ -0,0 +1,255 @@
+\input texinfo.tex @c -*-texinfo-*-
+@tableindent=0.9in
+
+@comment %**start of header
+@setfilename vve-port.info
+@settitle VVcode
+@node Porting Guide, Porting Guide, Top, Top
+@comment %**end of header
+
+@iftex
+@finalout
+@end iftex
+
+@c -------------------------------------------------------------------------
+@c Note: Please update the edition number, month, and year
+@c Edition number is set at: settitle, subtitle and top node
+@c Month or date is set at: subtitle and top node;
+@c Search for: !!set
+@c -------------------------------------------------------------------------
+
+@ifinfo
+This file documents Vvcode, a superior replacement for UUcode to allow the
+documentation system that uses a single source file to produce both on-line
+information and a printed manual.
+
+This is the first edition of the VVcode documentation,
+@w{May 1992,} for VVcode version 1.00.
+
+Copyright (C) 1992 Niel Kempson
+
+This is the first edition of the VVcode documentation,@*
+and is consistent with version 1.00 of VVcode.
+
+Permission is granted to make and distribute verbatim copies of
+this manual provided the copyright notice and this permission notice
+are preserved on all copies.
+
+@ignore
+Permission is granted to process this file through TeX and print the
+results, provided the printed document carries copying permission
+notice identical to this one except for the removal of this paragraph
+(this paragraph not being relevant to the printed manual).
+
+@end ignore
+Permission is granted to copy and distribute modified versions of this
+manual under the conditions for verbatim copying, provided that the entire
+resulting derived work is distributed under the terms of a permission
+notice identical to this one.
+
+Permission is granted to copy and distribute translations of this manual
+into another language, under the above conditions for modified versions,
+except that this permission notice may be stated in a translation approved
+by the Free Software Foundation.
+@end ifinfo
+
+
+
+@c
+@c *************************************************************************
+@c TITLE PAGE
+@c *************************************************************************
+@setchapternewpage odd
+@titlepage
+
+@c !!set Set the month and edition here.
+@title{VVcode}
+@subtitle{Last revised May 1992}
+@subtitle{for VVcode version 1.00}
+@author{Niel Kempson}
+@page
+
+@vskip 1in
+This is the first edition of the VVcode documentation and should be
+consistent with the following versions of VVcode:
+
+@itemize @bullet
+ @item VVcode system v1.00
+ @item MS-DOS port v1.00-001
+ @item OS/2 port v1.00-001
+ @item Unix port v1.00-001
+ @item VAX/VMS port v1.00-001
+ @item VM/CMS port v1.00-001
+@end itemize
+
+As VVcode is ported to new environments this documentation should be
+updated.
+
+@vskip 0pt plus 1filll
+Copyright @copyright{} 1992 Niel Kempson
+
+Permission is granted to make and distribute verbatim copies of
+this manual provided the copyright notice and this permission notice
+are preserved on all copies.
+
+Permission is granted to copy and distribute modified versions of this
+manual under the conditions for verbatim copying, provided also that
+the entire resulting derived work is distributed under the terms of a
+permission notice identical to this one.
+
+Permission is granted to copy and distribute translations of this manual
+into another language, under the above conditions for modified versions.
+@end titlepage
+@page
+
+
+
+@c *************************************************************************
+@c NODE: the top
+@c *************************************************************************
+@ifinfo
+@node Top, Copying, (dir), (dir)
+@top VVcode
+
+VVcode is a superior replacement for UUcode to enable the reliable
+transmission of data over the world's e-mail networks.
+
+@c !!set Set the date and edition here.
+This is the first edition of the VVcode documentation,
+@w{May 1992,} for VVcode version 1.00.
+@end ifinfo
+
+@menu
+* Copying:: VVcode copying conditions
+* Introduction:: Introduction to VVcode
+* User Manual:: Guide to using VVcode
+* Porting Guide:: How to port VVcode to a new environment
+* Testing Guide:: How to test VVcode
+* File Formats:: Definition of VVcode-related file formats
+@end menu
+
+
+
+@c *************************************************************************
+@c CHAPTER: VVcode copying conditions
+@c *************************************************************************
+@c node-name, next, previous, up
+@node Copying, Copying, Top, Top
+@unnumbered VVcode copying conditions
+
+The programs currently being distributed that relate to VVcode are
+@dfn{free}; this means that everyone is free to use them and free to
+redistribute them freely. The VVcode-related programs are not in the
+public domain; they are copyrighted and there are restrictions on their
+distribution, but these restrictions are designed to permit everything that
+a good cooperating citizen would want to do. What is not allowed is to try
+to prevent others from further sharing any version of these programs that
+they might get from you.@refill
+
+ Specifically, we want to make sure that you have the right to give away
+copies of the programs that relate to VVcode, that you receive source code
+or else can get it if you want it, that you can change these programs or
+use pieces of them in new free programs, and that you know you can do these
+things.@refill
+
+ To make sure that everyone has such rights, we have to forbid you to
+deprive anyone else of these rights. For example, if you distribute copies
+of the VVcode related programs, you must give the recipients all the rights
+that you have. You must make sure that they, too, receive or can get the
+source code. And you must tell them their rights.@refill
+
+ Also, for our own protection, we must make certain that everyone finds
+out that there is no warranty for the programs that relate to VVcode. If
+these programs are modified by someone else and passed on, we want their
+recipients to know that what they have is not what we distributed, so that
+any problems introduced by others will not reflect on our
+reputation.@refill
+
+ The precise conditions of the licenses for the programs currently being
+distributed that relate to VVcode are found in the General Public Licenses
+that accompany them.@refill
+
+
+
+@c *************************************************************************
+@c CHAPTER: Contributors to VVcode
+@c *************************************************************************
+@c node-name, next, previous, up
+@node Contributors, Contributors, Top, Top
+@unnumbered Contributors to VVcode
+
+In addition to Niel Kempson, several people have contributed to the
+development of VVcode.
+
+@itemize @bullet
+ @item Rainer Sch@"opf @code{<schoepf@@sc.ZIB-Berlin.de>} wrote the VM/CMS
+ implementation and has been very helpful during the testing of
+ VVcode.
+ @item Brian Hamilton Kelly @code{<TeX@@rmcs.cranfield.ac.uk>} for
+ encouragement and testing of the VAX/VMS implementation.
+ @item Konrad Bernlohr @code{<bern@@dhdmpi50.bitnet>} made some helpful
+ suggestions for improvements to the original version.
+ @item The Aston University @TeX{} archive group for help and
+ encouragement during the long gestation period. In alphabetical
+ order:
+ @itemize @bullet
+ @item Adrian Clark @code{<alien@@essex.ac.uk>}
+ @item Brian Hamilton Kelly @code{<tex@@rmcs.cranfield.ac.uk>}
+ @item Dave Osborne @code{<d.osborne@@mips.nottingham.ac.uk>}
+ @item Max Calvini @code{<m_calvini@@TeX.ac.uk>}
+ @item Peter Abbott @code{<p.abbott@@aston.ac.uk>}
+ @item Phil Taylor @code{<chaa006@@vax.rhbnc.ac.uk>}
+ @item Rainer Sch@"opf @code{<schoepf@@sc.ZIB-Berlin.de>}
+ @item Sebastian Rahtz @code{<s_rahtz@@TeX.ac.uk>}
+ @end itemize
+@end itemize
+
+
+
+@c *************************************************************************
+@c CHAPTER: Introduction to VVcode
+@c *************************************************************************
+@include vvintro.texinfo
+
+
+
+@c *************************************************************************
+@c CHAPTER: Guide to using VVcode
+@c *************************************************************************
+@include vvuser.texinfo
+
+
+
+@c *************************************************************************
+@c CHAPTER: Installing VVcode
+@c *************************************************************************
+@include vvinstal.texinfo
+
+
+
+@c *************************************************************************
+@c CHAPTER: How to port VVcode to a new environment
+@c *************************************************************************
+@include vvport.texinfo
+
+
+
+@c *************************************************************************
+@c CHAPTER: How to test VVcode
+@c *************************************************************************
+@include vvtest.texinfo
+
+
+
+@c *************************************************************************
+@c CHAPTER: Definition of VVcode-related file formats
+@c *************************************************************************
+@include vvfiles.texinfo
+
+
+
+@c *************************************************************************
+@c Table of Contents
+@c *************************************************************************
+@contents
+@bye
diff --git a/support/vvcode/doc/vvfiles.tex b/support/vvcode/doc/vvfiles.tex
new file mode 100644
index 0000000000..bf019f4ddb
--- /dev/null
+++ b/support/vvcode/doc/vvfiles.tex
@@ -0,0 +1,1287 @@
+@c *************************************************************************
+@c CHAPTER: Definition of VVcode-related file formats
+@c *************************************************************************
+@c node-name, next, previous, up
+@node File Formats, File Formats, Top, Top
+@chapter Definition of VVcode-related file formats
+
+
+@c =========================================================================
+@c SECTION: Format of the VVE file
+@c =========================================================================
+@section Format of the VVE file
+
+A VVE file consists of three logical sections in the following logical
+format:
+
+@example
+<VVE file> ::= <initial preamble>
+ <encoded data lines>
+ <terminal postamble>
+@end example
+
+The @code{<initial preamble>} and @code{<terminal postamble>} sections
+contain VVE "header" lines used to record and control the characteristics
+of the encoding/decoding process. The @code{<encoded data lines>} section
+contains the data from the original file, encoded using the VVcode scheme.
+
+It is sometimes desirable to transmit the VVE file in more than one part,
+so the logical format is extended to cater for multi-part files:
+
+@example
+<first part> ::= <initial preamble>
+ <encoded data lines>
+ <continuation postamble>
+
+<middle part> ::= <continuation preamble>
+ <encoded data lines>
+ <continuation postamble>
+
+<last part> ::= <continuation preamble>
+ <encoded data lines>
+ <terminal postamble>
+@end example
+
+There is always one @code{<first part>} and one @code{<last part>} part in
+a multi-part VVE file. There may be zero (for a two part file) or more
+@code{<middle part>} parts.
+
+The sections are described in more detail below.
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: Line Prefix and Suffix
+@c -------------------------------------------------------------------------
+@subsection Line Prefix and Suffix
+@itemize @bullet
+ @item each line has a "Vv" prefix and "V" suffix
+
+ @item prefix - elimination of mailer lines
+
+ @item postfix - avoid space stripping by certain mailers
+@end itemize
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: Preamble Sections
+@c -------------------------------------------------------------------------
+@subsection Preamble Sections
+The preamble sections are used to initialize VVdecode before it starts to
+decode the encoded file data. Each preamble consists of a set of VVE
+header lines, each specifying a particular parameter relevant to the
+encoding/decoding operation. Each preamble section comprises a set of
+optional header lines followed by the set of required header lines. the
+syntax and use of the header lines is described in section 1.4.
+
+
+@subsubsection Preamble
+The initial preamble is used to initialize VVdecode parameters before it
+starts to decode the encoded file (e.g. the file mode and timestamp). The
+logical format of this section is:
+
+@example
+<initial preamble> ::= <optional initialization headers>
+ <begin header>
+@end example
+
+The @code{mode}, @code{format} and optional headers may be in any order,
+but the @code{begin} header must be the last header in this preamble
+section. None, any or all of the following optional headers may be present
+in the initial preamble section:
+
+@example
+<optional initializiation headers> ::= <characterset header>
+ <comment header>
+ <decodeversion header>
+ <format header>
+ <mode header>
+ <operatingsystem header>
+ <recordlength header>
+ <table header>
+ <timestamp header>
+@end example
+
+Note that only the @code{comment} header line may appear more than once in
+this section.
+
+@subsubsection Continuation Preamble
+
+The initial preamble is used to reset certain VVdecode parameters before it
+starts to decode the next section of the VVE file. The logical format of
+this section is:
+
+@example
+<continuation preamble> ::= <optional continuation headers>
+ <skipfrom header>
+@end example
+
+The optional headers may be in any order, but the @code{skipfrom} header
+must be the last header in this preamble section. None, any or all of the
+following optional headers may be present in this section:
+
+@example
+<optional initializiation headers> ::= <comment header>
+ <table header>
+@end example
+
+Note that only the @code{comment} header line may appear more than once in
+this section.
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: Postamble Sections
+@c -------------------------------------------------------------------------
+@subsection Postamble Sections
+The preamble sections are used to initialize VVdecode before it starts to
+decode the encoded file data. Each preamble consists of a set of VVE
+header lines, each specifying a particular parameter relevant to the
+encoding/decoding operation. Each preamble section comprises a set of
+optional header lines followed by the set of required header lines.
+
+@subsubsection Postamble
+[TODO] put in some text here
+@example
+<continuation postamble> ::= <skipto header>
+ <comment header>
+@end example
+
+The @code{comment} header line is optional and may appear more than once in
+this section.
+
+@subsubsection Terminal Postamble
+[TODO] put in some text here
+@example
+<continuation preamble> ::= <end header>
+ <optional terminal headers>
+
+<optional initializiation headers> ::= <bytecount header>
+ <comment header>
+ <crc32 header>
+@end example
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: Encoded Data Lines
+@c -------------------------------------------------------------------------
+@subsection Encoded Data Lines
+[TODO] put in some text here
+@itemize @bullet
+ @item describe what these lines are used for
+
+ @item format of the encoded line
+
+ @item termination of each section of encoded data (zero length line)
+
+ @item describe the different underlying data formats for fixed, stream
+ and variable format records
+@end itemize
+
+
+@c =========================================================================
+@c SECTION: VVE Header Lines
+@c =========================================================================
+@section VVE Header Lines
+
+A VVE header line takes the form
+
+@example
+<header-name> <parameter-1> <parameter-2> ... <parameter-N>
+@end example
+
+Most headers take only one parameter and parameters are normally separated
+by whitespace, though certain headers (e.g. @code{begin}) take more than one
+parameter and can include whitespace in the parameters. The format of each
+of the VVE header lines is described below. Two important symbols used in
+the description are:
+
+@table @code
+ @item <WS>
+ used to denote whitespace which may include spaces, tabs but not
+ the end of the line. The syntax
+
+ @example
+ xyz <WS> parameter <WS> <EOL>
+ @end example
+
+ states that header @code{xyz} takes a parameter which starts at the
+ first non-whitespace character after the @code{xyz} header name and
+ is terminated by the first whitespace character after that or the
+ end of line. This syntax is used to specify parameters which do
+ not contain whitespace.
+
+ @item <EOL>
+ used to denote the end of the line. The syntax
+
+ @example
+ xyz <WS> parameter <EOL>
+ @end example
+
+ states that header @code{xyz} takes a parameter which starts at the
+ first non-whitespace character after the @code{xyz} header name and
+ is terminated by the end of the line. This format would be used to
+ specify that parameters can include whitespace.
+
+ @item <NXT-HDR>
+ used to denote the next VVE header in the file. The syntax
+
+ @example
+ xyz <WS> parameter <NXT-HDR>
+ @end example
+
+ states that the header @code{xyz} takes a parameter which starts at
+ the first non-whitespace character after the @code{xyz} header
+ name and is terminated by the start of the next VVE header. This
+ format would be used to specify that parameters can span several
+ lines.
+
+ NOTE: the @code{<EOL>} characters are removed when the contents of
+ the lines are joined together.
+@end table
+
+Following is a detailed description of each VVE header. For each header
+there is a set of headings in the format shown below for the @code{example}
+header.
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: @code{example}
+@c -------------------------------------------------------------------------
+@page
+@subsection @code{example}
+
+@table @strong
+ @item Purpose:
+ Brief summary of the purpose of this header.
+
+ @item Location:
+ Describe where in the VVE file that this header will be found. The
+ locations are:
+
+ @itemize @bullet
+ @item initial preamble
+ @item continuation preamble
+ @item continuation postamble
+ @item terminal postamble
+ @end itemize
+
+ Also indicated is whether the header is required or optional.
+
+ @item Syntax:
+ @code{example <WS> parameter <WS> <EOL>}
+
+ This part shows the syntax of the header including the header name,
+ the number of parameters and the delimiters used to separate the
+ parameters.
+
+ @item Remarks:
+ This part provides extra information on the use of the header and
+ includes any limits that are imposed on the parameter value.
+
+ @item VVencode:
+ The header will be written to the VVE file by Vvencode and this
+ part describes the circumstances under which VVencode will write
+ the header line.
+
+ @item VVdecode:
+ This part describes how VVdecode should behave when it encounters
+ the header in a VVE file. In addition, specific processing rules
+ are documented for specific cases, namely:
+
+ @table @code
+ @item OK
+ what VVdecode should do if a valid header line is found in
+ the VVE file.
+
+ @item MISSING
+ what VVdecode should do if the header line was not found in
+ the VVE file.
+
+ @item INVALID
+ what VVdecode should do if the header line was found, but
+ with missing or invalid parameter values.
+ @end table
+
+ @item Example:
+ @code{example parameter}
+
+ Here you'll find a simple example of a valid example header line.
+@end table
+
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: @code{begin}
+@c -------------------------------------------------------------------------
+@page
+@subsection @code{begin}
+@table @strong
+ @item Purpose:
+ Signifies the absolute start of the VVencoded data.
+
+ @item Location:
+ Initial preamble (required).
+
+ @item Syntax:
+ @code{begin <WS> file-specification <EOL>}
+
+ @item Remarks:
+ The file specification may include spaces, though leading and
+ trailing spaces will be lost. There is no restriction on the
+ characters used in the file specification, but characters outside
+ the VVcode default encoding table may be corrupted when passing
+ through mail gateways or systems with differing character sets.
+
+ @item VVencode:
+ The file specification recorded in the VVE file is usually derived
+ from the input file specification stripped of any preamble or
+ postamble components and will therefore consist only of a name
+ and/or extension component. The value recorded can be explicitly
+ specified with the @code{header_filespec} command qualifier.
+
+ @item VVdecode:
+ VVdecode will use the file specification recorded to construct the
+ default file specification for the output file. If the output file
+ is specified on the VVdecode command line, the value specified on
+ the @code{begin} header will only be used if the implementation of
+ VVcode for the operating system has been defined to use "sticky
+ defaults".
+
+ The file specification may have been derived from a different
+ operating system and may therefore be invalid on the local system.
+ Before it is used VVdecode will convert the file specification to
+ one that is valid.
+
+ Processing rules:
+
+ @table @code
+ @item OK
+ If required, convert the file specification so that it is
+ legal on the local operating system and use the legal value
+ as the default file specification for the output file.
+
+ @item MISSING
+ Issue a fatal error message and stop.
+
+ @item INVALID
+ Issue a fatal error message and stop.
+ @end table
+
+ @item Example:
+ @code{begin input-file.txt}@*
+ @code{begin input file name with spaces}
+@end table
+
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: @code{bytecount}
+@c -------------------------------------------------------------------------
+@page
+@subsection @code{bytecount}
+@table @strong
+ @item Purpose:
+ Records the total number of bytes read by VVencode.
+
+ @item Location:
+ Final postamble (optional).
+
+ @item Syntax:
+ @code{bytecount <WS> total-bytes-read <WS> <EOL>}
+
+ @item Remarks:
+ The total is a positive signed 32 decimal bit number and must
+ therefore be in the range 0 - 2147483647. On systems which
+ differentiate between binary and text files, this number is likely
+ to be dependent on the mode (i.e. binary/text) used to read and
+ encode the file.
+
+ @item VVencode:
+ VVencode keeps a cumulative total of the bytes read and record this
+ total in the terminal postamble of VVE file.
+
+ @item VVdecode:
+ VVdecode keeps a cumulative total of the bytes decoded and written
+ and compare it with the VVE recorded value as a confidence check.
+
+ Processing rules:
+
+ @table @code
+ @item OK
+ Compare the VVE recorded value with the total bytes written
+ by VVdecode. Issue a warning if the two totals are
+ different.
+
+ @item MISSING
+ Don't attempt the comparison.
+
+ @item INVALID
+ Issue a non-fatal error message and assume that the header
+ is missing.
+ @end table
+
+ @item Example:
+ @code{bytecount 8388608}
+@end table
+
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: @code{characterset}
+@c -------------------------------------------------------------------------
+@page
+@subsection @code{characterset}
+@table @strong
+ @item Purpose:
+ Records the character set of the VVencoded data.
+
+ @item Location:
+ Initial preamble (optional).
+
+ @item Syntax:
+ @code{characterset <WS> charset-string <WS> <EOL>}
+
+ @item Remarks:
+ The parameter string records the character set of the encoded data
+ in the VVE file. There are no formal controls on the string to use
+ for a particular character set, the string is simply compared
+ against a local value. Eventually, an informal directory of
+ character set strings may evolve.
+
+ @item VVencode:
+ VVencode will record the character set of the encoded data which
+ under normal circumstances the character set will be the local
+ character set for the operating system. If the
+ @code{translation_file} command line qualifier is specified,
+ VVencode will translate the original data from the local character
+ set to a new character set specified by the translation file. In
+ this case, VVencode will record the new character set.
+
+ @item VVdecode:
+ VVdecode uses this header to determine whether the encoded data in
+ the VVE file is of the same character set as that used on the local
+ operating system. If the character sets are different, a warning
+ will be issued.
+
+ If the @code{translation_file} command line qualifier is specified,
+ VVdecode will translate the VVE encoded data to a new character set
+ specified by the translation file. In this case, VVdecode will
+ compare the VVE file character set with the "from" character set
+ expected by the translation file.
+
+ Processing rules:
+
+ @table @code
+ @item OK
+ Compare the VVE character set with the local operating
+ system character set (or the translation file "from"
+ character set if appropriate). Issue a warning message if
+ the two character sets are different.
+
+ @item MISSING
+ Assume that the VVE character set is the same as the local
+ operating system character set.
+
+ @item INVALID
+ Issue a non-fatal error message and assume that the header
+ is missing.
+ @end table
+
+ @item Example:
+ @code{characterset ASCII}
+@end table
+
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: @code{comment}
+@c -------------------------------------------------------------------------
+@page
+@subsection @code{comment}
+@table @strong
+ @item Purpose:
+ Records commentary information deemed to be of sufficient
+ importance to warrant displaying it when VVdecoding the file.
+
+ @item Location:
+ Initial preamble, continuation preamble, continuation postamble,
+ final postamble (optional).
+
+ @item Syntax:
+ @code{comment <WS> comment-string <EOL>}
+
+ @item Remarks:
+ The comment string is free form text, but care should be taken not
+ to use characters that may be corrupted by mail gateways or when
+ passing through systems with different character sets.
+
+ @item VVencode:
+ VVencode will record information deemed (by the programmer) to be
+ important and worth flagging to the VVdecode user. Currently this
+ facility is only used to record the original character set when
+ VVencode has been invoked with @code{translation_file} command line
+ qualifier to convert the original data to a new character set
+ before VVencoding.
+
+ @item VVdecode:
+ Generally VVdecode will display any comments encountered on the log
+ file.
+
+ Processing rules:
+
+ @table @code
+ @item OK
+ If the @code{log} command line qualifier was specified,
+ display the comment on the log file, otherwise ignore the
+ comment.
+
+ @item MISSING
+ No action.
+
+ @item INVALID
+ Issue a non-fatal error message and ignore the comment.
+ @end table
+
+ @item Example:
+ @code{comment This file is only useful on Unix systems}@*
+ @code{Original character set was `EBCDIC'}
+@end table
+
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: @code{crc32}
+@c -------------------------------------------------------------------------
+@page
+@subsection @code{crc32}
+@table @strong
+ @item Purpose:
+ Records the 32 bit CRC of the bytes read by VVencode.
+
+ @item Location:
+ Final postamble (optional).
+
+ @item Syntax:
+ @code{crc32 <WS> input-file-crc32 <WS> <EOL>}
+
+ @item Remarks:
+ The CRC value is an unsigned 32 bit hexadecimal number and must
+ therefore be in the range 0 - FFFFFFFF. On systems which
+ differentiate between binary and text files, this number is likely
+ to be dependent on the mode (i.e. binary/text) used to read and
+ encode the file.
+
+ The CRC polynomial used is the same as that used by the popular ZIP
+ and ARJ archiving programs. When encoding in binary mode, the CRC
+ recorded should be identical to that computed by ARJ and ZIP.
+
+ @item VVencode:
+ VVencode computes a 32 bit CRC of the bytes read and record this
+ CRC in the terminal postamble of VVE file.
+
+ @item VVdecode:
+ VVdecode computes a 32 bit CRC of the bytes decoded and written and
+ compare it with the VVE recorded value as a confidence check.
+
+ Processing rules:
+
+ @table @code
+ @item OK
+ Compare the VVE recorded value with the total bytes written
+ by VVdecode. Issue a warning if the two CRCs are
+ different.
+
+ @item MISSING
+ Don't attempt the comparison.
+
+ @item INVALID
+ Issue a non-fatal error message and assume that the header
+ is missing.
+ @end table
+
+
+ @item Example:
+ @code{crc32 1e0cb8a7}
+@end table
+
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: @code{decodeversion}
+@c -------------------------------------------------------------------------
+@page
+@subsection @code{decodeversion}
+@table @strong
+ @item Purpose:
+ Records the minimum major version number of VVcode required to
+ decode the VVE file.
+
+ @item Location:
+ Initial preamble (optional).
+
+ @item Syntax:
+ @code{decodeversion <WS> min-decode-version <WS> <EOL>}
+
+ @item Remarks:
+ The minimum decode version is a positive integer and records the
+ minimum major version of VVcode required to decode the VVE file.
+
+ The VVcode version number has a "major" and "minor" version. For
+ example, VVcode version 1.2 has a major version of 1 and a minor
+ version of 2 and the header
+
+ @example
+ decodeversion 2
+ @end example
+
+ signifies that VVdecode version 2.0 or later is required to decode
+ the file.
+
+ Whenever a change is made to the VVE file format that is not
+ backwards compatible, the major version number of VVcode will be
+ incremented.
+
+ @item VVencode:
+ VVencode records the minimum major version number required to
+ decode the VVE file in the initial preamble of the VVE file.
+
+ @item VVdecode:
+ VVdecode uses the recorded value to check whether it can decode the
+ file.
+
+ Processing rules:
+
+ @table @code
+ @item OK
+ Check that the major version of VVdecode is not less than
+ the recorded value. If it is, issue a fatal error message
+ and stop.
+
+ @item MISSING
+ Assume that the current version of VVdecode is OK and
+ proceed.
+
+ @item INVALID
+ Issue a non-fatal error message and assume that the header
+ is missing.
+ @end table
+
+ @item Example:
+ @code{decodeversion 1}
+@end table
+
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: @code{end}
+@c -------------------------------------------------------------------------
+@page
+@subsection @code{end}
+@table @strong
+ @item Purpose:
+ Signifies the absolute end of the VVencoded data.
+
+ @item Location:
+ Final postamble (required).
+
+ @item Syntax:
+ @code{end <WS> <EOL>}
+
+ @item Remarks:
+ This header signifies that there are no more encoded data lines to
+ process and that the terminal preamble is about to start.
+
+ @item VVencode:
+ After the complete input file has been encoded, VVencode will write
+ a "zero length" encoded line followed by the @code{end} header line
+ and the terminal postamble section.
+
+ @item VVdecode:
+ After reading this header, VVdecode will cease decoding the encoded
+ data bytes and start to read the terminal postamble.
+
+ Processing rules:
+
+ @table @code
+ @item OK
+ Cease decoding the encoded data bytes and start to read the
+ terminal postamble.
+
+ @item MISSING
+ Issue a fatal error message and stop.
+
+ @item INVALID
+ This shouldn't be possible, but if so issue a fatal error
+ message and stop.
+ @end table
+
+ @item Example:
+ @code{end}
+@end table
+
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: @code{format}
+@c -------------------------------------------------------------------------
+@page
+@subsection @code{format}
+@table @strong
+ @item Purpose:
+ Records the file organization format of the VVencoded file.
+
+ @item Location:
+ Initial preamble (optional).
+
+ @item Syntax:
+ @code{format <WS> format-string <WS> <EOL>}
+
+ @item Remarks:
+ The format string must be one of "fixed", "stream" or "variable",
+ though the value may be lower, upper or mixed case. VVcode
+ supports these three type of file organization, though not all
+ operating systems will support all three. Note that the internal
+ format of the encoded data will depend on the file organization.
+
+ @item VVencode:
+ VVencode records the organization of the encoded file. Note that
+ this is the format used by VVencode to read the file which may not
+ necessarily be the real format of the original file.
+
+ @item VVdecode:
+ VVdecode will use this header to identify the internal format of
+ the encoded data to enable it to be decoded correctly. The format
+ will also be used as the default format to create the output file.
+
+ If the VVE file format is not supported by the local operating
+ system, VVdecode will create the output file using the default file
+ format for the operating system. The @code{format} command line
+ qualifier may be used to override the format of the output file.
+
+ Processing rules:
+
+ @table @code
+ @item OK
+ Use the header value to decode the encoded data bytes and
+ to determine the default format of the output file.
+
+ @item MISSING
+ Issue a fatal error message and stop.
+
+ @item INVALID
+ Issue a fatal error message and stop.
+ @end table
+
+ @item Example:
+ @code{format stream}
+@end table
+
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: @code{mode}
+@c -------------------------------------------------------------------------
+@page
+@subsection @code{mode}
+@table @strong
+ @item Purpose:
+ Records the mode of the VVencoded file.
+
+ @item Location:
+ Initial preamble (optional).
+
+ @item Syntax:
+ @code{mode <WS> mode-string <WS> <EOL>}
+
+ @item Remarks:
+ The format string must be one of "binary" or "text", though the
+ value may be lower, upper or mixed case. VVcode supports both
+ binary and text mode files, though not all operating systems will
+ support both modes. The mode will often influence the default file
+ format used by the operating system. Most operating systems
+ distinguish between text and binary files, though Unix is a notable
+ exception.
+
+ @item VVencode:
+ VVencode records the mode of the encoded file. Note that this is
+ the mode used by VVencode to read the file which may not
+ necessarily be the real mode of the original file.
+
+ @item VVdecode:
+ VVdecode will use this header to mode of the encoded file. The
+ mode will also be used as the default mode for the output file.
+
+ If the VVE file mode is not supported by the local operating
+ system, VVdecode will create the output file using the default file
+ mode for the operating system. The @code{mode} command line
+ qualifier may be used to override the mode of the output file.
+
+ Processing rules:
+
+ @table @code
+ @item OK
+ Use the header value to determine the default mode of the
+ output file.
+
+ @item MISSING
+ Issue a fatal error message and stop.
+
+ @item INVALID
+ Issue a fatal error message and stop.
+ @end table
+
+ @item Example:
+ @code{mode binary}
+@end table
+
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: @code{operatingsystem}
+@c -------------------------------------------------------------------------
+@page
+@subsection @code{operatingsystem}
+@table @strong
+ @item Purpose:
+ Records the operating system on which the file was VVencoded.
+
+ @item Location:
+ Initial preamble (optional).
+
+ @item Syntax:
+ @code{operatingsystem <WS> operating-system-name <WS> <EOL>}
+
+ @item Remarks:
+ The parameter string records the operating system on which the
+ version of VVencode used to create the VVE file was running. There
+ are no formal controls on the string to use for a particular
+ character set, the string is simply compared against a local value.
+ The string is coded into the VVcode machine dependent header file
+ so this shouldn't be too much of a problem.
+
+ It is useful for the decoder to know whether the file was encoded
+ on the same operating system to influence the decoding process.
+ For example, if the original operating system is different any
+ private data would usually be ignored.
+
+ @item VVencode:
+ VVencode will record the string for the local operating system as
+ coded in the machine dependent header file (machine.h).
+
+ @item VVdecode:
+ VVdecode will compare the header value with that recorded for the
+ local operating system in the machine dependent header file
+ (machine.h) to determine whether the original file was encoded on
+ the same operating system.
+
+ Processing rules:
+
+ @table @code
+ @item OK
+ Compare the header value with the local operating system
+ string to determine whether the two operating systems are
+ different. Parts of the decoding process will be affected
+ by this decision.
+
+ @item MISSING
+ Assume that the operating system on which the file was
+ encoded is the same as the local operating system.
+
+ @item INVALID
+ Issue a non-fatal error message and assume that the header
+ is missing.
+ @end table
+
+ @item Example:
+ @code{operatingsystem MS-DOS}@*
+ @code{operatingsystem Unix}
+@end table
+
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: @code{recordlength}
+@c -------------------------------------------------------------------------
+@page
+@subsection @code{recordlength}
+@table @strong
+ @item Purpose:
+ Records the maximum and longest length records in the VVencoded
+ file.
+
+ @item Location:
+ Initial preamble (optional).
+
+ @item Syntax:
+ @code{recordlength <WS> max-rec-len <WS> long-rec-len <WS> <EOL>}
+
+ @item Remarks:
+ Both versions of the record length must be either a decimal number
+ within the VVcode supported range of 0 - 65535 or -1. The value -1
+ has a special meaning for each of the record lengths:
+
+ max-rec-len the maximum record length is unknown or there is no
+ explicit maximum record length for this file
+ (this usually defaults to the maximum record
+ length supported by the operating system).
+
+ lng-rec-len the length of the longest record in the file is
+ unknown.
+
+ The record length is usually relevant only for fixed and variable
+ length record format files. The maximum record length is that
+ allowed by the operating system for the file, whereas the longest
+ is the length of the longest record in the file. For variable
+ length record files the longest length must be less than or equal
+ to the maximum record length, whereas for fixed length record
+ files, the longest record length should be equal to the maximum
+ record length.
+
+ @item VVencode:
+ Where possible, VVencode will attempt to determine these parameters
+ and record them in the VVE file. Note that the @code{recordlength}
+ header is in the initial preamble so these parameters must be
+ determined before the file is opened for encoding. The value may
+ be overridden by the @code{record_length} command line qualifier.
+
+ @item VVdecode:
+ If the output file format is fixed or variable length records,
+ Vvdecode will use these values to create a file of the correct
+ type. The parameter values will be checked, even if they will not
+ be used during the subsequent decoding activities. If the
+ parameter values are unknown or invalid, VVdecode will use default
+ values appropriate to the file format and the local operating
+ system.
+
+ Note that the record length might be valid for the VVE file (i.e.
+ in the range 0 - 65535), but be invalid for the file format and
+ local operating system.
+
+ Processing rules:
+
+ @table @code
+ @item OK
+ Use the values to create a file of the correct type and
+ format.
+
+ @item MISSING
+ Use appropriate default values for the file format and
+ local operating system.
+
+ @item INVALID
+ Issue a non-fatal error message and assume that the header
+ is missing.
+ @end table
+
+ @item Example:
+ @code{recordlength -1 132}@*
+ @code{recordlength 255 -1}@*
+ @code{recordlength 32256 32256}
+@end table
+
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: @code{skipfrom}
+@c -------------------------------------------------------------------------
+@page
+@subsection @code{skipfrom}
+@table @strong
+ @item Purpose:
+ Signifies the start of a segment of VVencoded data.
+
+ @item Location:
+ Continuation preamble (required).
+
+ @item Syntax:
+ @code{skipfrom <WS> part-number <WS> file-specification <EOL>}
+
+ @item Remarks:
+ The @code{skipfrom} header is used when VVencode creates a
+ multi-part VVE file and is analogous to the @code{begin} header in
+ the first part. The part-number parameter records the number of
+ the previous VVE file part. Both parameters are included in the
+ header to provide a reasonable degree of confidence that the wanted
+ part of the encoded file has been found.
+
+ @item VVencode:
+ A @code{skipfrom} header will only be written if VVencode was
+ invoked with the @code{split_size} command line qualifier and the
+ VVE file is long enough to require more than one part. The file
+ specification recorded in the VVE file is the same as that in the
+ @code{begin} header. The number of the previous VVE file part is
+ also recorded.
+
+ @item VVdecode:
+ VVdecode will check that the file specification and part number
+ match those expected for the next part. If both do not match,
+ VVdecode will continue to look for the wanted VVE file part.
+
+ Processing rules:
+
+ @table @code
+ @item OK
+ If the wanted part has been found, start to decode the next
+ section of encoded data lines. If this @code{skipfrom}
+ does not correspond to the wanted part, continue to search
+ for the correct @code{skipfrom} header.
+
+ @item MISSING
+ Issue a fatal error message and stop.
+
+ @item INVALID
+ Issue a non-fatal error message and ignore the header.
+ @end table
+
+ @item Example:
+ @code{skipfrom 2 input-file.txt}@*
+ @code{skipfrom 2 file name with spaces}
+@end table
+
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: @code{skipto}
+@c -------------------------------------------------------------------------
+@page
+@subsection @code{skipto}
+@table @strong
+ @item Purpose:
+ Signifies the end of a segment of VVencoded data with more data
+ still to come.
+
+ @item Location:
+ Continuation postamble (required).
+
+ @item Syntax:
+ @code{skipto <WS> part-number <WS> <EOL>}
+
+ @item Remarks:
+ The @code{skipto} is used when VVencode creates a multi-part VVE
+ file and is analogous to the @code{end} header in the last part.
+ The parameter records the number of the next VVE file part.
+
+ @item VVencode:
+ A @code{skipto} header will only be written if VVencode was invoked
+ with the @code{split_size} command line qualifier and the VVE file
+ is long enough to require more than one part. The number of the
+ next VVE file part is recorded.
+
+ After the section of encoded files has been completed, VVencode
+ will write a "zero length" encoded line followed by the @code{skipto}
+ header line.
+
+ @item VVdecode:
+ After reading this header, VVdecode will check that the part number
+ recorded is correct. If it is, VVdecode will start to search for
+ the next VVE file part.
+
+ Processing rules:
+
+ @table @code
+ @item OK
+ Start to search for the next VVE file part.
+
+ @item MISSING
+ Issue a fatal error message and stop.
+
+ @item INVALID
+ Issue a fatal error message and stop.
+ @end table
+
+ @item Example:
+ @code{skipto 2}
+@end table
+
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: @code{table}
+@c -------------------------------------------------------------------------
+@page
+@subsection @code{table}
+@table @strong
+ @item Purpose:
+ Records the character table used to encode the file data bytes.
+
+ @item Location:
+ Initial preamble, continuation preamble (optional).
+
+ @item Syntax:
+ @code{table <WS> table-contents <NXT-HDR>}
+
+ @item Remarks:
+ The encoding table is recorded along with the data to enable the
+ decoding program to detect any simple character translations or
+ corruptions that may have occurred during the transmission of the
+ VVE file. There is no restriction on the characters that may be
+ used in the encoding table, but it is sensible to use characters
+ that are normally immune to network corruptions.
+
+ The table comprises 64 characters which are used to represent the
+ codes 0 - 63 of the VVcode encoding character set. The table
+ contents may be presented on the same line as the @code{table}
+ header or preferably split over several lines to avoid the wrapping
+ of long lines performed by some mail gateways. If the table
+ contents are split over several lines, the newline characters are
+ removed before the lines are concatenated. The next valid header
+ line encountered will terminate the reading of the table contents.
+
+ Note that whitespace characters at the end of a line may be removed
+ in transmission by certain systems that strip trailing whitespace
+ from files. It is strongly recommended that whitespace characters
+ are not used in encoding tables.
+
+ @item VVencode:
+ VVencode will record the contents of the encoding table used to
+ encode the original file.
+
+ @item VVdecode:
+ VVdecode will use the contents of the encoding table to construct
+ (by inversion) the table to decode the VVE file data. The table
+ contents will be checked for length and repeated characters which
+ would prevent the construction of a valid decoding table.
+
+ Processing rules:
+
+ @table @code
+ @item OK
+ Use the table contents to construct the decoding table and
+ thus decode the VVE file.
+
+ @item MISSING
+ Assume the default VVcode table.
+
+ @item INVALID
+ Issue a fatal error message and stop.
+ @end table
+
+ @item Example:
+ @code{table}@*
+ @code{+-0123456789}@*
+ @code{abcdefghijklmnopqrstuvwxyz}@*
+ @code{ABCDEFGHIJKLMNOPQRSTUVWXYZ}@*
+ @code{begin file-specification}
+@end table
+
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: @code{timestamp}
+@c -------------------------------------------------------------------------
+@page
+@subsection @code{timestamp}
+@table @strong
+ @item Purpose:
+ Records the modification time of the VVencoded file.
+
+ @item Location:
+ Initial preamble (optional).
+
+ @item Syntax:
+ @code{timestamp <WS> VVcode-timestamp <WS> <EOL>}
+
+ @item Remarks:
+ This header is used to record the modification time of the encoded
+ file so that it can be preserved when the file is decoded. The
+ timestamp is recorded in the format:
+
+ @example
+ YYYY.MM.DD-HH:MM:SS
+ @end example
+
+ where each of the components are defined as:
+
+ @table @code
+ @item YYYY
+ year (range: 1970 - 2037)
+ @item MM
+ month (range: 01 -12)
+ @item DD
+ day of month (range: 01 - 31)
+ @item HH
+ hour (range: 00 - 23)
+ @item MM
+ minutes (range: 00 - 59)
+ @item SS
+ seconds (range: 00 - 59)
+ @end table
+
+ The time is based on the Unix internal time format which represents
+ the time as a signed 32 bit integer recording the number of seconds
+ since 1-Jan-1970 00:00 GMT. The VVE timestamp recorded must be in
+ the range:
+
+ 1970.01.01-00:00:00 to 2037.12.31-23:59:59 GMT
+
+ Some operating systems support a wider range of system times (e.g.
+ VAX/VMS) and some support only a narrower range (e.g. MS-DOS) but
+ implementations of VVcode for these systems must ensure that
+ timestamps in the VVcode range can be handled when encoding and
+ decoding.
+
+ Note: The timestamp is always recorded as a GMT (or Coordinated
+ Universal Time) time.
+
+ @item VVencode:
+ VVencode will record the modification time of the encoded file or
+ that specified with the @code{timestamp} command line qualifier.
+ If VVencode cannot determine the modification time of the encoded
+ file and the time is not specified using the @code{timestamp}
+ command line qualifier, the @code{timestamp} VVE header line will
+ not be recorded. If the timestamp of the file is outside the range
+ of times supported by the VVE file, VVencode should either
+ "truncate" the time value to a value that is within the range or
+ not record the timestamp. In either case, a warning should be
+ issued.
+
+ @item VVdecode:
+ VVdecode will use the @code{timestamp} header value to set the
+ modification of the decoded file to that recorded. If the
+ implementation of VVdecode is unable to do this, it should issue a
+ warning.
+
+ If the timestamp recorded in the VVE file is outside the range of
+ times supported by the operating system, VVdecode should either
+ "truncate" the time value to a value that is within the range or
+ not set the file timestamp. In either case, a warning should be
+ issued.
+
+ Processing rules:
+
+ @table @code
+ @item OK
+ Use the header value to set the modification time of the
+ decoded file.
+
+ @item MISSING
+ Do not attempt to set the modification time of the output
+ file (it will probably be created with a timestamp of the
+ current date and time).
+
+ @item INVALID
+ Issue a non-fatal error message and assume that the header
+ is missing.
+ @end table
+
+ @item Example:
+ @code{timestamp 1991.12.01-12:10:34 GMT}
+@end table
+
+
+@c =========================================================================
+@c SECTION: VVE encoded data format
+@c =========================================================================
+@section VVE encoded data format
+
+
+@c =========================================================================
+@c SECTION: XLT translation file format
+@c =========================================================================
+@section XLT translation file format
+
+
+@c =========================================================================
+@c SECTION: TBL encoding table file format
+@c =========================================================================
+@section TBL encoding table file format
+
+
diff --git a/support/vvcode/doc/vvinstal.tex b/support/vvcode/doc/vvinstal.tex
new file mode 100644
index 0000000000..58700b0e5a
--- /dev/null
+++ b/support/vvcode/doc/vvinstal.tex
@@ -0,0 +1,17 @@
+@c *************************************************************************
+@c CHAPTER: Installing VVcode
+@c *************************************************************************
+@c node-name, next, previous, up
+@node Installing, Installing, Top, Top
+@chapter Installing VVcode
+
+
+@c =========================================================================
+@c SECTION: File distribution
+@c =========================================================================
+@section{File distribution}
+
+@c =========================================================================
+@c SECTION: Installation examples
+@c =========================================================================
+@section{Installation examples}
diff --git a/support/vvcode/doc/vvintro.tex b/support/vvcode/doc/vvintro.tex
new file mode 100644
index 0000000000..303a08ce48
--- /dev/null
+++ b/support/vvcode/doc/vvintro.tex
@@ -0,0 +1,483 @@
+@c *************************************************************************
+@c CHAPTER: Introduction to VVcode
+@c *************************************************************************
+@c node-name, next, previous, up
+@node Introduction, Introduction, Top, Top
+@chapter Introduction to VVcode
+
+Reliable and faithful exchange of binary files between computers over
+networks is a well-known problem, especially if the computers use different
+operating systems and are connected to different networks via a gateway.
+Unfortunately inter-networking and electronic mail are very much children
+of the 1960s: they might have had to wait until the 1970s for their
+naissance, but their progenitors were mentally locked-in to the concept of
+the 7-bit ASCII code for conveying textual information. The @TeX{}
+community has long been aware of this problem when trying to exchange
+``machine-independent'' @file{.dvi} files and font-related data such as
+@file{.tfm} and @file{.pk} files. It has sometimes been possible to
+exchange this binary data by using encoding schemes that allow the data to
+be represented using a subset of the seven-bit ASCII character set.
+
+Academics and authors in many fields have hitherto been able to pass
+@file{.tex} files back-and-forth by electronic mail---apart from a few
+minor quirks and blemishes, such @TeX{} source files pass unharmed across
+the planet's networks. Problems are encountered when mail passes through
+certain gateway machines which introduce irreversible character
+corruptions. Particularly notorious is the Janet/Bitnet gateway
+which has the unfortunate habit of converting @samp{^} to @samp{~} and
+@samp{~} to @samp{%}: since it leaves @samp{%} itself unaffected, this
+makes recovery of the original file a non-trivial exercise. It sometimes
+also changes the brace characters @samp{@{@}} into odd characters above
+128: this is particularly embarrassing, of course, for @file{.tex} files!
+
+For some years many @TeX{} users, particularly those working in languages
+other than English, and thus familiar with character set encodings
+containing other than the basic ASCII set, have been agitating for
+@TeX{} to be able to handle input in their mother tongues, using their own
+languages' character sets. In 1989, Knuth announced @TeX{} V3, and
+implementors world-wide beavered away to bring each implementation
+up-to-date. @TeX{} V3 now supports eight-bit character sets and so
+@file{.tex} source files are now effectively `binary' files and will
+therefore suffer from the same exchange problems experienced with
+@file{.dvi} files.
+
+All those authors that had previously been able to cooperate, despite being
+separated by hundreds or thousands of miles, might once again be forced to
+entrust floppy disks to the vagaries of the world's postal systems
+(although one shouldn't underestimate the bandwidth of the Royal [or other]
+Mail system).
+
+Unless or until the various e-mail protocols, networks and software are
+converted to support uncorrupted transmission of characters codes
+@code{0x20 @dots{} 0x7e} and @code{0xa1 @dots{} 0xfe}, it will have to
+become the norm for @file{.tex} sources to be encoded for transmission by
+e-mail.
+
+This problem is of course well known outside the @TeX{} community.
+
+
+@c =========================================================================
+@c SECTION: The Aston Archive
+@c =========================================================================
+@section{The Aston Archive}
+The author is a volunteer assistant to Peter Abbott in running the world's
+principal repository of @TeX{}-related material at Aston University in
+Birmingham. The archive (host: @code{TeX.Ac.Uk}) holds several hundred
+megabytes of text and binary files including:
+
+@itemize @bullet
+ @item program sources for @TeX{}, @code{METAFONT}, DVI drivers and many
+ other utilities;
+ @item binary executables for a variety of popular operating systems (e.g.
+ Atari, Macintosh, MS-DOS, Unix, VAX/VMS and VM/CMS);
+ @item @code{METAFONT} sources for Computer Modern and other fonts;
+ @item binary font files (mainly @file{.tfm} and @file{.pk}) for a number of
+ different output devices;
+ @item text macro and style files.
+@end itemize
+
+The archive provides access to these files via the following services:
+
+@itemize @bullet
+ @item NIFTP@footnote{Network Independent File Transfer Protocol --- in the
+ UK, one does not perform the pseudo-login that
+ Internet users are accustomed to using with the FTP
+ protocol: instead, one issues a ``transfer request''
+ for a file to be sent to or from the remote
+ machine --- the transfer itself takes place
+ asynchronously. One nice consequence is that such
+ transfers can be queued for overnight execution,
+ leaving daytime bandwidth free for e-mail and true
+ remote interactive logins.}
+ from Janet hosts---typically 300 megabytes of data are transferred
+ every month; this would probably be much greater if we were not
+ limited by the bandwidth of our 9600Bd connection to Janet.
+ @item FTP and Telnet access from Internet hosts.
+ @item Interactive browsing service via Janet PAD, including the facility
+ to send files out using NIFTP (and later FTP).
+ @item Interactive browsing service via dialup modem lines, including the
+ facility to download files using Kermit and similar protocols.
+ @item An e-mail file server which typically sends 150 megabytes of data per
+ month to sites all over the world (though predominantly to
+ EARN/Bitnet sites).
+ @item A magnetic media distribution service via surface carriers.
+ Copies of the entire archive have been sent to embryonic @TeX{}
+ communities in Czechoslovakia, Hungary and Poland.
+@end itemize
+
+We have experienced many problems trying to support all of these file
+types, operating systems and access methods. The e-mail file server
+clearly needs a reliable method of encoding files if its many customers are
+not to be denied access to the non-text files in the archive.
+
+Binary files such as @file{.pk} font files are stored in different ways to
+accommodate the requirements of the different operating systems supported.
+Currently we maintain multiple font directory trees for the Macintosh,
+MS-DOS, Unix and VAX/VMS with all the attendant problems of
+synchronization, disk space and archivists' time. We need a single storage
+format which allows export to all of our supported operating systems.
+
+
+@c =========================================================================
+@c SECTION: Specification for a Coding Scheme
+@c =========================================================================
+@section{Specification for a Coding Scheme}
+In mid-1990, the archivists came to the conclusion that a universal
+encoding scheme was required to accommodate the many different kinds of
+file and file organizations that needed to be supported by the archive.
+
+Niel Kempson formulated the first draft of this specification in mid-1990;
+the requirements of the encoding scheme may be summarized as follows:
+
+@table @strong
+ @item Preserving File Structure
+ It is insufficient, especially for an archive holding text and
+ binary files for a variety of machine types, merely to encode data
+ simply as a stream of bytes:
+
+ @itemize @bullet
+ @item Virtually all operating systems (except Unix) make a
+ distinction between binary and text files, so the coding
+ system should recognize and maintain this distinction.
+ @item Unix and most PC-based operating systems treat files as
+ streams of bytes with no further structure imposed. On the
+ other hand, certain widely-used operating systems (e.g.
+ VAX/VMS and VM/CMS) have record-oriented file systems where
+ different types of file are stored in a format appropriate to
+ the type of file@footnote{It is often argued that the
+ increase in efficiency more than offsets the increase in
+ complexity.}.
+
+ For these operating systems, we consider it essential that
+ the encoding scheme should identify, preserve and record the
+ most commonly used file organizations. The decoding program
+ should be able to use this information to create the output
+ file using the organization appropriate to the operating
+ system in use. If the information is of no consequence to
+ the receiving system, the default file structure (if any)
+ should be created. If the encoding system does not have
+ structure in its files, the receiving system may provide
+ suitable defaults automatically. In all cases the programs
+ should permit the user to override or supplement file
+ structure information.
+
+ @item Whenever possible, these details of structure should be
+ determined automatically by the encoding program; at the very
+ least, an indication of whether the file is text or binary
+ shall be provided, even under an operating system such as
+ Unix that need make no such distinction for its own use, to
+ allow decoding to an appropriate file organization on those
+ systems that {@emph do} make such a distinction.
+ @end itemize
+
+ @item Coding Scheme
+ Whatever method is used must allow encoded data to be e-mailed:
+
+ @itemize @bullet
+ @item It should be possible to specify the coding table to be used
+ to encode the data. The coding table used shall be recorded
+ with each part of the encoded data.
+ @item If a recorded coding table is found while decoding, it should
+ be used to construct an appropriate decoding table. Simple
+ one-to-one character corruptions should be corrected as long
+ as only one of the input characters is mapped to any one
+ output character.
+ @item The recommended encoding uses only the following characters:
+ @quotation
+ @code{+-0123456789}@*
+ @code{abcdefghijklmnopqrstuvwxyz}@*
+ @code{ABCDEFGHIJKLMNOPQRSTUVWXYZ}
+ @end quotation
+
+ Such an encoding as originally used for XXcode has been shown
+ to pass successfully through all the gateways which are known
+ to corrupt characters.
+ @end itemize
+
+ @item Integrity of Encoded Data
+ We want to ensure that the @emph{whole} encoded file passes through
+ the e-mail network.
+
+ @itemize @bullet
+ @item Encoded lines should be prefixed by an appropriate character
+ string to distinguish them from unwanted lines such as mail
+ headers and trailers. Whilst not essential, this feature
+ does assist the decoding program in ignoring these spurious
+ data.
+ @item Lines should not end with whitespace characters as some
+ mailers and operating systems strip off trailing whitespace.
+ @item The encoding program should calculate parameters of the input
+ file such as the number of bytes and CRC and record them at
+ the end of the encoded data.
+
+ The decoding program should calculate the same parameters
+ from the decoded data and compare the values obtained from
+ those recorded at the end of the encoded data.
+ @end itemize
+ @item Making Files Mailable
+ A mechanism is needed to overcome some gateways' refusal to handle
+ large files.
+
+ @itemize @bullet
+ @item The encoding program should be able to split the encoded
+ output into parts, each no larger than a maximum specified
+ size. Splitting the output into smaller parts is useful if
+ the encoded data is to be transmitted using electronic mail
+ or over unreliable network links that do not stay up long
+ enough to transmit a large file. The recommended default
+ maximum part size is 30kB.
+ @item The decoding program should be able to decode a multi-part
+ encoded file very flexibly. It should @emph{not} be
+ necessary to:
+
+ @enumerate
+ @item strip out mail headers and trailers;
+ @item combine all of the parts into one file in the
+ correct order;
+ @item process each part of the encoded data as a
+ separate file.
+ @end enumerate
+ @item In addition any file specifications from the operating system
+ on which the VVE file was created must not prevent the file
+ from being decoded.
+ @end itemize
+
+ @item Miscellaneous
+ Further considerations include:
+
+ @itemize @bullet
+ @item Support for character sets other than ASCII is essential
+ if the encoding scheme is to be useful to IBM hosts. The
+ encoding program should label the character set used by the
+ encoded data, and both encoder and decoder should enable the
+ conversion between the local character set and another
+ character set. For example a user on an EBCDIC host
+ should be able to encode text files for transmission to another
+ EBCDIC host, or to convert them to ASCII before
+ encoding and transmission to an ASCII host. Similarly,
+ that user should be able to decode text files from ASCII
+ and EBCDIC machines, creating EBCDIC output files.
+ @item Where possible, the original file's timestamp should be encoded
+ and used by the decoding program when recreating the file: this
+ will permit archives to retain the originator's time of
+ creation for files, and thus permit the users (not to mention
+ the archivists) to identify more clearly when a new version of
+ a file has been made available. Timezones should be supported
+ where possible.
+ @item The encoding and decoding schemes should be able to read and
+ write files that are compatible with one or more of the well
+ established coding schemes (e.g. UUcode, XXcode).
+ @item The source code for the programs should be freely available.
+ It should also be portable and usable with as many computers,
+ operating systems and compilers as possible.
+ @end itemize
+@end table
+
+
+@c =========================================================================
+@c SECTION: The Search Commences
+@c =========================================================================
+@section{The Search Commences}
+Naturally, the first step was to examine the existing coding schemes in
+comparison with the above ideal specification. Such schemes fell into two
+broad classes: @dfn{portable schemes}, which were intended to permit the
+encoding of files on any computer architecture into a form that could be
+transmitted electronically, and decoded on the same or a different
+architecture; and @dfn{platform-specific schemes}, which provided rather
+better support for transferring files between two computers using the same
+architecture and operating system.
+
+@subsection{Portable Coding Schemes}
+The most commonly used coding schemes supported by a variety of platforms
+are:
+
+@itemize @bullet
+ @item @code{BOO}
+ @item @code{UU}
+ @item @code{XX}
+@end itemize
+
+Most implementations of these schemes known to the authors are designed for
+use with stream file systems. These programs have no means of recording,
+let alone preserving, record structure and are thus unsuitable for our
+purposes. This is not surprising since @code{UUcode} and its mutation
+@code{XXcode} were developed specifically for exchanging files between Unix
+systems. In fairness to these schemes, they are well suited to the
+transmission of text files and certain unstructured binary files.
+
+Standard @code{UUcode} encodes files using characters @samp{ } @dots
+@samp{_} of ASCII. This can result in one or more spaces appearing at
+the ends of lines: some mailers decide that this is information not worth
+transmitting, with consequent inability to reconstruct the original file.
+
+Files containing characters such as @samp{^} are often irreversibly
+corrupted by mail gateways; this problem led to the development of
+@code{XXcode} which uses a rather more robust character set, namely:
+
+@quotation
+ @code{+-0123456789}@*
+ @code{abcdefghijklmnopqrstuvwxyz}@*
+ @code{ABCDEFGHIJKLMNOPQRSTUVWXYZ}
+@end quotation
+
+The encoding table used is recorded with the encoded data to allow the
+detection of character corruptions, and the correction of reversible
+character transpositions. Whilst superficially a step forward,
+@code{XXcode} offered little more than most existing versions of
+@code{UUcode}, which already supported coding tables. Its major
+contribution was in formalizing the encoding table, and in particular its
+default table was proof against all the known gateway-induced corruptions.
+
+
+@subsection{Platform Specific Coding Schemes}
+
+Encoding schemes have been developed to support transfer of files
+possessing some structure which therefore cannot be reconstructed correctly
+when encoded by the portable schemes. When the encoding and decoding
+programs of such a platform specific scheme are each used on the same
+computer and operating system type, files may be encoded and transmitted
+with a great deal of confidence that the decoded file will reproduce the
+original's structure and attributes in their entirety.
+
+Examples of such programs are @code{TELCODE} and @code{MFTU} for VMS,
+@code{NETDATA} for IBM mainframes, and @code{Stuffit} and @code{MacBinary}
+for the Macintosh. But these programs have the major disadvantage that
+they have each been implemented @emph{only} on the single architecture for
+which they were designed: thus the only two of these schemes that could be
+used on the VMS-based Aston Archive would be of minimal interest elsewhere!
+
+The Archive's content is in some respects artificially inflated by the
+presence of @file{.hqx} files for Macintoshes, @file{.boo} for MS-DOS,
+etc., which have to be held in pre-encoded form for transfer by those
+requiring them.
+
+
+@c =========================================================================
+@c SECTION: VVcode is Born
+@c =========================================================================
+@section{VVcode is Born}
+
+Realizing that none of the existing portable schemes were close enough to
+our ideal, an early version of our specification was circulated on various
+mailing lists by Niel Kempson towards the end of 1990. When the anticipated
+``nil return'' was all that resulted, Brian Hamilton Kelly went ahead and
+created a rudimentary @code{VVencode} by modifying an existing VAX Pascal
+implementation of @code{uuencode}. After generating the companion
+@code{VVdecode}, he then re-implemented the programs in Turbo C under the
+MS-DOS operating system on the IBM-PC, and thereby was able to prove that
+the new scheme was both viable and sufficient.
+
+This version didn't support file formats, time stamping, file splitting,
+character sets or CRC checking.
+
+
+@subsection{A Production VVcode}
+
+Following the minor feasibility study, Niel Kempson re-engineered the pair
+of programs from scratch (adding certain features of the evolving
+specification), paying particular attention to making the code portable
+across a wide variety of operating systems. Particular care was taken to
+avoid the use of supposedly ``standard'' C functions that experience had
+shown behaved differently under individual manufacturer's implementations,
+or were even non-existent in some. Therefore the code may sometimes appear
+to be performing certain operations in a very long-winded way; it's very
+easy to look at it and say ``why didn't the author use the @code{foo()}
+function, which does this much more efficiently?'', but this function may
+not even exist under another implementation of C, or behave in a subtly
+different manner.
+
+The core functions of @code{VVcode} are implemented as a collection of
+routines written in as portable a fashion as possible, and a separate
+module of a few operating system specific routines for file I/O,
+timestamping, command-line or other interface, etc. Porting @code{VVcode}
+to a new platform should require only that this latter module be
+re-implemented, in most cases by adapting an existing one.
+
+@code{VVcode} implements all of the features listed in the specification,
+apart from the ability to generate @code{UUcode} and @code{XXcode}
+compatible files. However, the decoding program is backwards compatible
+and can decode files generated by @code{UUcode} and @code{XXcode}.
+
+
+@subsection{Arguments against VVcode}
+
+When the advent of the @code{VVcode} system was first aired in the various
+electronic digests, some heated debate followed along the lines that a new
+encoding scheme was unnecessary, since @code{UUcode}/@code{XXcode} sufficed
+@emph{for them}. However, all these correspondents were Unix users who had
+interpreted the @samp{VV} as meaning ``Vax-to-Vax'' by analogy with
+@samp{uu}@footnote{@samp{V} was chosen simply because it followed @samp{U};
+at one time, we'd seriously considered calling it @code{YAFES} --- Yet
+Another File Encoding Scheme!} and who felt that such a scheme should be
+private to VAXen. The authors' reply was to the effect that the encoding
+scheme was intended to support the needs of archives like Aston's, and as
+such, had to provide
+
+@enumerate
+ @item an automated tool (it would be somewhat difficult to expect our
+ users to be able to tell the encoder what sort of file structure
+ it was handling, when this concept was entirely alien to many of
+ them);
+ @item facilities to encode binaries for many operating systems;
+ @item mail server features, such as splitting of large files;
+ @item operation across the widest possible combination of platforms.
+@end enumerate
+
+The overhead of using the @code{VVcode} system is at most a couple of
+hundred bytes over using @code{UUcode}, and the extra functionality and
+@emph{universality} with respect to @code{UUcode} or @code{XXcode} thereby
+comes almost for free.
+
+
+@c =========================================================================
+@c SECTION:
+@c =========================================================================
+@section{Availability of VVcode}
+
+At present, the @code{VVcode} system is only available in C, but it has
+been shown to run successfully on the following combinations of hardware,
+operating system and compiler:
+
+@table @strong
+ @item Macintosh
+ At the time of writing (May 1991) John Rawnsley of the University
+ of Warwick had commenced development of a Macintosh port, which
+ will encode the resource and data forks in a manner that will
+ permit the former to be ignored by non-Macintosh systems.
+
+ @item MS-DOS
+ @itemize @bullet
+ @item IBM PS/2, PC (and clones); MS-DOS 3.3, 4.01, 5.00;
+ Borland Turbo C 1.5, 2.0, Borland C++ 1.0, 2.0, 3.0 and
+ Microsoft C 5.1, 6.0
+ @end itemize
+
+ @item OS/2
+ @itemize @bullet
+ @item IBM PS/2, PC (and clones); OS/2 2.0; Microsoft C 6.0 and
+ GNU C 2.1
+ @end itemize
+
+ @item Unix
+ @itemize @bullet
+ @item Sun 3; SunOS 3.x and 4.0.3; native C and GNU C
+ @item Sun Sparcstation 1; SunOS 4.1; native C and GNU C
+ @item SCO Unix V/386 v3.2.2, Microsoft C compiler
+ @end itemize
+
+ @item VAX/VMS
+ @itemize @bullet
+ @item All VAXen; VMS 5.2--5.4-1; VAX C V3.0--V3.2 and GNU C 1.40
+ @end itemize
+
+ @item VM/CMS
+ @itemize @bullet
+ @item VM/CMS; Whitesmith C compiler v1.0 (This implementation was
+ ported by Rainer Sch@"opf; basing it upon the Unix
+ implementation, this took him about one day.)
+ @end itemize
+
+@end table
+
+
+
diff --git a/support/vvcode/doc/vvport.tex b/support/vvcode/doc/vvport.tex
new file mode 100644
index 0000000000..a385c5644d
--- /dev/null
+++ b/support/vvcode/doc/vvport.tex
@@ -0,0 +1,704 @@
+@c *************************************************************************
+@c CHAPTER: How to port VVcode to a new environment
+@c *************************************************************************
+@c node-name, next, previous, up
+@node Porting Guide, Porting Guide, Top, Top
+@chapter How to port VVcode to a new environment
+
+This chapter introduces the facilities provided for porting VVcode to a new
+environment and recommends the approach that should be taken for particular
+examples.
+
+@itemize @bullet
+ @item introduction and philosophy
+ @item @file{machine.h}
+ @item @file{specific.h} and @file{xxx.c}
+ @item local.h
+@end itemize
+
+
+
+
+@c =========================================================================
+@c SECTION: The @file{os.h} header file
+@c =========================================================================
+@c node-name, next, previous, up
+@section The @file{os.h} header file
+
+The @file{os.h} file contains tests to identify the environment on which
+VVcode is being built. Once the environment has been identified the file
+defines preprocessor macros to define the environment in the format
+expected by VVcode. Environments are defined as the operating system and
+variants due to dialects of the operating system or the compiler.
+
+@itemize @bullet
+ @item explain the @samp{OS_xxxx} macros, including the operating systems
+ currently supported
+ @item explain the @samp{UNIX_yyyy} and related macros
+@end itemize
+
+
+
+@c =========================================================================
+@c SECTION: The @file{machine.h} header file
+@c =========================================================================
+@c node-name, next, previous, up
+@section The @file{machine.h} header file
+
+The header file @file{machine.h}
+
+@itemize @bullet
+ @item defines macros to control the behaviour and compilation of VVcode
+ @item several categories of definition required:
+
+ @itemize @bullet
+ @item environment
+ @item command line interface
+ @item file specifications
+ @item file formats
+ @end itemize
+@end itemize
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: VVcode environment
+@c -------------------------------------------------------------------------
+@subsection VVcode Environment
+
+@itemize @bullet
+ @item definitions for the environment in which VVcode is built
+@end itemize
+
+@subsubsection @code{VV_OPERATING_SYSTEM}
+
+A string recording the operating system for which this version of VVcode
+has been implemented. This value is recorded in the VVE file and used by
+VVdecode to detect whether the original file was encoded on a different
+operating system. For example:
+
+@example
+#define VV_OPERATING_SYSTEM "MS-DOS"
+@end example
+
+
+@subsubsection @code{VV_IMPLEMENTATION}
+
+A string describing the implementation of VVcode. Displayed when VVcode
+programs are started and recorded in log and VVE files. For example:
+
+@example
+#define VV_IMPLEMENTATION "MS-DOS Turbo-C version 09.1-001 (31 May 1992)"
+@end example
+
+
+@subsubsection @code{ANSI_SYNTAX}
+
+Define as @code{TRUE} if the compiler supports the draft ANSI standard for
+C syntax (it shouldn't matter if the run time library is not fully ANSI
+compliant). Define as @code{FALSE} if this syntax is not supported. The
+macro is used to control the declaration of functions and the use of new
+ANSI keywords such as @samp{const}. If your compiler requires old-style
+function declarations like:
+
+@example
+char *allocate_buffer (); /* Declaration */
+...
+char *allocate_buffer (buf_len, buf_name) /* Function code */
+ size_t buf_len;
+ char *buf_name;
+@{
+...
+@}
+@end example
+
+you should define @code{ANSI_SYNTAX} to @code{FALSE}. Many Unix systems
+have compilers that fall into this category, though the GNU C compiler is a
+notable exception. If you have a modern compiler that accepts ANSI style
+function declarations like:
+
+@example
+char *allocate_buffer (const size_t buf_len, /* Declaration */
+ const char *buf_name);
+...
+char *allocate_buffer (const size_t buf_len, /* Function code */
+ const char *buf_name)
+@{
+...
+@}
+@end example
+
+you should define @code{ANSI_SYNTAX} to @code{TRUE}. The GNU C compiler
+and most of the PC compilers support the ANSI standard.
+
+
+@c -------------------------------------------------------------------------
+@c SECTION: VVcode Command Line Interface
+@c -------------------------------------------------------------------------
+@subsection{VVcode Command Line Interface}
+
+@itemize @bullet
+ @item defines how to start VVcode and how it interprets the command line
+ @item explain concepts of @dfn{parameters} and @dfn{qualifiers}
+ @item @dfn{parameters} -
+ @item @dfn{qualifiers} - modify the behaviour of a command#
+ @item give an example and compare the commands @code{rm -i foo} and
+ @code{delete /confirm foo}
+ @item this does not preclude implementations that may not usually use
+ a command line interface (e.g. Mac). For example VMS does use a
+ CLI but provides a set of system services to handle the CL. Under
+ these circumstances these definitions will only be used to display
+ help text in the correct format
+@end itemize
+
+@subsubsection @code{QUAL_INTRO}
+
+A string containing a set of characters, each of which may be used to
+introduce a command line qualifier. For example:
+
+@example
+#define QUAL_INTRO "/-" /* MS-DOS */
+#define QUAL_INTRO "-" /* Unix */
+@end example
+
+The examples above indicate that on a Unix system @samp{-} would be used to
+introduce a command qualifier, whereas on MS-DOS either @samp{-} or
+@samp{/} could be used.
+
+
+@subsubsection @code{QUAL_SEP}
+
+A string containing a set of characters, each of which may be used to
+separate a command line qualifier from its value. For example:
+
+@example
+#define QUAL_SEP "=:-" /* MS-DOS */
+#define QUAL_SEP " " /* Unix */
+#define QUAL_SEP " " /* Unix */
+@end example
+
+The examples above indicate that on an MS-DOS system the qualifier value is
+separated from the qualifier by one of the characters @samp{=}, @samp{:} or
+@samp{-}. The Unix example indicates that the value is separated from the
+qualifier by a space, i.e. it is the next command line parameter.
+
+
+@subsubsection @code{OPTIONAL_QUALIFIER_VALUES}
+
+Define as @code{TRUE} if the operating system convention can handle command
+line qualifiers with optional values. On systems such as MS-DOS, VAX/VMS
+and VM/CMS the qualifiers are separated from each other by spaces and from
+their values by another character such as an equals sign (@samp{=}). In
+the following example it is obvious whether the optional value for the
+@samp{log} qualifier is present:
+
+@example
+ vvencode /overwrite /log=log-file ip-file op-file
+ vvencode /overwrite /log ip-file op-file
+@end example
+
+On Unix, the convention is to separate qualifiers from each other by spaces
+and from their qualifiers by spaces. In the following example it is
+difficult if not impossible to determine whether the @samp{log} qualifier
+value is present:
+
+@example
+ vvencode -overwrite -log log-file ip-file op-file
+ vvencode -overwrite -log ip-file op-file
+@end example
+
+This problem could be overcome by forcing Unix users to use a different
+character like @samp{=} to introduce the qualifier value or by imposing
+strict rules on the ordering of parameters and qualifiers. Neither of
+these approaches is likely to be popular so we take the easy way out and
+specify whether such optional qualifier values are supported. If they are
+not supported, the qualifiers which could take optional values are modified
+either to require a value or to take no value.
+
+Example:
+
+@example
+ #define OPTIONAL_QUALIFIER_VALUES TRUE /* MS-DOS, VMS */
+ #define OPTIONAL_QUALIFIER_VALUES FALSE /* Unix */
+@end example
+
+
+@subsubsection @code{STICKY_DEFAULTS}
+
+Define as @code{TRUE} if the VVcode programs should apply default file
+names when determining output file specifications. For example, on Unix
+the definition would usually be:
+
+@example
+ #define STICKY_DEFAULTS FALSE /* Unix */
+@end example
+
+and the commands:
+
+@example
+ vvencode one
+ vvencode one two
+ vvencode one two -log three
+@end example
+
+would create the files @file{one.vve}, @file{two}, and @file{two} plus a
+log file @file{three} respectively. On other systems such as MS-DOS and
+VAX/VMS where default file names are customary the definition would usually
+be
+
+@example
+ #define STICKY_DEFAULTS TRUE /* MS-DOS, VMS */
+@end example
+
+and the commands:
+
+@example
+ vvencode one
+ vvencode one two
+ vvencode one two -log three
+@end example
+
+would create the files @file{one.vve}, @file{two.vve} and @file{two.vve}
+plus a log file @file{three.log} respectively.
+
+
+@subsubsection @code{STDOUT_OUTPUT}
+
+Define as @code{TRUE} if the VVencode program should write to standard
+output if an output file is not explicitly specified on the command line.
+The command:
+
+@example
+ vvencode ip-file
+@end example
+
+would write the VVE file to standard output if @code{STDOUT_OUTPUT} is defined
+as @code{TRUE} or to @file{ip-file.vve} if it is defined as @code{FALSE}.
+
+Examples:
+
+@example
+ #define STDOUT_OUTPUT TRUE /* Unix */
+ #define STDOUT_OUTPUT FALSE /* MS-DOS, VMS */
+@end example
+
+
+@subsubsection @code{SUPPORT_PIPING}
+
+Define as @code{TRUE} if the VVcode programs should support reading from
+standard input and/or writing to standard output so that they may be used
+as filters. The programs do not behave as true filters since an input file
+must always be specified, but specifying a certain string (e.g. @samp{-})
+as the input file specification will cause the program to read from
+standard input. The string used is defined by the macro
+@code{STDIO_SYMBOL}.
+
+Examples:
+
+@example
+ #define SUPPORT_PIPING TRUE /* Unix, MS-DOS */
+ #define SUPPORT_PIPING FALSE /* VMS, VM/CMS */
+@end example
+
+@subsubsection @code{STDIO_SYMBOL}
+
+A string which when used as a file specification will cause the VVcode
+programs to read/write to standard input/output depending on whether that
+file is an input or output file. This string is only used if the macro
+@code{SUPPORT_PIPING} is defined as @code{TRUE}. If it is unused, define
+it as "".
+
+On a Unix system, the following definitions would be usual:
+
+@example
+ #define SUPPORT_PIPING TRUE
+ #define STDIO_SYMBOL "-" /* Unix, MS-DOS */
+@end example
+
+and piping a binary file into VVencode to could be achieved with the shell
+command:
+
+@example
+ cat binary-file | vvencode - - | mail kempson@@TeX.Ac.Uk
+@end example
+
+
+@c -------------------------------------------------------------------------
+@c SECTION: File Specifications
+@c -------------------------------------------------------------------------
+@subsection File Specifications
+
+explain here the VVcode file specification model and how it is used
+
+
+@subsubsection @code{MAX_PATH}
+
+The maximum number of characters allowed in a file specification.
+
+Example:
+
+@example
+ #define MAX_PATH 80 /* MS-DOS */
+ #define MAX_PATH 255 /* BSD Unix */
+ #define MAX_PATH 255 /* VAX/VMS, some Unix */
+@end example
+
+
+@subsubsection @code{MAX_PREAMBLE}
+
+The maximum number of characters in the preamble component of a file
+specification. If the system does not support a preamble component, define
+as zero.
+
+Example:
+
+@example
+ #define MAX_PREAMBLE 64 /* MS-DOS */
+ #define MAX_PREAMBLE 255 /* BSD Unix */
+ #define MAX_PREAMBLE 255 /* VAX/VMS */
+@end example
+
+
+@subsubsection @code{MAX_NAME}
+
+The maximum number of characters in the name component of a file
+specification.
+
+Example:
+
+@example
+ #define MAX_NAME 8 /* MS-DOS */
+ #define MAX_NAME 255 /* BSD Unix */
+ #define MAX_NAME 39 /* VAX/VMS */
+@end example
+
+
+@subsubsection @code{MAX_EXT}
+
+The maximum number of characters in the extension component of a file
+specification. If the system does not support an extension component,
+define as zero.
+
+Example:
+
+@example
+ #define MAX_EXT 3 /* MS-DOS */
+ #define MAX_EXT 255 /* BSD Unix */
+ #define MAX_EXT 39 /* VAX/VMS */
+@end example
+
+
+@subsubsection @code{MAX_POSTAMBLE}
+
+The maximum number of characters in the postamble component of a file
+specification. If the system does not support a postamble component,
+define as zero.
+
+Example:
+
+@example
+ #define MAX_POSTAMBLE 0 /* MS-DOS */
+ #define MAX_POSTAMBLE 0 /* BSD Unix */
+ #define MAX_POSTAMBLE 5 /* VAX/VMS */
+@end example
+
+
+@subsubsection @code{PREAMBLE_END}
+
+A string containing a set of characters, each of which may be used to
+denote the end of the preamble component of a file specification. If the
+system does not support a preamble component, define as "".
+
+Example:
+
+@example
+ #define PREAMBLE_END ":\\" /* MS-DOS */
+ #define PREAMBLE_END ":/" /* BSD Unix */
+ #define PREAMBLE_END ":>]" /* VAX/VMS */
+@end example
+
+
+@subsubsection @code{EXTENSION_BEGIN}
+
+The single character that may be used to denote the start of the extension
+component of a file specification. If the system does not support an
+extension component, define as @samp{\000}.
+
+Example:
+
+@example
+ #define EXTENSION_BEGIN '.' /* MS-DOS */
+ #define EXTENSION_BEGIN '.' /* BSD Unix */
+ #define EXTENSION_BEGIN '.' /* VAX/VMS */
+@end example
+
+
+@subsubsection @code{POSTAMBLE_BEGIN}
+
+A string containing a set of characters, each of which may be used to denote
+the start of the postamble component of a file specification. If the system
+does not support a postamble component, define as "".
+
+Example:
+
+@example
+ #define POSTAMBLE_BEGIN "" /* MS-DOS */
+ #define POSTAMBLE_BEGIN "" /* BSD Unix */
+ #define POSTAMBLE_BEGIN ";" /* VAX/VMS */
+@end example
+
+
+@subsubsection @code{UPPERCASE_FILESYSTEM}
+
+Define as @code{TRUE} if the file system is case insensitive. For the
+benefit of file systems that do care (where lower case names are usual),
+VVencode will convert file specifications to lower case before recording
+them in the VVE file.
+
+Example:
+
+@example
+ #define UPPERCASE_FILESYSTEM TRUE /* MS-DOS, VAX/VMS */
+ #define UPPERCASE_FILESYSTEM FALSE /* Unix */
+@end example
+
+
+@c -------------------------------------------------------------------------
+@c SECTION: File Formats
+@c -------------------------------------------------------------------------
+@subsection{File Formats}
+
+explain the different file formats and provide a small table showing how
+they are used for different operating systems
+
+
+@subsubsection @code{SUPPORT_FIXED_FMT}
+
+Define as @code{TRUE} if the file system supports fixed length record
+format files.
+
+Example:
+
+@example
+ #define SUPPORT_FIXED_FORMAT TRUE /* VAX/VMS, VM/CMS */
+ #define SUPPORT_FIXED_FORMAT FALSE /* MS-DOS, Unix */
+@end example
+
+
+@subsubsection @code{SUPPORT_STREAM_FMT}
+
+Define as @code{TRUE} if the file system supports stream format files.
+
+Example:
+
+@example
+ #define SUPPORT_STREAM_FILES TRUE /* MS-DOS, Unix, VAX/VMS */
+ #define SUPPORT_STREAM_FILES FALSE /* VM/CMS */
+@end example
+
+
+@subsubsection @code{SUPPORT_VARIABLE_FMT}
+
+Define as @code{TRUE} if the file system supports variable length record
+format files.
+
+Example:
+
+@example
+ #define SUPPORT_VARIABLE_FORMAT TRUE /* VAX/VMS, VM/CMS */
+ #define SUPPORT_VARIABLE_FORMAT FALSE /* MS-DOS, Unix */
+@end example
+
+
+@subsubsection @code{TEXT_LINE_OVERHEAD}
+
+The extra number of characters written by the file system when writing
+lines to text files. For example, when writing to text files MS-DOS
+converts @samp{\n} to @samp{\r\n} and therefore has an overhead of 1.
+
+Example:
+
+@example
+ #define TEXT_LINE_OVERHEAD 1 /* MS-DOS, VAX/VMS */
+ #define TEXT_LINE_OVERHEAD 0 /* Unix */
+@end example
+
+
+@subsubsection @code{DEF_MODE}
+
+Define as the default mode for file encoding & decoding to be used if the
+mode is not specified on the command line and cannot be determined from the
+input file. It must be @code{MODE_BINARY} or @code{MODE_TEXT}.
+
+Example:
+
+@example
+ #define DEF_MODE MODE_BINARY /* most systems */
+@end example
+
+
+@subsubsection @code{DEF_TEXT_FMT}
+
+Define as the default file format for text files. It must be one of
+@code{FMT_FIXED}, @code{FMT_STREAM} and @code{FMT_VARIABLE} and only a
+supported format may be specified.
+
+Example:
+
+@example
+ #define DEF_TEXT_FMT FMT_STREAM /* MS-DOS, Unix */
+ #define DEF_TEXT_FMT FMT_VARIABLE /* VAX/VMS */
+@end example
+
+
+@subsubsection @code{DEF_BINARY_FMT}
+
+Define as the default file format for text files. It must be one of
+@code{FMT_FIXED}, @code{FMT_STREAM} and @code{FMT_VARIABLE} and only a
+supported format may be specified.
+
+Example:
+
+@example
+ #define DEF_BINARY_FMT FMT_STREAM /* MS-DOS, Unix */
+ #define DEF_BINARY_FMT FMT_FIXED /* VAX/VMS */
+@end example
+
+
+@subsubsection @code{MIN_VARIABLE_RECORD_LEN}
+
+The minimum record length in bytes supported by the file system for
+variable length record format files. Must be within the VVcode limits of 0
+to 65535. If the system doesn't support variable length record format files
+define as @code{INV_RECORD_LEN}.
+
+Example:
+
+@example
+ #define MIN_VARIABLE_RECORD_LEN INV_RECORD_LEN /* MS-DOS, Unix */
+ #define MIN_VARIABLE_RECORD_LEN 0 /* VAX/VMS */
+@end example
+
+
+@subsubsection @code{MAX_VARIABLE_RECORD_LEN}
+
+The maximum record length in bytes supported by the file system for
+variable length record format files. Must be within the VVcode limits of 0
+to 65535. If the system doesn't support variable length record format files
+define as @code{INV_RECORD_LEN}.
+
+Example:
+
+@example
+ #define MAX_VARIABLE_RECORD_LEN INV_RECORD_LEN /* MS-DOS, Unix */
+ #define MAX_VARIABLE_RECORD_LEN 32765 /* VAX/VMS */
+ #define MAX_VARIABLE_RECORD_LEN 65535 /* VM/CMS */
+@end example
+
+
+@subsubsection @code{DEF_VARIABLE_RECORD_LEN}
+
+The default maximum record length in bytes supported by the file system for
+variable length record format files. Must be in the range defined by
+@code{MIN_VARIABLE_RECORD_LEN} and @code{MAX_VARIABLE_RECORD_LEN}. If the
+system doesn't support variable length record format files define as
+@code{INV_RECORD_LEN}.
+
+Example:
+
+@example
+ #define DEF_VARIABLE_RECORD_LEN INV_RECORD_LEN /* MS-DOS, Unix */
+ #define DEF_VARIABLE_RECORD_LEN 512 /* VAX/VMS */
+ #define DEF_VARIABLE_RECORD_LEN 255 /* VM/CMS */
+@end example
+
+
+@subsubsection @code{MIN_FIXED_RECORD_LEN}
+
+The minimum record length in bytes supported by the file system for fixed
+length record format files. Must be within the VVcode limits of 0 to
+65535. If the system doesn't support fixed length record format files
+define as @code{INV_RECORD_LEN}.
+
+Example:
+
+@example
+ #define MIN_FIXED_RECORD_LEN INV_RECORD_LEN /* MS-DOS, Unix */
+ #define MIN_FIXED_RECORD_LEN 0 /* VAX/VMS */
+@end example
+
+
+@subsubsection @code{MAX_FIXED_RECORD_LEN}
+
+The maximum record length in bytes supported by the file system for fixed
+length record format files. Must be within the VVcode limits of 0 to
+65535. If the system doesn't support fixed length record format files
+define as @code{INV_RECORD_LEN}.
+
+Example:
+
+@example
+ #define MAX_FIXED_RECORD_LEN INV_RECORD_LEN /* MS-DOS, Unix */
+ #define MAX_FIXED_RECORD_LEN 32765 /* VAX/VMS */
+ #define MAX_FIXED_RECORD_LEN 65535 /* VM/CMS */
+@end example
+
+
+@subsubsection @code{DEF_FIXED_RECORD_LEN}
+
+The default record length in bytes supported by the file system for fixed
+length record format files. Must be in the range defined by
+@code{MIN_FIXED_RECORD_LEN} and @code{MAX_FIXED_RECORD_LEN}. If the system
+doesn't support fixed length record format files define as
+@code{INV_RECORD_LEN}.
+
+Example:
+
+@example
+ #define DEF_FIXED_RECORD_LEN INV_RECORD_LEN /* MS-DOS, Unix */
+ #define DEF_FIXED_RECORD_LEN 512 /* VAX/VMS */
+ #define DEF_FIXED_RECORD_LEN 255 /* VM/CMS */
+@end example
+
+
+@subsubsection @code{DEF_TEXT_PADCHAR}
+
+Define as the default character used to pad out short records in text fixed
+length record format files. Must be a valid character constant and will
+usually be a space character. If the system doesn't support fixed length
+record format files, define as @samp{\000}.
+
+Example:
+
+@example
+ #define DEF_TEXT_PADCHAR '\000' /* MS-DOS, Unix */
+ #define DEF_TEXT_PADCHAR ' ' /* VAX/VMS, VM/CMS */
+@end example
+
+
+@subsubsection @code{DEF_BINARY_PADCHAR}
+
+Define as the default character used to pad out short records in binary
+fixed length record format files. Must be a valid character constant and
+will usually be a null character. If the system doesn't support fixed
+length record format files, define as '\000'.
+
+Example:
+
+@example
+ #define DEF_BINARY_PADCHAR '\000' /* MS_DOS, Unix */
+ #define DEF_BINARY_PADCHAR '\000' /* VAX/VMS, VM/CMS */
+@end example
+
+
+
+@c =========================================================================
+@c SECTION: The @file{xxx.c} operating system specific module
+@c =========================================================================
+@section The @file{xxx.c} operating system specific module
+
+
+
+@c =========================================================================
+@c SECTION: Porting VVcode - an example
+@c =========================================================================
+@section Porting VVcode - an example
diff --git a/support/vvcode/doc/vvtest.tex b/support/vvcode/doc/vvtest.tex
new file mode 100644
index 0000000000..60fef19959
--- /dev/null
+++ b/support/vvcode/doc/vvtest.tex
@@ -0,0 +1,432 @@
+@c *************************************************************************
+@c CHAPTER: How to test VVcode
+@c *************************************************************************
+@c node-name, next, previous, up
+@node Testing Guide, Testing Guide, Top, Top
+@chapter How to test VVcode
+
+
+@c =========================================================================
+@c SECTION: Testing VVencode
+@c =========================================================================
+@section Testing VVencode
+
+
+@subsection User Help
+@itemize @bullet
+ @item @samp{help} qualifier should cause ``usage'' message to be displayed
+ @item invalid qualifier (e.g. @samp{ZZZZ}) should cause ``usage'' message
+ to be displayed
+@end itemize
+
+
+@subsection User Information (@samp{log} & @samp{debug} qualifiers)
+@itemize @bullet
+ @item @samp{log} with no qualifier value writes to @code{stderr}
+ @item @samp{log} qualifier value specifying invalid output file
+ @item @samp{log} file spec missing @file{.log} extension component
+ @file{.log} added if @code{STICKY_DEFAULTS} defined)
+ @item @samp{debug} writes extra information to @code{stderr}
+ @item @samp{debug} assumes @samp{log} even if @samp{log} not specified
+@end itemize
+
+
+@subsection File overwriting (@samp{overwrite_files} qualifier)
+@itemize @bullet
+ @item @samp{overwrite_files} should always overwrite unless the operating
+ system objects
+ @item should ask before overwriting an existing file
+ @item don't ask whether to overwrite if reading from @code{stdin} - just
+ fail
+@end itemize
+
+
+@subsection VVE header file specification (@samp{header_file} qualifier)
+@itemize @bullet
+ @item missing qualifier value
+ @item if @samp{header_file} not specified, the input file specification
+ is used, stripped of any preamble and postamble components
+ @item check that command line value overrides input file specification
+ and is used without modification
+@end itemize
+
+
+@subsection Maximum VVE file size (@samp{split_size} qualifier)
+@itemize @bullet
+ @item missing qualifier value
+ @item invalid qualifier (less than 4)
+ @item check that O/P files are really no greater than this size
+ @item file splitting disabled when writing to @code{stdout}, a pipe or
+ non-file device
+@end itemize
+
+
+@subsection Input file examination
+@itemize @bullet
+ @item mode
+ @item format
+ @item modification time (unsupported timestamps ``normalized'')
+ @item maximum record length
+ @item longest record length
+ @item unsupported file organizations rejected (mainly by format and
+ record length)
+@end itemize
+
+
+@subsection File mode (@samp{mode} qualifier)
+@itemize @bullet
+ @item missing qualifier value
+ @item invalid qualifier value
+ @item check that command line value overrides @code{examine_file()} and
+ default mode values
+ @item check that @code{examine_file()} mode value overrides default
+@end itemize
+
+
+@subsection File format (@samp{format} qualifier)
+@itemize @bullet
+ @item missing qualifier value
+ @item invalid qualifier value
+ @item check that command line value overrides @code{examine_file()} and
+ default format values
+ @item check that @code{examine_file()} format value overrides default
+@end itemize
+
+
+@subsection File record length (@samp{record_length} qualifier)
+@itemize @bullet
+ @item missing qualifier value
+ @item invalid qualifier value (within OS limits and < 65536)
+ @item check that command line value overrides @code{examine_file()} and
+ default format values and also resets longest record length
+ @item check that @code{examine_file()} format value overrides default
+@end itemize
+
+
+@subsection File timestamp (@samp{timestamp} qualifier)
+@itemize @bullet
+ @item missing qualifier value (optional on some systems, required on
+ others)
+ @item invalid qualifier value (before 1970 or after 2037)
+ @item check that command line value overrides @code{examine_file()} value
+@end itemize
+
+
+@subsection Encoding table (@samp{encoding_table} qualifier)
+@itemize @bullet
+ @item missing qualifier file spec
+ @item non-existent file specified
+ @item file spec missing @file{.enc} extension component
+ @item short encoding table file: @file{tooshort.enc}
+ @item long encoding table file: @file{toolong.enc}
+ @item correct encoding table file: @file{uucode.enc}
+ @item duplication of character(s) in encoding file: @file{duplicat.enc}
+ @item contents of file specified on command line overrides default
+ table
+@end itemize
+
+
+@subsection Character set translation (@samp{translation_file} qualifier)
+@itemize @bullet
+ @item missing qualifier file spec
+ @item non-existent file specified
+ @item file spec missing @file{.xlt} extension component
+ @item comment handling
+ @item correct translation table file: @file{encode.xlt}
+ @item short translation table file: @file{tooshort.xlt}
+ @item long translation table file: @file{toolong.xlt}
+ @item translation table with invalid values: @file{badvalue.xlt}
+ @item translation of unsupported characters: @file{toascii.xlt}
+ @item missing @file{xlt-from} header: @file{frommiss.xlt}
+ @item invalid @file{xlt-from} header value: @file{frombad.xlt}
+ @item missing @file{xlt-to} header: @file{tomiss.xlt}
+ @item invalid @file{xlt-to} header value: @file{tobad.xlt}
+ @item missing @file{xlt-substchar} header: @file{submiss.xlt}
+ @item invalid @file{xlt-substchar} header value: @file{subbad.xlt}
+ @item @file{xlt-from} character set different to the local character set:
+ @file{difffrom.xlt}
+@end itemize
+
+
+@subsection Input file
+@itemize @bullet
+ @item missing command line value
+ @item non-existent file specified
+ @item file opened using the correct parameters (mode, format etc)
+ @item rejection of unsupported file types
+ @item specify null device (@code{NUL}, @code{NL:}, @code{/dev/null} etc)
+ @item specify zero length (empty) file
+ @item specify @code{stdin}
+@end itemize
+
+
+@subsection Output file
+@itemize @bullet
+ @item missing command line value - use input file name plus @file{.vve}
+ extension
+ @item invalid or unwritable file specification
+ @item check correct application of file specification defaults when
+ partial specification is supplied (if @code{STICKY_DEFAULTS}
+ defined)
+ @item O/P file opened using the correct parameters (mode, format etc)
+ @item specify null device (@code{NUL}, @code{NL:}, @code{/dev/null} etc)
+ @item specify @code{stdout}
+@end itemize
+
+
+@subsection Internal
+@itemize @bullet
+ @item for variable length records, check that zero and maximum length
+ records are handled and recorded correctly
+ @item total byte count - may be different for text/binary
+ @item CRC-32 value (check with ZIP or ARJ) - may be different for
+ text/binary
+ @item internal buffer allocation
+ @item file closing
+ @item running out of memory
+ @item log information
+@end itemize
+
+
+
+@c =========================================================================
+@c SECTION: Testing VVdecode
+@c =========================================================================
+@section Testing VVdecode
+
+@subsection User Help
+@itemize @bullet
+ @item @samp{help} qualifier should cause ``usage'' message to be displayed
+ @item invalid qualifier (e.g. @samp{ZZZZ}) should cause ``usage'' message
+ to be displayed
+@end itemize
+
+
+@subsection User Information (@samp{log} & @samp{debug} qualifiers)
+@itemize @bullet
+ @item @samp{log} with no qualifier value
+ @item @samp{log} qualifier value specifying invalid output file
+ @item @samp{log} file spec missing @file{.log} extension component
+ @item @samp{debug} generates extra information
+ @item @samp{debug} assumes @samp{log} even if @samp{log} not specified
+@end itemize
+
+
+@subsection File overwriting (@samp{overwrite_files} qualifier)
+@itemize @bullet
+ @item @samp{overwrite_files} should always overwrite unless the operating
+ system objects
+ @item should ask before overwriting an existing file
+ @item when reading from a pipe or non-file device, don't ask whether
+ to overwrite - just fail
+@end itemize
+
+
+@subsection VVE input file examination
+@itemize @bullet
+ @item @code{decodeversion}
+ @item @code{operatingsystem}
+ @item @code{characterset}
+ @item @code{comment}
+ @item @code{mode}
+ @item @code{format}
+ @item @code{modification time}
+ @item @code{recordlength}
+ @item @code{table}
+@end itemize
+
+
+@subsection File mode (@samp{mode qualifier})
+@itemize @bullet
+ @item missing qualifier value
+ @item invalid qualifier value
+ @item check that command line value overrides VVE file and default
+ mode values
+ @item check that VVE file mode value overrides default
+@end itemize
+
+
+@subsection File format (@samp{format qualifier})
+@itemize @bullet
+ @item missing qualifier value
+ @item invalid qualifier value
+ @item check that command line value overrides VVE file and default
+ format values
+ @item check that VVE file format value overrides default
+@end itemize
+
+
+@subsection File record length (@samp{record_length} qualifier)
+@itemize @bullet
+ @item missing qualifier value
+ @item invalid qualifier value (within OS limits and < 65536)
+ @item check that command line value overrides VVE file and default
+ format values and also resets longest record length
+ @item check that VVE file format value overrides default
+@end itemize
+
+
+@subsection File timestamp (@samp{timestamp} qualifier)
+@itemize @bullet
+ @item missing qualifier value (optional on some systems, required on
+ others)
+ @item invalid qualifier value (before 1970 or after 2037)
+ @item check that command line value overrides VVE file value
+@end itemize
+
+
+@subsection Encoding table (@samp{encoding_table} qualifier)
+@itemize @bullet
+ @item missing qualifier file spec
+ @item non-existent file specified
+ @item file spec missing @file{.enc} extension component
+ @item short encoding table file: @file{tooshort.enc}
+ @item long encoding table file: @file{toolong.enc}
+ @item correct encoding table file: @file{uucode.enc}
+ @item duplication of character(s) in encoding file: @file{duplicat.enc}
+ @item contents of file specified on command line overrides VVE table
+ and default table
+ @item VVE table overrides default table
+@end itemize
+
+
+@subsection Character set translation (@samp{translation_file} qualifier)
+@itemize @bullet
+ @item missing qualifier file spec
+ @item non-existent file specified
+ @item file spec missing @file{.xlt} extension component
+ @item comment handling
+ @item correct translation table file: @file{decode.xlt}
+ @item short translation table file: @file{tooshort.xlt}
+ @item long translation table file: @file{toolong.xlt}
+ @item translation table with invalid values: @file{badvalue.xlt}
+ @item translation of unsupported characters: @file{toascii.xlt}
+ @item missing @samp{xlt-from} header: @file{frommiss.xlt}
+ @item invalid @samp{xlt-from} header value: @file{frombad.xlt}
+ @item missing @samp{xlt-to} header: @file{tomiss.xlt}
+ @item invalid @samp{xlt-to} header value: @file{tobad.xlt}
+ @item missing @samp{xlt-substchar} header: @file{submiss.xlt}
+ @item invalid @samp{xlt-substchar} header value: @file{subbad.xlt}
+ @item @samp{xlt-from} character set different to the VVE character set:
+ @file{difffrom.xlt}
+ @item @samp{xlt-to} character set different to the local character set:
+ @file{diffto.xlt}
+ @item @samp{xlt-from} character set different to the VVE character set
+ and @samp{xlt-to} character set different to the local character
+ set: @file{diffboth.xlt}
+@end itemize
+
+
+@subsection File padding character (@samp{pad_character} qualifier)
+@itemize @bullet
+ @item missing qualifier value
+ @item invalid qualifier
+ @item qualifier value overrides default values
+ @item use of different default values for text and binary files
+@end itemize
+
+
+@subsection UUdecoding (@samp{uudecode} qualifier)
+@itemize @bullet
+ @item correct decoding of UUencoded file without @samp{Vv} line start
+ @item error if file contains VVcode specific headers
+@end itemize
+
+
+@subsection XXdecoding (@samp{xxdecode} qualifier)
+@itemize @bullet
+ @item correct decoding of XXencoded file without @samp{Vv} line start
+ @item error if file contains VVcode specific headers
+@end itemize
+
+
+@subsection Input file
+@itemize @bullet
+ @item missing command line value
+ @item non-existent file specified
+ @item file opened using the correct parameters (mode, format etc)
+ @item specify null device (@code{NUL}, @code{NL:}, @code{/dev/null} etc)
+ @item specify zero length (empty) file
+ @item specify @code{stdin}
+@end itemize
+
+
+@subsection Output file
+@itemize @bullet
+ @item missing command line value - use of VVE header
+ @item invalid or unwritable file specification
+ @item check correct application of file specification defaults (for those
+ systems that use support them)
+ @item file opened using the correct parameters (mode, format etc)
+ @item specify null device (@code{NUL}, @code{NL:}, @code{/dev/null} etc)
+ @item specify @code{stdout}
+@end itemize
+
+
+@subsection Internal
+@itemize @bullet
+ @item for variable length records, check that zero and maximum length
+ records in the VVE file are handled and recorded correctly
+ @item total byte count
+ @item CRC-32 value (check with ZIP or ARJ)
+ @item internal buffer allocation
+ @item file closing
+ @item running out of memory
+@end itemize
+
+
+@c =========================================================================
+@c SECTION: Testing file interchnage
+@c =========================================================================
+@section Testing file interchange
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: Interchange of Common Files between Operating Systems
+@c -------------------------------------------------------------------------
+@subsection Interchange of Common Files between Operating Systems
+@itemize @bullet
+ @item text file
+ @item @TeX{} @file{.dvi}file
+ @item @TeX{} @file{.tfm} file
+ @item @TeX{} @file{.pk} file
+@end itemize
+
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: Operating System-specific Files
+@c -------------------------------------------------------------------------
+@subsection Operating System-specific Files
+
+@subsubsection MS-DOS
+@itemize @bullet
+ @item @file{.zip} file
+ @item @file {.Z} @code{compress} file
+@end itemize
+
+@subsubsection OS/2
+@itemize @bullet
+ @item @file{.zip} file
+ @item @file {.Z} @code{compress} file
+@end itemize
+
+@subsubsection Unix
+@itemize @bullet
+ @item @file{.tar} file
+ @item @file {.Z} @code{compress} file
+@end itemize
+
+@subsubsection VAX/VMS
+@itemize @bullet
+ @item backup save set (fixed length 32256 byte records)
+ @item @file{.obj} file (variable length binary)
+ @item @file{.exe} file (fixed length 512 byte records)
+ @item text file (@code{STREAM_LF} format)
+ @item compress @file{.Z} file (variable length binary)
+@end itemize
+
+@subsubsection VM/CMS
+@itemize @bullet
+ @item @code{EXEC} file
+ @item @code{MODULE} file (variable length 65535 byte records)
+@end itemize
diff --git a/support/vvcode/doc/vvuser.tex b/support/vvcode/doc/vvuser.tex
new file mode 100644
index 0000000000..26f0a1ec51
--- /dev/null
+++ b/support/vvcode/doc/vvuser.tex
@@ -0,0 +1,200 @@
+@c *************************************************************************
+@c CHAPTER: Guide to using VVcode
+@c *************************************************************************
+@c node-name, next, previous, up
+@node User Manual, User Manual, Top, Top
+@chapter Guide to using VVcode
+
+@itemize @bullet
+ @item general introduction
+@end itemize
+
+@c =========================================================================
+@c SECTION: VVencode command options
+@c =========================================================================
+@section{VVencode command options}
+
+@itemize @bullet
+ @item described in a generic manner with operating system specifics at
+ the end of the section
+@end itemize
+
+The general syntax of the VVencode command line is:
+@example
+ vvencode [options] input-file [options] [output-file] [options]
+@end example
+
+There are two @dfn{parameters} and many optional @dfn{qualifiers}. The
+parameters are:
+
+@table @code
+ @item input-file
+
+ @item output-file
+@end table
+
+The command qualifiers modify the behaviour of VVcode and are all optional.
+Qualifiers may appear before, between or after the parameters. The
+qualifiers acceptable to VVencode are:
+
+@table @code
+ @item debug
+ Write copious debugging output to the standard error device or to
+ the log file if the @code{+log} qualifier was specified. This
+ qualifier would normally only be used when trying to report a
+ @code{VVencode} problem and may indeed have been disabled for the
+ version that you are using.
+ @item encoding_table file-spec
+ Read the encoding table to be used from the file @file{file-spec}.
+ The file must contain the 64 characters to be used by
+ @code{VVencode}. If this qualifier is not specified, the default
+ @code{VVencode} encoding table will be used.
+ @item format file-format
+ Explicitly specify the file format that should be assumed by
+ @code{VVencode} when it is reading the input file. The
+ @code{file-format} value must be one of @samp{fixed}, @samp{stream}
+ and @samp{variable}. This qualifier would only be used if it was
+ necessary to override the value determined automatically by
+ VVencode.
+ @item header_filespec file-spec
+
+ @item help
+ VVencode will display a usage message on the standard error device
+ and exit.
+ @item log file-spec
+
+ @item mode file-mode
+ Explicitly specify the file mode that should be assumed by
+ @code{VVencode} when it is reading the input file. The
+ @code{file-format} value must be one of @samp{binary} and
+ @samp{text}. This qualifier would only be used if it was
+ necessary to override the value determined automatically by
+ VVencode.
+ @item overwrite
+
+ @item record_length
+
+ @item split_size
+
+ @item timestamp time
+
+ @item translation_file file-spec
+
+@end table
+
+
+@c =========================================================================
+@c SECTION: VVdecode command options
+@c =========================================================================
+@section{VVdecode command options}
+
+The general syntax of the VVdecode command line is:
+@example
+ vvdecode [options] input-file [options] [output-file] [options]
+@end example
+
+
+@c =========================================================================
+@c SECTION: Operating system specific considerations
+@c =========================================================================
+@section{Operating system specific considerations}
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: MS-DOS
+@c -------------------------------------------------------------------------
+@subsection MS-DOS
+@itemize @bullet
+ @item qualifiers introduced with @samp{/} or @samp{-} and must be
+ separated from each other by whitespace
+ @item values separated from qualifier by @samp{=} or @samp{:}
+ @item optional values supported
+ @item VVcode will act as a filter when @samp{-} is specified as the input
+ or output file
+ @item optional file specification for @samp{log} qualifier
+ @item examples of VVencode usage
+@end itemize
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: OS/2
+@c -------------------------------------------------------------------------
+@subsection OS/2
+@itemize @bullet
+ @item qualifiers introduced with @samp{/} or @samp{-} and must be
+ separated from each other by whitespace
+ @item values separated from qualifier by @samp{=} or @samp{:}
+ @item optional values supported
+ @item VVcode will act as a filter when @samp{-} is specified as the input
+ or output file
+ @item optional file specification for @samp{log} qualifier
+ @item GCC 2.1 implementation does not support file timestamping
+ @item HPFS file names supported
+ @item OS/2 extended attributes not supported yet
+ @item examples of VVencode usage
+@end itemize
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: Unix
+@c -------------------------------------------------------------------------
+@subsection Unix
+@itemize @bullet
+ @item qualifiers introduced with @samp{-} or @samp{+} and must be
+ separated from each other by whitespace
+ @item values separated from qualifier by whitespace
+ @item optional values not supported
+ @item VVcode will act as a filter when @samp{-} is specified as the input
+ or output file
+ @item examples of VVencode usage
+@end itemize
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: VAX/VMS
+@c -------------------------------------------------------------------------
+@subsection VAX/VMS
+@itemize @bullet
+ @item qualifiers introduced with @samp{/}
+ @item values separated from qualifier by @samp{=}
+ @item standard VMS CLD conventions
+ @item optional values supported
+ @item VVcode will act as a filter when @samp{-} is specified as the input
+ or output file though meaningless on VMS
+ @item optional file specification for @samp{log} qualifier
+ @item examples of VVencode usage
+@end itemize
+
+@c -------------------------------------------------------------------------
+@c SUBSECTION: VM/CMS
+@c -------------------------------------------------------------------------
+@subsection VM/CMS
+@itemize @bullet
+ @item qualifiers introduced with @samp{(} and must be
+ separated from each other by whitespace
+ @item values separated from qualifier by @samp{=} or @samp{:}
+ @item command line driven through REXX EXEC
+ @item optional values supported
+ @item VVcode does not support input or output from/to standard I/O
+ @item optional file specification for @samp{log} qualifier
+ @item examples of VVencode usage
+@end itemize
+
+
+@c =========================================================================
+@c SECTION: Transferring files between systems
+@c =========================================================================
+@section{Transferring files between systems}
+@itemize @bullet
+ @item file type and format
+ @item character set
+ @item electronic mail
+ @item timestamping
+@end itemize
+
+
+@c =========================================================================
+@c SECTION: Unusual applications of VVcode
+@c =========================================================================
+@section{Unusual applications of VVcode}
+@itemize @bullet
+ @item character set conversion
+ @item file type conversion
+ @item VMS file format conversion vs. @code{CONVERT}
+@end itemize