diff options
author | jmacd <jmacd@FreeBSD.org> | 1997-01-11 02:32:23 +0000 |
---|---|---|
committer | jmacd <jmacd@FreeBSD.org> | 1997-01-11 02:32:23 +0000 |
commit | 9f2cebccb1ff493f1fa0b53fe3296a0e71b193c7 (patch) | |
tree | ceb15326965f89864b8323e75d2afbdfcffbb815 /gnu/usr.bin/texinfo | |
parent | 52ed0489e7f93e652aa842eedbf6aae77fe83f05 (diff) | |
download | FreeBSD-src-9f2cebccb1ff493f1fa0b53fe3296a0e71b193c7.zip FreeBSD-src-9f2cebccb1ff493f1fa0b53fe3296a0e71b193c7.tar.gz |
Clearing out the old stuff, its all in contrib now.
Diffstat (limited to 'gnu/usr.bin/texinfo')
78 files changed, 95 insertions, 48330 deletions
diff --git a/gnu/usr.bin/texinfo/Makefile b/gnu/usr.bin/texinfo/Makefile index 172255c..f1539d5 100644 --- a/gnu/usr.bin/texinfo/Makefile +++ b/gnu/usr.bin/texinfo/Makefile @@ -1,9 +1,7 @@ # -# Bmake file for texinfo -# $Id: Makefile,v 1.2 1994/09/15 12:09:35 jkh Exp $ +# $Id$ # -SUBDIR= info info-files makedoc makeinfo texindex doc +SUBDIR= libtxi makeinfo info install-info doc .include <bsd.subdir.mk> - diff --git a/gnu/usr.bin/texinfo/Makefile.inc b/gnu/usr.bin/texinfo/Makefile.inc deleted file mode 100644 index a5dfdf8..0000000 --- a/gnu/usr.bin/texinfo/Makefile.inc +++ /dev/null @@ -1,3 +0,0 @@ -# Texinfo defaults. -# $Id: Makefile.inc,v 1.4 1995/07/16 10:23:51 joerg Exp $ - diff --git a/gnu/usr.bin/texinfo/doc/Makefile b/gnu/usr.bin/texinfo/doc/Makefile index 65c89da..76e56b1 100644 --- a/gnu/usr.bin/texinfo/doc/Makefile +++ b/gnu/usr.bin/texinfo/doc/Makefile @@ -1,8 +1,13 @@ -INFO= info info-stnd makeinfo texi -.if exists(${.OBJDIR}/../makeinfo) -MAKEINFO= ${.OBJDIR}/../makeinfo/makeinfo -.else -MAKEINFO= ${.CURDIR}/../makeinfo/makeinfo -.endif +# +# $Id$ +# + +TEXINFODIR= ${.CURDIR}/../../../../contrib/texinfo +INFODIR= ${.CURDIR}/../../../../contrib/texinfo/info +MAKEINFODIR= ${.CURDIR}/../../../../contrib/texinfo/makeinfo + +INFO= texinfo info info-stnd makeinfo + +.PATH: $(TEXINFODIR) $(INFODIR) $(MAKEINFODIR) .include <bsd.info.mk> diff --git a/gnu/usr.bin/texinfo/doc/info-stnd.texi b/gnu/usr.bin/texinfo/doc/info-stnd.texi deleted file mode 100644 index 286973b..0000000 --- a/gnu/usr.bin/texinfo/doc/info-stnd.texi +++ /dev/null @@ -1,1359 +0,0 @@ -\input texinfo @c -*-texinfo-*- -@comment %**start of header -@setfilename info-stnd.info -@settitle GNU Info -@set InfoProgVer 2.9 -@paragraphindent none -@footnotestyle separate -@synindex vr cp -@synindex fn cp -@synindex ky cp -@comment %**end of header - -@ifinfo -This file documents GNU Info, a program for viewing the on-line formatted -versions of Texinfo files. This documentation is different from the -documentation for the Info reader that is part of GNU Emacs. If you do -not know how to use Info, but have a working Info reader, you should -read that documentation first. - -Copyright @copyright{} 1992, 1993 Free Software Foundation, Inc. - -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 a 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 also that the -sections entitled ``Copying'' and ``GNU General Public License'' are -included exactly as in the original, and 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 - -@titlepage -@title GNU Info User's Guide -@subtitle For GNU Info version @value{InfoProgVer} -@author Brian J. Fox (bfox@@ai.mit.edu) -@page -@vskip 0pt plus 1filll -Copyright @copyright{} 1992, 1993 Free Software Foundation - -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 -sections entitled ``Copying'' and ``GNU General Public License'' are -included exactly as in the original, and 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 titlepage - -@ifinfo -@node Top, What is Info, (dir), (dir) -@top The GNU Info Program - -This file documents GNU Info, a program for viewing the on-line -formatted versions of Texinfo files, version @value{InfoProgVer}. This -documentation is different from the documentation for the Info reader -that is part of GNU Emacs. -@end ifinfo - -@menu -* What is Info:: -* Options:: Options you can pass on the command line. -* Cursor Commands:: Commands which move the cursor within a node. -* Scrolling Commands:: Commands for moving the node around - in a window. -* Node Commands:: Commands for selecting a new node. -* Searching Commands:: Commands for searching an Info file. -* Xref Commands:: Commands for selecting cross references. -* Window Commands:: Commands which manipulate multiple windows. -* Printing Nodes:: How to print out the contents of a node. -* Miscellaneous Commands:: A few commands that defy categories. -* Variables:: How to change the default behavior of Info. -* GNU Info Global Index:: Global index containing keystrokes, - command names, variable names, - and general concepts. -@end menu - -@node What is Info, Options, Top, Top -@chapter What is Info? - -@iftex -This file documents GNU Info, a program for viewing the on-line formatted -versions of Texinfo files, version @value{InfoProgVer}. -@end iftex - -@dfn{Info} is a program which is used to view Info files on an ASCII -terminal. @dfn{Info files} are the result of processing Texinfo files -with the program @code{makeinfo} or with one of the Emacs commands, such -as @code{M-x texinfo-format-buffer}. Texinfo itself is a documentation -system that uses a single source file to produce both on-line -information and printed output. You can typeset and print the -files that you read in Info.@refill - -@node Options, Cursor Commands, What is Info, Top -@chapter Command Line Options -@cindex command line options -@cindex arguments, command line - -GNU Info accepts several options to control the initial node being -viewed, and to specify which directories to search for Info files. Here -is a template showing an invocation of GNU Info from the shell: - -@example -info [--@var{option-name} @var{option-value}] @var{menu-item}@dots{} -@end example - -The following @var{option-names} are available when invoking Info from -the shell: - -@table @code -@cindex directory path -@item --directory @var{directory-path} -@itemx -d @var{directory-path} -Add @var{directory-path} to the list of directory paths searched when -Info needs to find a file. You may issue @code{--directory} multiple -times; once for each directory which contains Info files. -Alternatively, you may specify a value for the environment variable -@code{INFOPATH}; if @code{--directory} is not given, the value of -@code{INFOPATH} is used. The value of @code{INFOPATH} is a colon -separated list of directory names. If you do not supply @code{INFOPATH} -or @code{--directory-path}, Info uses a default path. - -@item --file @var{filename} -@itemx -f @var{filename} -@cindex Info file, selecting -Specify a particular Info file to visit. By default, Info visits -the file @code{dir}; if you use this option, Info will start with -@code{(@var{filename})Top} as the first file and node. - -@item --node @var{nodename} -@itemx -n @var{nodename} -@cindex node, selecting -Specify a particular node to visit in the initial file that Info -loads. This is especially useful in conjunction with -@code{--file}@footnote{Of course, you can specify both the file and node -in a @code{--node} command; but don't forget to escape the open and -close parentheses from the shell as in: @code{info --node -'(emacs)Buffers'}}. You may specify @code{--node} multiple times; for -an interactive Info, each @var{nodename} is visited in its own window, -for a non-interactive Info (such as when @code{--output} is given) each -@var{nodename} is processed sequentially. - -@item --output @var{filename} -@itemx -o @var{filename} -@cindex file, outputting to -@cindex outputting to a file -Specify @var{filename} as the name of a file to which to direct output. -Each node that Info visits will be output to @var{filename} instead of -interactively viewed. A value of @code{-} for @var{filename} specifies -the standard output. - -@item --subnodes -@cindex @code{--subnodes}, command line option -This option only has meaning when given in conjunction with -@code{--output}. It means to recursively output the nodes appearing in -the menus of each node being output. Menu items which resolve to -external Info files are not output, and neither are menu items which are -members of an index. Each node is only output once. - -@item --help -@itemx -h -Produces a relatively brief description of the available Info options. - -@item --version -@cindex version information -Prints the version information of Info and exits. - -@item @var{menu-item} -@cindex menu, following -Info treats its remaining arguments as the names of menu items. The -first argument is a menu item in the initial node visited, while -the second argument is a menu item in the first argument's node. -You can easily move to the node of your choice by specifying the menu -names which describe the path to that node. For example, - -@example -info emacs buffers -@end example - -@noindent -first selects the menu item @samp{Emacs} in the node @samp{(dir)Top}, -and then selects the menu item @samp{Buffers} in the node -@samp{(emacs)Top}. -@end table - -@node Cursor Commands, Scrolling Commands, Options, Top -@chapter Moving the Cursor -@cindex cursor, moving - -Many people find that reading screens of text page by page is made -easier when one is able to indicate particular pieces of text with some -kind of pointing device. Since this is the case, GNU Info (both the -Emacs and standalone versions) have several commands which allow you to -move the cursor about the screen. The notation used in this manual to -describe keystrokes is identical to the notation used within the Emacs -manual, and the GNU Readline manual. @xref{Characters, , Character -Conventions, emacs, the GNU Emacs Manual}, if you are unfamiliar with the -notation. - -The following table lists the basic cursor movement commands in Info. -Each entry consists of the key sequence you should type to execute the -cursor movement, the @code{M-x}@footnote{@code{M-x} is also a command; it -invokes @code{execute-extended-command}. @xref{M-x, , Executing an -extended command, emacs, the GNU Emacs Manual}, for more detailed -information.} command name (displayed in parentheses), and a short -description of what the command does. All of the cursor motion commands -can take an @dfn{numeric} argument (@pxref{Miscellaneous Commands, -@code{universal-argument}}), to find out how to supply them. With a -numeric argument, the motion commands are simply executed that -many times; for example, a numeric argument of 4 given to -@code{next-line} causes the cursor to move down 4 lines. With a -negative numeric argument, the motion is reversed; an argument of -4 -given to the @code{next-line} command would cause the cursor to move -@emph{up} 4 lines. - -@table @asis -@item @code{C-n} (@code{next-line}) -@kindex C-n -@findex next-line -Move the cursor down to the next line. - -@item @code{C-p} (@code{prev-line}) -@kindex C-p -@findex prev-line -Move the cursor up to the previous line. - -@item @code{C-a} (@code{beginning-of-line}) -@kindex C-a, in Info windows -@findex beginning-of-line -Move the cursor to the start of the current line. - -@item @code{C-e} (@code{end-of-line}) -@kindex C-e, in Info windows -@findex end-of-line -Move the cursor to the end of the current line. - -@item @code{C-f} (@code{forward-char}) -@kindex C-f, in Info windows -@findex forward-char -Move the cursor forward a character. - -@item @code{C-b} (@code{backward-char}) -@kindex C-b, in Info windows -@findex backward-char -Move the cursor backward a character. - -@item @code{M-f} (@code{forward-word}) -@kindex M-f, in Info windows -@findex forward-word -Move the cursor forward a word. - -@item @code{M-b} (@code{backward-word}) -@kindex M-b, in Info windows -@findex backward-word -Move the cursor backward a word. - -@item @code{M-<} (@code{beginning-of-node}) -@itemx @code{b} -@kindex b, in Info windows -@kindex M-< -@findex beginning-of-node -Move the cursor to the start of the current node. - -@item @code{M->} (@code{end-of-node}) -@kindex M-> -@findex end-of-node -Move the cursor to the end of the current node. - -@item @code{M-r} (@code{move-to-window-line}) -@kindex M-r -@findex move-to-window-line -Move the cursor to a specific line of the window. Without a numeric -argument, @code{M-r} moves the cursor to the start of the line in the -center of the window. With a numeric argument of @var{n}, @code{M-r} -moves the cursor to the start of the @var{n}th line in the window. -@end table - -@node Scrolling Commands, Node Commands, Cursor Commands, Top -@chapter Moving Text Within a Window -@cindex scrolling - -Sometimes you are looking at a screenful of text, and only part of the -current paragraph you are reading is visible on the screen. The -commands detailed in this section are used to shift which part of the -current node is visible on the screen. - -@table @asis -@item @code{SPC} (@code{scroll-forward}) -@itemx @code{C-v} -@kindex SPC, in Info windows -@kindex C-v -@findex scroll-forward -Shift the text in this window up. That is, show more of the node which -is currently below the bottom of the window. With a numeric argument, -show that many more lines at the bottom of the window; a numeric -argument of 4 would shift all of the text in the window up 4 lines -(discarding the top 4 lines), and show you four new lines at the bottom -of the window. Without a numeric argument, @key{SPC} takes the bottom -two lines of the window and places them at the top of the window, -redisplaying almost a completely new screenful of lines. - -@item @code{DEL} (@code{scroll-backward}) -@itemx @code{M-v} -@kindex DEL, in Info windows -@kindex M-v -@findex scroll-backward -Shift the text in this window down. The inverse of -@code{scroll-forward}. -@end table - -@cindex scrolling through node structure -The @code{scroll-forward} and @code{scroll-backward} commands can also -move forward and backward through the node structure of the file. If -you press @key{SPC} while viewing the end of a node, or @key{DEL} while -viewing the beginning of a node, what happens is controlled by the -variable @code{scroll-behavior}. @xref{Variables, -@code{scroll-behavior}}, for more information. - -@table @asis -@item @code{C-l} (@code{redraw-display}) -@kindex C-l -@findex redraw-display -Redraw the display from scratch, or shift the line containing the cursor -to a specified location. With no numeric argument, @samp{C-l} clears -the screen, and then redraws its entire contents. Given a numeric -argument of @var{n}, the line containing the cursor is shifted so that -it is on the @var{n}th line of the window. - -@item @code{C-x w} (@code{toggle-wrap}) -@kindex C-w -@findex toggle-wrap -Toggles the state of line wrapping in the current window. Normally, -lines which are longer than the screen width @dfn{wrap}, i.e., they are -continued on the next line. Lines which wrap have a @samp{\} appearing -in the rightmost column of the screen. You can cause such lines to be -terminated at the rightmost column by changing the state of line -wrapping in the window with @code{C-x w}. When a line which needs more -space than one screen width to display is displayed, a @samp{$} appears -in the rightmost column of the screen, and the remainder of the line is -invisible. -@end table - -@node Node Commands, Searching Commands, Scrolling Commands, Top -@chapter Selecting a New Node -@cindex nodes, selection of - -This section details the numerous Info commands which select a new node -to view in the current window. - -The most basic node commands are @samp{n}, @samp{p}, @samp{u}, and -@samp{l}. - -When you are viewing a node, the top line of the node contains some Info -@dfn{pointers} which describe where the next, previous, and up nodes -are. Info uses this line to move about the node structure of the file -when you use the following commands: - -@table @asis -@item @code{n} (@code{next-node}) -@kindex n -@findex next-node -Select the `Next' node. - -@item @code{p} (@code{prev-node}) -@kindex p -@findex prev-node -Select the `Prev' node. - -@item @code{u} (@code{up-node}) -@kindex u -@findex up-node -Select the `Up' node. -@end table - -You can easily select a node that you have already viewed in this window -by using the @samp{l} command -- this name stands for "last", and -actually moves through the list of already visited nodes for this -window. @samp{l} with a negative numeric argument moves forward through -the history of nodes for this window, so you can quickly step between -two adjacent (in viewing history) nodes. - -@table @asis -@item @code{l} (@code{history-node}) -@kindex l -@findex history-node -Select the most recently selected node in this window. -@end table - -Two additional commands make it easy to select the most commonly -selected nodes; they are @samp{t} and @samp{d}. - -@table @asis -@item @code{t} (@code{top-node}) -@kindex t -@findex top-node -Select the node @samp{Top} in the current Info file. - -@item @code{d} (@code{dir-node}) -@kindex d -@findex dir-node -Select the directory node (i.e., the node @samp{(dir)}). -@end table - -Here are some other commands which immediately result in the selection -of a different node in the current window: - -@table @asis -@item @code{<} (@code{first-node}) -@kindex < -@findex first-node -Selects the first node which appears in this file. This node is most -often @samp{Top}, but it does not have to be. - -@item @code{>} (@code{last-node}) -@kindex > -@findex last-node -Select the last node which appears in this file. - -@item @code{]} (@code{global-next-node}) -@kindex ] -@findex global-next-node -Move forward or down through node structure. If the node that you are -currently viewing has a @samp{Next} pointer, that node is selected. -Otherwise, if this node has a menu, the first menu item is selected. If -there is no @samp{Next} and no menu, the same process is tried with the -@samp{Up} node of this node. - -@item @code{[} (@code{global-prev-node}) -@kindex [ -@findex global-prev-node -Move backward or up through node structure. If the node that you are -currently viewing has a @samp{Prev} pointer, that node is selected. -Otherwise, if the node has an @samp{Up} pointer, that node is selected, -and if it has a menu, the last item in the menu is selected. -@end table - -You can get the same behavior as @code{global-next-node} and -@code{global-prev-node} while simply scrolling through the file with -@key{SPC} and @key{DEL}; @xref{Variables, @code{scroll-behavior}}, for -more information. - -@table @asis -@item @code{g} (@code{goto-node}) -@kindex g -@findex goto-node -Read the name of a node and select it. No completion is done while -reading the node name, since the desired node may reside in a separate -file. The node must be typed exactly as it appears in the Info file. A -file name may be included as with any node specification, for example - -@example -@code{g(emacs)Buffers} -@end example - -finds the node @samp{Buffers} in the Info file @file{emacs}. - -@item @code{C-x k} (@code{kill-node}) -@kindex C-x k -@findex kill-node -Kill a node. The node name is prompted for in the echo area, with a -default of the current node. @dfn{Killing} a node means that Info tries -hard to forget about it, removing it from the list of history nodes kept -for the window where that node is found. Another node is selected in -the window which contained the killed node. - -@item @code{C-x C-f} (@code{view-file}) -@kindex C-x C-f -@findex view-file -Read the name of a file and selects the entire file. The command -@example -@code{C-x C-f @var{filename}} -@end example -is equivalent to typing -@example -@code{g(@var{filename})*} -@end example - -@item @code{C-x C-b} (@code{list-visited-nodes}) -@kindex C-x C-b -@findex list-visited-nodes -Make a window containing a menu of all of the currently visited nodes. -This window becomes the selected window, and you may use the standard -Info commands within it. - -@item @code{C-x b} (@code{select-visited-node}) -@kindex C-x b -@findex select-visited-node -Select a node which has been previously visited in a visible window. -This is similar to @samp{C-x C-b} followed by @samp{m}, but no window is -created. -@end table - -@node Searching Commands, Xref Commands, Node Commands, Top -@chapter Searching an Info File -@cindex searching - -GNU Info allows you to search for a sequence of characters throughout an -entire Info file, search through the indices of an Info file, or find -areas within an Info file which discuss a particular topic. - -@table @asis -@item @code{s} (@code{search}) -@kindex s -@findex search -Read a string in the echo area and search for it. - -@item @code{C-s} (@code{isearch-forward}) -@kindex C-s -@findex isearch-forward -Interactively search forward through the Info file for a string as you -type it. - -@item @code{C-r} (@code{isearch-backward}) -@kindex C-r -@findex isearch-backward -Interactively search backward through the Info file for a string as -you type it. - -@item @code{i} (@code{index-search}) -@kindex i -@findex index-search -Look up a string in the indices for this Info file, and select a node -where the found index entry points to. - -@item @code{,} (@code{next-index-match}) -@kindex , -@findex next-index-match -Move to the node containing the next matching index item from the last -@samp{i} command. -@end table - -The most basic searching command is @samp{s} (@code{search}). The -@samp{s} command prompts you for a string in the echo area, and then -searches the remainder of the Info file for an occurrence of that string. -If the string is found, the node containing it is selected, and the -cursor is left positioned at the start of the found string. Subsequent -@samp{s} commands show you the default search string within @samp{[} and -@samp{]}; pressing @key{RET} instead of typing a new string will use the -default search string. - -@dfn{Incremental searching} is similar to basic searching, but the -string is looked up while you are typing it, instead of waiting until -the entire search string has been specified. - -@node Xref Commands, Window Commands, Searching Commands, Top -@chapter Selecting Cross References - -We have already discussed the @samp{Next}, @samp{Prev}, and @samp{Up} -pointers which appear at the top of a node. In addition to these -pointers, a node may contain other pointers which refer you to a -different node, perhaps in another Info file. Such pointers are called -@dfn{cross references}, or @dfn{xrefs} for short. - -@menu -* Parts of an Xref:: What a cross reference is made of. -* Selecting Xrefs:: Commands for selecting menu or note items. -@end menu - -@node Parts of an Xref, Selecting Xrefs, , Xref Commands -@section Parts of an Xref - -Cross references have two major parts: the first part is called the -@dfn{label}; it is the name that you can use to refer to the cross -reference, and the second is the @dfn{target}; it is the full name of -the node that the cross reference points to. - -The target is separated from the label by a colon @samp{:}; first the -label appears, and then the target. For example, in the sample menu -cross reference below, the single colon separates the label from the -target. - -@example -* Foo Label: Foo Target. More information about Foo. -@end example - -Note the @samp{.} which ends the name of the target. The @samp{.} is -not part of the target; it serves only to let Info know where the target -name ends. - -A shorthand way of specifying references allows two adjacent colons to -stand for a target name which is the same as the label name: - -@example -* Foo Commands:: Commands pertaining to Foo. -@end example - -In the above example, the name of the target is the same as the name of -the label, in this case @code{Foo Commands}. - -You will normally see two types of cross reference while viewing nodes: -@dfn{menu} references, and @dfn{note} references. Menu references -appear within a node's menu; they begin with a @samp{*} at the beginning -of a line, and continue with a label, a target, and a comment which -describes what the contents of the node pointed to contains. - -Note references appear within the body of the node text; they begin with -@code{*Note}, and continue with a label and a target. - -Like @samp{Next}, @samp{Prev}, and @samp{Up} pointers, cross references -can point to any valid node. They are used to refer you to a place -where more detailed information can be found on a particular subject. -Here is a cross reference which points to a node within the Texinfo -documentation: @xref{xref, , Writing an Xref, texinfo, the Texinfo -Manual}, for more information on creating your own texinfo cross -references. - -@node Selecting Xrefs, , Parts of an Xref, Xref Commands -@section Selecting Xrefs - -The following table lists the Info commands which operate on menu items. - -@table @asis -@item @code{1} (@code{menu-digit}) -@itemx @code{2} @dots{} @code{9} -@cindex 1 @dots{} 9, in Info windows -@kindex 1 @dots{} 9, in Info windows -@findex menu-digit -Within an Info window, pressing a single digit, (such as @samp{1}), -selects that menu item, and places its node in the current window. -For convenience, there is one exception; pressing @samp{0} selects the -@emph{last} item in the node's menu. - -@item @code{0} (@code{last-menu-item}) -@kindex 0, in Info windows -@findex last-menu-item -Select the last item in the current node's menu. - -@item @code{m} (@code{menu-item}) -@kindex m -@findex menu-item -Reads the name of a menu item in the echo area and selects its node. -Completion is available while reading the menu label. - -@item @code{M-x find-menu} -@findex find-menu -Move the cursor to the start of this node's menu. -@end table - -This table lists the Info commands which operate on note cross references. - -@table @asis -@item @code{f} (@code{xref-item}) -@itemx @code{r} -@kindex f -@kindex r -@findex xref-item -Reads the name of a note cross reference in the echo area and selects -its node. Completion is available while reading the cross reference -label. -@end table - -Finally, the next few commands operate on menu or note references alike: - -@table @asis -@item @code{TAB} (@code{move-to-next-xref}) -@kindex TAB, in Info windows -@findex move-to-next-xref -Move the cursor to the start of the next nearest menu item or note -reference in this node. You can then use @key{RET} -(@code{select-reference-this-line}) to select the menu or note reference. - -@item @code{M-TAB} (@code{move-to-prev-xref}) -@kindex M-TAB, in Info windows -@findex move-to-prev-xref -Move the cursor the start of the nearest previous menu item or note -reference in this node. - -@item @code{RET} (@code{select-reference-this-line}) -@kindex RET, in Info windows -@findex select-reference-this-line -Select the menu item or note reference appearing on this line. -@end table - -@node Window Commands, Printing Nodes, Xref Commands, Top -@chapter Manipulating Multiple Windows -@cindex windows, manipulating - -A @dfn{window} is a place to show the text of a node. Windows have a -view area where the text of the node is displayed, and an associated -@dfn{mode line}, which briefly describes the node being viewed. - -GNU Info supports multiple windows appearing in a single screen; each -window is separated from the next by its modeline. At any time, there -is only one @dfn{active} window, that is, the window in which the cursor -appears. There are commands available for creating windows, changing -the size of windows, selecting which window is active, and for deleting -windows. - -@menu -* The Mode Line:: What appears in the mode line? -* Basic Windows:: Manipulating windows in Info. -* The Echo Area:: Used for displaying errors and reading input. -@end menu - -@node The Mode Line, Basic Windows, , Window Commands -@section The Mode Line - -A @dfn{mode line} is a line of inverse video which appears at the bottom -of an Info window. It describes the contents of the window just above -it; this information includes the name of the file and node appearing in -that window, the number of screen lines it takes to display the node, -and the percentage of text that is above the top of the window. It can -also tell you if the indirect tags table for this Info file needs to be -updated, and whether or not the Info file was compressed when stored on -disk. - -Here is a sample mode line for a window containing an uncompressed file -named @file{dir}, showing the node @samp{Top}. - -@example -@group ------Info: (dir)Top, 40 lines --Top--------------------------------------- - ^^ ^ ^^^ ^^ - (file)Node #lines where -@end group -@end example - -When a node comes from a file which is compressed on disk, this is -indicated in the mode line with two small @samp{z}'s. In addition, if -the Info file containing the node has been split into subfiles, the name -of the subfile containing the node appears in the modeline as well: - -@example ---zz-Info: (emacs)Top, 291 lines --Top-- Subfile: emacs-1.Z--------------- -@end example - -When Info makes a node internally, such that there is no corresponding -info file on disk, the name of the node is surrounded by asterisks -(@samp{*}). The name itself tells you what the contents of the window -are; the sample mode line below shows an internally constructed node -showing possible completions: - -@example ------Info: *Completions*, 7 lines --All----------------------------------- -@end example - -@node Basic Windows, The Echo Area, The Mode Line, Window Commands -@section Window Commands - -It can be convenient to view more than one node at a time. To allow -this, Info can display more than one @dfn{window}. Each window has its -own mode line (@pxref{The Mode Line}) and history of nodes viewed in that -window (@pxref{Node Commands, , @code{history-node}}). - -@table @asis -@item @code{C-x o} (@code{next-window}) -@cindex windows, selecting -@kindex C-x o -@findex next-window -Select the next window on the screen. Note that the echo area can only be -selected if it is already in use, and you have left it temporarily. -Normally, @samp{C-x o} simply moves the cursor into the next window on -the screen, or if you are already within the last window, into the first -window on the screen. Given a numeric argument, @samp{C-x o} moves over -that many windows. A negative argument causes @samp{C-x o} to select -the previous window on the screen. - -@item @code{M-x prev-window} -@findex prev-window -Select the previous window on the screen. This is identical to -@samp{C-x o} with a negative argument. - -@item @code{C-x 2} (@code{split-window}) -@cindex windows, creating -@kindex C-x 2 -@findex split-window -Split the current window into two windows, both showing the same node. -Each window is one half the size of the original window, and the cursor -remains in the original window. The variable @code{automatic-tiling} -can cause all of the windows on the screen to be resized for you -automatically, please @pxref{Variables, , automatic-tiling} for more -information. - -@item @code{C-x 0} (@code{delete-window}) -@cindex windows, deleting -@kindex C-x 0 -@findex delete-window -Delete the current window from the screen. If you have made too many -windows and your screen appears cluttered, this is the way to get rid of -some of them. - -@item @code{C-x 1} (@code{keep-one-window}) -@kindex C-x 1 -@findex keep-one-window -Delete all of the windows excepting the current one. - -@item @code{ESC C-v} (@code{scroll-other-window}) -@kindex ESC C-v, in Info windows -@findex scroll-other-window -Scroll the other window, in the same fashion that @samp{C-v} might -scroll the current window. Given a negative argument, scroll the -"other" window backward. - -@item @code{C-x ^} (@code{grow-window}) -@kindex C-x ^ -@findex grow-window -Grow (or shrink) the current window. Given a numeric argument, grow -the current window that many lines; with a negative numeric argument, -shrink the window instead. - -@item @code{C-x t} (@code{tile-windows}) -@cindex tiling -@kindex C-x t -@findex tile-windows -Divide the available screen space among all of the visible windows. -Each window is given an equal portion of the screen in which to display -its contents. The variable @code{automatic-tiling} can cause -@code{tile-windows} to be called when a window is created or deleted. -@xref{Variables, , @code{automatic-tiling}}. -@end table - -@node The Echo Area, , Basic Windows, Window Commands -@section The Echo Area -@cindex echo area - -The @dfn{echo area} is a one line window which appears at the bottom of -the screen. It is used to display informative or error messages, and to -read lines of input from you when that is necessary. Almost all of the -commands available in the echo area are identical to their Emacs -counterparts, so please refer to that documentation for greater depth of -discussion on the concepts of editing a line of text. The following -table briefly lists the commands that are available while input is being -read in the echo area: - -@table @asis -@item @code{C-f} (@code{echo-area-forward}) -@kindex C-f, in the echo area -@findex echo-area-forward -Move forward a character. - -@item @code{C-b} (@code{echo-area-backward}) -@kindex C-b, in the echo area -@findex echo-area-backward -Move backward a character. - -@item @code{C-a} (@code{echo-area-beg-of-line}) -@kindex C-a, in the echo area -@findex echo-area-beg-of-line -Move to the start of the input line. - -@item @code{C-e} (@code{echo-area-end-of-line}) -@kindex C-e, in the echo area -@findex echo-area-end-of-line -Move to the end of the input line. - -@item @code{M-f} (@code{echo-area-forward-word}) -@kindex M-f, in the echo area -@findex echo-area-forward-word -Move forward a word. - -@item @code{M-b} (@code{echo-area-backward-word}) -@kindex M-b, in the echo area -@findex echo-area-backward-word -Move backward a word. - -@item @code{C-d} (@code{echo-area-delete}) -@kindex C-d, in the echo area -@findex echo-area-delete -Delete the character under the cursor. - -@item @code{DEL} (@code{echo-area-rubout}) -@kindex DEL, in the echo area -@findex echo-area-rubout -Delete the character behind the cursor. - -@item @code{C-g} (@code{echo-area-abort}) -@kindex C-g, in the echo area -@findex echo-area-abort -Cancel or quit the current operation. If completion is being read, -@samp{C-g} discards the text of the input line which does not match any -completion. If the input line is empty, @samp{C-g} aborts the calling -function. - -@item @code{RET} (@code{echo-area-newline}) -@kindex RET, in the echo area -@findex echo-area-newline -Accept (or forces completion of) the current input line. - -@item @code{C-q} (@code{echo-area-quoted-insert}) -@kindex C-q, in the echo area -@findex echo-area-quoted-insert -Insert the next character verbatim. This is how you can insert control -characters into a search string, for example. - -@item @var{printing character} (@code{echo-area-insert}) -@kindex printing characters, in the echo area -@findex echo-area-insert -Insert the character. - -@item @code{M-TAB} (@code{echo-area-tab-insert}) -@kindex M-TAB, in the echo area -@findex echo-area-tab-insert -Insert a TAB character. - -@item @code{C-t} (@code{echo-area-transpose-chars}) -@kindex C-t, in the echo area -@findex echo-area-transpose-chars -Transpose the characters at the cursor. -@end table - -The next group of commands deal with @dfn{killing}, and @dfn{yanking} -text. For an in depth discussion of killing and yanking, -@pxref{Killing, , Killing and Deleting, emacs, the GNU Emacs Manual} - -@table @asis -@item @code{M-d} (@code{echo-area-kill-word}) -@kindex M-d, in the echo area -@findex echo-area-kill-word -Kill the word following the cursor. - -@item @code{M-DEL} (@code{echo-area-backward-kill-word}) -@kindex M-DEL, in the echo area -@findex echo-area-backward-kill-word -Kill the word preceding the cursor. - -@item @code{C-k} (@code{echo-area-kill-line}) -@kindex C-k, in the echo area -@findex echo-area-kill-line -Kill the text from the cursor to the end of the line. - -@item @code{C-x DEL} (@code{echo-area-backward-kill-line}) -@kindex C-x DEL, in the echo area -@findex echo-area-backward-kill-line -Kill the text from the cursor to the beginning of the line. - -@item @code{C-y} (@code{echo-area-yank}) -@kindex C-y, in the echo area -@findex echo-area-yank -Yank back the contents of the last kill. - -@item @code{M-y} (@code{echo-area-yank-pop}) -@kindex M-y, in the echo area -@findex echo-area-yank-pop -Yank back a previous kill, removing the last yanked text first. -@end table - -Sometimes when reading input in the echo area, the command that needed -input will only accept one of a list of several choices. The choices -represent the @dfn{possible completions}, and you must respond with one -of them. Since there are a limited number of responses you can make, -Info allows you to abbreviate what you type, only typing as much of the -response as is necessary to uniquely identify it. In addition, you can -request Info to fill in as much of the response as is possible; this -is called @dfn{completion}. - -The following commands are available when completing in the echo area: - -@table @asis -@item @code{TAB} (@code{echo-area-complete}) -@itemx @code{SPC} -@kindex TAB, in the echo area -@kindex SPC, in the echo area -@findex echo-area-complete -Insert as much of a completion as is possible. - -@item @code{?} (@code{echo-area-possible-completions}) -@kindex ?, in the echo area -@findex echo-area-possible-completions -Display a window containing a list of the possible completions of what -you have typed so far. For example, if the available choices are: - -@example -@group -bar -foliate -food -forget -@end group -@end example - -@noindent -and you have typed an @samp{f}, followed by @samp{?}, the possible -completions would contain: - -@example -@group -foliate -food -forget -@end group -@end example - -@noindent -i.e., all of the choices which begin with @samp{f}. Pressing @key{SPC} -or @key{TAB} would result in @samp{fo} appearing in the echo area, since -all of the choices which begin with @samp{f} continue with @samp{o}. -Now, typing @samp{l} followed by @samp{TAB} results in @samp{foliate} -appearing in the echo area, since that is the only choice which begins -with @samp{fol}. - -@item @code{ESC C-v} (@code{echo-area-scroll-completions-window}) -@kindex ESC C-v, in the echo area -@findex echo-area-scroll-completions-window -Scroll the completions window, if that is visible, or the "other" -window if not. -@end table - -@node Printing Nodes, Miscellaneous Commands, Window Commands, Top -@chapter Printing Out Nodes -@cindex printing - -You may wish to print out the contents of a node as a quick reference -document for later use. Info provides you with a command for doing -this. In general, we recommend that you use @TeX{} to format the -document and print sections of it, by running @code{tex} on the Texinfo -source file. - -@table @asis -@item @code{M-x print-node} -@findex print-node -@cindex INFO_PRINT_COMMAND, environment variable -Pipe the contents of the current node through the command in the -environment variable @code{INFO_PRINT_COMMAND}. If the variable does not -exist, the node is simply piped to @code{lpr}. -@end table - -@node Miscellaneous Commands, Variables, Printing Nodes, Top -@chapter Miscellaneous Commands - -GNU Info contains several commands which self-document GNU Info: - -@table @asis -@item @code{M-x describe-command} -@cindex functions, describing -@cindex commands, describing -@findex describe-command -Read the name of an Info command in the echo area and then display a -brief description of what that command does. - -@item @code{M-x describe-key} -@cindex keys, describing -@findex describe-key -Read a key sequence in the echo area, and then display the name and -documentation of the Info command that the key sequence invokes. - -@item @code{M-x describe-variable} -Read the name of a variable in the echo area and then display a brief -description of what the variable affects. - -@item @code{M-x where-is} -@findex where-is -Read the name of an Info command in the echo area, and then display -a key sequence which can be typed in order to invoke that command. - -@item @code{C-h} (@code{get-help-window}) -@itemx @code{?} -@kindex C-h -@kindex ?, in Info windows -@findex get-help-window -Create (or Move into) the window displaying @code{*Help*}, and place -a node containing a quick reference card into it. This window displays -the most concise information about GNU Info available. - -@item @code{h} (@code{get-info-help-node}) -@kindex h -@findex get-info-help-node -Try hard to visit the node @code{(info)Help}. The Info file -@file{info.texi} distributed with GNU Info contains this node. Of -course, the file must first be processed with @code{makeinfo}, and then -placed into the location of your Info directory. -@end table - -Here are the commands for creating a numeric argument: - -@table @asis -@item @code{C-u} (@code{universal-argument}) -@cindex numeric arguments -@kindex C-u -@findex universal-argument -Start (or multiply by 4) the current numeric argument. @samp{C-u} is -a good way to give a small numeric argument to cursor movement or -scrolling commands; @samp{C-u C-v} scrolls the screen 4 lines, while -@samp{C-u C-u C-n} moves the cursor down 16 lines. - -@item @code{M-1} (@code{add-digit-to-numeric-arg}) -@itemx @code{M-2} @dots{} @code{M-9} -@kindex M-1 @dots{} M-9 -@findex add-digit-to-numeric-arg -Add the digit value of the invoking key to the current numeric -argument. Once Info is reading a numeric argument, you may just type -the digits of the argument, without the Meta prefix. For example, you -might give @samp{C-l} a numeric argument of 32 by typing: - -@example -@kbd{C-u 3 2 C-l} -@end example - -@noindent -or - -@example -@kbd{M-3 2 C-l} -@end example -@end table - -@samp{C-g} is used to abort the reading of a multi-character key -sequence, to cancel lengthy operations (such as multi-file searches) and -to cancel reading input in the echo area. - -@table @asis -@item @code{C-g} (@code{abort-key}) -@cindex cancelling typeahead -@cindex cancelling the current operation -@kindex C-g, in Info windows -@findex abort-key -Cancel current operation. -@end table - -The @samp{q} command of Info simply quits running Info. - -@table @asis -@item @code{q} (@code{quit}) -@cindex quitting -@kindex q -@findex quit -Exit GNU Info. -@end table - -If the operating system tells GNU Info that the screen is 60 lines tall, -and it is actually only 40 lines tall, here is a way to tell Info that -the operating system is correct. - -@table @asis -@item @code{M-x set-screen-height} -@findex set-screen-height -@cindex screen, changing the height of -Read a height value in the echo area and set the height of the -displayed screen to that value. -@end table - -Finally, Info provides a convenient way to display footnotes which might -be associated with the current node that you are viewing: - -@table @asis -@item @code{ESC C-f} (@code{show-footnotes}) -@kindex ESC C-f -@findex show-footnotes -@cindex footnotes, displaying -Show the footnotes (if any) associated with the current node in another -window. You can have Info automatically display the footnotes -associated with a node when the node is selected by setting the variable -@code{automatic-footnotes}. @xref{Variables, , @code{automatic-footnotes}}. -@end table - -@node Variables, GNU Info Global Index, Miscellaneous Commands, Top -@chapter Manipulating Variables - -GNU Info contains several @dfn{variables} whose values are looked at by various -Info commands. You can change the values of these variables, and thus -change the behavior of Info to more closely match your environment and -Info file reading manner. - -@table @asis -@item @code{M-x set-variable} -@cindex variables, setting -@findex set-variable -Read the name of a variable, and the value for it, in the echo area and -then set the variable to that value. Completion is available when -reading the variable name; often, completion is available when reading -the value to give to the variable, but that depends on the variable -itself. If a variable does @emph{not} supply multiple choices to -complete over, it expects a numeric value. - -@item @code{M-x describe-variable} -@cindex variables, describing -@findex describe-variable -Read the name of a variable in the echo area and then display a brief -description of what the variable affects. -@end table - -Here is a list of the variables that you can set in Info. - -@table @code -@item automatic-footnotes -@vindex automatic-footnotes -When set to @code{On}, footnotes appear and disappear automatically. -This variable is @code{On} by default. When a node is selected, a -window containing the footnotes which appear in that node is created, -and the footnotes are displayed within the new window. The window that -Info creates to contain the footnotes is called @samp{*Footnotes*}. If -a node is selected which contains no footnotes, and a @samp{*Footnotes*} -window is on the screen, the @samp{*Footnotes*} window is deleted. -Footnote windows created in this fashion are not automatically tiled so -that they can use as little of the display as is possible. - -@item automatic-tiling -@vindex automatic-tiling -When set to @code{On}, creating or deleting a window resizes other -windows. This variable is @code{Off} by default. Normally, typing -@samp{C-x 2} divides the current window into two equal parts. When -@code{automatic-tiling} is set to @code{On}, all of the windows are -resized automatically, keeping an equal number of lines visible in each -window. There are exceptions to the automatic tiling; specifically, the -windows @samp{*Completions*} and @samp{*Footnotes*} are @emph{not} -resized through automatic tiling; they remain their original size. - -@item visible-bell -@vindex visible-bell -When set to @code{On}, GNU Info attempts to flash the screen instead of -ringing the bell. This variable is @code{Off} by default. Of course, -Info can only flash the screen if the terminal allows it; in the case -that the terminal does not allow it, the setting of this variable has no -effect. However, you can make Info perform quietly by setting the -@code{errors-ring-bell} variable to @code{Off}. - -@item errors-ring-bell -@vindex errors-ring-bell -When set to @code{On}, errors cause the bell to ring. The default -setting of this variable is @code{On}. - -@item gc-compressed-files -@vindex gc-compressed-files -When set to @code{On}, Info garbage collects files which had to be -uncompressed. The default value of this variable is @code{Off}. -Whenever a node is visited in Info, the Info file containing that node -is read into core, and Info reads information about the tags and nodes -contained in that file. Once the tags information is read by Info, it -is never forgotten. However, the actual text of the nodes does not need -to remain in core unless a particular Info window needs it. For -non-compressed files, the text of the nodes does not remain in core when -it is no longer in use. But de-compressing a file can be a time -consuming operation, and so Info tries hard not to do it twice. -@code{gc-compressed-files} tells Info it is okay to garbage collect the -text of the nodes of a file which was compressed on disk. - -@item show-index-match -@vindex show-index-match -When set to @code{On}, the portion of the matched search string is -highlighted in the message which explains where the matched search -string was found. The default value of this variable is @code{On}. -When Info displays the location where an index match was found, -(@pxref{Searching Commands, , @code{next-index-match}}), the portion of the -string that you had typed is highlighted by displaying it in the inverse -case from its surrounding characters. - -@item scroll-behavior -@vindex scroll-behavior -Control what happens when forward scrolling is requested at the end of -a node, or when backward scrolling is requested at the beginning of a -node. The default value for this variable is @code{Continuous}. There -are three possible values for this variable: - -@table @code -@item Continuous -Try to get the first item in this node's menu, or failing that, the -@samp{Next} node, or failing that, the @samp{Next} of the @samp{Up}. -This behavior is identical to using the @samp{]} -(@code{global-next-node}) and @samp{[} (@code{global-prev-node}) -commands. - -@item Next Only -Only try to get the @samp{Next} node. - -@item Page Only -Simply give up, changing nothing. If @code{scroll-behavior} is -@code{Page Only}, no scrolling command can change the node that is being -viewed. -@end table - -@item scroll-step -@vindex scroll-step -The number of lines to scroll when the cursor moves out of the window. -Scrolling happens automatically if the cursor has moved out of the -visible portion of the node text when it is time to display. Usually -the scrolling is done so as to put the cursor on the center line of the -current window. However, if the variable @code{scroll-step} has a -nonzero value, Info attempts to scroll the node text by that many lines; -if that is enough to bring the cursor back into the window, that is what -is done. The default value of this variable is 0, thus placing the -cursor (and the text it is attached to) in the center of the window. -Setting this variable to 1 causes a kind of "smooth scrolling" which -some people prefer. - -@item ISO-Latin -@cindex ISO Latin characters -@vindex ISO-Latin -When set to @code{On}, Info accepts and displays ISO Latin characters. -By default, Info assumes an ASCII character set. @code{ISO-Latin} tells -Info that it is running in an environment where the European standard -character set is in use, and allows you to input such characters to -Info, as well as display them. -@end table - - - -@c the following is incomplete -@ignore -@c node Info for Sys Admins -@c chapter Info for System Administrators - -This text describes some common ways of setting up an Info hierarchy -from scratch, and details the various options that are available when -installing Info. This text is designed for the person who is installing -GNU Info on the system; although users may find the information present -in this section interesting, none of it is vital to understanding how to -use GNU Info. - -@menu -* Setting the INFOPATH:: Where are my Info files kept? -* Editing the DIR node:: What goes in `DIR', and why? -* Storing Info files:: Alternate formats allow flexibility in setups. -* Using `localdir':: Building DIR on the fly. -* Example setups:: Some common ways to organize Info files. -@end menu - -@c node Setting the INFOPATH -@c section Setting the INFOPATH - -Where are my Info files kept? - -@c node Editing the DIR node -@c section Editing the DIR node - -What goes in `DIR', and why? - -@c node Storing Info files -@c section Storing Info files - -Alternate formats allow flexibility in setups. - -@c node Using `localdir' -@c section Using `localdir' - -Building DIR on the fly. - -@c node Example setups -@c section Example setups - -Some common ways to organize Info files. -@end ignore - -@node GNU Info Global Index, , Variables, Top -@appendix Global Index - -@printindex cp - -@contents -@bye diff --git a/gnu/usr.bin/texinfo/doc/info.texi b/gnu/usr.bin/texinfo/doc/info.texi deleted file mode 100644 index 5eec9f1..0000000 --- a/gnu/usr.bin/texinfo/doc/info.texi +++ /dev/null @@ -1,861 +0,0 @@ -\input texinfo @c -*-texinfo-*- -@comment %**start of header -@setfilename info.info -@settitle Info 1.0 -@comment %**end of header - -@iftex -@finalout -@end iftex - -@ifinfo -This file describes how to use Info, -the on-line, menu-driven GNU documentation system. - -Copyright (C) 1989, 1992 Free Software Foundation, Inc. - -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 - -@setchapternewpage odd -@titlepage -@sp 11 -@center @titlefont{Info} -@sp 2 -@center The -@sp 2 -@center On-line, Menu-driven -@sp 2 -@center GNU Documentation System - -@page -@vskip 0pt plus 1filll -Copyright @copyright{} 1989, 1992, 1993 Free Software Foundation, Inc. -@sp 2 - -Published by the Free Software Foundation @* -675 Massachusetts Avenue, @* -Cambridge, MA 02139 USA @* - -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 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 titlepage - -@ifinfo -@node Top, Getting Started, (dir), (dir) -@top Info: An Introduction - -Info is a program for reading documentation, which you are using now. - -To learn how to use Info, type the command @kbd{h}. It brings you -to a programmed instruction sequence. - -@c Need to make sure that `Info-help' goes to the right node, -@c which is the first node of the first chapter. (It should.) -@c (Info-find-node "info" -@c (if (< (window-height) 23) -@c "Help-Small-Screen" -@c "Help"))) - -To learn advanced Info commands, type @kbd{n} twice. This -brings you to @cite{Info for Experts}, skipping over the . -`Getting Started' chapter. -@end ifinfo - -@menu -* Getting Started:: -* Advanced Info:: -* Create an Info File:: -@end menu - -@node Getting Started, Advanced Info, Top, Top -@comment node-name, next, previous, up -@chapter Getting Started - -This first part of the Info manual describes how to get around inside -of Info. The second part of the manual describes various advanced -Info commands, and how to write an Info as distinct from a Texinfo -file. The third part is about how to generate Info files from -Texinfo files. - -@iftex -This manual is primarily designed for use on a computer, so that you can -try Info commands while reading about them. Reading it on paper is less -effective, since you must take it on faith that the commands described -really do what the manual says. By all means go through this manual now -that you have it; but please try going through the on-line version as -well. - -There are two ways of looking at the online version of this manual: - -@enumerate -@item -Type @code{info} at your shell's command line. This approach uses a -small stand-alone program designed just to read Info files. - -@item -Type @code{emacs} at the command line; then type @kbd{C-h i} (Control -@kbd{h}, followed by @kbd{i}). This approach uses -the Info mode of the Emacs program, an editor with many other -capabilities. -@end enumerate - -In either case, then type @kbd{mInfo} (just the letters), followed by -@key{RET}---the ``Return'' or ``Enter'' key. At this point, you should -be ready to follow the instructions in this manual as you read them on -the screen. -@c FIXME! (pesch@cygnus.com, 14 dec 1992) -@c Is it worth worrying about what-if the beginner goes to somebody -@c else's Emacs session, which already has an Info running in the middle -@c of something---in which case these simple instructions won't work? -@end iftex - -@menu -* Help-Small-Screen:: Starting Info on a Small Screen -* Help:: How to use Info -* Help-P:: Returning to the Previous node -* Help-^L:: The Space, Rubout, B and ^L commands. -* Help-M:: Menus -* Help-Adv:: Some advanced Info commands -* Help-Q:: Quitting Info -@end menu - -@node Help-Small-Screen, Help, , Getting Started -@comment node-name, next, previous, up -@section Starting Info on a Small Screen - -@iftex -(In Info, you only see this section if your terminal has a small -number of lines; most readers pass by it without seeing it.) -@end iftex - -Since your terminal has an unusually small number of lines on its -screen, it is necessary to give you special advice at the beginning. - -If you see the text @samp{--All----} at near the bottom right corner -of the screen, it means the entire text you are looking at fits on the -screen. If you see @samp{--Top----} instead, it means that there is -more text below that does not fit. To move forward through the text -and see another screen full, press the Space bar, @key{SPC}. To move -back up, press the key labeled @samp{Rubout} or @samp{Delete} or -@key{DEL}. - -@ifinfo -Here are 40 lines of junk, so you can try @key{SPC} and @key{DEL} and -see what they do. At the end are instructions of what you should do -next. - -This is line 17 @* -This is line 18 @* -This is line 19 @* -This is line 20 @* -This is line 21 @* -This is line 22 @* -This is line 23 @* -This is line 24 @* -This is line 25 @* -This is line 26 @* -This is line 27 @* -This is line 28 @* -This is line 29 @* -This is line 30 @* -This is line 31 @* -This is line 32 @* -This is line 33 @* -This is line 34 @* -This is line 35 @* -This is line 36 @* -This is line 37 @* -This is line 38 @* -This is line 39 @* -This is line 40 @* -This is line 41 @* -This is line 42 @* -This is line 43 @* -This is line 44 @* -This is line 45 @* -This is line 46 @* -This is line 47 @* -This is line 48 @* -This is line 49 @* -This is line 50 @* -This is line 51 @* -This is line 52 @* -This is line 53 @* -This is line 54 @* -This is line 55 @* -This is line 56 @* - -If you have managed to get here, go back to the beginning with -@key{DEL}, and come back here again, then you understand @key{SPC} and -@key{DEL}. So now type an @kbd{n}---just one character; do not type -the quotes and do not type the Return key, @key{RET}, afterward---to -get to the normal start of the course. -@end ifinfo - -@node Help, Help-P, Help-Small-Screen, Getting Started -@comment node-name, next, previous, up -@section How to use Info - -You are talking to the program Info, for reading documentation. - - Right now you are looking at one @dfn{Node} of Information. -A node contains text describing a specific topic at a specific -level of detail. This node's topic is ``how to use Info''. - - The top line of a node is its @dfn{header}. This node's header (look at -it now) says that it is the node named @samp{Help} in the file -@file{info}. It says that the @samp{Next} node after this one is the node -called @samp{Help-P}. An advanced Info command lets you go to any node -whose name you know. - - Besides a @samp{Next}, a node can have a @samp{Previous} or an @samp{Up}. -This node has a @samp{Previous} but no @samp{Up}, as you can see. - - Now it is time to move on to the @samp{Next} node, named @samp{Help-P}. - ->> Type @samp{n} to move there. Type just one character; - do not type the quotes and do not type a @key{RET} afterward. - -@samp{>>} in the margin means it is really time to try a command. - -@node Help-P, Help-^L, Help, Getting Started -@comment node-name, next, previous, up -@section Returning to the Previous node - -This node is called @samp{Help-P}. The @samp{Previous} node, as you see, -is @samp{Help}, which is the one you just came from using the @kbd{n} -command. Another @kbd{n} command now would take you to the next -node, @samp{Help-^L}. - ->> But do not do that yet. First, try the @kbd{p} command, which takes - you to the @samp{Previous} node. When you get there, you can do an - @kbd{n} again to return here. - - This all probably seems insultingly simple so far, but @emph{do not} be -led into skimming. Things will get more complicated soon. Also, -do not try a new command until you are told it is time to. Otherwise, -you may make Info skip past an important warning that was coming up. - ->> Now do an @kbd{n} to get to the node @samp{Help-^L} and learn more. - -@node Help-^L, Help-M, Help-P, Getting Started -@comment node-name, next, previous, up -@section The Space, Rubout, B and ^L commands. - - This node's header tells you that you are now at node @samp{Help-^L}, and -that @kbd{p} would get you back to @samp{Help-P}. The node's title is -underlined; it says what the node is about (most nodes have titles). - - This is a big node and it does not all fit on your display screen. -You can tell that there is more that is not visible because you -can see the string @samp{--Top-----} rather than @samp{--All----} near -the bottom right corner of the screen. - - The @key{SPC}, @key{DEL} and @kbd{b} commands exist to allow you to ``move -around'' in a node that does not all fit on the screen at once. -@key{SPC} moves forward, to show what was below the bottom of the screen. -@key{DEL} moves backward, to show what was above the top of the screen -(there is not anything above the top until you have typed some spaces). - ->> Now try typing a @key{SPC} (afterward, type a @key{DEL} to return here). - - When you type the @key{SPC}, the two lines that were at the bottom -of the screen appear at the top, followed by more lines. @key{DEL} -takes the two lines from the top and moves them to the bottom, -@emph{usually}, but if there are not a full screen's worth of lines above -them they may not make it all the way to the bottom. - - If you type a @key{SPC} when there is no more to see, it rings the -bell and otherwise does nothing. The same goes for a @key{DEL} when -the header of the node is visible. - - If your screen is ever garbaged, you can tell Info to print it out -again by typing @kbd{C-l} (@kbd{Control-L}, that is---hold down ``Control'' and -type an @key{L} or @kbd{l}). - ->> Type @kbd{C-l} now. - - To move back to the beginning of the node you are on, you can type -a lot of @key{DEL}s. You can also type simply @kbd{b} for beginning. - ->> Try that now. (I have put in enough verbiage to make sure you are - not on the first screenful now). Then come back, typing @key{SPC} - several times. - - You have just learned a considerable number of commands. If you -want to use one but have trouble remembering which, you should type -a @key{?} which prints out a brief list of commands. When you are -finished looking at the list, make it go away by typing a @key{SPC}. - ->> Type a @key{?} now. After it finishes, type a @key{SPC}. - - (If you are using the standalone Info reader, type `l' to return here.) - - From now on, you will encounter large nodes without warning, and -will be expected to know how to use @key{SPC} and @key{DEL} to move -around in them without being told. Since not all terminals have -the same size screen, it would be impossible to warn you anyway. - ->> Now type @kbd{n} to see the description of the @kbd{m} command. - -@node Help-M, Help-Adv, Help-^L, Getting Started -@comment node-name, next, previous, up -@section Menus - -Menus and the @kbd{m} command - - With only the @kbd{n} and @kbd{p} commands for moving between nodes, nodes -are restricted to a linear sequence. Menus allow a branching -structure. A menu is a list of other nodes you can move to. It is -actually just part of the text of the node formatted specially so that -Info can interpret it. The beginning of a menu is always identified -by a line which starts with @samp{* Menu:}. A node contains a menu if and -only if it has a line in it which starts that way. The only menu you -can use at any moment is the one in the node you are in. To use a -menu in any other node, you must move to that node first. - - After the start of the menu, each line that starts with a @samp{*} -identifies one subtopic. The line usually contains a brief name -for the subtopic (followed by a @samp{:}), the name of the node that talks -about that subtopic, and optionally some further description of the -subtopic. Lines in the menu that do not start with a @samp{*} have no -special meaning---they are only for the human reader's benefit and do -not define additional subtopics. Here is an example: - -@example -* Foo: FOO's Node This tells about FOO -@end example - -The subtopic name is Foo, and the node describing it is @samp{FOO's Node}. -The rest of the line is just for the reader's Information. -[[ But this line is not a real menu item, simply because there is -no line above it which starts with @samp{* Menu:}.]] - - When you use a menu to go to another node (in a way that will be -described soon), what you specify is the subtopic name, the first -thing in the menu line. Info uses it to find the menu line, extracts -the node name from it, and goes to that node. The reason that there -is both a subtopic name and a node name is that the node name must be -meaningful to the computer and may therefore have to be ugly looking. -The subtopic name can be chosen just to be convenient for the user to -specify. Often the node name is convenient for the user to specify -and so both it and the subtopic name are the same. There is an -abbreviation for this: - -@example -* Foo:: This tells about FOO -@end example - -@noindent -This means that the subtopic name and node name are the same; they are -both @samp{Foo}. - ->> Now use @key{SPC}s to find the menu in this node, then come back to - the front with a @kbd{b}. As you see, a menu is actually visible in - its node. If you cannot find a menu in a node by looking at it, - then the node does not have a menu and the @kbd{m} command is not - available. - - The command to go to one of the subnodes is @kbd{m}---but @emph{do not do it -yet!} Before you use @kbd{m}, you must understand the difference between -commands and arguments. So far, you have learned several commands -that do not need arguments. When you type one, Info processes it and -is instantly ready for another command. The @kbd{m} command is different: -it is incomplete without the @dfn{name of the subtopic}. Once you have -typed @kbd{m}, Info tries to read the subtopic name. - - Now look for the line containing many dashes near the bottom of the -screen. There is one more line beneath that one, but usually it is -blank If it is empty, Info is ready for a command, such as @kbd{n} or @kbd{b} -or @key{SPC} or @kbd{m}. If that line contains text ending in a colon, it -mean Info is trying to read the @dfn{argument} to a command. At such -times, commands do not work, because Info tries to use them as the -argument. You must either type the argument and finish the command -you started, or type @kbd{Control-g} to cancel the command. When you have -done one of those things, the line becomes blank again. - - The command to go to a subnode via a menu is @kbd{m}. After you type -the @kbd{m}, the line at the bottom of the screen says @samp{Menu item: }. -You must then type the name of the subtopic you want, and end it with -a @key{RET}. - - You can abbreviate the subtopic name. If the abbreviation is not -unique, the first matching subtopic is chosen. Some menus put -the shortest possible abbreviation for each subtopic name in capital -letters, so you can see how much you need to type. It does not -matter whether you use upper case or lower case when you type the -subtopic. You should not put any spaces at the end, or inside of the -item name, except for one space where a space appears in the item in -the menu. - - Here is a menu to give you a chance to practice. - -* Menu: The menu starts here. - -This menu givs you three ways of going to one place, Help-FOO. - -* Foo: Help-FOO. A node you can visit for fun.@* -* Bar: Help-FOO. Strange! two ways to get to the same place.@* -* Help-FOO:: And yet another!@* - - ->> Now type just an @kbd{m} and see what happens: - - Now you are ``inside'' an @kbd{m} command. Commands cannot be used -now; the next thing you will type must be the name of a subtopic. - - You can change your mind about doing the @kbd{m} by typing Control-g. - ->> Try that now; notice the bottom line clear. - ->> Then type another @kbd{m}. - ->> Now type @samp{BAR} item name. Do not type @key{RET} yet. - - While you are typing the item name, you can use the @key{DEL} -character to cancel one character at a time if you make a mistake. - ->> Type one to cancel the @samp{R}. You could type another @samp{R} to - replace it. You do not have to, since @samp{BA} is a valid abbreviation. - ->> Now you are ready to go. Type a @key{RET}. - - After visiting Help-FOO, you should return here. - ->> Type @kbd{n} to see more commands. - -@c If a menu appears at the end of this node, remove it. -@c It is an accident of the menu updating command. - -Here is another way to get to Help-FOO, a menu. You can ignore this -if you want, or else try it (but then please come back to here). - -@menu -* Help-FOO:: -@end menu - -@node Help-FOO, , , Help-M -@comment node-name, next, previous, up -@subsection The @kbd{u} command - - Congratulations! This is the node @samp{Help-FOO}. Unlike the other -nodes you have seen, this one has an @samp{Up}: @samp{Help-M}, the node you -just came from via the @kbd{m} command. This is the usual -convention---the nodes you reach from a menu have @samp{Up} nodes that lead -back to the menu. Menus move Down in the tree, and @samp{Up} moves Up. -@samp{Previous}, on the other hand, is usually used to ``stay on the same -level but go backwards'' - - You can go back to the node @samp{Help-M} by typing the command -@kbd{u} for ``Up''. That puts you at the @emph{front} of the -node---to get back to where you were reading you have to type -some @key{SPC}s. - ->> Now type @kbd{u} to move back up to @samp{Help-M}. - -@node Help-Adv, Help-Q, Help-M, Getting Started -@comment node-name, next, previous, up -@section Some advanced Info commands - - The course is almost over, so please stick with it to the end. - - If you have been moving around to different nodes and wish to -retrace your steps, the @kbd{l} command (@kbd{l} for @dfn{last}) will -do that, one node at a time. If you have been following directions, -an @kbd{l} command now will get you back to @samp{Help-M}. Another -@kbd{l} command would undo the @kbd{u} and get you back to -@samp{Help-FOO}. Another @kbd{l} would undo the @kbd{m} and get you -back to @samp{Help-M}. - ->> Try typing three @kbd{l}'s, pausing in between to see what each - @kbd{l} does. - -Then follow directions again and you will end up back here. - - Note the difference between @kbd{l} and @kbd{p}: @kbd{l} moves to -where @emph{you} last were, whereas @kbd{p} always moves to the node -which the header says is the @samp{Previous} node (from this node, to -@samp{Help-M}). - - The @samp{d} command gets you instantly to the Directory node. -This node, which is the first one you saw when you entered Info, -has a menu which leads (directly, or indirectly through other menus), -to all the nodes that exist. - ->> Try doing a @samp{d}, then do an @kbd{l} to return here (yes, - @emph{do} return). - - Sometimes, in Info documentation, you will see a cross reference. -Cross references look like this: @xref{Help-Cross, Cross}. That is a -real, live cross reference which is named @samp{Cross} and points at -the node named @samp{Help-Cross}. - - If you wish to follow a cross reference, you must use the @samp{f} -command. The @samp{f} must be followed by the cross reference name -(in this case, @samp{Cross}). You can use @key{DEL} to edit the name, -and if you change your mind about following any reference you can use -@kbd{Control-g} to cancel the command. - - Completion is available in the @samp{f} command; you can complete among -all the cross reference names in the current node. - ->> Type @samp{f}, followed by @samp{Cross}, and a @key{RET}. - - To get a list of all the cross references in the current node, you can -type @kbd{?} after an @samp{f}. The @samp{f} continues to await a -cross reference name even after printing the list, so if you do not -actually want to follow a reference you should type a @kbd{Control-g} -to cancel the @samp{f}. - ->> Type "f?" to get a list of the footnotes in this node. Then type a - @kbd{Control-g} and see how the @samp{f} gives up. - ->> Now type @kbd{n} to see the last node of the course. - -@c If a menu appears at the end of this node, remove it. -@c It is an accident of the menu updating command. - -@node Help-Cross, , , Help-Adv -@comment node-name, next, previous, up -@unnumberedsubsec The node reached by the cross reference in Info - - This is the node reached by the cross reference named @samp{Cross}. - - While this node is specifically intended to be reached by a cross -reference, most cross references lead to nodes that ``belong'' -someplace else far away in the structure of Info. So you cannot expect -the footnote to have a @samp{Next}, @samp{Previous} or @samp{Up} pointing back to -where you came from. In general, the @kbd{l} (el) command is the only -way to get back there. - ->> Type @kbd{l} to return to the node where the cross reference was. - -@node Help-Q, , Help-Adv, Getting Started -@comment node-name, next, previous, up -@section Quitting Info - - To get out of Info, back to what you were doing before, type @kbd{q} -for @dfn{Quit}. - - This is the end of the course on using Info. There are some other -commands that are not essential or are meant for experienced users; -they are useful, and you can find them by looking in the directory for -documentation on Info. Finding them will be a good exercise in using -Info in the usual manner. - ->> Type @samp{d} to go to the Info directory node; then type - @samp{mInfo} and @key{RET}, to get to the node about Info - and see what other help is available. - -@node Advanced Info, Create an Info File, Getting Started, Top -@comment node-name, next, previous, up -@chapter Info for Experts - -This chapter describes various advanced Info commands, and how to write -an Info as distinct from a Texinfo file. (However, in most cases, writing a -Texinfo file is better, since you can use it @emph{both} to generate an -Info file and to make a printed manual. @xref{Top,, Overview of -Texinfo, texinfo, Texinfo: The GNU Documentation Format}.) - -@menu -* Expert:: Advanced Info commands: g, s, e, and 1 - 5. -* Add:: Describes how to add new nodes to the hierarchy. - Also tells what nodes look like. -* Menus:: How to add to or create menus in Info nodes. -* Cross-refs:: How to add cross-references to Info nodes. -* Tags:: How to make tag tables for Info files. -* Checking:: Checking an Info File -@end menu - -@node Expert, Add, , Advanced Info -@comment node-name, next, previous, up -@section Advanced Info Commands - -@kbd{g}, @kbd{s}, @kbd{1}, -- @kbd{5}, and @kbd{e} - -If you know a node's name, you can go there by typing @kbd{g}, the -name, and @key{RET}. Thus, @kbd{gTop@key{RET}} would go to the node -called @samp{Top} in this file (its directory node). -@kbd{gExpert@key{RET}} would come back here. - -Unlike @kbd{m}, @kbd{g} does not allow the use of abbreviations. - -To go to a node in another file, you can include the filename in the -node name by putting it at the front, in parentheses. Thus, -@kbd{g(dir)Top@key{RET}} would go to the Info Directory node, which is -node @samp{Top} in the file @file{dir}. - -The node name @samp{*} specifies the whole file. So you can look at -all of the current file by typing @kbd{g*@key{RET}} or all of any -other file with @kbd{g(FILENAME)@key{RET}}. - -The @kbd{s} command allows you to search a whole file for a string. -It switches to the next node if and when that is necessary. You -type @kbd{s} followed by the string to search for, terminated by -@key{RET}. To search for the same string again, just @kbd{s} followed -by @key{RET} will do. The file's nodes are scanned in the order -they are in in the file, which has no necessary relationship to the -order that they may be in in the tree structure of menus and @samp{next} pointers. -But normally the two orders are not very different. In any case, -you can always do a @kbd{b} to find out what node you have reached, if -the header is not visible (this can happen, because @kbd{s} puts your -cursor at the occurrence of the string, not at the beginning of the -node). - -If you grudge the system each character of type-in it requires, you -might like to use the commands @kbd{1}, @kbd{2}, @kbd{3}, @kbd{4}, and -@kbd{5}. They are short for the @kbd{m} command together with an -argument. "1", "2", "3", "4", and "5". @kbd{1} goes through the -first item in the current node's menu; @kbd{2} goes through the second -item, etc. Note that numbers larger than 5 are not allowed. If the -item you want is that far down, you are better off using an -abbreviation for its name than counting. - -The Info command @kbd{e} changes from Info mode to an ordinary -Emacs editing mode, so that you can edit the text of the current node. -Type @kbd{C-c C-c} to switch back to Info. The @kbd{e} command is allowed -only if the variable @code{Info-enable-edit} is non-@code{nil}. - -@node Add, Menus, Expert, Advanced Info -@comment node-name, next, previous, up -@section Adding a new node to Info - -To add a new topic to the list in the directory, you must: - -@enumerate -@item -Create a node, in some file, to document that topic. - -@item -Put that topic in the menu in the directory. @xref{Menus, Menu}. -@end enumerate - - The new node can live in an existing documentation file, or in a new -one. It must have a @key{^_} character before it (invisible to the -user; this node has one but you cannot see it), and it ends with either -a @key{^_}, a @key{^L}, or the end of file. Note: If you put in a -@key{^L} to end a new node, be sure that there is a @key{^_} after it -to start the next one, since @key{^L} cannot @emph{start} a node. -Also, a nicer way to make a node boundary be a page boundary as well -is to put a @key{^L} @emph{right after} the @key{^_}. - - The @key{^_} starting a node must be followed by a newline or a -@key{^L} newline, after which comes the node's header line. The -header line must give the node's name (by which Info finds it), -and state the names of the @samp{Next}, @samp{Previous}, and @samp{Up} nodes (if -there are any). As you can see, this node's @samp{Up} node is the node -@samp{Top}, which points at all the documentation for Info. The @samp{Next} -node is @samp{Menus}. - - The keywords @dfn{Node}, @dfn{Previous}, @dfn{Up} and @dfn{Next}, -may appear in any order, anywhere in the header line, but the -recommended order is the one in this sentence. Each keyword must be -followed by a colon, spaces and tabs, and then the appropriate name. -The name may be terminated with a tab, a comma, or a newline. A space -does not end it; node names may contain spaces. The case of letters -in the names is insignificant. - - A node name has two forms. A node in the current file is named by -what appears after the @samp{Node: } in that node's first line. For -example, this node's name is @samp{Add}. A node in another file is -named by @samp{(@var{filename})@var{node-within-file}}, as in -@samp{(info)Add} for this node. If the file name is relative, it is -taken starting from the standard Info file directory of your site. -The name @samp{(@var{filename})Top} can be abbreviated to just -@samp{(@var{filename})}. By convention, the name @samp{Top} is used for -the ``highest'' node in any single file---the node whose @samp{Up} points -out of the file. The Directory node is @file{(dir)}. The @samp{Top} node -of a document file listed in the Directory should have an @samp{Up: -(dir)} in it. - - The node name @kbd{*} is special: it refers to the entire file. -Thus, @kbd{g*} shows you the whole current file. The use of the -node @kbd{*} is to make it possible to make old-fashioned, -unstructured files into nodes of the tree. - - The @samp{Node:} name, in which a node states its own name, must not -contain a filename, since Info when searching for a node does not -expect one to be there. The @samp{Next}, @samp{Previous} and @samp{Up} names may -contain them. In this node, since the @samp{Up} node is in the same file, -it was not necessary to use one. - - Note that the nodes in this file have a file name in the header -line. The file names are ignored by Info, but they serve as comments -to help identify the node for the user. - -@node Menus, Cross-refs, Add, Advanced Info -@comment node-name, next, previous, up -@section How to Create Menus - - Any node in the Info hierarchy may have a @dfn{menu}---a list of subnodes. -The @kbd{m} command searches the current node's menu for the topic which it -reads from the terminal. - - A menu begins with a line starting with @samp{* Menu:}. The rest of the -line is a comment. After the starting line, every line that begins -with a @samp{* } lists a single topic. The name of the topic--the -argument that the user must give to the @kbd{m} command to select this -topic---comes right after the star and space, and is followed by a -colon, spaces and tabs, and the name of the node which discusses that -topic. The node name, like node names following @samp{Next}, @samp{Previous} -and @samp{Up}, may be terminated with a tab, comma, or newline; it may also -be terminated with a period. - - If the node name and topic name are the same, than rather than -giving the name twice, the abbreviation @samp{* NAME::} may be used -(and should be used, whenever possible, as it reduces the visual -clutter in the menu). - - It is considerate to choose the topic names so that they differ -from each other very near the beginning---this allows the user to type -short abbreviations. In a long menu, it is a good idea to capitalize -the beginning of each item name which is the minimum acceptable -abbreviation for it (a long menu is more than 5 or so entries). - - The nodes listed in a node's menu are called its ``subnodes'', and -it is their ``superior''. They should each have an @samp{Up:} pointing at -the superior. It is often useful to arrange all or most of the -subnodes in a sequence of @samp{Next} and @samp{Previous} pointers so that someone who -wants to see them all need not keep revisiting the Menu. - - The Info Directory is simply the menu of the node @samp{(dir)Top}---that -is, node @samp{Top} in file @file{.../info/dir}. You can put new entries -in that menu just like any other menu. The Info Directory is @emph{not} the -same as the file directory called @file{info}. It happens that many of -Info's files live on that file directory, but they do not have to; and -files on that directory are not automatically listed in the Info -Directory node. - - Also, although the Info node graph is claimed to be a ``hierarchy'', -in fact it can be @emph{any} directed graph. Shared structures and -pointer cycles are perfectly possible, and can be used if they are -appropriate to the meaning to be expressed. There is no need for all -the nodes in a file to form a connected structure. In fact, this file -has two connected components. You are in one of them, which is under -the node @samp{Top}; the other contains the node @samp{Help} which the -@kbd{h} command goes to. In fact, since there is no garbage -collector, nothing terrible happens if a substructure is not pointed -to, but such a substructure is rather useless since nobody can -ever find out that it exists. - -@node Cross-refs, Tags, Menus, Advanced Info -@comment node-name, next, previous, up -@section Creating Cross References - - A cross reference can be placed anywhere in the text, unlike a menu -item which must go at the front of a line. A cross reference looks -like a menu item except that it has @samp{*note} instead of @kbd{*}. -It @emph{cannot} be terminated by a @samp{)}, because @samp{)}'s are -so often part of node names. If you wish to enclose a cross reference -in parentheses, terminate it with a period first. Here are two -examples of cross references pointers: - -@example -*Note details: commands. (See *note 3: Full Proof.) -@end example - -They are just examples. The places they ``lead to'' do not really exist! - -@node Tags, Checking, Cross-refs, Advanced Info -@comment node-name, next, previous, up -@section Tag Tables for Info Files - - You can speed up the access to nodes of a large Info file by giving -it a tag table. Unlike the tag table for a program, the tag table for -an Info file lives inside the file itself and is used -automatically whenever Info reads in the file. - - To make a tag table, go to a node in the file using Emacs Info mode and type -@kbd{M-x Info-tagify}. Then you must use @kbd{C-x C-s} to save the -file. - - Once the Info file has a tag table, you must make certain it is up -to date. If, as a result of deletion of text, any node moves back -more than a thousand characters in the file from the position -recorded in the tag table, Info will no longer be able to find that -node. To update the tag table, use the @code{Info-tagify} command again. - - An Info file tag table appears at the end of the file and looks like -this: - -@example -^_ -Tag Table: -File: info, Node: Cross-refs^?21419 -File: info, Node: Tags^?22145 -^_ -End Tag Table -@end example - -@noindent -Note that it contains one line per node, and this line contains -the beginning of the node's header (ending just after the node name), -a @key{DEL} character, and the character position in the file of the -beginning of the node. - -@node Checking, , Tags, Advanced Info -@comment node-name, next, previous, up -@section Checking an Info File - - When creating an Info file, it is easy to forget the name of a node -when you are making a pointer to it from another node. If you put in -the wrong name for a node, this is not detected until someone -tries to go through the pointer using Info. Verification of the Info -file is an automatic process which checks all pointers to nodes and -reports any pointers which are invalid. Every @samp{Next}, @samp{Previous}, and -@samp{Up} is checked, as is every menu item and every cross reference. In -addition, any @samp{Next} which does not have a @samp{Previous} pointing back is -reported. Only pointers within the file are checked, because checking -pointers to other files would be terribly slow. But those are usually -few. - - To check an Info file, do @kbd{M-x Info-validate} while looking at -any node of the file with Emacs Info mode. - -@node Create an Info File, , Advanced Info, Top -@comment node-name, next, previous, up -@chapter Creating an Info File from a Makeinfo file - -@code{makeinfo} is a utility that converts a Texinfo file into an Info -file; @code{texinfo-format-region} and @code{texinfo-format-buffer} are -GNU Emacs functions that do the same. - -@xref{Create an Info File, , Creating an Info File, texinfo, the Texinfo -Manual}, to learn how to create an Info file from a Texinfo file. - -@xref{Top,, Overview of Texinfo, texinfo, Texinfo: The GNU Documentation -Format}, to learn how to write a Texinfo file. - -@bye - diff --git a/gnu/usr.bin/texinfo/doc/makeinfo.texi b/gnu/usr.bin/texinfo/doc/makeinfo.texi deleted file mode 100644 index 21ee2d3..0000000 --- a/gnu/usr.bin/texinfo/doc/makeinfo.texi +++ /dev/null @@ -1,285 +0,0 @@ -\input texinfo @c -*-texinfo-*- -@comment %**start of header -@setfilename makeinfo.info -@set VERSION 1.51 -@paragraphindent none -@comment %**start of header - -@ifinfo -This file is an extract from the @cite{Texinfo} manual.@* -It documents @code{makeinfo}, a program that converts Texinfo -files into Info files. - -Copyright (C) 1992, 1993 Free Software Foundation, Inc. - -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 - -@titlepage -@title Makeinfo -@author Brian J. Fox and Robert J. Chassell - -@page -@vskip 0pt plus 1filll -Copyright @copyright{} 1992, 1993 Free Software Foundation, Inc. - - -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 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 titlepage - -@ifinfo -@node Top, What is makeinfo, (dir), (dir) -@unnumbered @code{makeinfo} - -This file documents the use of the @code{makeinfo} program, versions -@value{VERSION} and later. It is an extract from the @cite{Texinfo} manual. -@end ifinfo - -@menu -* What is makeinfo:: -@end menu - -@node What is makeinfo, , Top, Top -@chapter What is @code{makeinfo}? - -@iftex -This file documents the use of the @code{makeinfo} program, versions -@value{VERSION} and later. It is an extract from the @cite{Texinfo} manual. -@end iftex - -@code{makeinfo} is a program for converting @dfn{Texinfo} files into @dfn{Info} -files. Texinfo is a documentation system that uses a single source file to -produce both on-line information and printed output. - -You can read the on-line information using Info; type @code{info} to -learn about Info. -@ifinfo -@xref{Top, Texinfo, Overview of Texinfo, texinfo.texi, Texinfo}, -@end ifinfo -@iftex -See the @cite{Texinfo} manual, -@end iftex -to learn about the Texinfo documentation system. - -@menu -* Formatting Control:: -* Options:: -* Pointer Validation:: -@end menu - -@node Formatting Control, Options, , What is makeinfo -@section Controlling Paragraph Formats - -In general, @code{makeinfo} @dfn{fills} the paragraphs that it outputs -to an Info file. Filling is the process of breaking and connecting -lines so that lines are the same length as or shorter than the number -specified as the fill column. Lines are broken between words. With -@code{makeinfo}, you can control: - -@itemize @bullet -@item -The width of each paragraph (the @dfn{fill-column}). -@item -The amount of indentation that the first line of -each paragraph receives (the @dfn{paragraph-indentation}). -@end itemize - -@node Options, Pointer Validation, Formatting Control, What is makeinfo -@section Command Line Options - -The following command line options are available for @code{makeinfo}. - -@need 100 -@table @code -@item -D @var{var} -Cause @var{var} to be defined. This is equivalent to -@code{@@set @var{var}} in the Texinfo file. - -@need 150 -@item --error-limit @var{limit} -Set the maximum number of errors that @code{makeinfo} will report -before exiting (on the assumption that continuing would be useless). -The default number of errors that can be reported before -@code{makeinfo} gives up is 100.@refill - -@need 150 -@item --fill-column @var{width} -Specify the maximum number of columns in a line; this is the right-hand -edge of a line. Paragraphs that are filled will be filled to this -width. The default value for @code{fill-column} is 72. -@refill - -@item --footnote-style @var{style} -Set the footnote style to @var{style}, either @samp{end} for the end -node style or @samp{separate} for the separate node style. The value -set by this option overrides the value set in a Texinfo file by an -@code{@@footnotestyle} command. When the footnote style is -@samp{separate}, @code{makeinfo} makes a new node containing the -footnotes found in the current node. When the footnote style is -@samp{end}, @code{makeinfo} places the footnote references at the end -of the current node.@refill - -@need 150 -@item -I @var{dir} -Add @code{dir} to the directory search list for finding files that are -included using the @code{@@include} command. By default, -@code{makeinfo} searches only the current directory. - -@need 150 -@item --no-headers -Do not include menus or node lines in the output. This results in an -@sc{ascii} file that you cannot read in Info since it does not contain -the requisite nodes or menus; but you can print such a file in a -single, typewriter-like font and produce acceptable output. - -@need 150 -@item --no-split -Suppress the splitting stage of @code{makeinfo}. Normally, large -output files (where the size is greater than 70k bytes) are split into -smaller subfiles, each one approximately 50k bytes. If you specify -@samp{--no-split}, @code{makeinfo} will not split up the output -file.@refill - -@need 100 -@item --no-pointer-validate -@item --no-validate -Suppress the pointer-validation phase of @code{makeinfo}. Normally, -after a Texinfo file is processed, some consistency checks are made to -ensure that cross references can be resolved, etc. -@xref{Pointer Validation}.@refill - -@need 150 -@item --no-warn -Suppress the output of warning messages. This does @emph{not} -suppress the output of error messages, only warnings. You might -want this if the file you are creating has examples of Texinfo cross -references within it, and the nodes that are referenced do not actually -exist.@refill - -@item --no-number-footnotes -Supress automatic footnote numbering. By default, @code{makeinfo} -numbers each footnote sequentially in a single node, resetting the -current footnote number to 1 at the start of each node. - -@need 150 -@item --output @var{file} -@itemx -o @var{file} -Specify that the output should be directed to @var{file} and not to the -file name specified in the @code{@@setfilename} command found in the Texinfo -source. @var{file} can be the special token @samp{-}, which specifies -standard output. - -@need 150 -@item --paragraph-indent @var{indent} -Set the paragraph indentation style to @var{indent}. The value set by -this option overrides the value set in a Texinfo file by an -@code{@@paragraphindent} command. The value of @var{indent} is -interpreted as follows:@refill - -@itemize @bullet -@item -If the value of @var{indent} is @samp{asis}, do not change the -existing indentation at the starts of paragraphs.@refill - -@item -If the value of @var{indent} is zero, delete any existing -indentation.@refill - -@item -If the value of @var{indent} is greater than zero, indent each -paragraph by that number of spaces.@refill -@end itemize - -@need 100 -@item --reference-limit @var{limit} -Set the value of the number of references to a node that -@code{makeinfo} will make without reporting a warning. If a node has more -than this number of references in it, @code{makeinfo} will make the -references but also report a warning.@refill - -@need 150 -@item -U @var{var} -Cause @var{var} to be undefined. This is equivalent to -@code{@@clear @var{var}} in the Texinfo file. - -@need 100 -@item --verbose -Cause @code{makeinfo} to display messages saying what it is doing. -Normally, @code{makeinfo} only outputs messages if there are errors or -warnings.@refill - -@need 100 -@item --version -Report the version number of this copy of @code{makeinfo}.@refill -@end table - -@node Pointer Validation, , Options, What is makeinfo -@section Pointer Validation -@cindex Pointer validation with @code{makeinfo} -@cindex Validation of pointers - -If you do not suppress pointer-validation (by using the -@samp{--no-pointer-validation} option), @code{makeinfo} -will check the validity of the final Info file. Mostly, -this means ensuring that nodes you have referenced -really exist. Here is a complete list of what is -checked:@refill - -@enumerate -@item -If a `Next', `Previous', or `Up' node reference is a reference to a -node in the current file and is not an external reference such as to -@file{(dir)}, then the referenced node must exist.@refill - -@item -In every node, if the `Previous' node is different from the `Up' node, -then the `Previous' node must also be pointed to by a `Next' node.@refill - -@item -Every node except the `Top' node must have an `Up' pointer.@refill - -@item -The node referenced by an `Up' pointer must contain a reference to the -current node in some manner other than through a `Next' reference. -This includes menu entries and cross references.@refill - -@item -If the `Next' reference of a node is not the same as the `Next' reference -of the `Up' reference, then the node referenced by the `Next' pointer -must have a `Previous' pointer that points back to the current node. -This rule allows the last node in a section to point to the first node -of the next chapter.@refill -@end enumerate - -@bye diff --git a/gnu/usr.bin/texinfo/doc/texi.texi b/gnu/usr.bin/texinfo/doc/texi.texi deleted file mode 100644 index f77f662..0000000 --- a/gnu/usr.bin/texinfo/doc/texi.texi +++ /dev/null @@ -1,15626 +0,0 @@ -\input texinfo @c -*-texinfo-*- -@comment %**start of header -@setfilename texi.info -@settitle Texinfo @value{edition} -@syncodeindex vr fn -@c footnotestyle separate -@c paragraphindent 2 -@smallbook -@comment %**end of header - -@ignore -@ifinfo -@format -START-INFO-DIR-ENTRY -* Texinfo: (texi.info). The documentation format for the GNU Project. -END-INFO-DIR-ENTRY -@end format -@end ifinfo -@end ignore - -@c Set smallbook if printing in smallbook format so the example of the -@c smallbook font is actually written using smallbook; in bigbook, a kludge -@c is used for TeX output. -@c set smallbook -@clear smallbook - -@set edition 2.18 -@set update-date 26 March 1993 -@set update-month March 1993 - -@c Experiment with smaller amounts of whitespace between chapters -@c and sections. -@tex -\global\chapheadingskip = 15pt plus 4pt minus 2pt -\global\secheadingskip = 12pt plus 3pt minus 2pt -\global\subsecheadingskip = 9pt plus 2pt minus 2pt -@end tex - -@c Experiment with smaller amounts of whitespace between paragraphs in -@c the 8.5 by 11 inch format. -@ifclear smallbook -@tex -\global\parskip 6pt plus 1pt -@end tex -@end ifclear - -@finalout - -@c Currently undocumented commands, 24 March 1993: -@c See documentation in `texinfmt.el' file. -@c -@c raisesections (Two useful commands.) -@c lowersections -@c nwnode (Same as node, but no warnings; for `makeinfo'.) -@c math (Unsatisfactory TeX definition; no processing for Info.) -@c definfoenclose (For ifinfo text only; not supported by `makeinfo'; -@c each instance requires a corresponding TeX definition.) - -@ifinfo -This file documents Texinfo, a documentation system that uses a single -source file to produce both on-line information and a printed manual. - -Copyright (C) 1988, 1990, 1991, 1992, 1993 Free Software Foundation, Inc. - -This is the second edition of the Texinfo documentation,@* -and is consistent with version 2 of @file{texinfo.tex}. - -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 - -@setchapternewpage odd -@titlepage -@c use the new format for titles -@title Texinfo -@subtitle The GNU Documentation Format -@subtitle Edition @value{edition}, for Texinfo Version Two -@subtitle @value{update-month} - -@author by Robert J. Chassell and Richard M. Stallman - -@comment Include the Distribution inside the titlepage so -@c that headings are turned off. - -@page -@vskip 0pt plus 1filll -Copyright @copyright{} 1988, 1990, 1991, 1992, 1993 Free Software Foundation, Inc. - -@sp 2 -This is the second edition of the Texinfo documentation,@* -and is consistent with version 2 of @file{texinfo.tex}. -@sp 2 - -Published by the Free Software Foundation @* -675 Massachusetts Avenue, @* -Cambridge, MA 02139 USA @* -Printed copies are available for $15 each.@* -ISBN-1882114-12-4 - -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 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. -@sp 2 -Cover art by Etienne Suvasa. -@end titlepage - -@ifinfo -@node Top, Copying, (dir), (dir) -@top Texinfo - -Texinfo is a documentation system that uses a single source file to -produce both on-line information and printed output.@refill - -The first part of this master menu lists the major nodes in this Info -document, including the @@-command and concept indices. The rest of -the menu lists all the lower level nodes in the document.@refill - -This is Edition @value{edition} of the Texinfo documentation, -@w{@value{update-date},} for Texinfo Version 2. -@end ifinfo - -@c Here is a spare copy of the chapter menu entry descriptions, -@c in case they are accidently deleted -@ignore -Your rights. -Texinfo in brief. -How to use Texinfo mode. -What is at the beginning of a Texinfo file? -What is at the end of a Texinfo file? -How to create chapters, sections, subsections, - appendices, and other parts. -How to provide structure for a document. -How to write nodes. -How to write menus. -How to write cross references. -How to mark words and phrases as code, - keyboard input, meta-syntactic - variables, and the like. -How to write quotations, examples, etc. -How to write lists and tables. -How to create indices. -How to insert @@-signs, braces, etc. -How to indicate results of evaluation, - expansion of macros, errors, etc. -How to force and prevent line and page breaks. -How to describe functions and the like in a uniform manner. -How to write footnotes. -How to specify text for either @TeX{} or Info. -How to print hardcopy. -How to create an Info file. -How to install an Info file -A list of all the Texinfo @@-commands. -Hints on how to write a Texinfo document. -A sample Texinfo file to look at. -Tell readers they have the right to copy - and distribute. -How to incorporate other Texinfo files. -How to write page headings and footings. -How to find formatting mistakes. -All about paragraph refilling. -A description of @@-Command syntax. -Texinfo second edition features. -A menu containing commands and variables. -A menu covering many topics. -@end ignore - -@menu -* Copying:: Your rights. -* Overview:: Texinfo in brief. -* Texinfo Mode:: How to use Texinfo mode. -* Beginning a File:: What is at the beginning of a Texinfo file? -* Ending a File:: What is at the end of a Texinfo file? -* Structuring:: How to create chapters, sections, subsections, - appendices, and other parts. -* Nodes:: How to write nodes. -* Menus:: How to write menus. -* Cross References:: How to write cross references. -* Marking Text:: How to mark words and phrases as code, - keyboard input, meta-syntactic - variables, and the like. -* Quotations and Examples:: How to write quotations, examples, etc. -* Lists and Tables:: How to write lists and tables. -* Indices:: How to create indices. -* Insertions:: How to insert @@-signs, braces, etc. -* Glyphs:: How to indicate results of evaluation, - expansion of macros, errors, etc. -* Breaks:: How to force and prevent line and page breaks. -* Definition Commands:: How to describe functions and the like - in a uniform manner. -* Footnotes:: How to write footnotes. -* Conditionals:: How to specify text for either @TeX{} or Info. -* Format/Print Hardcopy:: How to convert a Texinfo file to a file - for printing and how to print that file. -* Create an Info File:: Convert a Texinfo file into an Info file. -* Install an Info File:: Make an Info file accessible to users. -* Command List:: All the Texinfo @@-commands. -* Tips:: Hints on how to write a Texinfo document. -* Sample Texinfo File:: A sample Texinfo file to look at. -* Sample Permissions:: Tell readers they have the right to copy - and distribute. -* Include Files:: How to incorporate other Texinfo files. -* Headings:: How to write page headings and footings. -* Catching Mistakes:: How to find formatting mistakes. -* Refilling Paragraphs:: All about paragraph refilling. -* Command Syntax:: A description of @@-Command syntax. -* Obtaining TeX:: How to Obtain @TeX{}. -* New Features:: Texinfo second edition features. -* Command and Variable Index:: A menu containing commands and variables. -* Concept Index:: A menu covering many topics. - - --- The Detailed Node Listing --- - -Overview of Texinfo - -* Using Texinfo:: Create a conventional printed book - or an Info file. -* Info Files:: What is an Info file? -* Printed Books:: Characteristics of a printed book or manual. -* Formatting Commands:: @@-commands are used for formatting. -* Conventions:: General rules for writing a Texinfo file. -* Comments:: How to write comments and mark regions that - the formatting commands will ignore. -* Minimum:: What a Texinfo file must have. -* Six Parts:: Usually, a Texinfo file has six parts. -* Short Sample:: A short sample Texinfo file. -* Acknowledgements:: - -Using Texinfo Mode - -* Texinfo Mode Overview:: How Texinfo mode can help you. -* Emacs Editing:: Texinfo mode adds to GNU Emacs' general - purpose editing features. -* Inserting:: How to insert frequently used @@-commands. -* Showing the Structure:: How to show the structure of a file. -* Updating Nodes and Menus:: How to update or create new nodes and menus. -* Info Formatting:: How to format for Info. -* Printing:: How to format and print part or all of a file. -* Texinfo Mode Summary:: Summary of all the Texinfo mode commands. - -Updating Nodes and Menus - -* Updating Commands:: Five major updating commands. -* Updating Requirements:: How to structure a Texinfo file for - using the updating command. -* Other Updating Commands:: How to indent descriptions, insert - missing nodes lines, and update - nodes in sequence. - -Beginning a Texinfo File - -* Four Parts:: Four parts begin a Texinfo file. -* Sample Beginning:: Here is a sample beginning for a Texinfo file. -* Header:: The very beginning of a Texinfo file. -* Info Summary and Permissions:: Summary and copying permissions for Info. -* Titlepage & Copyright Page:: Creating the title and copyright pages. -* The Top Node:: Creating the `Top' node and master menu. -* Software Copying Permissions:: Ensure that you and others continue to - have the right to use and share software. - -The Texinfo File Header - -* First Line:: The first line of a Texinfo file. -* Start of Header:: Formatting a region requires this. -* setfilename:: Tell Info the name of the Info file. -* settitle:: Create a title for the printed work. -* setchapternewpage:: Start chapters on right-hand pages. -* paragraphindent:: An option to specify paragraph indentation. -* End of Header:: Formatting a region requires this. - -The Title and Copyright Pages - -* titlepage:: Create a title for the printed document. -* titlefont center sp:: The @code{@@titlefont}, @code{@@center}, - and @code{@@sp} commands. -* title subtitle author:: The @code{@@title}, @code{@@subtitle}, - and @code{@@author} commands. -* Copyright & Permissions:: How to write the copyright notice and - include copying permissions. -* end titlepage:: Turn on page headings after the title and - copyright pages. -* headings on off:: An option for turning headings on and off - and double or single sided printing. - -The `Top' Node and Master Menu - -* Title of Top Node:: Sketch what the file is about. -* Master Menu Parts:: A master menu has three or more parts. - -Ending a Texinfo File - -* Printing Indices & Menus:: How to print an index in hardcopy and - generate index menus in Info. -* Contents:: How to create a table of contents. -* File End:: How to mark the end of a file. - -Chapter Structuring - -* Tree Structuring:: A manual is like an upside down tree @dots{} -* Structuring Command Types:: How to divide a manual into parts. -* makeinfo top:: The @code{@@top} command, part of the `Top' node. -* chapter:: -* unnumbered & appendix:: -* majorheading & chapheading:: -* section:: -* unnumberedsec appendixsec heading:: -* subsection:: -* unnumberedsubsec appendixsubsec subheading:: -* subsubsection:: Commands for the lowest level sections. - -Nodes - -* Two Paths:: Different commands to structure - Info output and printed output. -* Node Menu Illustration:: A diagram, and sample nodes and menus. -* node:: How to write a node, in detail. -* makeinfo Pointer Creation:: How to create node pointers with @code{makeinfo}. - -The @code{@@node} Command - -* Node Names:: How to choose node and pointer names. -* Writing a Node:: How to write an @code{@@node} line. -* Node Line Tips:: Keep names short. -* Node Line Requirements:: Keep names unique, without @@-commands. -* First Node:: How to write a `Top' node. -* makeinfo top command:: How to use the @code{@@top} command. -* Top Node Summary:: Write a brief description for readers. - -Menus - -* Menu Location:: Put a menu in a short node. -* Writing a Menu:: What is a menu? -* Menu Parts:: A menu entry has three parts. -* Less Cluttered Menu Entry:: Two part menu entry. -* Menu Example:: Two and three part menu entries. -* Other Info Files:: How to refer to a different Info file. - -Cross References - -* References:: What cross references are for. -* Cross Reference Commands:: A summary of the different commands. -* Cross Reference Parts:: A cross reference has several parts. -* xref:: Begin a reference with `See' @dots{} -* Top Node Naming:: How to refer to the beginning of another file. -* ref:: A reference for the last part of a sentence. -* pxref:: How to write a parenthetical cross reference. -* inforef:: How to refer to an Info-only file. - -@code{@@xref} - -* Reference Syntax:: What a reference looks like and requires. -* One Argument:: @code{@@xref} with one argument. -* Two Arguments:: @code{@@xref} with two arguments. -* Three Arguments:: @code{@@xref} with three arguments. -* Four and Five Arguments:: @code{@@xref} with four and five arguments. - -Marking Words and Phrases - -* Indicating:: How to indicate definitions, files, etc. -* Emphasis:: How to emphasize text. - -Indicating Definitions, Commands, etc. - -* Useful Highlighting:: Highlighting provides useful information. -* code:: How to indicate code. -* kbd:: How to show keyboard input. -* key:: How to specify keys. -* samp:: How to show a literal sequence of characters. -* var:: How to indicate a metasyntactic variable. -* file:: How to indicate the name of a file. -* dfn:: How to specify a definition. -* cite:: How to refer to a book that is not in Info. - -Emphasizing Text - -* emph & strong:: How to emphasize text in Texinfo. -* Smallcaps:: How to use the small caps font. -* Fonts:: Various font commands for printed output. - -Quotations and Examples - -* Block Enclosing Commands:: Use different constructs for - different purposes. -* quotation:: How to write a quotation. -* example:: How to write an example in a fixed-width font. -* noindent:: How to prevent paragraph indentation. -* Lisp Example:: How to illustrate Lisp code. -* smallexample & smalllisp:: Forms for the @code{@@smallbook} option. -* display:: How to write an example in the current font. -* format:: How to write an example that does not narrow - the margins. -* exdent:: How to undo the indentation of a line. -* flushleft & flushright:: How to push text flushleft or flushright. -* cartouche:: How to draw cartouches around examples. - -Making Lists and Tables - -* Introducing Lists:: Texinfo formats lists for you. -* itemize:: How to construct a simple list. -* enumerate:: How to construct a numbered list. -* Two-column Tables:: How to construct a two-column table. - -Making a Two-column Table - -* table:: How to construct a two-column table. -* ftable vtable:: How to construct a two-column table - with automatic indexing. -* itemx:: How to put more entries in the first column. - -Creating Indices - -* Index Entries:: Choose different words for index entries. -* Predefined Indices:: Use different indices for different kinds - of entry. -* Indexing Commands:: How to make an index entry. -* Combining Indices:: How to combine indices. -* New Indices:: How to define your own indices. - -Combining Indices - -* syncodeindex:: How to merge two indices, using @code{@@code} - font for the merged-from index. -* synindex:: How to merge two indices, using the - default font of the merged-to index. - -Special Insertions - -* Braces Atsigns Periods:: How to insert braces, @samp{@@} and periods. -* dmn:: How to format a dimension. -* Dots Bullets:: How to insert dots and bullets. -* TeX and copyright:: How to insert the @TeX{} logo - and the copyright symbol. -* minus:: How to insert a minus sign. - -Inserting @samp{@@}, Braces, and Periods - -* Inserting An Atsign:: -* Inserting Braces:: How to insert @samp{@{} and @samp{@}} -* Controlling Spacing:: How to insert the right amount of space - after punctuation within a sentence. - -Inserting Ellipsis, Dots, and Bullets - -* dots:: How to insert dots @dots{} -* bullet:: How to insert a bullet. - -Inserting @TeX{} and the Copyright Symbol - -* tex:: How to insert the @TeX{} logo. -* copyright symbol:: How to use @code{@@copyright}@{@}. - -Glyphs for Examples - -* Glyphs Summary:: -* result:: How to show the result of expression. -* expansion:: How to indicate an expansion. -* Print Glyph:: How to indicate printed output. -* Error Glyph:: How to indicate an error message. -* Equivalence:: How to indicate equivalence. -* Point Glyph:: How to indicate the location of point. - -Making and Preventing Breaks - -* Break Commands:: Cause and prevent splits. -* Line Breaks:: How to force a single line to use two lines. -* w:: How to prevent unwanted line breaks. -* sp:: How to insert blank lines. -* page:: How to force the start of a new page. -* group:: How to prevent unwanted page breaks. -* need:: Another way to prevent unwanted page breaks. - -Definition Commands - -* Def Cmd Template:: How to structure a description using a - definition command. -* Optional Arguments:: How to handle optional and repeated arguments. -* deffnx:: How to group two or more `first' lines. -* Def Cmds in Detail:: All the definition commands. -* Def Cmd Conventions:: Conventions for writing definitions. -* Sample Function Definition:: - -The Definition Commands - -* Functions Commands:: Commands for functions and similar entities. -* Variables Commands:: Commands for variables and similar entities. -* Typed Functions:: Commands for functions in typed languages. -* Typed Variables:: Commands for variables in typed languages. -* Abstract Objects:: Commands for object-oriented programming. -* Data Types:: The definition command for data types. - -Conditionally Visible Text - -* Conditional Commands:: How to specify text for Info or @TeX{}. -* Using Ordinary TeX Commands:: You can use any and all @TeX{} commands. -* set clear value:: How to designate which text to format (for - both Info and @TeX{}); and how to set a - flag to a string that you can insert. - -@code{@@set}, @code{@@clear}, and @code{@@value} - -* ifset ifclear:: Format a region if a flag is set. -* value:: Replace a flag with a string. -* value Example:: An easy way to update edition information. - -Format and Print Hardcopy - -* Use TeX:: Use @TeX{} to format for hardcopy. -* Shell Format & Print:: How to format and print a hardcopy manual - with shell commands. -* Within Emacs:: How to format and print from an Emacs shell. -* Texinfo Mode Printing:: How to format and print in Texinfo mode. -* Compile-Command:: How to print using Emacs's compile command. -* Requirements Summary:: @TeX{} formatting requirements summary. -* Preparing for TeX:: What you need to do to use @TeX{}. -* Overfull hboxes:: What are and what to do with overfull hboxes. -* smallbook:: How to print small format books and manuals. -* A4 Paper:: How to print on European A4 paper. -* Cropmarks and Magnification:: How to print marks to indicate the size - of pages and how to print scaled up output. - -Creating an Info File - -* makeinfo advantages:: @code{makeinfo} provides better error checking. -* Invoking makeinfo:: How to run @code{makeinfo} from a shell. -* makeinfo options:: Specify fill-column and other options. -* Pointer Validation:: How to check that pointers point somewhere. -* makeinfo in Emacs:: How to run @code{makeinfo} from Emacs. -* texinfo-format commands:: Two Info formatting commands written - in Emacs Lisp are an alternative - to @code{makeinfo}. -* Batch Formatting:: How to format for Info in Emacs Batch mode. -* Tag and Split Files:: How tagged and split files help Info - to run better. - -Installing an Info File - -* Directory file:: The top level menu for all Info files. -* New Info File:: Listing a new info file. -* Other Info Directories:: How to specify Info files that are - located in other directories. - -Sample Permissions - -* Inserting Permissions:: How to put permissions in your document. -* ifinfo Permissions:: Sample @samp{ifinfo} copying permissions. -* Titlepage Permissions:: Sample Titlepage copying permissions. - -Include Files - -* Using Include Files:: How to use the @code{@@include} command. -* texinfo-multiple-files-update:: How to create and update nodes and - menus when using included files. -* Include File Requirements:: What @code{texinfo-multiple-files-update} expects. -* Sample Include File:: A sample outer file with included files - within it; and a sample included file. -* Include Files Evolution:: How use of the @code{@@include} command - has changed over time. - -Page Headings - -* Headings Introduced:: Conventions for using page headings. -* Heading Format:: Standard page heading formats. -* Heading Choice:: How to specify the type of page heading. -* Custom Headings:: How to create your own headings and footings. - -Formatting Mistakes - -* makeinfo preferred:: @code{makeinfo} finds errors. -* Debugging with Info:: How to catch errors with Info formatting. -* Debugging with TeX:: How to catch errors with @TeX{} formatting. -* Using texinfo-show-structure:: How to use @code{texinfo-show-structure}. -* Using occur:: How to list all lines containing a pattern. -* Running Info-Validate:: How to find badly referenced nodes. - -Finding Badly Referenced Nodes - -* Using Info-validate:: How to run @code{Info-validate}. -* Unsplit:: How to create an unsplit file. -* Tagifying:: How to tagify a file. -* Splitting:: How to split a file manually. - -Second Edition Features - -* New Texinfo Mode Commands:: The updating commands are especially useful. -* New Commands:: Many newly described @@-commands. -@end menu - -@node Copying, Overview, Top, Top -@comment node-name, next, previous, up -@unnumbered Texinfo Copying Conditions -@cindex Copying conditions -@cindex Conditions for copying Texinfo - -The programs currently being distributed that relate to Texinfo include -portions of GNU Emacs, plus other separate programs (including -@code{makeinfo}, @code{info}, @code{texindex}, and @file{texinfo.tex}). -These programs are @dfn{free}; this means that everyone is free to use -them and free to redistribute them on a free basis. The Texinfo-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 Texinfo, 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 Texinfo 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 Texinfo. -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 Texinfo are found in the General Public -Licenses that accompany them.@refill - -@node Overview, Texinfo Mode, Copying, Top -@comment node-name, next, previous, up -@chapter Overview of Texinfo -@cindex Overview of Texinfo -@cindex Texinfo overview - -@dfn{Texinfo}@footnote{Note that the first syllable of ``Texinfo'' is -pronounced like ``speck'', not ``hex''. This odd pronunciation is -derived from, but is not the same as, the pronunciation of @TeX{}. In -the word @TeX{}, the @samp{X} is actually the Greek letter ``chi'' -rather than the English letter ``ex''. Pronounce @TeX{} as if the -@samp{X} were the last sound in the name `Bach'; but pronounce Texinfo -as if the @samp{x} were a `k'. Spell ``Texinfo'' with a capital ``T'' -and write the other letters in lower case.} -is a documentation system that uses a single source file to produce both -on-line information and printed output. This means that instead of -writing two different documents, one for the on-line help or other on-line -information and the other for a typeset manual or other printed work, you -need write only one document. When the work is revised, you need revise -only one document. (You can read the on-line information, known as an -@dfn{Info file}, with an Info documentation-reading program.)@refill - -@menu -* Using Texinfo:: Create a conventional printed book - or an Info file. -* Info Files:: What is an Info file? -* Printed Books:: Characteristics of a printed book or manual. -* Formatting Commands:: @@-commands are used for formatting. -* Conventions:: General rules for writing a Texinfo file. -* Comments:: How to write comments and mark regions that - the formatting commands will ignore. -* Minimum:: What a Texinfo file must have. -* Six Parts:: Usually, a Texinfo file has six parts. -* Short Sample:: A short sample Texinfo file. -* Acknowledgements:: -@end menu - -@node Using Texinfo, Info Files, , Overview -@ifinfo -@heading Using Texinfo -@end ifinfo - -Using Texinfo, you can create a printed document with the normal -features of a book, including chapters, sections, cross references, -and indices. From the same Texinfo source file, you can create a -menu-driven, on-line Info file with nodes, menus, cross references, -and indices. You can, if you wish, make the chapters and sections of -the printed document correspond to the nodes of the on-line -information; and you use the same cross references and indices for -both the Info file and the printed work. @cite{The GNU -Emacs Manual} is a good example of a Texinfo file, as is this manual.@refill - -To make a printed document, you process a Texinfo source file with the -@TeX{} typesetting program. This creates a @sc{dvi} file that you can -typeset and print as a book or report. (Note that the Texinfo language is -completely different from @TeX{}'s usual language, Plain@TeX{}, which -Texinfo replaces.) If you do not have @TeX{}, but do have -@code{troff} or @code{nroff}, you can use the @code{texi2roff} program -instead.@refill - -To make an Info file, you process a Texinfo source file with the -@code{makeinfo} utility or Emacs's @code{texinfo-format-buffer} command; -this creates an Info file that you can install on-line.@refill - -@TeX{} and @code{texi2roff} work with many types of printer; similarly, -Info works with almost every type of computer terminal. This power -makes Texinfo a general purpose system, but brings with it a constraint, -which is that a Texinfo file may contain only the customary -``typewriter'' characters (letters, numbers, spaces, and punctuation -marks) but no special graphics.@refill - -A Texinfo file is a plain @sc{ascii} file containing text and -@dfn{@@-commands} (words preceded by an @samp{@@}) that tell the -typesetting and formatting programs what to do. You may edit a -Texinfo file with any text editor; but it is especially convenient to -use GNU Emacs since that editor has a special mode, called Texinfo -mode, that provides various Texinfo-related features. (@xref{Texinfo -Mode}.)@refill - -Before writing a Texinfo source file, you should become familiar with -the Info documentation reading program and learn about nodes, -menus, cross references, and the rest. (@inforef{Top, info, info}, -for more information.)@refill - -You can use Texinfo to create both on-line help and printed manuals; -moreover, Texinfo is freely redistributable. For these reasons, Texinfo -is the format in which documentation for GNU utilities and libraries is -written.@refill - -@node Info Files, Printed Books, Using Texinfo, Overview -@comment node-name, next, previous, up -@section Info files -@cindex Info files - -An Info file is a Texinfo file formatted so that the Info documentation -reading program can operate on it. (@code{makeinfo} -and @code{texinfo-format-buffer} are two commands that convert a Texinfo file -into an Info file.)@refill - -Info files are divided into pieces called @dfn{nodes}, each of which -contains the discussion of one topic. Each node has a name, and -contains both text for the user to read and pointers to other nodes, -which are identified by their names. The Info program displays one node -at a time, and provides commands with which the user can move to other -related nodes.@refill - -@ifinfo -@inforef{Top, info, info}, for more information about using Info.@refill -@end ifinfo - -Each node of an Info file may have any number of child nodes that -describe subtopics of the node's topic. The names of child -nodes are listed in a @dfn{menu} within the parent node; this -allows you to use certain Info commands to move to one of the child -nodes. Generally, an Info file is organized like a book. If a node -is at the logical level of a chapter, its child nodes are at the level -of sections; likewise, the child nodes of sections are at the level -of subsections.@refill - -All the children of any one parent are linked together in a -bidirectional chain of `Next' and `Previous' pointers. The `Next' -pointer provides a link to the next section, and the `Previous' pointer -provides a link to the previous section. This means that all the nodes -that are at the level of sections within a chapter are linked together. -Normally the order in this chain is the same as the order of the -children in the parent's menu. Each child node records the parent node -name as its `Up' pointer. The last child has no `Next' pointer, and the -first child has the parent both as its `Previous' and as its `Up' -pointer.@footnote{In some documents, the first child has no `Previous' -pointer. Occasionally, the last child has the node name of the next -following higher level node as its `Next' pointer.}@refill - -The book-like structuring of an Info file into nodes that correspond -to chapters, sections, and the like is a matter of convention, not a -requirement. The `Up', `Previous', and `Next' pointers of a node can -point to any other nodes, and a menu can contain any other nodes. -Thus, the node structure can be any directed graph. But it is usually -more comprehensible to follow a structure that corresponds to the -structure of chapters and sections in a printed book or report.@refill - -In addition to menus and to `Next', `Previous', and `Up' pointers, Info -provides pointers of another kind, called references, that can be -sprinkled throughout the text. This is usually the best way to -represent links that do not fit a hierarchical structure.@refill - -Usually, you will design a document so that its nodes match the -structure of chapters and sections in the printed output. But there -are times when this is not right for the material being discussed. -Therefore, Texinfo uses separate commands to specify the node -structure for the Info file and the section structure for the printed -output.@refill - -Generally, you enter an Info file through a node that by convention is -called @samp{Top}. This node normally contains just a brief summary -of the file's purpose, and a large menu through which the rest of the -file is reached. From this node, you can either traverse the file -systematically by going from node to node, or you can go to a specific -node listed in the main menu, or you can search the index menus and -then go directly to the node that has the information you want.@refill -@c !!! With the standalone Info system you may go to specific nodes -@c directly.. - -If you want to read through an Info file in sequence, as if it were a -printed manual, you can get the whole file with the advanced Info -command @kbd{g* @key{RET}}. (@inforef{Expert, Advanced Info commands, -info}.)@refill - -@c !!! dir file may be located in one of many places: -@c /usr/local/emacs/info mentioned in info.c DEFAULT_INFOPATH -@c /usr/local/lib/emacs/info mentioned in info.c DEFAULT_INFOPATH -@c /usr/gnu/info mentioned in info.c DEFAULT_INFOPATH -@c /usr/local/info -@c /usr/local/lib/info -The @file{dir} file in the @file{info} directory serves as the -departure point for the whole Info system. From it, you can reach the -`Top' nodes of each of the documents in a complete Info system.@refill - -@node Printed Books, Formatting Commands, Info Files, Overview -@comment node-name, next, previous, up -@section Printed Books -@cindex Printed book and manual characteristics -@cindex Manual characteristics, printed -@cindex Book characteristics, printed -@cindex Texinfo printed book characteristics -@cindex Characteristics, printed books or manuals - -A Texinfo file can be formatted and typeset as a printed book or manual. -To do this, you need @TeX{}, a powerful, sophisticated typesetting -program written by Donald Knuth.@footnote{You can also use the -@code{texi2roff} program if you do not have @TeX{}; since Texinfo is -designed for use with @TeX{}, @code{texi2roff} is not described here. -@code{texi2roff} is part of the standard GNU distribution.}@refill - -A Texinfo-based book is similar to any other typeset, printed work: it -can have a title page, copyright page, table of contents, and preface, -as well as chapters, numbered or unnumbered sections and subsections, -page headers, cross references, footnotes, and indices.@refill - -You can use Texinfo to write a book without ever having the intention -of converting it into on-line information. You can use Texinfo for -writing a printed novel, and even to write a printed memo, although -this latter application is not recommended since electronic mail is so -much easier.@refill - -@TeX{} is a general purpose typesetting program. Texinfo provides a -file called @file{texinfo.tex} that contains information (definitions or -@dfn{macros}) that @TeX{} uses when it typesets a Texinfo file. -(@file{texinfo.tex} tells @TeX{} how to convert the Texinfo @@-commands -to @TeX{} commands, which @TeX{} can then process to create the typeset -document.) @file{texinfo.tex} contains the specifications for printing -a document.@refill - -Most often, documents are printed on 8.5 inch by 11 inch -pages (216@dmn{mm} by 280@dmn{mm}; this is the default size), but you -can also print for 7 inch by 9.25 inch pages (178@dmn{mm} by -235@dmn{mm}; the @code{@@smallbook} size) or on European A4 size paper -(@code{@@afourpaper}). (@xref{smallbook, , Printing ``Small'' Books}. -Also, see @ref{A4 Paper, ,Printing on A4 Paper}.)@refill - -By changing the parameters in @file{texinfo.tex}, you can change the -size of the printed document. In addition, you can change the style in -which the printed document is formatted; for example, you can change the -sizes and fonts used, the amount of indentation for each paragraph, the -degree to which words are hyphenated, and the like. By changing the -specifications, you can make a book look dignified, old and serious, or -light-hearted, young and cheery.@refill - -@TeX{} is freely distributable. It is written in a dialect of Pascal -called WEB and can be compiled either in Pascal or (by using a -conversion program that comes with the @TeX{} distribution) in C. -(@xref{TeX Mode, ,@TeX{} Mode, emacs, The GNU Emacs Manual}, for information -about @TeX{}.)@refill - -@TeX{} is very powerful and has a great many features. Because a -Texinfo file must be able to present information both on a -character-only terminal in Info form and in a typeset book, the -formatting commands that Texinfo supports are necessarily -limited.@refill - -@xref{Obtaining TeX, , How to Obtain @TeX{}}. - - -@node Formatting Commands, Conventions, Printed Books, Overview -@comment node-name, next, previous, up -@section @@-commands -@cindex @@-commands -@cindex Formatting commands - -In a Texinfo file, the commands that tell @TeX{} how to typeset the -printed manual and tell @code{makeinfo} and -@code{texinfo-format-buffer} how to create an Info file are preceded -by @samp{@@}; they are called @dfn{@@-commands}. For example, -@code{@@node} is the command to indicate a node and @code{@@chapter} -is the command to indicate the start of a chapter.@refill - -@quotation -@strong{Please note:} All the @@-commands, with the exception of the -@code{@@TeX@{@}} command, must be written entirely in lower -case.@refill -@end quotation - -The Texinfo @@-commands are a strictly limited set of constructs. The -strict limits make it possible for Texinfo files to be understood both -by @TeX{} and by the code that converts them into Info files. You can -display Info files on any terminal that displays alphabetic and -numeric characters. Similarly, you can print the output generated by -@TeX{} on a wide variety of printers.@refill - -Depending on what they do or what arguments@footnote{The word -@dfn{argument} comes from the way it is used in mathematics and does -not refer to a disputation between two people; it refers to the -information presented to the command. According to the @cite{Oxford -English Dictionary}, the word derives from the Latin for @dfn{to make -clear, prove}; thus it came to mean `the evidence offered as proof', -which is to say, `the information offered', which led to its -mathematical meaning. In its other thread of derivation, the word -came to mean `to assert in a manner against which others may make -counter assertions', which led to the meaning of `argument' as a -disputation.} they take, you need to write @@-commands on lines of -their own or as part of sentences:@refill - -@itemize @bullet -@item -Write a command such as @code{@@noindent} at the beginning of a line as -the only text on the line. (@code{@@noindent} prevents the beginning of -the next line from being indented as the beginning of a -paragraph.)@refill - -@item -Write a command such as @code{@@chapter} at the beginning of a line -followed by the command's arguments, in this case the chapter title, on -the rest of the line. (@code{@@chapter} creates chapter titles.)@refill - -@item -Write a command such as @code{@@dots@{@}} wherever you wish but usually -within a sentence. (@code{@@dots@{@}} creates dots @dots{})@refill - -@item -Write a command such as @code{@@code@{@var{sample-code}@}} wherever you -wish (but usually within a sentence) with its argument, -@var{sample-code} in this example, between the braces. (@code{@@code} -marks text as being code.)@refill - -@item -Write a command such as @code{@@example} at the beginning of a line of -its own; write the body-text on following lines; and write the matching -@code{@@end} command, @code{@@end example} in this case, at the -beginning of a line of its own after the body-text. (@code{@@example} -@dots{} @code{@@end example} indents and typesets body-text as an -example.)@refill -@end itemize - -@noindent -@cindex Braces, when to use -As a general rule, a command requires braces if it mingles among other -text; but it does not need braces if it starts a line of its own. The -non-alphabetic commands, such as @code{@@:}, are exceptions to the rule; -they do not need braces.@refill - -As you gain experience with Texinfo, you will rapidly learn how to -write the different commands: the different ways to write commands -make it easier to write and read Texinfo files than if all commands -followed exactly the same syntax. (For details about @@-command -syntax, see @ref{Command Syntax, , @@-Command Syntax}.)@refill - -@node Conventions, Comments, Formatting Commands, Overview -@comment node-name, next, previous, up -@section General Syntactic Conventions -@cindex General syntactic conventions -@cindex Syntactic conventions -@cindex Conventions, syntactic - -All @sc{ascii} printing characters except @samp{@@}, @samp{@{} and -@samp{@}} can appear in a Texinfo file and stand for themselves. -@samp{@@} is the escape character which introduces commands. -@samp{@{} and @samp{@}} should be used only to surround arguments to -certain commands. To put one of these special characters into the -document, put an @samp{@@} character in front of it, like this: -@samp{@@@@}, @samp{@@@{}, and @samp{@@@}}.@refill - -@ifinfo -It is customary in @TeX{} to use doubled single-quote characters to -begin and end quotations: ` ` and ' ' (but without a space between the -two single-quote characters). This convention should be followed in -Texinfo files. @TeX{} converts doubled single-quote characters to -left- and right-hand doubled quotation marks and Info converts doubled -single-quote characters to @sc{ascii} double-quotes: ` ` and ' ' to " .@refill -@end ifinfo -@iftex -It is customary in @TeX{} to use doubled single-quote characters to -begin and end quotations: @w{@tt{ `` }} and @w{@tt{ '' }}. This -convention should be followed in Texinfo files. @TeX{} converts -doubled single-quote characters to left- and right-hand doubled -quotation marks, ``like this'', and Info converts doubled single-quote -characters to @sc{ascii} double-quotes: @w{@tt{ `` }} and -@w{@tt{ '' }} to @w{@tt{ " }}.@refill -@end iftex - -Use three hyphens in a row, @samp{---}, for a dash---like this. In -@TeX{}, a single or even a double hyphen produces a printed dash that -is shorter than the usual typeset dash. Info reduces three hyphens to two for -display on the screen.@refill - -To prevent a paragraph from being indented in the printed manual, put -the command @code{@@noindent} on a line by itself before the -paragraph.@refill - -If you mark off a region of the Texinfo file with the @code{@@iftex} -and @w{@code{@@end iftex}} commands, that region will appear only in -the printed copy; in that region, you can use certain commands -borrowed from Plain@TeX{} that you cannot use in Info. Likewise, if -you mark off a region with the @code{@@ifinfo} and @code{@@end ifinfo} -commands, that region will appear only in the Info file; in that -region, you can use Info commands that you cannot use in @TeX{}. -(@xref{Conditionals}.) - -@cindex Tabs; don't use! -@quotation -@strong{Caution:} Do not use tabs in a Texinfo file! @TeX{} uses -variable-width fonts, which means that it cannot predefine a tab to work -in all circumstances. Consequently, @TeX{} treats tabs like single -spaces, and that is not what they look like.@refill - -@noindent -To avoid this problem, Texinfo mode causes GNU Emacs to insert multiple -spaces when you press the @key{TAB} key.@refill - -@noindent -Also, you can run @code{untabify} in Emacs to convert tabs in a region -to multiple spaces.@refill -@end quotation - -@node Comments, Minimum, Conventions, Overview -@comment node-name, next, previous, up -@section Comments - -You can write comments in a Texinfo file that will not appear in -either the Info file or the printed manual by using the -@code{@@comment} command (which may be abbreviated to @code{@@c}). -Such comments are for the person who reads the Texinfo file. All the -text on a line that follows either @code{@@comment} or @code{@@c} is a -comment; the rest of the line does not appear in either the Info file -or the printed manual. (Often, you can write the @code{@@comment} or -@code{@@c} in the middle of a line, and only the text that follows after -the @code{@@comment} or @code{@@c} command does not appear; but some -commands, such as @code{@@settitle} and @code{@@setfilename}, work on a -whole line. You cannot use @code{@@comment} or @code{@@c} in a line -beginning with such a command.)@refill -@cindex Comments -@findex comment -@findex c @r{(comment)} - -You can write long stretches of text that will not appear in either -the Info file or the printed manual by using the @code{@@ignore} and -@code{@@end ignore} commands. Write each of these commands on a line -of its own, starting each command at the beginning of the line. Text -between these two commands does not appear in the processed output. -You can use @code{@@ignore} and @code{@@end ignore} for writing -comments. Often, @code{@@ignore} and @code{@@end ignore} is used -to enclose a part of the copying permissions that applies to the -Texinfo source file of a document, but not to the Info or printed -version of the document.@refill -@cindex Ignored text -@cindex Unprocessed text -@findex ignore -@c !!! Perhaps include this comment about ignore and ifset: -@ignore -Text enclosed by @code{@@ignore} or by failing @code{@@ifset} or -@code{@@ifclear} conditions is ignored in the sense that it will not -contribute to the formatted output. However, TeX and makeinfo must -still parse the ignored text, in order to understand when to -@emph{stop} ignoring text from the source file; that means that you -will still get error messages if you have invalid Texinfo markup -within ignored text. -@end ignore - -@node Minimum, Six Parts, Comments, Overview -@comment node-name, next, previous, up -@section What a Texinfo File Must Have -@cindex Minimal Texinfo file (requirements) -@cindex Must have in Texinfo file -@cindex Required in Texinfo file -@cindex Texinfo file minimum - -By convention, the names of Texinfo files end with one of the -extensions @file{.texinfo}, @file{.texi}, or @file{.tex}. The longer -extension is preferred since it describes more clearly to a human -reader the nature of the file. The shorter extensions are for -operating systems that cannot handle long file names.@refill - -In order to be made into a printed manual and an Info file, a -Texinfo file @strong{must} begin with lines like this:@refill - -@example -@group -\input texinfo -@@setfilename @var{info-file-name} -@@settitle @var{name-of-manual} -@end group -@end example - -@noindent -The contents of the file follow this beginning, and then you @strong{must} end -a Texinfo file with a line like this:@refill - -@example -@@bye -@end example - -@findex input @r{(@TeX{} command)} -@noindent -The @samp{\input texinfo} line tells @TeX{} to use the -@file{texinfo.tex} file, which tells @TeX{} how to translate the Texinfo -@@-commands into @TeX{} typesetting commands. (Note the use of the -backslash, @samp{\}; this is correct for @TeX{}.) The -@samp{@@setfilename} line provides a name for the Info file and the -@samp{@@settitle} line specifies a title for the page headers (or -footers) of the printed manual.@refill - -The @code{@@bye} line at the end of the file on a line of its own tells -the formatters that the file is ended and to stop formatting.@refill - -Usually, you will not use quite such a spare format, but will include -mode setting and start-of-header and end-of-header lines at the -beginning of a Texinfo file, like this:@refill - -@example -@group -\input texinfo @@c -*-texinfo-*- -@@c %**start of header -@@setfilename @var{info-file-name} -@@settitle @var{name-of-manual} -@@c %**end of header -@end group -@end example - -@noindent -In the first line, @samp{-*-texinfo-*-} causes Emacs to switch into -Texinfo mode when you edit the file. - -The @code{@@c} lines which surround the @samp{@@setfilename} and -@samp{@@settitle} lines are optional, but you need them in order to -run @TeX{} or Info on just part of the file. (@xref{Start of Header}, -for more information.)@refill - -Furthermore, you will usually provide a Texinfo file with a title -page, indices, and the like. But the minimum, which can be useful -for short documents, is just the three lines at the beginning and the -one line at the end.@refill - -@node Six Parts, Short Sample, Minimum, Overview -@comment node-name, next, previous, up -@section Six Parts of a Texinfo File - -Generally, a Texinfo file contains more than the minimal -beginning and end---it usually contains six parts:@refill - -@table @r -@item 1. Header -The @dfn{Header} names the file, tells @TeX{} which definitions' file to -use, and performs other ``housekeeping'' tasks.@refill - -@item 2. Summary Description and Copyright -The @dfn{Summary Description and Copyright} segment describes the document -and contains the copyright notice and copying permissions for the Info -file. The segment must be enclosed between @code{@@ifinfo} and -@code{@@end ifinfo} commands so that the formatters place it only in the Info -file.@refill - -@item 3. Title and Copyright -The @dfn{Title and Copyright} segment contains the title and copyright pages -and copying permissions for the printed manual. The segment must be -enclosed between @code{@@titlepage} and @code{@@end titlepage} commands. -The title and copyright page appear only in the printed @w{manual}.@refill - -@item 4. `Top' Node and Master Menu -The @dfn{Master Menu} contains a complete menu of all the nodes in the whole -Info file. It appears only in the Info file, in the `Top' node.@refill - -@item 5. Body -The @dfn{Body} of the document may be structured like a traditional book or -encyclopedia or it may be free form.@refill - -@item 6. End -The @dfn{End} contains commands for printing indices and generating -the table of contents, and the @code{@@bye} command on a line of its -own.@refill -@end table - -@node Short Sample, Acknowledgements, Six Parts, Overview -@comment node-name, next, previous, up -@section A Short Sample Texinfo File -@cindex Sample Texinfo file - -Here is a complete but very short Texinfo file, in 6 parts. The first -three parts of the file, from @samp{\input texinfo} through to -@samp{@@end titlepage}, look more intimidating than they are. Most of -the material is standard boilerplate; when you write a manual, simply -insert the names for your own manual in this segment. (@xref{Beginning a -File}.)@refill - -@noindent -In the following, the sample text is @emph{indented}; comments on it are -not. The complete file, without any comments, is shown in -@ref{Sample Texinfo File}. - -@subheading Part 1: Header - -@noindent -The header does not appear in either the Info file or the@* -printed output. It sets various parameters, including the@* -name of the Info file and the title used in the header. - -@example -@group -\input texinfo @@c -*-texinfo-*- -@@c %**start of header -@@setfilename sample.info -@@settitle Sample Document -@@c %**end of header - -@@setchapternewpage odd -@end group -@end example - -@subheading Part 2: Summary Description and Copyright - -@noindent -The summary description and copyright segment does not@* -appear in the printed document. - -@example -@group -@@ifinfo -This is a short example of a complete Texinfo file. - -Copyright @@copyright@{@} 1990 Free Software Foundation, Inc. -@@end ifinfo -@end group -@end example - -@subheading Part 3: Titlepage and Copyright - -@noindent -The titlepage segment does not appear in the Info file. - -@example -@group -@@titlepage -@@sp 10 -@@comment The title is printed in a large font. -@@center @@titlefont@{Sample Title@} -@end group - -@group -@@c The following two commands start the copyright page. -@@page -@@vskip 0pt plus 1filll -Copyright @@copyright@{@} 1990 Free Software Foundation, Inc. -@@end titlepage -@end group -@end example - -@subheading Part 4: `Top' Node and Master Menu - -@noindent -The `Top' node contains the master menu for the Info file.@* -Since a printed manual uses a table of contents rather than@* -a menu, the master menu appears only in the Info file. - -@example -@group -@@node Top, First Chapter, (dir), (dir) -@@comment node-name, next, previous, up -@end group -@end example - -@example -@group -@@menu -* First Chapter:: The first chapter is the - only chapter in this sample. -* Concept Index:: This index has two entries. -@@end menu -@end group -@end example - -@subheading Part 5: The Body of the Document - -@noindent -The body segment contains all the text of the document, but not the -indices or table of contents. This example illustrates a node and a -chapter containing an enumerated list.@refill - -@example -@group -@@node First Chapter, Concept Index, Top, Top -@@comment node-name, next, previous, up -@@chapter First Chapter -@@cindex Sample index entry -@end group - -@group -This is the contents of the first chapter. -@@cindex Another sample index entry -@end group - -@group -Here is a numbered list. - -@@enumerate -@@item -This is the first item. - -@@item -This is the second item. -@@end enumerate -@end group - -@group -The @@code@{makeinfo@} and @@code@{texinfo-format-buffer@} -commands transform a Texinfo file such as this into -an Info file; and @@TeX@{@} typesets it for a printed -manual. -@end group -@end example - -@subheading Part 6: The End of the Document - -@noindent -The end segment contains commands both for generating an index in a node -and unnumbered chapter of its own and for generating the table of -contents; and it contains the @code{@@bye} command that marks the end of -the document.@refill - -@example -@group -@@node Concept Index, , First Chapter, Top -@@comment node-name, next, previous, up -@@unnumbered Concept Index -@end group - -@group -@@printindex cp - -@@contents -@@bye -@end group -@end example - -@subheading The Results - -Here is what the contents of the first chapter of the sample look like: - -@sp 1 -@need 700 -@quotation -This is the contents of the first chapter. - -Here is a numbered list. - -@enumerate -@item -This is the first item. - -@item -This is the second item. -@end enumerate - -The @code{makeinfo} and @code{texinfo-format-buffer} -commands transform a Texinfo file such as this into -an Info file; and @TeX{} typesets it for a printed -manual. -@end quotation - -@node Acknowledgements, , Short Sample, Overview -@comment node-name, next, previous, up -@section Acknowledgements - -Richard M.@: Stallman wrote Edition 1.0 of this manual. -@w{Robert J.@: Chassell} revised and extended it, -starting with Edition 1.1. - -Our thanks go out to all who helped improve this work, particularly to -@w{Francois Pinard} and @w{David D.@: Zuhn}, who tirelessly recorded -and reported mistakes and obscurities; our special thanks go to -@w{Melissa Weisshaus} for her frequent and often tedious reviews of -nearly similar editions. Our mistakes are our own. - -@c ignore until mailing lists set up -@ignore -Please send suggestions and corrections to: - -@example -@group -@r{Internet address:} - bug-gnu-texinfo@@prep.ai.mit.edu - -@r{UUCP path:} - mit-eddie!prep.ai.mit.edu!bug-gnu-texinfo -@end group -@end example - -@noindent -Please include the manual's edition number in your messages. -@end ignore - -@node Texinfo Mode, Beginning a File, Overview, Top -@comment node-name, next, previous, up -@chapter Using Texinfo Mode -@cindex Texinfo mode -@cindex Mode, using Texinfo -@cindex GNU Emacs -@cindex Emacs - -You may edit a Texinfo file with any text editor you choose. A Texinfo -file is no different from any other @sc{ascii} file. However, GNU Emacs -comes with a special mode, called Texinfo -mode, that provides Emacs commands and tools to help ease your work.@refill - -This chapter describes features of GNU Emacs' Texinfo mode but not any -features of the Texinfo formatting language. If you are reading this -manual straight through from the beginning, you may want to skim through -this chapter briefly and come back to it after reading succeeding -chapters which describe the Texinfo formatting language in -detail.@refill - -@menu -* Texinfo Mode Overview:: How Texinfo mode can help you. -* Emacs Editing:: Texinfo mode adds to GNU Emacs' general - purpose editing features. -* Inserting:: How to insert frequently used @@-commands. -* Showing the Structure:: How to show the structure of a file. -* Updating Nodes and Menus:: How to update or create new nodes and menus. -* Info Formatting:: How to format for Info. -* Printing:: How to format and print part or all of a file. -* Texinfo Mode Summary:: Summary of all the Texinfo mode commands. -@end menu - -@node Texinfo Mode Overview, Emacs Editing, , Texinfo Mode -@ifinfo -@heading Texinfo Mode Overview -@end ifinfo - -Texinfo mode provides special features for working with Texinfo -files:@refill - -@itemize @bullet -@item -Insert frequently used @@commands. @refill - -@item -Automatically create @code{@@node} lines. - -@item -Show the structure of a Texinfo source file.@refill - -@item -Automatically create or update the `Next',@* -`Previous', and `Up' pointers of a node. - -@item -Automatically create or update menus.@refill - -@item -Automatically create a master menu.@refill - -@item -Format a part or all of a file for Info.@refill - -@item -Typeset and print part or all of a file.@refill -@end itemize - -Perhaps the two most helpful features are those for inserting frequently -used @@-commands and for creating node pointers and menus.@refill - -@node Emacs Editing, Inserting, Texinfo Mode Overview, Texinfo Mode -@section The Usual GNU Emacs Editing Commands - -In most cases, the usual Text mode commands work the same in Texinfo -mode as they do in Text mode. Texinfo mode adds new editing commands -and tools to GNU Emacs' general purpose editing features. The major -difference concerns filling. In Texinfo mode, the paragraph -separation variable and syntax table are redefined so that Texinfo -commands that should be on lines of their own are not inadvertently -included in paragraphs. Thus, the @kbd{M-q} (@code{fill-paragraph}) -command will refill a paragraph but not mix an indexing command on a -line adjacent to it into the paragraph.@refill - -In addition, Texinfo mode sets the @code{page-delimiter} variable to -the value of @code{texinfo-chapter-level-regexp}; by default, this is -a regular expression matching the commands for chapters and their -equivalents, such as appendices. With this value for the page -delimiter, you can jump from chapter title to chapter title with the -@kbd{C-x ]} (@code{forward-page}) and @kbd{C-x [} -(@code{backward-page}) commands and narrow to a chapter with the -@kbd{C-x p} (@code{narrow-to-page}) command. (@xref{Pages, , ,emacs, -The GNU Emacs Manual}, for details about the page commands.)@refill - -You may name a Texinfo file however you wish, but the convention is to -end a Texinfo file name with one of the three extensions -@file{.texinfo}, @file{.texi}, or @file{.tex}. A longer extension is -preferred, since it is explicit, but a shorter extension may be -necessary for operating systems that limit the length of file names. -GNU Emacs automatically enters Texinfo mode when you visit a file with -a @file{.texinfo} or @file{.texi} -extension. Also, Emacs switches to Texinfo mode -when you visit a -file that has @samp{-*-texinfo-*-} in its first line. If ever you are -in another mode and wish to switch to Texinfo mode, type @code{M-x -texinfo-mode}.@refill - -Like all other Emacs features, you can customize or enhance Texinfo -mode as you wish. In particular, the keybindings are very easy to -change. The keybindings described here are the default or standard -ones.@refill - -@node Inserting, Showing the Structure, Emacs Editing, Texinfo Mode -@comment node-name, next, previous, up -@section Inserting Frequently Used Commands -@cindex Inserting frequently used commands -@cindex Frequently used commands, inserting -@cindex Commands, inserting them - -Texinfo mode provides commands to insert various frequently used -@@-commands into the buffer. You can use these commands to save -keystrokes.@refill - -The insert commands are invoked by typing @kbd{C-c} twice and then the -first letter of the @@-command:@refill - -@table @kbd -@item C-c C-c c -@itemx M-x texinfo-insert-@@code -@findex texinfo-insert-@@code -Insert @code{@@code@{@}} and put the -cursor between the braces.@refill - -@item C-c C-c d -@itemx M-x texinfo-insert-@@dfn -@findex texinfo-insert-@@dfn -Insert @code{@@dfn@{@}} and put the -cursor between the braces.@refill - -@item C-c C-c e -@itemx M-x texinfo-insert-@@end -@findex texinfo-insert-@@end -Insert @code{@@end} and attempt to insert the correct following word, -such as @samp{example} or @samp{table}. (This command does not handle -nested lists correctly, but inserts the word appropriate to the -immediately preceding list.)@refill - -@item C-c C-c i -@itemx M-x texinfo-insert-@@item -@findex texinfo-insert-@@item -Insert @code{@@item} and put the -cursor at the beginning of the next line.@refill - -@item C-c C-c k -@itemx M-x texinfo-insert-@@kbd -@findex texinfo-insert-@@kbd -Insert @code{@@kbd@{@}} and put the -cursor between the braces.@refill - -@item C-c C-c n -@itemx M-x texinfo-insert-@@node -@findex texinfo-insert-@@node -Insert @code{@@node} and a comment line -listing the sequence for the `Next', -`Previous', and `Up' nodes. -Leave point after the @code{@@node}.@refill - -@item C-c C-c o -@itemx M-x texinfo-insert-@@noindent -@findex texinfo-insert-@@noindent -Insert @code{@@noindent} and put the -cursor at the beginning of the next line.@refill - -@item C-c C-c s -@itemx M-x texinfo-insert-@@samp -@findex texinfo-insert-@@samp -Insert @code{@@samp@{@}} and put the -cursor between the braces.@refill - -@item C-c C-c t -@itemx M-x texinfo-insert-@@table -@findex texinfo-insert-@@table -Insert @code{@@table} followed by a @key{SPC} -and leave the cursor after the @key{SPC}.@refill - -@item C-c C-c v -@itemx M-x texinfo-insert-@@var -@findex texinfo-insert-@@var -Insert @code{@@var@{@}} and put the -cursor between the braces.@refill - -@item C-c C-c x -@itemx M-x texinfo-insert-@@example -@findex texinfo-insert-@@example -Insert @code{@@example} and put the -cursor at the beginning of the next line.@refill - -@c M-@{ was the binding for texinfo-insert-braces; -@c in Emacs 19, backward-paragraph will take this binding. -@item C-c C-c @{ -@itemx M-x texinfo-insert-braces -@findex texinfo-insert-braces -Insert @code{@{@}} and put the cursor between the braces.@refill - -@item C-c C-c @} -@itemx C-c C-c ] -@itemx M-x up-list -@findex up-list -Move from between a pair of braces forward past the closing brace. -Typing @kbd{C-c C-c ]} is easier than typing @kbd{C-c C-c @}}, which -is, however, more mnemonic; hence the two keybindings. (Also, you can -move out from between braces by typing @kbd{C-f}.)@refill -@end table - -To put a command such as @w{@code{@@code@{@dots{}@}}} around an -@emph{existing} word, position the cursor in front of the word and type -@kbd{C-u 1 C-c C-c c}. This makes it easy to edit existing plain text. -The value of the prefix argument tells Emacs how many words following -point to include between braces---1 for one word, 2 for two words, and -so on. Use a negative argument to enclose the previous word or words. -If you do not specify a prefix argument, Emacs inserts the @@-command -string and positions the cursor between the braces. This feature works -only for those @@-commands that operate on a word or words within one -line, such as @code{@@kbd} and @code{@@var}.@refill - -This set of insert commands was created after analyzing the frequency -with which different @@-commands are used in the @cite{GNU Emacs -Manual} and the @cite{GDB Manual}. If you wish to add your own insert -commands, you can bind a keyboard macro to a key, use abbreviations, -or extend the code in @file{texinfo.el}.@refill - -@findex texinfo-start-menu-description -@cindex Menu description, start -@cindex Description for menu, start -@kbd{C-c C-c C-d} (@code{texinfo-start-menu-description}) is an insert -command that works differently from the other insert commands. It -inserts a node's section or chapter title in the space for the -description in a menu entry line. (A menu entry has three parts, the -entry name, the node name, and the description. Only the node name is -required, but a description helps explain what the node is about. -@xref{Menu Parts, , The Parts of a Menu}.)@refill - -To use @code{texinfo-start-menu-description}, position point in a menu -entry line and type @kbd{C-c C-c C-d}. The command looks for and copies -the title that goes with the node name, and inserts the title as a -description; it positions point at beginning of the inserted text so you -can edit it. The function does not insert the title if the menu entry -line already contains a description.@refill - -This command is only an aid to writing descriptions; it does not do the -whole job. You must edit the inserted text since a title tends to use -the same words as a node name but a useful description uses different -words.@refill - -@node Showing the Structure, Updating Nodes and Menus, Inserting, Texinfo Mode -@comment node-name, next, previous, up -@section Showing the Section Structure of a File -@cindex Showing the section structure of a file -@cindex Section structure of a file, showing it -@cindex Structure of a file, showing it -@cindex Outline of file structure, showing it -@cindex Contents-like outline of file structure -@cindex File section structure, showing it -@cindex Texinfo file section structure, showing it - -You can show the section structure of a Texinfo file by using the -@kbd{C-c C-s} command (@code{texinfo-show-structure}). This command -shows the section structure of a Texinfo file by listing the lines -that begin with the @@-commands for @code{@@chapter}, -@code{@@section}, and the like. It constructs what amounts -to a table of contents. These lines are displayed in another buffer -called the @samp{*Occur*} buffer. In that buffer, you can position -the cursor over one of the lines and use the @kbd{C-c C-c} command -(@code{occur-mode-goto-occurrence}), to jump to the corresponding spot -in the Texinfo file.@refill - -@table @kbd -@item C-c C-s -@itemx M-x texinfo-show-structure -@findex texinfo-show-structure -Show the @code{@@chapter}, @code{@@section}, and such lines of a -Texinfo file.@refill - -@item C-c C-c -@itemx M-x occur-mode-goto-occurrence -@findex occur-mode-goto-occurrence -Go to the line in the Texinfo file corresponding to the line under the -cursor in the @file{*Occur*} buffer.@refill -@end table - -If you call @code{texinfo-show-structure} with a prefix argument by -typing @w{@kbd{C-u C-c C-s}}, it will list not only those lines with the -@@-commands for @code{@@chapter}, @code{@@section}, and the like, -but also the @code{@@node} lines. (This is how the -@code{texinfo-show-structure} command worked without an argument in -the first version of Texinfo. It was changed because @code{@@node} -lines clutter up the @samp{*Occur*} buffer and are usually not -needed.) You can use @code{texinfo-show-structure} with a prefix -argument to check whether the `Next', `Previous', and `Up' pointers of -an @code{@@node} line are correct.@refill - -Often, when you are working on a manual, you will be interested only -in the structure of the current chapter. In this case, you can mark -off the region of the buffer that you are interested in with the -@kbd{C-x n} (@code{narrow-to-region}) command and -@code{texinfo-show-structure} will work on only that region. To see -the whole buffer again, use @w{@kbd{C-x w}} (@code{widen}). -(@xref{Narrowing, , , emacs, The GNU Emacs Manual}, for more -information about the narrowing commands.)@refill - -@vindex page-delimiter -@cindex Page delimiter in Texinfo mode -In addition to providing the @code{texinfo-show-structure} command, -Texinfo mode sets the value of the page delimiter variable to match -the chapter-level @@-commands. This enables you to use the @kbd{C-x -]} (@code{forward-page}) and @kbd{C-x [} (@code{backward-page}) -commands to move forward and backward by chapter, and to use the -@kbd{C-x p} (@code{narrow-to-page}) command to narrow to a chapter. -@xref{Pages, , , emacs, The GNU Emacs Manual}, for more information -about the page commands.@refill - -@node Updating Nodes and Menus, Info Formatting, Showing the Structure, Texinfo Mode -@comment node-name, next, previous, up -@section Updating Nodes and Menus -@cindex Updating nodes and menus -@cindex Create nodes, menus automatically -@cindex Insert nodes, menus automatically -@cindex Automatically insert nodes, menus - -Texinfo mode provides commands for automatically creating or updating -menus and node pointers. The commands are called ``update'' commands -because their most frequent use is for updating a Texinfo file after -you have worked on it; but you can use them to insert the `Next', -`Previous', and `Up' pointers into an @code{@@node} line that has none and to -create menus in a file that has none.@refill - -If you do not use the updating commands, you need to write menus and -node pointers by hand, which is a tedious task.@refill - -@menu -* Updating Commands:: Five major updating commands. -* Updating Requirements:: How to structure a Texinfo file for - using the updating command. -* Other Updating Commands:: How to indent descriptions, insert - missing nodes lines, and update - nodes in sequence. -@end menu - -@node Updating Commands, Updating Requirements, , Updating Nodes and Menus -@ifinfo -@subheading The Updating Commands -@end ifinfo - -You can use the updating commands@refill - -@itemize @bullet -@item -to insert or update the `Next', `Previous', and `Up' pointers of a -node,@refill - -@item -to insert or update the menu for a section, and@refill - -@item -to create a master menu for a Texinfo source file.@refill -@end itemize - -You can also use the commands to update all the nodes and menus in a -region or in a whole Texinfo file.@refill - -The updating commands work only with conventional Texinfo files, which -are structured hierarchically like books. In such files, a structuring -command line must follow closely after each @code{@@node} line, except -for the `Top' @code{@@node} line. (A @dfn{structuring command line} is -a line beginning with @code{@@chapter}, @code{@@section}, or other -similar command.) - -You can write the structuring command line on the line that follows -immediately after an @code{@@node} line or else on the line that -follows after a single @code{@@comment} line or a single -@code{@@ifinfo} line. You cannot interpose more than one line between -the @code{@@node} line and the structuring command line; and you may -interpose only an @code{@@comment} line or an @code{@@ifinfo} line. - -Commands which work on a whole buffer require that the `Top' node be -followed by a node with an @code{@@chapter} or equivalent-level command. -Note that the menu updating commands will not create a main or master -menu for a Texinfo file that has only @code{@@chapter}-level nodes! The -menu updating commands only create menus @emph{within} nodes for lower level -nodes. To create a menu of chapters, you must provide a `Top' -node.@refill - -The menu updating commands remove menu entries that refer to other Info -files since they do not refer to nodes within the current buffer. This -is a deficiency. Rather than use menu entries, you can use cross -references to refer to other Info files. None of the updating commands -affect cross references.@refill - -Texinfo mode has five updating commands that are used most often: two -are for updating the node pointers or menu of a single node (or a -region); two are for updating every node pointer and menu in a file; -and one, the @code{texinfo-master-menu} command, is for creating a -master menu for a complete file, and optionally, for updating every -node and menu in the whole Texinfo file.@refill - -The @code{texinfo-master-menu} command is the primary command:@refill - -@table @kbd -@item C-c C-u m -@itemx M-x texinfo-master-menu -@findex texinfo-master-menu -Create or update a master menu that includes all the other menus -(incorporating the descriptions from pre-existing menus, if -any).@refill - -With an argument (prefix argument, @kbd{C-u,} if interactive), first create or -update all the nodes and all the regular menus in the buffer before -constructing the master menu. (@xref{The Top Node, , The Top Node and -Master Menu}, for more about a master menu.)@refill - -For @code{texinfo-master-menu} to work, the Texinfo file must have a -`Top' node and at least one subsequent node.@refill - -After extensively editing a Texinfo file, you can type the following: - -@example -C-u M-x texinfo-master-menu -@exdent or -C-u C-c C-u m -@end example - -@noindent -This updates all the nodes and menus completely and all at once.@refill -@end table - -The other major updating commands do smaller jobs and are designed for -the person who updates nodes and menus as he or she writes a Texinfo -file.@refill - -@need 1000 -The commands are:@refill - -@table @kbd -@item C-c C-u C-n -@itemx M-x texinfo-update-node -@findex texinfo-update-node -Insert the `Next', `Previous', and `Up' pointers for the node that point is -within (i.e., for the @code{@@node} line preceding point). If the -@code{@@node} line has pre-existing `Next', `Previous', or `Up' -pointers in it, the old pointers are removed and new ones inserted. -With an argument (prefix argument, @kbd{C-u}, if interactive), this command -updates all @code{@@node} lines in the region (which is the text -between point and mark).@refill - -@item C-c C-u C-m -@itemx M-x texinfo-make-menu -@findex texinfo-make-menu -Create or update the menu in the node that point is within. -With an argument (@kbd{C-u} as prefix argument, if -interactive), the command makes or updates menus for the -nodes which are either within or a part of the -region.@refill - -Whenever @code{texinfo-make-menu} updates an existing menu, the -descriptions from that menu are incorporated into the new menu. This -is done by copying descriptions from the existing menu to the entries -in the new menu that have the same node names. If the node names are -different, the descriptions are not copied to the new menu.@refill - -@item C-c C-u C-e -@itemx M-x texinfo-every-node-update -@findex texinfo-every-node-update -Insert or update the `Next', `Previous', and `Up' pointers for every -node in the buffer.@refill - -@item C-c C-u C-a -@itemx M-x texinfo-all-menus-update -@findex texinfo-all-menus-update -Create or update all the menus in the buffer. With an argument -(@kbd{C-u} as prefix argument, if interactive), first insert -or update all the node -pointers before working on the menus.@refill - -If a master menu exists, the @code{texinfo-all-menus-update} command -updates it; but the command does not create a new master menu if none -already exists. (Use the @code{texinfo-master-menu} command for -that.)@refill - -When working on a document that does not merit a master menu, you can -type the following: - -@example -C-u C-c C-u C-a -@exdent or -C-u M-x texinfo-all-menus-update -@end example - -@noindent -This updates all the nodes and menus.@refill -@end table - -The @code{texinfo-column-for-description} variable specifies the -column to which menu descriptions are indented. By default, the value -is 32 although it is often useful to reduce it to as low as 24. You -can set the variable with the @kbd{M-x edit-options} command -(@pxref{Edit Options, , Editing Variable Values, emacs, The GNU Emacs -Manual}) or with the @kbd{M-x set-variable} command (@pxref{Examining, -, Examining and Setting Variables, emacs, The GNU Emacs -Manual}).@refill - -Also, the @code{texinfo-indent-menu-description} command may be used to -indent existing menu descriptions to a specified column. Finally, if -you wish, you can use the @code{texinfo-insert-node-lines} command to -insert missing @code{@@node} lines into a file. (@xref{Other Updating -Commands}, for more information.)@refill - -@node Updating Requirements, Other Updating Commands, Updating Commands, Updating Nodes and Menus -@comment node-name, next, previous, up -@subsection Updating Requirements -@cindex Updating requirements -@cindex Requirements for updating commands - -To use the updating commands, you must organize the Texinfo file -hierarchically with chapters, sections, subsections, and the like. -When you construct the hierarchy of the manual, do not `jump down' -more than one level at a time: you can follow the `Top' node with a -chapter, but not with a section; you can follow a chapter with a -section, but not with a subsection. However, you may `jump up' any -number of levels at one time---for example, from a subsection to a -chapter.@refill - -Each @code{@@node} line, with the exception of the line for the `Top' -node, must be followed by a line with a structuring command such as -@code{@@chapter}, @code{@@section}, or -@code{@@unnumberedsubsec}.@refill - -Each @code{@@node} line/structuring-command line combination -must look either like this:@refill - -@example -@group -@@node Comments, Minimum, Conventions, Overview -@@comment node-name, next, previous, up -@@section Comments -@end group -@end example - -or like this (without the @code{@@comment} line): - -@example -@group -@@node Comments, Minimum, Conventions, Overview -@@section Comments -@end group -@end example - -@noindent -In this example, `Comments' is the name of both the node and the -section. The next node is called `Minimum' and the previous node is -called `Conventions'. The `Comments' section is within the `Overview' -node, which is specified by the `Up' pointer. (Instead of an -@code{@@comment} line, you can write an @code{@@ifinfo} line.)@refill - -If a file has a `Top' node, it must be called @samp{top} or @samp{Top} -and be the first node in the file.@refill - -The menu updating commands create a menu of sections within a chapter, -a menu of subsections within a section, and so on. This means that -you must have a `Top' node if you want a menu of chapters.@refill - -Incidentally, the @code{makeinfo} command will create an Info file for -a hierarchically organized Texinfo file that lacks `Next', `Previous' -and `Up' pointers. Thus, if you can be sure that your Texinfo file -will be formatted with @code{makeinfo}, you have no need for the -`update node' commands. (@xref{Create an Info File, , Creating an -Info File}, for more information about @code{makeinfo}.) However, -both @code{makeinfo} and the @code{texinfo-format-@dots{}} commands -require that you insert menus in the file.@refill - -@node Other Updating Commands, , Updating Requirements, Updating Nodes and Menus -@comment node-name, next, previous, up -@subsection Other Updating Commands - -In addition to the five major updating commands, Texinfo mode -possesses several less frequently used updating commands:@refill - -@table @kbd -@item M-x texinfo-insert-node-lines -@findex texinfo-insert-node-lines -Insert @code{@@node} lines before the @code{@@chapter}, -@code{@@section}, and other sectioning commands wherever they are -missing throughout a region in a Texinfo file.@refill - -With an argument (@kbd{C-u} as prefix argument, if interactive), the -@code{texinfo-insert-node-lines} command not only inserts -@code{@@node} lines but also inserts the chapter or section titles as -the names of the corresponding nodes. In addition, it inserts the -titles as node names in pre-existing @code{@@node} lines that lack -names. Since node names should be more concise than section or -chapter titles, you must manually edit node names so inserted.@refill - -For example, the following marks a whole buffer as a region and inserts -@code{@@node} lines and titles throughout:@refill - -@example -C-x h C-u M-x texinfo-insert-node-lines -@end example - -(Note that this command inserts titles as node names in @code{@@node} -lines; the @code{texinfo-start-menu-description} command -(@pxref{Inserting, Inserting Frequently Used Commands}) inserts titles -as descriptions in menu entries, a different action. However, in both -cases, you need to edit the inserted text.)@refill - -@item M-x texinfo-multiple-files-update -@findex texinfo-multiple-files-update @r{(in brief)} -Update nodes and menus in a document built from several separate files. -With @kbd{C-u} as a prefix argument, create and insert a master menu in -the outer file. With a numeric prefix argument, such as @kbd{C-u 2}, first -update all the menus and all the `Next', `Previous', and `Up' pointers -of all the included files before creating and inserting a master menu in -the outer file. The @code{texinfo-multiple-files-update} command is -described in the appendix on @code{@@include} files. -@ifinfo -@xref{texinfo-multiple-files-update}.@refill -@end ifinfo -@iftex -@xref{texinfo-multiple-files-update, , -@code{texinfo-multiple-files-update}}.@refill -@end iftex - -@item M-x texinfo-indent-menu-description -@findex texinfo-indent-menu-description -Indent every description in the menu following point to the specified -column. You can use this command to give yourself more space for -descriptions. With an argument (@kbd{C-u} as prefix argument, if -interactive), the @code{texinfo-indent-menu-description} command indents -every description in every menu in the region. However, this command -does not indent the second and subsequent lines of a multi-line -description.@refill - -@item M-x texinfo-sequential-node-update -@findex texinfo-sequential-node-update -Insert the names of the nodes immediately following and preceding the -current node as the `Next' or `Previous' pointers regardless of those -nodes' hierarchical level. This means that the `Next' node of a -subsection may well be the next chapter. Sequentially ordered nodes are -useful for novels and other documents that you read through -sequentially. (However, in Info, the @code{g* @key{RET}} command lets -you look through the file sequentially, so sequentially ordered nodes -are not strictly necessary.) With an argument (prefix argument, if -interactive), the @code{texinfo-sequential-node-update} command -sequentially updates all the nodes in the region.@refill -@end table - -@node Info Formatting, Printing, Updating Nodes and Menus, Texinfo Mode -@comment node-name, next, previous, up -@section Formatting for Info -@cindex Formatting for Info -@cindex Running an Info formatter -@cindex Info formatting - -Texinfo mode provides several commands for formatting part or all of a -Texinfo file for Info. Often, when you are writing a document, you -want to format only part of a file---that is, a region.@refill - -You can use either the @code{texinfo-format-region} or the -@code{makeinfo-region} command to format a region:@refill - -@table @kbd -@findex texinfo-format-region -@item C-c C-e C-r -@itemx M-x texinfo-format-region -@itemx C-c C-m C-r -@itemx M-x makeinfo-region -Format the current region for Info.@refill -@end table - -You can use either the @code{texinfo-format-buffer} or the -@code{makeinfo-buffer} command to format a whole buffer:@refill - -@table @kbd -@findex texinfo-format-buffer -@item C-c C-e C-b -@itemx M-x texinfo-format-buffer -@itemx C-c C-m C-b -@itemx M-x makeinfo-buffer -Format the current buffer for Info.@refill -@end table - -@need 1000 -For example, after writing a Texinfo file, you can type the following: - -@example -C-u C-c C-u m -@exdent or -C-u M-x texinfo-master-menu -@end example - -@noindent -This updates all the nodes and menus. Then type the following to create -an Info file: - -@example -C-c C-m C-b -@exdent or -M-x makeinfo-buffer -@end example - -For the Info formatting commands to work, the file @emph{must} include -a line that has @code{@@setfilename} in its header.@refill - -Not all systems support the @code{makeinfo}-based formatting commands.@refill - -@xref{Create an Info File}, for details about Info formatting.@refill - -@node Printing, Texinfo Mode Summary, Info Formatting, Texinfo Mode -@comment node-name, next, previous, up -@section Formatting and Printing -@cindex Formatting for printing -@cindex Printing a region or buffer -@cindex Region formatting and printing -@cindex Buffer formatting and printing -@cindex Part of file formatting and printing - -Typesetting and printing a Texinfo file is a multi-step process in which -you first create a file for printing (called a @sc{dvi} file), and then -print the file. Optionally, you may also create indices. To do this, -you must run the @code{texindex} command after first running the -@code{tex} typesetting command; and then you must run the @code{tex} -command again. @refill - -Often, when you are writing a document, you want to typeset and print -only part of a file to see what it will look like. You can use the -@code{texinfo-tex-region} and related commands for this purpose. Use -the @code{texinfo-tex-buffer} command to format all of a -buffer.@refill - -@table @kbd -@item C-c C-t C-r -@itemx M-x texinfo-tex-region -@findex texinfo-tex-region -Run @TeX{} on the region.@refill - -@item C-c C-t C-b -@itemx M-x texinfo-tex-buffer -@findex texinfo-tex-buffer -Run @TeX{} on the buffer.@refill - -@item C-c C-t C-i -@itemx M-x texinfo-texindex -Run @code{texindex} to sort the indices of a Texinfo file formatted with -@code{texinfo-tex-region} or @code{texinfo-tex-buffer}. You must run -the @code{tex} command a second time after sorting the raw index -files.@refill - -@item C-c C-t C-p -@itemx M-x texinfo-tex-print -@findex texinfo-tex-print -Print the file (or the part of the file) previously formatted with -@code{texinfo-tex-buffer} or @code{texinfo-tex-region}.@refill -@end table - -For @code{texinfo-tex-region} or @code{texinfo-tex-buffer} to work, the -file @emph{must} start with a @samp{\input texinfo} line and must -include an @code{@@settitle} line. The file must end with @code{@@bye} -on a line by itself. (When you use @code{texinfo-tex-region}, you must -surround the @code{@@settitle} line with start-of-header and -end-of-header lines.)@refill - -@xref{Format/Print Hardcopy}, for a description of the other @TeX{} related -commands, such as @code{tex-show-print-queue}.@refill - -@node Texinfo Mode Summary, , Printing, Texinfo Mode -@comment node-name, next, previous, up -@section Texinfo Mode Summary - -In Texinfo mode, each set of commands has default keybindings that -begin with the same keys. All the commands that are custom-created -for Texinfo mode begin with @kbd{C-c}. The keys are somewhat -mnemonic.@refill - -@subheading Insert Commands - -The insert commands are invoked by typing @kbd{C-c} twice and then the -first letter of the @@-command to be inserted. (It might make more -sense mnemonically to use @kbd{C-c C-i}, for `custom insert', but -@kbd{C-c C-c} is quick to type.)@refill - -@example -C-c C-c c @r{Insert} @samp{@@code}. -C-c C-c d @r{Insert} @samp{@@dfn}. -C-c C-c e @r{Insert} @samp{@@end}. -C-c C-c i @r{Insert} @samp{@@item}. -C-c C-c n @r{Insert} @samp{@@node}. -C-c C-c s @r{Insert} @samp{@@samp}. -C-c C-c v @r{Insert} @samp{@@var}. -C-c C-c @{ @r{Insert braces.} -C-c C-c ] -C-c C-c @} @r{Move out of enclosing braces.} - -@group -C-c C-c C-d @r{Insert a node's section title} - @r{in the space for the description} - @r{in a menu entry line.} -@end group -@end example - -@subheading Show Structure - -The @code{texinfo-show-structure} command is often used within a -narrowed region.@refill - -@example -C-c C-s @r{List all the headings.} -@end example - -@subheading The Master Update Command - -The @code{texinfo-master-menu} command creates a master menu; and can -be used to update every node and menu in a file as well.@refill - -@example -@group -C-c C-u m -M-x texinfo-master-menu - @r{Create or update a master menu.} -@end group - -@group -C-u C-c C-u m @r{With @kbd{C-u} as a prefix argument, first} - @r{create or update all nodes and regular} - @r{menus, and then create a master menu.} -@end group -@end example - -@subheading Update Pointers - -@c !!! added verbiage to prevent overfull hbox --bob 26 Mar 93 -The update pointer commands are invoked by typing @kbd{C-c C-u} and -then either typing @kbd{C-n} for @code{texinfo-update-node} or typing -@kbd{C-e} for @code{texinfo-every-node-update}.@refill - -@example -C-c C-u C-n @r{Update a node.} -C-c C-u C-e @r{Update every node in the buffer.} -@end example - -@subheading Update Menus - -Invoke the update menu commands by typing @kbd{C-c C-u} -and then either @kbd{C-m} for @code{texinfo-make-menu} or -@kbd{C-a} for @code{texinfo-all-menus-update}. To update -both nodes and menus at the same time, precede @kbd{C-c C-u -C-a} with @kbd{C-u}.@refill - -@example -C-c C-u C-m @r{Make or update a menu.} - -@group -C-c C-u C-a @r{Make or update all} - @r{menus in a buffer.} -@end group - -@group -C-u C-c C-u C-a @r{With @kbd{C-u} as a prefix argument,} - @r{first create or update all nodes and} - @r{then create or update all menus.} -@end group -@end example - -@subheading Format for Info - -The Info formatting commands that are written in Emacs Lisp are -invoked by typing @kbd{C-c C-e} and then either @kbd{C-r} for a region -or @kbd{C-b} for the whole buffer.@refill - -The Info formatting commands that are written in C and based on the -@code{makeinfo} program are invoked by typing @kbd{C-c C-m} and then -either @kbd{C-r} for a region or @kbd{C-b} for the whole buffer.@refill - -@need 800 -@noindent -Use the @code{texinfo-format@dots{}} commands: - -@example -@group -C-c C-e C-r @r{Format the region.} -C-c C-e C-b @r{Format the buffer.} -@end group -@end example - -@need 750 -@noindent -Use @code{makeinfo}: - -@example -C-c C-m C-r @r{Format the region.} -C-c C-m C-b @r{Format the buffer.} -C-c C-m C-l @r{Recenter the @code{makeinfo} output buffer.} -C-c C-m C-k @r{Kill the @code{makeinfo} formatting job.} -@end example - -@subheading Typeset and Print - -The @TeX{} typesetting and printing commands are invoked by typing -@kbd{C-c C-t} and then another control command: @kbd{C-r} for -@code{texinfo-tex-region}, @kbd{C-b} for @code{texinfo-tex-buffer}, -and so on.@refill - -@example -C-c C-t C-r @r{Run @TeX{} on the region.} -C-c C-t C-b @r{Run @TeX{} on the buffer.} -C-c C-t C-i @r{Run} @code{texindex}. -C-c C-t C-p @r{Print the @sc{dvi} file.} -C-c C-t C-q @r{Show the print queue.} -C-c C-t C-d @r{Delete a job from the print queue.} -C-c C-t C-k @r{Kill the current @TeX{} formatting job.} -C-c C-t C-x @r{Quit a currently stopped @TeX{} formatting job.} -C-c C-t C-l @r{Recenter the output buffer.} -@end example - -@subheading Other Updating Commands - -The `other updating commands' do not have standard keybindings because -they are rarely used. - -@example -@group -M-x texinfo-insert-node-lines - @r{Insert missing @code{@@node} lines in region.} - @r{With @kbd{C-u} as a prefix argument,} - @r{use section titles as node names.} -@end group - -@group -M-x texinfo-multiple-files-update - @r{Update a multi-file document.} - @r{With @kbd{C-u 2} as a prefix argument,} - @r{create or update all nodes and menus} - @r{in all included files first.} -@end group - -@group -M-x texinfo-indent-menu-description - @r{Indent descriptions.} -@end group - -@group -M-x texinfo-sequential-node-update - @r{Insert node pointers in strict sequence.} -@end group -@end example - -@node Beginning a File, Ending a File, Texinfo Mode, Top -@comment node-name, next, previous, up -@chapter Beginning a Texinfo File -@cindex Beginning a Texinfo file -@cindex Texinfo file beginning -@cindex File beginning - -Certain pieces of information must be provided at the beginning of a -Texinfo file, such as the name of the file and the title of the -document.@refill - -@menu -* Four Parts:: Four parts begin a Texinfo file. -* Sample Beginning:: Here is a sample beginning for a Texinfo file. -* Header:: The very beginning of a Texinfo file. -* Info Summary and Permissions:: Summary and copying permissions for Info. -* Titlepage & Copyright Page:: Creating the title and copyright pages. -* The Top Node:: Creating the `Top' node and master menu. -* Software Copying Permissions:: Ensure that you and others continue to - have the right to use and share software. -@end menu - -@node Four Parts, Sample Beginning, , Beginning a File -@ifinfo -@heading Four Parts Begin a File -@end ifinfo - -Generally, the beginning of a Texinfo file has four parts:@refill - -@enumerate -@item -The header, delimited by special comment lines, that includes the -commands for naming the Texinfo file and telling @TeX{} what -definitions' file to use when processing the Texinfo file.@refill - -@item -A short statement of what the file is about, with a copyright notice -and copying permissions. This is enclosed in @code{@@ifinfo} and -@code{@@end ifinfo} commands so that the formatters place it only -in the Info file.@refill - -@item -A title page and copyright page, with a copyright notice and copying -permissions. This is enclosed between @code{@@titlepage} and -@code{@@end titlepage} commands. The title and copyright page appear -only in the printed @w{manual}.@refill - -@item -The `Top' node that contains a menu for the whole Info file. The -contents of this node appear only in the Info file.@refill -@end enumerate - -Also, optionally, you may include the copying conditions for a program -and a warranty disclaimer. The copying section will be followed by an -introduction or else by the first chapter of the manual.@refill - -Since the copyright notice and copying permissions for the Texinfo -document (in contrast to the copying permissions for a program) are in -parts that appear only in the Info file or only in the printed manual, -this information must be given twice.@refill - -@node Sample Beginning, Header, Four Parts, Beginning a File -@comment node-name, next, previous, up -@section Sample Texinfo File Beginning - -The following sample shows what is needed.@refill - -@example -\input texinfo @@c -*-texinfo-*- -@@c %**start of header -@@setfilename @var{name-of-info-file} -@@settitle @var{name-of-manual} -@@setchapternewpage odd -@@c %**end of header - -@@ifinfo -This file documents @dots{} - -Copyright @var{year} @var{copyright-owner} - -@group -Permission is granted to @dots{} -@@end ifinfo -@end group - -@group -@@c This title page illustrates only one of the -@@c two methods of forming a title page. -@end group - -@group -@@titlepage -@@title @var{name-of-manual-when-printed} -@@subtitle @var{subtitle-if-any} -@@subtitle @var{second-subtitle} -@@author @var{author} -@end group - -@group -@@c The following two commands -@@c start the copyright page. -@@page -@@vskip 0pt plus 1filll -Copyright @@copyright@{@} @var{year} @var{copyright-owner} -@end group - -Published by @dots{} - -Permission is granted to @dots{} -@@end titlepage - -@@node Top, Overview, (dir), (dir) - -@@ifinfo -This document describes @dots{} - -This document applies to version @dots{} -of the program named @dots{} -@@end ifinfo - -@group -@@menu -* Copying:: Your rights and freedoms. -* First Chapter:: Getting started @dots{} -* Second Chapter:: @dots{} - @dots{} - @dots{} -@@end menu -@end group - -@group -@@node First Chapter, Second Chapter, top, top -@@comment node-name, next, previous, up -@@chapter First Chapter -@@cindex Index entry for First Chapter -@end group -@end example - -@node Header, Info Summary and Permissions, Sample Beginning, Beginning a File -@comment node-name, next, previous, up -@section The Texinfo File Header -@cindex Header for Texinfo files -@cindex Texinfo file header - -Texinfo files start with at least three lines that provide Info and -@TeX{} with necessary information. These are the @code{\input -texinfo} line, the @code{@@settitle} line, and the -@code{@@setfilename} line. If you want to run @TeX{} on just a part -of the Texinfo File, you must write the @code{@@settitle} -and @code{@@setfilename} lines between start-of-header and end-of-header -lines.@refill - -Thus, the beginning of a Texinfo file looks like this: - -@example -@group -\input texinfo @@c -*-texinfo-*- -@@setfilename sample.info -@@settitle Sample Document -@end group -@end example - -@noindent -or else like this: - -@example -@group -\input texinfo @@c -*-texinfo-*- -@@c %**start of header -@@setfilename sample.info -@@settitle Sample Document -@@c %**end of header -@end group -@end example - -@menu -* First Line:: The first line of a Texinfo file. -* Start of Header:: Formatting a region requires this. -* setfilename:: Tell Info the name of the Info file. -* settitle:: Create a title for the printed work. -* setchapternewpage:: Start chapters on right-hand pages. -* paragraphindent:: An option to specify paragraph indentation. -* End of Header:: Formatting a region requires this. -@end menu - -@node First Line, Start of Header, , Header -@comment node-name, next, previous, up -@subsection The First Line of a Texinfo File -@cindex First line of a Texinfo file -@cindex Beginning line of a Texinfo file -@cindex Header of a Texinfo file - -Every Texinfo file that is to be the top-level input to @TeX{} must begin -with a line that looks like this:@refill - -@example -\input texinfo @@c -*-texinfo-*- -@end example - -@noindent -This line serves two functions: - -@enumerate -@item -When the file is processed by @TeX{}, the @code{\input texinfo} command -tells @TeX{} to load the macros needed for processing a Texinfo file. -These are in a file called @file{texinfo.tex}, which is usually located -in the @file{/usr/lib/tex/macros} directory. @TeX{} uses the backslash, -@samp{\}, to mark the beginning of a command, just as Texinfo uses -@code{@@}. The @file{texinfo.tex} file causes the switch from @samp{\} -to @samp{@@}; before the switch occurs, @TeX{} requires @samp{\}, which -is why it appears at the beginning of the file.@refill - -@item -When the file is edited in GNU Emacs, the @samp{-*-texinfo-*-} mode -specification tells Emacs to use Texinfo mode.@refill -@end enumerate - -@node Start of Header, setfilename, First Line, Header -@comment node-name, next, previous, up -@subsection Start of Header -@cindex Start of header line - -Write a start-of-header line on the second line of a Texinfo file. -Follow the start-of-header line with @code{@@setfilename} and -@code{@@settitle} lines and, optionally, with other command lines, such -as @code{@@smallbook} or @code{@@footnotestyle}; and then by an -end-of-header line (@pxref{End of Header}).@refill - -With these lines, you can format part of a Texinfo file for Info or -typeset part for printing.@refill - -A start-of-header line looks like this:@refill - -@example -@@c %**start of header -@end example - -The odd string of characters, @samp{%**}, is to ensure that no other -comment is accidentally taken for a start-of-header line.@refill - -@node setfilename, settitle, Start of Header, Header -@comment node-name, next, previous, up -@subsection @code{@@setfilename} -@cindex Info file requires @code{@@setfilename} -@findex setfilename - -In order to be made into an Info file, a Texinfo file must contain a line -that looks like this:@refill - -@example -@@setfilename @var{info-file-name} -@end example - -Write the @code{@@setfilename} command at the beginning of a line and -follow it on the same line by the Info file name. Do not write -anything else on the line; anything on the line after the command is -considered part of the file name, including a comment.@refill - -The @code{@@setfilename} line specifies the name of the Info file to be -generated. This name should be different from the name of the Texinfo -file. The convention is to write a name with a @samp{.info} extension, -to produce an Info file name such as @file{texinfo.info}.@refill - -Some operating systems cannot handle long file names. You can run into -a problem even when the file name you specify is itself short enough. -This occurs because the Info formatters split a long Info file into -short indirect subfiles, and name them by appending `-1', `-2', @dots{}, -`-10', `-11', and so on, to the original file name. (@xref{Tag and -Split Files, , Tag Files and Split Files}.) The subfile name -@file{texinfo.info-10}, for example, is too long for some systems; so -the Info file name for this document is actually @file{texinfo} rather than -@file{texinfo.info}.@refill - -The Info formatting commands ignore everything written before the -@code{@@setfilename} line, which is why the very first line of -the file (the @code{\input} line) does not need to be commented out. -The @code{@@setfilename} line is ignored when you typeset a printed -manual.@refill - -@node settitle, setchapternewpage, setfilename, Header -@comment node-name, next, previous, up -@subsection @code{@@settitle} -@findex settitle - -In order to be made into a printed manual, a Texinfo file must contain -a line that looks like this:@refill - -@example -@@settitle @var{title} -@end example - -Write the @code{@@settitle} command at the beginning of a line and -follow it on the same line by the title. This tells @TeX{} the title -to use in a header or footer. Do not write anything else on the line; -anything on the line after the command is considered part of the -title, including a comment.@refill - -Conventionally, @TeX{} formats a Texinfo file for double-sided output -so as to print the title in the left-hand (even-numbered) page -headings and the current chapter titles in the right-hand -(odd-numbered) page headings. (@TeX{} learns the title of each -chapter from each @code{@@chapter} command.) Page footers are not -printed.@refill - -Even if you are printing in a single-sided style, @TeX{} looks for an -@code{@@settitle} command line, in case you include the manual title -in the heading. @refill - -The @code{@@settitle} command should precede everything that generates -actual output in @TeX{}.@refill - -Although the title in the @code{@@settitle} command is usually the -same as the title on the title page, it does not affect the title as -it appears on the title page. Thus, the two do not need not match -exactly; and the title in the @code{@@settitle} command can be a -shortened or expanded version of the title as it appears on the title -page. (@xref{titlepage, , @code{@@titlepage}}.)@refill - -@TeX{} prints page headings only for that text that comes after the -@code{@@end titlepage} command in the Texinfo file, or that comes -after an @code{@@headings} command that turns on headings. -(@xref{headings on off, , The @code{@@headings} Command}, for more -information.)@refill - -You may, if you wish, create your own, customized headings and -footings. @xref{Headings, , Page Headings}, for a detailed discussion -of this process.@refill - -@node setchapternewpage, paragraphindent, settitle, Header -@comment node-name, next, previous, up -@subsection @code{@@setchapternewpage} -@cindex Starting chapters -@cindex Pages, starting odd -@findex setchapternewpage - -In a book or a manual, text is usually printed on both sides of the -paper, chapters start on right-hand pages, and right-hand pages have -odd numbers. But in short reports, text often is printed only on one -side of the paper. Also in short reports, chapters sometimes do not -start on new pages, but are printed on the same page as the end of the -preceding chapter, after a small amount of vertical whitespace.@refill - -You can use the @code{@@setchapternewpage} command with various -arguments to specify how @TeX{} should start chapters and whether it -should typeset pages for printing on one or both sides of the paper -(single-sided or double-sided printing).@refill - -Write the @code{@@setchapternewpage} command at the beginning of a -line followed by its argument.@refill - -For example, you would write the following to cause each chapter to -start on a fresh odd-numbered page:@refill - -@example -@@setchapternewpage odd -@end example - -You can specify one of three alternatives with the -@code{@@setchapternewpage} command:@refill - -@table @asis -@ignore -@item No @code{@@setchapternewpage} command -If the Texinfo file does not contain an @code{@@setchapternewpage} -command before the @code{@@titlepage} command, @TeX{} automatically -begins chapters on new pages and prints headings in the standard -format for single-sided printing. This is the conventional format for -single-sided printing.@refill - -The result is exactly the same as when you write -@code{@@setchapternewpage on}.@refill -@end ignore -@item @code{@@setchapternewpage off} -Cause @TeX{} to typeset a new chapter on the same page as the last -chapter, after skipping some vertical whitespace. Also, cause @TeX{} to -format page headers for single-sided printing. (You can override the -headers format with the @code{@@headings double} command; see -@ref{headings on off, , The @code{@@headings} Command}.)@refill - -@item @code{@@setchapternewpage on} -Cause @TeX{} to start new chapters on new pages and to typeset page -headers for single-sided printing. This is the form most often -used for short reports.@refill - -This alternative is the default.@refill - -@item @code{@@setchapternewpage odd} -Cause @TeX{} to start new chapters on new, odd-numbered pages -(right-handed pages) and to typeset for double-sided printing. This is -the form most often used for books and manuals.@refill -@end table - -@noindent -Texinfo does not have an @code{@@setchapternewpage even} command.@refill - -@noindent -(You can countermand or modify an @code{@@setchapternewpage} command -with an @code{@@headings} command. @xref{headings on off, , The -@code{@@headings} Command}.)@refill - -At the beginning of a manual or book, pages are not numbered---for -example, the title and copyright pages of a book are not numbered. -By convention, table of contents pages are numbered with roman -numerals and not in sequence with the rest of the document.@refill - -Since an Info file does not have pages, the @code{@@setchapternewpage} -command has no effect on it.@refill - -Usually, you do not write an @code{@@setchapternewpage} command for -single-sided printing, but accept the default which is to typeset for -single-sided printing and to start new chapters on new pages. Usually, -you write an @code{@@setchapternewpage odd} command for double-sided -printing.@refill - -@node paragraphindent, End of Header, setchapternewpage, Header -@comment node-name, next, previous, up -@subsection Paragraph Indenting -@cindex Indenting paragraphs -@cindex Paragraph indentation -@findex paragraphindent - -The Info formatting commands may insert spaces at the beginning of the -first line of each paragraph, thereby indenting that paragraph. You -can use the @code{@@paragraphindent} command to specify the -indentation. Write an @code{@@paragraphindent} command at the -beginning of a line followed by either @samp{asis} or a number. The -template is:@refill - -@example -@@paragraphindent @var{indent} -@end example - -The Info formatting commands indent according to the value of -@var{indent}:@refill - -@itemize @bullet -@item -If the value of @var{indent} is @samp{asis}, the Info formatting -commands do not change the existing indentation.@refill - -@item -If the value of @var{indent} is 0, the Info formatting commands delete -existing indentation.@refill - -@item -If the value of @var{indent} is greater than 0, the Info formatting -commands indent the paragraph by that number of spaces.@refill -@end itemize - -The default value of @var{indent} is @samp{asis}.@refill - -Write the @code{@@paragraphindent} command before or shortly after the -end-of-header line at the beginning of a Texinfo file. (If you write -the command between the start-of-header and end-of-header lines, the -region formatting commands indent paragraphs as specified.)@refill - -@c !!! added verbiage to prevent overfull hbox --bob 26 Mar 93 -A peculiarity of @code{texinfo-format-buffer} and -@code{texinfo-format-region} is that they do not indent (nor -fill) paragraphs that contain @code{@@w} or @code{@@*} commands. -@xref{Refilling Paragraphs}, for a detailed description of what goes -on.@refill - -@node End of Header, , paragraphindent, Header -@comment node-name, next, previous, up -@subsection End of Header -@cindex End of header line - -Follow the header lines with an @w{end-of-header} line. -An end-of-header line looks like this:@refill - -@example -@@c %**end of header -@end example - -If you include the @code{@@setchapternewpage} command between the -start-of-header and end-of-header lines, @TeX{} will typeset a region as -that command specifies. Similarly, if you include an @code{@@smallbook} -command between the start-of-header and end-of-header lines, @TeX{} will -typeset a region in the ``small'' book format.@refill - -@ifinfo -The reason for the odd string of characters (@samp{%**}) is so that the -@code{texinfo-tex-region} command does not accidentally find -something that it should not when it is looking for the header.@refill - -The start-of-header line and the end-of-header line are Texinfo mode -variables that you can change.@refill -@end ifinfo - -@iftex -@xref{Start of Header}. -@end iftex - -@node Info Summary and Permissions, Titlepage & Copyright Page, Header, Beginning a File -@comment node-name, next, previous, up -@section Summary and Copying Permissions for Info - -The title page and the copyright page appear only in the printed copy of -the manual; therefore, the same information must be inserted in a -section that appears only in the Info file. This section usually -contains a brief description of the contents of the Info file, a -copyright notice, and copying permissions.@refill - -The copyright notice should read:@refill - -@example -Copyright @var{year} @var{copyright-owner} -@end example - -@noindent -and be put on a line by itself.@refill - -Standard text for the copyright permissions is contained in an appendix -to this manual; see @ref{ifinfo Permissions, , @samp{ifinfo} Copying -Permissions}, for the complete text.@refill - -The permissions text appears in an Info file @emph{before} the first -node. This mean that a reader does @emph{not} see this text when -reading the file using Info, except when using the advanced Info command -@kbd{g *}. - -@node Titlepage & Copyright Page, The Top Node, Info Summary and Permissions, Beginning a File -@comment node-name, next, previous, up -@section The Title and Copyright Pages - -A manual's name and author are usually printed on a title page. -Sometimes copyright information is printed on the title page as well; -more often, copyright information is printed on the back of the title -page. - -The title and copyright pages appear in the printed manual, but not in the -Info file. Because of this, it is possible to use several slightly -obscure @TeX{} typesetting commands that cannot be used in an Info file. -In addition, this part of the beginning of a Texinfo file contains the text -of the copying permissions that will appear in the printed manual.@refill - -@xref{Titlepage Permissions, , Titlepage Copying Permissions}, for the -standard text for the copyright permissions.@refill - -@menu -* titlepage:: Create a title for the printed document. -* titlefont center sp:: The @code{@@titlefont}, @code{@@center}, - and @code{@@sp} commands. -* title subtitle author:: The @code{@@title}, @code{@@subtitle}, - and @code{@@author} commands. -* Copyright & Permissions:: How to write the copyright notice and - include copying permissions. -* end titlepage:: Turn on page headings after the title and - copyright pages. -* headings on off:: An option for turning headings on and off - and double or single sided printing. -@end menu - -@node titlepage, titlefont center sp, , Titlepage & Copyright Page -@comment node-name, next, previous, up -@subsection @code{@@titlepage} -@cindex Title page -@findex titlepage - -Start the material for the title page and following copyright page -with @code{@@titlepage} on a line by itself and end it with -@code{@@end titlepage} on a line by itself.@refill - -The @code{@@end titlepage} command starts a new page and turns on page -numbering. (@xref{Headings, , Page Headings}, for details about how to -generate of page headings.) All the material that you want to -appear on unnumbered pages should be put between the -@code{@@titlepage} and @code{@@end titlepage} commands. By using the -@code{@@page} command you can force a page break within the region -delineated by the @code{@@titlepage} and @code{@@end titlepage} -commands and thereby create more than one unnumbered page. This is -how the copyright page is produced. (The @code{@@titlepage} command -might perhaps have been better named the -@code{@@titleandadditionalpages} command, but that would have been -rather long!)@refill - -@c !!! append refill to footnote when makeinfo can handle it. -When you write a manual about a computer program, you should write the -version of the program to which the manual applies on the title -page. If the manual changes more frequently than the program or is -independent of it, you should also include an edition -number@footnote{We have found that it is helpful to refer to versions -of manuals as `editions' and versions of programs as `versions'; -otherwise, we find we are liable to confuse each other in conversation -by referring to both the documentation and the software with the same -words.} for the manual. This helps readers keep track of which manual -is for which version of the program. (The `Top' node -should also contain this information; see @ref{makeinfo top, , -@code{@@top}}.)@refill - -Texinfo provides two methods for creating a title page. One method -uses the @code{@@titlefont}, @code{@@sp}, and @code{@@center} commands -to generate a title page in which the words on the page are -centered.@refill - -The second method uses the @code{@@title}, @code{@@subtitle}, and -@code{@@author} commands to create a title page with black rules under -the title and author lines and the subtitle text set flush to the -right hand side of the page. With this method, you do not specify any -of the actual formatting of the title page. You specify the text -you want, and Texinfo does the formatting. You may use either -method.@refill - -@node titlefont center sp, title subtitle author, titlepage, Titlepage & Copyright Page -@comment node-name, next, previous, up -@subsection @code{@@titlefont}, @code{@@center}, and @code{@@sp} -@findex titlefont -@findex center -@findex sp @r{(titlepage line spacing)} - -You can use the @code{@@titlefont}, @code{@@sp}, and @code{@@center} -commands to create a title page for a printed document. (This is the -first of the two methods for creating a title page in Texinfo.)@refill - -Use the @code{@@titlefont} command to select a large font suitable for -the title itself.@refill - -@need 700 -For example: - -@example -@@titlefont@{Texinfo@} -@end example - -Use the @code{@@center} command at the beginning of a line to center -the remaining text on that line. Thus,@refill - -@example -@@center @@titlefont@{Texinfo@} -@end example - -@noindent -centers the title, which in this example is ``Texinfo'' printed -in the title font.@refill - -Use the @code{@@sp} command to insert vertical space. For example:@refill - -@example -@@sp 2 -@end example - -@noindent -This inserts two blank lines on the printed page. (@xref{sp, , -@code{@@sp}}, for more information about the @code{@@sp} -command.)@refill - -A template for this method looks like this:@refill - -@example -@group -@@titlepage -@@sp 10 -@@center @@titlefont@{@var{name-of-manual-when-printed}@} -@@sp 2 -@@center @var{subtitle-if-any} -@@sp 2 -@@center @var{author} -@dots{} -@@end titlepage -@end group -@end example - -The spacing of the example fits an 8 1/2 by 11 inch manual.@refill - -@node title subtitle author, Copyright & Permissions, titlefont center sp, Titlepage & Copyright Page -@comment node-name, next, previous, up -@subsection @code{@@title}, @code{@@subtitle}, and @code{@@author} -@findex title -@findex subtitle -@findex author - -You can use the @code{@@title}, @code{@@subtitle}, and @code{@@author} -commands to create a title page in which the vertical and horizontal -spacing is done for you automatically. This contrasts with the method -described in -the previous section, in which the @code{@@sp} command is needed to -adjust vertical spacing.@refill - -Write the @code{@@title}, @code{@@subtitle}, or @code{@@author} -commands at the beginning of a line followed by the title, subtitle, -or author.@refill - -The @code{@@title} command produces a line in which the title is set -flush to the left-hand side of the page in a larger than normal font. -The title is underlined with a black rule.@refill - -The @code{@@subtitle} command sets subtitles in a normal-sized font -flush to the right-hand side of the page.@refill - -The @code{@@author} command sets the names of the author or authors in -a middle-sized font flush to the left-hand side of the page on a line -near the bottom of the title page. The names are underlined with a -black rule that is thinner than the rule that underlines the title. -(The black rule only occurs if the @code{@@author} command line is -followed by an @code{@@page} command line.)@refill - -There are two ways to use the @code{@@author} command: you can write -the name or names on the remaining part of the line that starts with -an @code{@@author} command:@refill - -@example -@@author by Jane Smith and John Doe -@end example - -@noindent -or you can write the names one above each other by using two (or more) -@code{@@author} commands:@refill - -@example -@group -@@author Jane Smith -@@author John Doe -@end group -@end example - -@noindent -(Only the bottom name is underlined with a black rule.)@refill - -@need 950 -A template for this method looks like this:@refill - -@example -@group -@@titlepage -@@title @var{name-of-manual-when-printed} -@@subtitle @var{subtitle-if-any} -@@subtitle @var{second-subtitle} -@@author @var{author} -@@page -@dots{} -@@end titlepage -@end group -@end example - -@ifinfo -@noindent -Contrast this form with the form of a title page written using the -@code{@@sp}, @code{@@center}, and @code{@@titlefont} commands:@refill - -@example -@@titlepage -@@sp 10 -@@center @@titlefont@{Name of Manual When Printed@} -@@sp 2 -@@center Subtitle, If Any -@@sp 1 -@@center Second subtitle -@@sp 2 -@@center Author -@@page -@dots{} -@@end titlepage -@end example -@end ifinfo - -@node Copyright & Permissions, end titlepage, title subtitle author, Titlepage & Copyright Page -@comment node-name, next, previous, up -@subsection Copyright Page and Permissions -@cindex Copyright page -@cindex Printed permissions -@cindex Permissions, printed - -By international treaty, the copyright notice for a book should be -either on the title page or on the back of the title page. The -copyright notice should include the year followed by the name of the -organization or person who owns the copyright.@refill - -When the copyright notice is on the back of the title page, that page -is customarily not numbered. Therefore, in Texinfo, the information -on the copyright page should be within @code{@@titlepage} and -@code{@@end titlepage} commands.@refill - -@findex vskip -@findex filll -@cindex Vertical whitespace (@samp{vskip}) -Use the @code{@@page} command to cause a page break. To push the -copyright notice and the other text on the copyright page towards the -bottom of the page, you can write a somewhat mysterious line after the -@code{@@page} command that reads like this:@refill - -@example -@@vskip 0pt plus 1filll -@end example - -@noindent -This is a @TeX{} command that is not supported by the Info formatting -commands. The @code{@@vskip} command inserts whitespace. The -@samp{0pt plus 1filll} means to put in zero points of mandatory whitespace, -and as much optional whitespace as needed to push the -following text to the bottom of the page. Note the use of three -@samp{l}s in the word @samp{filll}; this is the correct usage in -@TeX{}.@refill - -@findex copyright -In a printed manual, the @code{@@copyright@{@}} command generates a -@samp{c} inside a circle. (In Info, it generates @samp{(C)}.) The -copyright notice itself has the following legally defined sequence:@refill - -@example -Copyright @copyright{} @var{year} @var{copyright-owner} -@end example - -It is customary to put information on how to get a manual after the -copyright notice, followed by the copying permissions for the -manual.@refill - -Note that permissions must be given here as well as in the summary -segment within @code{@@ifinfo} and @code{@@end ifinfo} that -immediately follows the header since this text appears only in the -printed manual and the @samp{ifinfo} text appears only in the Info -file.@refill - -@xref{Sample Permissions}, for the standard text.@refill - -@node end titlepage, headings on off, Copyright & Permissions, Titlepage & Copyright Page -@comment node-name, next, previous, up -@subsection Heading Generation -@findex end titlepage -@cindex Headings, page, begin to appear -@cindex Titlepage end starts headings -@cindex End titlepage starts headings - -An @code{@@end titlepage} command on a line by itself not only marks -the end of the title and copyright pages, but also causes @TeX{} to start -generating page headings and page numbers. - -To repeat what is said elsewhere, Texinfo has two standard page heading -formats, one for documents which are printed on one side of each sheet of paper -(single-sided printing), and the other for documents which are printed on both -sides of each sheet (double-sided printing). -(@xref{setchapternewpage, ,@code{@@setchapternewpage}}.) -You can specify these formats in different ways:@refill - -@itemize @bullet -@item -The conventional way is to write an @code{@@setchapternewpage} command -before the title page commands, and then have the @code{@@end -titlepage} command start generating page headings in the manner desired. -(@xref{setchapternewpage, , @code{@@setchapternewpage}}.)@refill - -@item -Alternatively, you can use the @code{@@headings} command to prevent page -headings from being generated or to start them for either single or -double-sided printing. (Write an @code{@@headings} command immediately -after the @code{@@end titlepage} command. @xref{headings on off, , The -@code{@@headings} Command}, for more information.)@refill - -@item -Or, you may specify your own page heading and footing format. -@xref{Headings, , Page Headings}, for detailed -information about page headings and footings.@refill -@end itemize - -Most documents are formatted with the standard single-sided or -double-sided format, using @code{@@setchapternewpage odd} for -double-sided printing and no @code{@@setchapternewpage} command for -single-sided printing.@refill - -@node headings on off, , end titlepage, Titlepage & Copyright Page -@comment node-name, next, previous, up -@subsection The @code{@@headings} Command -@findex headings - -The @code{@@headings} command is rarely used. It specifies what kind of -page headings and footings to print on each page. Usually, this is -controlled by the @code{@@setchapternewpage} command. You need the -@code{@@headings} command only if the @code{@@setchapternewpage} command -does not do what you want, or if you want to turn off pre-defined page -headings prior to defining your own. Write an @code{@@headings} command -immediately after the @code{@@end titlepage} command.@refill - -There are four ways to use the @code{@@headings} command:@refill - -@table @code -@item @@headings off -Turn off printing of page headings.@refill - -@item @@headings single -Turn on page headings appropriate for single-sided printing. -@refill - -@item @@headings double -@itemx @@headings on -Turn on page headings appropriate for double-sided printing. The two -commands, @code{@@headings on} and @code{@@headings double}, are -synonymous.@refill -@end table - -For example, suppose you write @code{@@setchapternewpage off} before the -@code{@@titlepage} command to tell @TeX{} to start a new chapter on the -same page as the end of the last chapter. This command also causes -@TeX{} to typeset page headers for single-sided printing. To cause -@TeX{} to typeset for double sided printing, write @code{@@headings -double} after the @code{@@end titlepage} command. - -You can stop @TeX{} from generating any page headings at all by -writing @code{@@headings off} on a line of its own immediately after the -line containing the @code{@@end titlepage} command, like this:@refill - -@example -@@end titlepage -@@headings off -@end example - -@noindent -The @code{@@headings off} command overrides the @code{@@end titlepage} -command, which would otherwise cause @TeX{} to print page -headings.@refill - -You can also specify your own style of page heading and footing. -@xref{Headings, , Page Headings}, for more information.@refill - -@node The Top Node, Software Copying Permissions, Titlepage & Copyright Page, Beginning a File -@comment node-name, next, previous, up -@section The `Top' Node and Master Menu -@cindex @samp{@r{Top}} node -@cindex Master menu -@cindex Node, `Top' - -The `Top' node is the node from which you enter an Info file.@refill - -A `Top' node should contain a brief description of the Info file and an -extensive, master menu for the whole Info file. -This helps the reader understand what the Info file is -about. Also, you should write the version number of the program to -which the Info file applies; or, at least, the edition number.@refill - -The contents of the `Top' node should appear only in the Info file; none -of it should appear in printed output, so enclose it between -@code{@@ifinfo} and @code{@@end ifinfo} commands. (@TeX{} does not -print either an @code{@@node} line or a menu; they appear only in Info; -strictly speaking, you are not required to enclose these parts between -@code{@@ifinfo} and @code{@@end ifinfo}, but it is simplest to do so. -@xref{Conditionals, , Conditionally Visible Text}.)@refill - -@menu -* Title of Top Node:: Sketch what the file is about. -* Master Menu Parts:: A master menu has three or more parts. -@end menu - -@node Title of Top Node, Master Menu Parts, , The Top Node -@ifinfo -@subheading `Top' Node Title -@end ifinfo - -Sometimes, you will want to place an @code{@@top} sectioning command -line containing the title of the document immediately after the -@code{@@node Top} line (@pxref{makeinfo top command, , The @code{@@top} -Sectioning Command}, for more information).@refill - -For example, the beginning of the Top node of this manual contains an -@code{@@top} sectioning command, a short description, and edition and -version information. It looks like this:@refill - -@example -@group -@dots{} -@@end titlepage - -@@ifinfo -@@node Top, Copying, (dir), (dir) -@@top Texinfo - -Texinfo is a documentation system@dots{} -@end group - -@group -This is edition@dots{} -@dots{} -@@end ifinfo -@end group - -@group -@@menu -* Copying:: Texinfo is freely - redistributable. -* Overview:: What is Texinfo? -@dots{} -@end group -@@end menu -@end example - -In a `Top' node, the `Previous', and `Up' nodes usually refer to the top -level directory of the whole Info system, which is called @samp{(dir)}. -The `Next' node refers to the first node that follows the main or master -menu, which is usually the copying permissions, introduction, or first -chapter.@refill - -@node Master Menu Parts, , Title of Top Node, The Top Node -@subsection Parts of a Master Menu -@cindex Master menu parts -@cindex Parts of a master menu - -A @dfn{master menu} is a detailed main menu listing all the nodes in a -file. - -A master menu is enclosed in @code{@@menu} and @code{@@end menu} -commands and does not appear in the printed document.@refill - -Generally, a master menu is divided into parts.@refill - -@itemize @bullet -@item -The first part contains the major nodes in the Texinfo file: the nodes -for the chapters, chapter-like sections, and the appendices.@refill - -@item -The second part contains nodes for the indices.@refill - -@item -The third and subsequent parts contain a listing of the other, lower -level nodes, often ordered by chapter. This way, rather than go -through an intermediary menu, an inquirer can go directly to a -particular node when searching for specific information. These menu -items are not required; add them if you think they are a -convenience.@refill -@end itemize - -Each section in the menu can be introduced by a descriptive line. So -long as the line does not begin with an asterisk, it will not be -treated as a menu entry. (@xref{Writing a Menu}, for more -information.)@refill - -For example, the master menu for this manual looks like the following -(but has many more entries):@refill - -@example -@group -@@menu -* Copying:: Texinfo is freely - redistributable. -* Overview:: What is Texinfo? -* Texinfo Mode:: Special features in GNU Emacs. -@dots{} -@dots{} -@end group -@group -* Command and Variable Index:: - An entry for each @@-command. -* Concept Index:: An entry for each concept. -@end group - -@group - --- The Detailed Node Listing --- - -Overview of Texinfo - -* Info Files:: What is an Info file? -* Printed Manuals:: Characteristics of - a printed manual. -@dots{} -@dots{} -@end group - -@group -Using Texinfo Mode - -* Info on a Region:: Formatting part of a file - for Info. -@dots{} -@dots{} -@@end menu -@end group -@end example - -@node Software Copying Permissions, , The Top Node, Beginning a File -@comment node-name, next, previous, up -@section Software Copying Permissions -@cindex Software copying permissions -@cindex Copying software -@cindex Distribution -@cindex License agreement - -If the Texinfo file has a section containing the ``General Public -License'' and the distribution information and a warranty disclaimer -for the software that is documented, this section usually follows the -`Top' node. The General Public License is very important to Project -GNU software. It ensures that you and others will continue to have a -right to use and share the software.@refill - -The copying and distribution information and the disclaimer are -followed by an introduction or else by the first chapter of the -manual.@refill - -@cindex Introduction, as part of file -Although an introduction is not a required part of a Texinfo file, it -is very helpful. Ideally, it should state clearly and concisely what -the file is about and who would be interested in reading it. In -general, an introduction would follow the licensing and distribution -information, although sometimes people put it earlier in the document. -Usually, an introduction is put in an @code{@@unnumbered} section. -(@xref{unnumbered & appendix, , The @code{@@unnumbered} and -@code{@@appendix} Commands}.)@refill - -@node Ending a File, Structuring, Beginning a File, Top -@comment node-name, next, previous, up -@chapter Ending a Texinfo File -@cindex Ending a Texinfo file -@cindex Texinfo file ending -@cindex File ending -@findex bye - -The end of a Texinfo file should include the commands that create -indices and generate detailed and summary tables of contents. -And it must include the @code{@@bye} command that marks the last line -processed by @TeX{}.@refill - -@need 700 -For example: - -@example -@@node Concept Index, , Variables Index, Top -@@c node-name, next, previous, up -@@unnumbered Concept Index - -@@printindex cp - -@@contents -@@bye -@end example - -@menu -* Printing Indices & Menus:: How to print an index in hardcopy and - generate index menus in Info. -* Contents:: How to create a table of contents. -* File End:: How to mark the end of a file. -@end menu - -@node Printing Indices & Menus, Contents, , Ending a File -@comment node-name, next, previous, up -@section Index Menus and Printing an Index -@findex printindex -@cindex Printing an index -@cindex Indices, printing and menus -@cindex Generating menus with indices -@cindex Menus generated with indices - -To print an index means to include it as part of a manual or Info -file. This does not happen automatically just because you use -@code{@@cindex} or other index-entry generating commands in the -Texinfo file; those just cause the raw data for the index to be -accumulated. To generate an index, you must include the -@code{@@printindex} command at the place in the document where you -want the index to appear. Also, as part of the process of creating a -printed manual, you must run a program called @code{texindex} -(@pxref{Format/Print Hardcopy}) to sort the raw data to produce a sorted -index file. The sorted index file is what is actually used to -print the index.@refill - -Texinfo offers six different types of predefined index: the concept -index, the function index, the variables index, the keystroke index, the -program index, and the data type index (@pxref{Predefined Indices}). Each -index type has a two-letter name: @samp{cp}, @samp{fn}, @samp{vr}, -@samp{ky}, @samp{pg}, and @samp{tp}. You may merge indices, or put them -into separate sections (@pxref{Combining Indices}); or you may define -your own indices (@pxref{New Indices, , Defining New Indices}).@refill - -The @code{@@printindex} command takes a two-letter index name, reads -the corresponding sorted index file and formats it appropriately into -an index.@refill - -@ignore -The two-letter index names are: - -@table @samp -@item cp -concept index -@item fn -function index -@item vr -variable index -@item ky -key index -@item pg -program index -@item tp -data type index -@end table -@end ignore -The @code{@@printindex} command does not generate a chapter heading -for the index. Consequently, you should precede the -@code{@@printindex} command with a suitable section or chapter command -(usually @code{@@unnumbered}) to supply the chapter heading and put -the index into the table of contents. Precede the @code{@@unnumbered} -command with an @code{@@node} line.@refill - -@need 1200 -For example: - -@smallexample -@group -@@node Variable Index, Concept Index, Function Index, Top -@@comment node-name, next, previous, up -@@unnumbered Variable Index - -@@printindex vr -@end group - -@group -@@node Concept Index, , Variable Index, Top -@@comment node-name, next, previous, up -@@unnumbered Concept Index - -@@printindex cp -@end group - -@group -@@summarycontents -@@contents -@@bye -@end group -@end smallexample - -@noindent -(Readers often prefer that the concept index come last in a book, -since that makes it easiest to find.)@refill - -@ignore -In @TeX{}, the @code{@@printindex} command needs a sorted index file -to work from. @TeX{} does not know how to do sorting; this is a -deficiency. @TeX{} writes output files of raw index data; use the -@code{texindex} program to convert these files to sorted index files. -(@xref{Format/Print Hardcopy}, for more information.)@refill -@end ignore -@node Contents, File End, Printing Indices & Menus, Ending a File -@comment node-name, next, previous, up -@section Generating a Table of Contents -@cindex Table of contents -@cindex Contents, Table of -@findex contents -@findex summarycontents -@findex shortcontents - -The @code{@@chapter}, @code{@@section}, and other structuring commands -supply the information to make up a table of contents, but they do not -cause an actual table to appear in the manual. To do this, you must -use the @code{@@contents} and @code{@@summarycontents} -commands:@refill - -@table @code -@item @@contents -Generate a table of contents in a printed manual, including all -chapters, sections, subsections, etc., as well as appendices and -unnumbered chapters. (Headings generated by the @code{@@heading} -series of commands do not appear in the table of contents.) The -@code{@@contents} command should be written on a line by -itself.@refill - -@item @@shortcontents -@itemx @@summarycontents -(@code{@@summarycontents} is a synonym for @code{@@shortcontents}; the -two commands are exactly the same.)@refill - -Generate a short or summary table of contents that lists only the -chapters (and appendices and unnumbered chapters). Omit sections, subsections -and subsubsections. Only a long manual needs a short table -of contents in addition to the full table of contents.@refill - -Write the @code{@@shortcontents} command on a line by itself right -@emph{before} the @code{@@contents} command.@refill -@end table - -The table of contents commands automatically generate a chapter-like -heading at the top of the first table of contents page. Write the table -of contents commands at the very end of a Texinfo file, just before the -@code{@@bye} command, following any index sections---anything in the -Texinfo file after the table of contents commands will be omitted from -the table of contents.@refill - -When you print a manual with a table of contents, the table of -contents are printed last and numbered with roman numerals. You need -to place those pages in their proper place, after the title page, -yourself. (This is the only collating you need to do for a printed -manual. The table of contents is printed last because it is generated -after the rest of the manual is typeset.)@refill - -@need 700 -Here is an example of where to write table of contents commands:@refill - -@example -@group -@var{indices}@dots{} -@@shortcontents -@@contents -@@bye -@end group -@end example - -Since an Info file uses menus instead of tables of contents, the Info -formatting commands ignore the @code{@@contents} and -@code{@@shortcontents} commands.@refill - -@node File End, , Contents, Ending a File -@comment node-name, next, previous, up -@section @code{@@bye} File Ending -@findex bye - -An @code{@@bye} command terminates @TeX{} or Info formatting. None of -the formatting commands see any of the file following @code{@@bye}. -The @code{@@bye} command should be on a line by itself.@refill - -If you wish, you may follow the @code{@@bye} line with notes. These notes -will not be formatted and will not appear in either Info or a printed -manual; it is as if text after @code{@@bye} were within @code{@@ignore} -@dots{} @code{@@end ignore}. Also, you may follow the @code{@@bye} line -with a local variables list. @xref{Compile-Command, , Using Local -Variables and the Compile Command}, for more information.@refill - -@node Structuring, Nodes, Ending a File, Top -@comment node-name, next, previous, up -@chapter Chapter Structuring -@cindex Chapter structuring -@cindex Structuring of chapters - -The @dfn{chapter structuring} commands divide a document into a hierarchy of -chapters, sections, subsections, and subsubsections. These commands -generate large headings; they also provide information for the table -of contents of a printed manual (@pxref{Contents, , Generating a Table -of Contents}).@refill - -The chapter structuring commands do not create an Info node structure, -so normally you should put an @code{@@node} command immediately before -each chapter structuring command (@pxref{Nodes}). The only time you -are likely to use the chapter structuring commands without using the -node structuring commands is if you are writing a document that -contains no cross references and will never be transformed into Info -format.@refill - -It is unlikely that you will ever write a Texinfo file that is -intended only as an Info file and not as a printable document. If you -do, you might still use chapter structuring commands to create a -heading at the top of each node---but you don't need to.@refill - -@menu -* Tree Structuring:: A manual is like an upside down tree @dots{} -* Structuring Command Types:: How to divide a manual into parts. -* makeinfo top:: The @code{@@top} command, part of the `Top' node. -* chapter:: -* unnumbered & appendix:: -* majorheading & chapheading:: -* section:: -* unnumberedsec appendixsec heading:: -* subsection:: -* unnumberedsubsec appendixsubsec subheading:: -* subsubsection:: Commands for the lowest level sections. -@end menu - -@node Tree Structuring, Structuring Command Types, , Structuring -@comment node-name, next, previous, up -@section Tree Structure of Sections -@cindex Tree structuring - -A Texinfo file is usually structured like a book with chapters, -sections, subsections, and the like. This structure can be visualized -as a tree (or rather as an upside-down tree) with the root at the top -and the levels corresponding to chapters, sections, subsection, and -subsubsections.@refill - -Here is a diagram that shows a Texinfo file with three chapters, -each of which has two sections.@refill - -@example -@group - Top - | - ------------------------------------- - | | | - Chapter 1 Chapter 2 Chapter 3 - | | | - -------- -------- -------- - | | | | | | - Section Section Section Section Section Section - 1.1 1.2 2.1 2.2 3.1 3.2 - -@end group -@end example - -In a Texinfo file that has this structure, the beginning of Chapter 2 -looks like this:@refill - -@example -@group -@@node Chapter 2, Chapter 3, Chapter 1, top -@@chapter Chapter 2 -@end group -@end example - -The chapter structuring commands are described in the sections that -follow; the @code{@@node} and @code{@@menu} commands are described in -following chapters. (@xref{Nodes}, and see @ref{Menus}.)@refill - -@node Structuring Command Types, makeinfo top, Tree Structuring, Structuring -@comment node-name, next, previous, up -@section Types of Structuring Command - -The chapter structuring commands fall into four groups or series, each -of which contains structuring commands corresponding to the -hierarchical levels of chapters, sections, subsections, and -subsubsections.@refill - -The four groups are the @code{@@chapter} series, the -@code{@@unnumbered} series, the @code{@@appendix} series, and the -@code{@@heading} series.@refill - -Each command produces titles that have a different appearance on the -printed page or Info file; only some of the commands produce -titles that are listed in the table of contents of a printed book or -manual.@refill - -@itemize @bullet -@item -The @code{@@chapter} and @code{@@appendix} series of commands produce -numbered or lettered entries both in the body of a printed work and in -its table of contents.@refill - -@item -The @code{@@unnumbered} series of commands produce unnumbered entries -both in the body of a printed work and in its table of contents. The -@code{@@top} command, which has a special use, is a member of this -series (@pxref{makeinfo top, , @code{@@top}}).@refill - -@item -The @code{@@heading} series of commands produce unnumbered headings -that do not appear in a table of contents. The heading commands never -start a new page.@refill - -@item -The @code{@@majorheading} command produces results similar to using -the @code{@@chapheading} command but generates a larger vertical -whitespace before the heading.@refill - -@item -When an @code{@@setchapternewpage} command says to do so, the -@code{@@chapter}, @code{@@unnumbered}, and @code{@@appendix} commands -start new pages in the printed manual; the @code{@@heading} commands -do not.@refill -@end itemize - -@need 1000 -Here are the four groups of chapter structuring commands:@refill - -@c Slightly different formatting for regular sized books and smallbooks. -@ifset smallbook -@sp 1 -@tex -{\let\rm=\indrm \let\tt=\indtt -\halign{\hskip\itemindent#\hfil& \hskip.5em#\hfil& \hskip.5em#\hfil& -\hskip.5em#\hfil\cr - -& & & \rm No new pages\cr -\rm Numbered& \rm Unnumbered& \rm Lettered and numbered& \rm Unnumbered\cr -\rm In contents& \rm In contents& \rm In contents& \rm Not in contents\cr - -& & & \cr - & \tt @@top& & \tt @@majorheading\cr -\tt @@chapter& \tt @@unnumbered& \tt @@appendix& \tt @@chapheading\cr -\tt @@section& \tt @@unnumberedsec& \tt @@appendixsec& \tt @@heading\cr -\tt @@subsection&\tt @@unnumberedsubsec&\tt @@appendixsubsec& -\tt @@subheading\cr -\tt @@subsubsection& \tt @@unnumberedsubsubsec& \tt @@appendixsubsubsec& -\tt @@subsubheading\cr}} -@end tex -@end ifset -@ifclear smallbook -@sp 1 -@tex -\vbox{ -\halign{\hskip\itemindent\hskip.5em#\hfil& \hskip.5em#\hfil& -\hskip.5em#\hfil& \hskip.5em #\hfil\cr - -& & & \cr -& & & \rm No new pages\cr -\rm Numbered& \rm Unnumbered& \rm Lettered and numbered& \rm Unnumbered\cr -\rm In contents& \rm In contents& \rm In contents& \rm Not in contents\cr - -& & & \cr - & \tt @@top& & \tt @@majorheading\cr -\tt @@chapter& \tt @@unnumbered& \tt @@appendix& \tt @@chapheading\cr -\tt @@section& \tt @@unnumberedsec& \tt @@appendixsec& \tt @@heading\cr -\tt @@subsection&\tt @@unnumberedsubsec&\tt @@appendixsubsec& -\tt @@subheading\cr -\tt @@subsubsection& \tt @@unnumberedsubsubsec& \tt @@appendixsubsubsec& -\tt @@subsubheading\cr}} -@end tex -@end ifclear -@ifinfo -@example -@group - @r{No new pages} -@r{Numbered} @r{Unnumbered} @r{Lettered and numbered} @r{Unnumbered} -@r{In contents} @r{In contents} @r{In contents} @r{Not in contents} - - @@top @@majorheading -@@chapter @@unnumbered @@appendix @@chapheading -@@section @@unnumberedsec @@appendixsec @@heading -@@subsection @@unnumberedsubsec @@appendixsubsec @@subheading -@@subsubsection @@unnumberedsubsubsec @@appendixsubsubsec @@subsubheading -@end group -@end example -@end ifinfo - -@c Cannot line up columns properly inside of an example because of roman -@c proportional fonts. -@ignore -@ifset smallbook -@iftex -@smallexample -@group - @r{No new pages} -@r{Numbered} @r{Unnumbered} @r{Lettered and numbered} @r{Unnumbered} -@r{In contents} @r{In contents} @r{In contents} @r{Not in contents} - - @@top @@majorheading -@@chapter @@unnumbered @@appendix @@chapheading -@@section @@unnumberedsec @@appendixsec @@heading -@@subsection @@unnumberedsubsec @@appendixsubsec @@subheading -@@subsubsection @@unnumberedsubsubsec @@appendixsubsubsec @@subsubheading -@end group -@end smallexample -@end iftex -@end ifset -@ifclear smallbook -@iftex -@smallexample -@group - @r{No new pages} -@r{Numbered} @r{Unnumbered} @r{Lettered and numbered} @r{Unnumbered} -@r{In contents} @r{In contents} @r{In contents} @r{Not in contents} - - @@top @@majorheading -@@chapter @@unnumbered @@appendix @@chapheading -@@section @@unnumberedsec @@appendixsec @@heading -@@subsection @@unnumberedsubsec @@appendixsubsec @@subheading -@@subsubsection @@unnumberedsubsubsec @@appendixsubsubsec @@subsubheading -@end group -@end smallexample -@end iftex -@end ignore - -@node makeinfo top, chapter, Structuring Command Types, Structuring -@comment node-name, next, previous, up -@section @code{@@top} - -The @code{@@top} command is a special sectioning command that you use -only after an @code{@@node Top} line at the beginning of a Texinfo file. -The @code{@@top} command tells the @code{makeinfo} formatter -which node is the `Top' -node. It has the same typesetting effect as @code{@@unnumbered} -(@pxref{unnumbered & appendix, , @code{@@unnumbered}, @code{@@appendix}}). -For detailed information, see -@ref{makeinfo top command, , The @code{@@top} Command}.@refill - -@node chapter, unnumbered & appendix, makeinfo top, Structuring -@comment node-name, next, previous, up -@section @code{@@chapter} -@findex chapter - -@code{@@chapter} identifies a chapter in the document. Write the -command at the beginning of a line and follow it on the same line by -the title of the chapter.@refill - -For example, this chapter in this manual is entitled ``Chapter -Structuring''; the @code{@@chapter} line looks like this:@refill - -@example -@@chapter Chapter Structuring -@end example - -In @TeX{}, the @code{@@chapter} command creates a chapter in the -document, specifying the chapter title. The chapter is numbered -automatically.@refill - -In Info, the @code{@@chapter} command causes the title to appear on a -line by itself, with a line of asterisks inserted underneath. Thus, -in Info, the above example produces the following output:@refill - -@example -Chapter Structuring -******************* -@end example - -@node unnumbered & appendix, majorheading & chapheading, chapter, Structuring -@comment node-name, next, previous, up -@section @code{@@unnumbered}, @code{@@appendix} -@findex unnumbered -@findex appendix - -Use the @code{@@unnumbered} command to create a chapter that appears -in a printed manual without chapter numbers of any kind. Use the -@code{@@appendix} command to create an appendix in a printed manual -that is labelled by letter instead of by number.@refill - -For Info file output, the @code{@@unnumbered} and @code{@@appendix} -commands are equivalent to @code{@@chapter}: the title is printed on a -line by itself with a line of asterisks underneath. (@xref{chapter, , -@code{@@chapter}}.)@refill - -To create an appendix or an unnumbered chapter, write an -@code{@@appendix} or @code{@@unnumbered} command at the beginning of a -line and follow it on the same line by the title, as you would if you -were creating a chapter.@refill - -@node majorheading & chapheading, section, unnumbered & appendix, Structuring -@section @code{@@majorheading}, @code{@@chapheading} -@findex majorheading -@findex chapheading - -The @code{@@majorheading} and @code{@@chapheading} commands put -chapter-like headings in the body of a document.@refill - -However, neither command causes @TeX{} to produce a numbered heading -or an entry in the table of contents; and neither command causes -@TeX{} to start a new page in a printed manual.@refill - -In @TeX{}, an @code{@@majorheading} command generates a larger vertical -whitespace before the heading than an @code{@@chapheading} command but -is otherwise the same.@refill - -In Info, -the @code{@@majorheading} and -@code{@@chapheading} commands are equivalent to -@code{@@chapter}: the title is printed on a line by itself with a line -of asterisks underneath. (@xref{chapter, , @code{@@chapter}}.)@refill - -@node section, unnumberedsec appendixsec heading, majorheading & chapheading, Structuring -@comment node-name, next, previous, up -@section @code{@@section} -@findex section - -In a printed manual, an @code{@@section} command identifies a -numbered section within a chapter. The section title appears in the -table of contents. In Info, an @code{@@section} command provides a -title for a segment of text, underlined with @samp{=}.@refill - -This section is headed with an @code{@@section} command and looks like -this in the Texinfo file:@refill - -@example -@@section @@code@{@@@@section@} -@end example - -To create a section, write the @code{@@section} command at the -beginning of a line and follow it on the same line by the section -title.@refill - -Thus, - -@example -@@section This is a section -@end example - -@noindent -produces - -@example -@group -This is a section -================= -@end group -@end example - -@noindent -in Info. - -@node unnumberedsec appendixsec heading, subsection, section, Structuring -@comment node-name, next, previous, up -@section @code{@@unnumberedsec}, @code{@@appendixsec}, @code{@@heading} -@findex unnumberedsec -@findex appendixsec -@findex heading - -The @code{@@unnumberedsec}, @code{@@appendixsec}, and @code{@@heading} -commands are, respectively, the unnumbered, appendix-like, and -heading-like equivalents of the @code{@@section} command. -(@xref{section, , @code{@@section}}.)@refill - -@table @code -@item @@unnumberedsec -The @code{@@unnumberedsec} command may be used within an -unnumbered chapter or within a regular chapter or appendix to -provide an unnumbered section.@refill - -@item @@appendixsec -@itemx @@appendixsection -@code{@@appendixsection} is a longer spelling of the -@code{@@appendixsec} command; the two are synonymous.@refill -@findex appendixsection - -Conventionally, the @code{@@appendixsec} or @code{@@appendixsection} -command is used only within appendices.@refill - -@item @@heading -You may use the @code{@@heading} command anywhere you wish for a -section-style heading that will not appear in the table of contents.@refill -@end table - -@node subsection, unnumberedsubsec appendixsubsec subheading, unnumberedsec appendixsec heading, Structuring -@comment node-name, next, previous, up -@section The @code{@@subsection} Command -@findex subsection - -Subsections are to sections as sections are to chapters. -(@xref{section, , @code{@@section}}.) In Info, subsection titles are -underlined with @samp{-}. For example,@refill - -@example -@@subsection This is a subsection -@end example - -@noindent -produces - -@example -@group -This is a subsection --------------------- -@end group -@end example - -In a printed manual, subsections are listed in the table of contents -and are numbered three levels deep.@refill - -@node unnumberedsubsec appendixsubsec subheading, subsubsection, subsection, Structuring -@comment node-name, next, previous, up -@section The @code{@@subsection}-like Commands -@cindex Subsection-like commands -@findex unnumberedsubsec -@findex appendixsubsec -@findex subheading - -The @code{@@unnumberedsubsec}, @code{@@appendixsubsec}, and -@code{@@subheading} commands are, respectively, the unnumbered, -appendix-like, and heading-like equivalents of the @code{@@subsection} -command. (@xref{subsection, , @code{@@subsection}}.)@refill - -In Info, the @code{@@subsection}-like commands generate a title -underlined with hyphens. In a printed manual, an @code{@@subheading} -command produces a heading like that of a subsection except that it is -not numbered and does not appear in the table of contents. Similarly, -an @code{@@unnumberedsubsec} command produces an unnumbered heading like -that of a subsection and an @code{@@appendixsubsec} command produces a -subsection-like heading labelled with a letter and numbers; both of -these commands produce headings that appear in the table of -contents.@refill - -@node subsubsection, , unnumberedsubsec appendixsubsec subheading, Structuring -@comment node-name, next, previous, up -@section The `subsub' Commands -@cindex Subsub commands -@findex subsubsection -@findex unnumberedsubsubsec -@findex appendixsubsubsec -@findex subsubheading - -The fourth and lowest level sectioning commands in Texinfo are the -`subsub' commands. They are:@refill - -@table @code -@item @@subsubsection -Subsubsections are to subsections as subsections are to sections. -(@xref{subsection, , @code{@@subsection}}.) In a printed manual, -subsubsection titles appear in the table of contents and are numbered -four levels deep.@refill - -@item @@unnumberedsubsubsec -Unnumbered subsubsection titles appear in the table of contents of a -printed manual, but lack numbers. Otherwise, unnumbered -subsubsections are the same as subsubsections. In Info, unnumbered -subsubsections look exactly like ordinary subsubsections.@refill - -@item @@appendixsubsubsec -Conventionally, appendix commands are used only for appendices and are -lettered and numbered appropriately in a printed manual. They also -appear in the table of contents. In Info, appendix subsubsections look -exactly like ordinary subsubsections.@refill - -@item @@subsubheading -The @code{@@subsubheading} command may be used anywhere that you need -a small heading that will not appear in the table of contents. In -Info, subsubheadings look exactly like ordinary subsubsection -headings.@refill -@end table - -In Info, `subsub' titles are underlined with periods. -For example,@refill - -@example -@@subsubsection This is a subsubsection -@end example - -@noindent -produces - -@example -@group -This is a subsubsection -....................... -@end group -@end example - -@node Nodes, Menus, Structuring, Top -@comment node-name, next, previous, up -@chapter Nodes - -@dfn{Nodes} are the primary segments of a Texinfo file. They do not -themselves impose a hierarchic or any other kind of structure on a file. -Nodes contain @dfn{node pointers} that name other nodes, and can contain -@dfn{menus} which are lists of nodes. In Info, the movement commands -can carry you to a pointed-to node or to a node listed in a menu. Node -pointers and menus provide structure for Info files just as chapters, -sections, subsections, and the like, provide structure for printed -books.@refill - -@menu -* Two Paths:: Different commands to structure - Info output and printed output. -* Node Menu Illustration:: A diagram, and sample nodes and menus. -* node:: How to write a node, in detail. -* makeinfo Pointer Creation:: How to create node pointers with @code{makeinfo}. -@end menu - -@node Two Paths, Node Menu Illustration, , Nodes -@ifinfo -@heading Two Paths -@end ifinfo - -The node and menu commands and the chapter structuring commands are -independent of each other: - -@itemize @bullet -@item -In Info, node and menu commands provide structure. The chapter -structuring commands generate headings with different kinds of -underlining---asterisks for chapters, hyphens for sections, and so on; -they do nothing else.@refill - -@item -In @TeX{}, the chapter structuring commands generate chapter and section -numbers and tables of contents. The node and menu commands provide -information for cross references; they do nothing else.@refill -@end itemize - -You can use node pointers and menus to structure an Info file any way -you want; and you can write a Texinfo file so that its Info output has a -different structure than its printed output. However, most Texinfo -files are written such that the structure for the Info output -corresponds to the structure for the printed output. It is not -convenient to do otherwise.@refill - -Generally, printed output is structured in a tree-like hierarchy in -which the chapters are the major limbs from which the sections branch -out. Similarly, node pointers and menus are organized to create a -matching structure in the Info output.@refill - -@node Node Menu Illustration, node, Two Paths, Nodes -@comment node-name, next, previous, up -@section Node and Menu Illustration - -Here is a copy of the diagram shown earlier that illustrates a Texinfo -file with three chapters, each of which contains two sections.@refill - -Note that the ``root'' is at the top of the diagram and the ``leaves'' -are at the bottom. This is how such a diagram is drawn conventionally; -it illustrates an upside-down tree. For this reason, the root node is -called the `Top' node, and `Up' node pointers carry you closer to the -root.@refill - -@example -@group - Top - | - ------------------------------------- - | | | - Chapter 1 Chapter 2 Chapter 3 - | | | - -------- -------- -------- - | | | | | | - Section Section Section Section Section Section - 1.1 1.2 2.1 2.2 3.1 3.2 - -@end group -@end example - -Write the beginning of the node for Chapter 2 like this:@refill - -@example -@group -@@node Chapter 2, Chapter 3, Chapter 1, top -@@comment node-name, next, previous, up -@end group -@end example - -@noindent -This @code{@@node} line says that the name of this node is ``Chapter 2'', the -name of the `Next' node is ``Chapter 3'', the name of the `Previous' -node is ``Chapter 1'', and the name of the `Up' node is ``Top''. - -@quotation -@strong{Please Note:} `Next' refers to the next node at the same -hierarchical level in the manual, not necessarily to the next node -within the Texinfo file. In the Texinfo file, the subsequent node may -be at a lower level---a section-level node may follow a chapter-level -node, and a subsection-level node may follow a section-level node. -`Next' and `Previous' refer to nodes at the @emph{same} hierarchical -level. (The `Top' node contains the exception to this rule. Since the -`Top' node is the only node at that level, `Next' refers to the first -following node, which is almost always a chapter or chapter-level -node.)@refill -@end quotation - -To go to Sections 2.1 and 2.2 using Info, you need a menu inside Chapter -2. (@xref{Menus}.) You would write the menu just -before the beginning of Section 2.1, like this:@refill - -@example -@group - @@menu - * Sect. 2.1:: Description of this section. - * Sect. 2.2:: - @@end menu -@end group -@end example - -Write the node for Sect. 2.1 like this:@refill - -@example -@group - @@node Sect. 2.1, Sect. 2.2, Chapter 2, Chapter 2 - @@comment node-name, next, previous, up -@end group -@end example - -In Info format, the `Next' and `Previous' pointers of a node usually -lead to other nodes at the same level---from chapter to chapter or from -section to section (sometimes, as shown, the `Previous' pointer points -up); an `Up' pointer usually leads to a node at the level above (closer -to the `Top' node); and a `Menu' leads to nodes at a level below (closer -to `leaves'). (A cross reference can point to a node at any level; -see @ref{Cross References}.)@refill - -Usually, an @code{@@node} command and a chapter structuring command are -used in sequence, along with indexing commands. (You may follow the -@code{@@node} line with a comment line that reminds you which pointer is -which.)@refill - -Here is the beginning of the chapter in this manual called ``Ending a -Texinfo File''. This shows an @code{@@node} line followed by a comment -line, an @code{@@chapter} line, and then by indexing lines.@refill - -@example -@group -@@node Ending a File, Structuring, Beginning a File, Top -@@comment node-name, next, previous, up -@@chapter Ending a Texinfo File -@@cindex Ending a Texinfo file -@@cindex Texinfo file ending -@@cindex File ending -@end group -@end example - -@node node, makeinfo Pointer Creation, Node Menu Illustration, Nodes -@comment node-name, next, previous, up -@section The @code{@@node} Command - -@cindex Node, defined -A @dfn{node} is a segment of text that begins at an @code{@@node} -command and continues until the next @code{@@node} command. The -definition of node is different from that for chapter or section. A -chapter may contain sections and a section may contain subsections; -but a node cannot contain subnodes; the text of a node continues only -until the next @code{@@node} command in the file. A node usually -contains only one chapter structuring command, the one that follows -the @code{@@node} line. On the other hand, in printed output nodes -are used only for cross references, so a chapter or section may -contain any number of nodes. Indeed, a chapter usually contains -several nodes, one for each section, subsection, and -subsubsection.@refill - -To create a node, write an @code{@@node} command at the beginning of a -line, and follow it with four arguments, separated by commas, on the -rest of the same line. These arguments are the name of the node, and -the names of the `Next', `Previous', and `Up' pointers, in that order. -You may insert spaces before each pointer if you wish; the spaces are -ignored. You must write the name of the node, and the names of the -`Next', `Previous', and `Up' pointers, all on the same line. Otherwise, -the formatters fail. (@inforef{Top, info, info}, for more information -about nodes in Info.)@refill - -Usually, you write one of the chapter-structuring command lines -immediately after an @code{@@node} line---for example, an -@code{@@section} or @code{@@subsection} line. (@xref{Structuring -Command Types, , Types of Structuring Command}.)@refill - -@quotation -@strong{Please note:} The GNU Emacs Texinfo mode updating commands work -only with Texinfo files in which @code{@@node} lines are followed by chapter -structuring lines. @xref{Updating Requirements}.@refill -@end quotation - -@TeX{} uses @code{@@node} lines to identify the names to use for cross -references. For this reason, you must write @code{@@node} lines in a -Texinfo file that you intend to format for printing, even if you do not -intend to format it for Info. (Cross references, such as the one at the -end of this sentence, are made with @code{@@xref} and its related -commands; see @ref{Cross References}.)@refill - -@menu -* Node Names:: How to choose node and pointer names. -* Writing a Node:: How to write an @code{@@node} line. -* Node Line Tips:: Keep names short. -* Node Line Requirements:: Keep names unique, without @@-commands. -* First Node:: How to write a `Top' node. -* makeinfo top command:: How to use the @code{@@top} command. -* Top Node Summary:: Write a brief description for readers. -@end menu - -@node Node Names, Writing a Node, , node -@ifinfo -@subheading Choosing Node and Pointer Names -@end ifinfo - -The name of a node identifies the node. The pointers enable -you to reach other nodes and consist of the names of those nodes.@refill - -Normally, a node's `Up' pointer contains the name of the node whose menu -mentions that node. The node's `Next' pointer contains the name of the -node that follows that node in that menu and its `Previous' pointer -contains the name of the node that precedes it in that menu. When a -node's `Previous' node is the same as its `Up' node, both node pointers -name the same node.@refill - -Usually, the first node of a Texinfo file is the `Top' node, and its -`Up' and `Previous' pointers point to the @file{dir} file, which -contains the main menu for all of Info.@refill - -The `Top' node itself contains the main or master menu for the manual. -Also, it is helpful to include a brief description of the manual in the -`Top' node. @xref{First Node}, for information on how to write the -first node of a Texinfo file.@refill - -@node Writing a Node, Node Line Tips, Node Names, node -@comment node-name, next, previous, up -@subsection How to Write an @code{@@node} Line -@cindex Writing an @code{@@node} line -@cindex @code{@@node} line writing -@cindex Node line writing - -The easiest way to write an @code{@@node} line is to write @code{@@node} -at the beginning of a line and then the name of the node, like -this:@refill - -@example -@@node @var{node-name} -@end example - -If you are using GNU Emacs, you can use the update node commands -provided by Texinfo mode to insert the names of the pointers; or you -can leave the pointers out of the Texinfo file and let @code{makeinfo} -insert node pointers into the Info file it creates. (@xref{Texinfo -Mode}, and @ref{makeinfo Pointer Creation}.)@refill - -Alternatively, you can insert the `Next', `Previous', and `Up' -pointers yourself. If you do this, you may find it helpful to use the -Texinfo mode keyboard command @kbd{C-c C-c n}. This command inserts -@samp{@@node} and a comment line listing the names of the pointers in -their proper order. The comment line helps you keep track of which -arguments are for which pointers. This comment line is especially useful -if you are not familiar with Texinfo.@refill - -The template for a node line with `Next', `Previous', and `Up' pointers -looks like this:@refill - -@example -@@node @var{node-name}, @var{next}, @var{previous}, @var{up} -@end example - -If you wish, you can ignore @code{@@node} lines altogether in your first -draft and then use the @code{texinfo-insert-node-lines} command to -create @code{@@node} lines for you. However, we do not -recommend this practice. It is better to name the node itself -at the same time that you -write a segment so you can easily make cross references. A large number -of cross references are an especially important feature of a good Info -file.@refill - -After you have inserted an @code{@@node} line, you should immediately -write an @@-command for the chapter or section and insert its name. -Next (and this is important!), put in several index entries. Usually, -you will find at least two and often as many as four or five ways of -referring to the node in the index. Use them all. This will make it -much easier for people to find the node.@refill - -@node Node Line Tips, Node Line Requirements, Writing a Node, node -@comment node-name, next, previous, up -@subsection @code{@@node} Line Tips - -Here are three suggestions: - -@itemize @bullet -@item -Try to pick node names that are informative but short.@refill - -In the Info file, the file name, node name, and pointer names are all -inserted on one line, which may run into the right edge of the window. -(This does not cause a problem with Info, but is ugly.)@refill - -@item -Try to pick node names that differ from each other near the beginnings -of their names. This way, it is easy to use automatic name completion in -Info.@refill - -@item -By convention, node names are capitalized just as they would be for -section or chapter titles---initial and significant words are -capitalized; others are not.@refill -@end itemize - -@node Node Line Requirements, First Node, Node Line Tips, node -@comment node-name, next, previous, up -@subsection @code{@@node} Line Requirements - -@cindex Node line requirements -Here are several requirements for @code{@@node} lines: - -@itemize @bullet -@cindex Unique nodename requirement -@cindex Nodename must be unique -@item -All the node names for a single Info file must be unique.@refill - -Duplicates confuse the Info movement commands. This means, for -example, that if you end every chapter with a summary, you must name -each summary node differently. You cannot just call each one -``Summary''. You may, however, duplicate the titles of chapters, sections, -and the like. Thus you can end each chapter in a book with a section -called ``Summary'', so long as the node names for those sections are all -different.@refill - -@item -A pointer name must be the name of a node.@refill - -The node to which a pointer points may come before or after the -node containing the pointer.@refill - -@cindex @@-command in nodename -@cindex Nodename, cannot contain -@item -You cannot use any of the Texinfo @@-commands in a node name; -@w{@@-commands} confuse Info.@refill - -@need 750 -Thus, the beginning of the section called @code{@@chapter} looks like -this:@refill - -@smallexample -@group -@@node chapter, unnumbered & appendix, makeinfo top, Structuring -@@comment node-name, next, previous, up -@@section @@code@{@@@@chapter@} -@@findex chapter -@end group -@end smallexample - -@cindex Comma in nodename -@cindex Colon in nodename -@cindex Apostrophe in nodename -@item -You cannot use commas, colons, or apostrophes within a node name; these -confuse @TeX{} or the Info formatters.@refill - -@need 700 -For example, the following is a section title: - -@smallexample -@@code@{@@@@unnumberedsec@}, @@code@{@@@@appendixsec@}, @@code@{@@@@heading@} -@end smallexample - -@noindent -The corresponding node name is: - -@smallexample -unnumberedsec appendixsec heading -@end smallexample - -@cindex Case in nodename -@item -Case is significant. -@end itemize - -@node First Node, makeinfo top command, Node Line Requirements, node -@comment node-name, next, previous, up -@subsection The First Node -@cindex @samp{@r{Top}} node is first -@cindex First node - -The first node of a Texinfo file is the `Top' node, except in an -included file (@pxref{Include Files}). - -The `Top' node (which must be named @samp{top} or @samp{Top}) should -have as its `Up' and `Previous' nodes the name of a node in another -file, where there is a menu that leads to this file. Specify the file -name in parentheses. If the file is to be installed directly in the -Info directory file, use @samp{(dir)} as the parent of the `Top' node; -this is short for @samp{(dir)top}, and specifies the `Top' node in the -@file{dir} file, which contains the main menu for Info. For example, -the @code{@@node Top} line of this manual looks like this:@refill - -@example -@@node Top, Overview, (dir), (dir) -@end example - -@noindent -(You may use the Texinfo updating commands or the @code{makeinfo} -utility to insert these `Next' and @samp{(dir)} pointers -automatically.)@refill - -@xref{Install an Info File}, for more information about installing -an Info file in the @file{info} directory.@refill - -The `Top' node contains the main or master menu for the document. - -@node makeinfo top command, Top Node Summary, First Node, node -@comment node-name, next, previous, up -@subsection The @code{@@top} Sectioning Command -@findex top @r{(@@-command)} - -A special sectioning command, @code{@@top}, has been created for use -with the @code{@@node Top} line. The @code{@@top} sectioning command tells -@code{makeinfo} that it marks the `Top' node in the file. It provides -the information that @code{makeinfo} needs to insert node -pointers automatically. Write the @code{@@top} command at the -beginning of the line immediately following the @code{@@node Top} -line. Write the title on the remaining part of the same line as the -@code{@@top} command.@refill - -In Info, the @code{@@top} sectioning command causes the title to appear on a -line by itself, with a line of asterisks inserted underneath.@refill - -In @TeX{} and @code{texinfo-format-buffer}, the @code{@@top} -sectioning command is merely a synonym for @code{@@unnumbered}. -Neither of these formatters require an @code{@@top} command, and do -nothing special with it. You can use @code{@@chapter} or -@code{@@unnumbered} after the @code{@@node Top} line when you use -these formatters. Also, you can use @code{@@chapter} or -@code{@@unnumbered} when you use the Texinfo updating commands to -create or update pointers and menus.@refill - -Whatever sectioning command follows an @code{@@node Top} line, whether -it be @code{@@top} or @code{@@chapter}, the @code{@@node Top} line and -the immediately following line and any additional text must be -enclosed between @code{@@ifinfo} and @code{@@end ifinfo} commands. -(@xref{Conditionals}.) This prevents the title and the accompanying -text from appearing in printed output. Write the @code{@@ifinfo} -command before the @code{@@node} line and write the @code{@@end ifinfo} command -after the @code{@@top} or other sectioning command and after any -additional text. (You can write the @code{@@end ifinfo} command after -the @code{@@end menu} command if you like.)@refill - -@node Top Node Summary, , makeinfo top command, node -@subsection The `Top' Node Summary -@cindex @samp{@r{Top}} node summary - -You can help readers by writing a summary in the `Top' node, after the -@code{@@top} line, before the main or master menu. The summary should -briefly describe the Info file. You should also write the version -number of the program to which the manual applies in this section. This -helps the reader keep track of which manual is for which version of the -program. If the manual changes more frequently than the program or is -independent of it, you should also include an edition number for the -manual. (The title page should also contain this information: -see @ref{titlepage, , @code{@@titlepage}}.)@refill - -Put the whole of the `Top' node, including the @code{@@top} sectioning -command line if you -have one, between @code{@@ifinfo} and @code{@@end -ifinfo} so none of the text appears in the printed output -(@pxref{Conditionals, , Conditionally Visible Text}). (You may want to -repeat the brief description from the `Top' node within @code{@@iftex} -@dots{} @code{@@end iftex} at the beginning of the first chapter, for -those who read the printed manual.) - -@node makeinfo Pointer Creation, , node, Nodes -@section Creating Pointers with @code{makeinfo} -@cindex Creating pointers with @code{makeinfo} -@cindex Pointer creation with @code{makeinfo} -@cindex Automatic pointer creation with @code{makeinfo} - -The @code{makeinfo} program has a feature for automatically creating -node pointers for a hierarchically organized file that lacks -them.@refill - -When you take advantage of this feature, you do not need to write the -`Next', `Previous', and `Up' pointers after the name of a node. -However, you must write a sectioning command, such as @code{@@chapter} -or @code{@@section}, on the line immediately following each truncated -@code{@@node} line. You cannot write a comment line after a node -line; the section line must follow it immediately.@refill - -In addition, you must follow the `Top' @code{@@node} line with a line beginning -with @code{@@top} to mark the `Top' node in the file. @xref{makeinfo -top, , @code{@@top}}. - -Finally, you must write the name of each node (except for the `Top' -node) in a menu that is one or more hierarchical levels above the -node's hierarchical level.@refill - -This node pointer insertion feature in @code{makeinfo} is an -alternative to the menu and pointer creation and update commands in -Texinfo mode. (@xref{Updating Nodes and Menus}.) It is especially -helpful to people who do not use GNU Emacs for writing Texinfo -documents.@refill - -@node Menus, Cross References, Nodes, Top -@comment node-name, next, previous, up -@chapter Menus -@cindex Menus -@findex menu - -@dfn{Menus} contain pointers to subordinate -nodes.@footnote{Menus can carry you to any node, regardless -of the hierarchical structure; even to nodes in a different -Info file. However, the GNU Emacs Texinfo mode updating -commands work only to create menus of subordinate nodes. -Conventionally, cross references are used to refer to other -nodes.} In Info, you use menus to go to such nodes. Menus -have no effect in printed manuals and do not appear in -them.@refill - -By convention, a menu is put at the end of a node since a reader who -uses the menu may not see text that follows it.@refill - -@ifinfo -A node that has a menu should @emph{not} contain much text. If you -have a lot of text and a menu, move most of the text into a new -subnode---all but a few lines.@refill -@end ifinfo -@iftex -@emph{A node that has a menu should not contain much text.} If you -have a lot of text and a menu, move most of the text into a new -subnode---all but a few lines. Otherwise, a reader with a terminal -that displays only a few lines may miss the menu and its associated -text. As a practical matter, you should locate a menu within 20 lines -of the beginning of the node.@refill -@end iftex - -@menu -* Menu Location:: Put a menu in a short node. -* Writing a Menu:: What is a menu? -* Menu Parts:: A menu entry has three parts. -* Less Cluttered Menu Entry:: Two part menu entry. -* Menu Example:: Two and three part menu entries. -* Other Info Files:: How to refer to a different Info file. -@end menu - -@node Menu Location, Writing a Menu, , Menus -@ifinfo -@heading Menus Need Short Nodes -@end ifinfo -@cindex Menu location -@cindex Location of menus -@cindex Nodes for menus are short -@cindex Short nodes for menus - -@ifinfo -A reader can easily see a menu that is close to the beginning of the -node. The node should be short. As a practical matter, you should -locate a menu within 20 lines of the beginning of the node. -Otherwise, a reader with a terminal that displays only a few lines may -miss the menu and its associated text.@refill -@end ifinfo - -The short text before a menu may look awkward in a printed manual. To -avoid this, you can write a menu near the beginning of its node and -follow the menu by an @code{@@node} line, and then an @code{@@heading} -line located within @code{@@ifinfo} and @code{@@end ifinfo}. This way, -the menu, @code{@@node} line, and title appear only in the Info file, -not the printed document.@refill - -For example, the preceding two paragraphs follow an Info-only menu, -@code{@@node} line, and heading, and look like this:@refill - -@example -@group -@@menu -* Menu Location:: Put a menu in a short node. -* Writing a Menu:: What is a menu? -* Menu Parts:: A menu entry has three parts. -* Less Cluttered Menu Entry:: Two part menu entry. -* Menu Example:: Two and three part entries. -* Other Info Files:: How to refer to a different - Info file. -@@end menu - -@@node Menu Location, Writing a Menu, , Menus -@@ifinfo -@@heading Menus Need Short Nodes -@@end ifinfo -@end group -@end example - -The Texinfo file for this document contains more than a dozen -examples of this procedure. One is at the beginning of this chapter; -another is at the beginning of the ``Cross References'' chapter.@refill - -@node Writing a Menu, Menu Parts, Menu Location, Menus -@section Writing a Menu -@cindex Writing a menu -@cindex Menu writing - -A menu consists of an @code{@@menu} command on a line by -itself followed by menu entry lines or menu comment lines -and then by an @code{@@end menu} command on a line by -itself.@refill - -A menu looks like this:@refill - -@example -@group -@@menu -Larger Units of Text - -* Files:: All about handling files. -* Multiples: Buffers. Multiple buffers; editing - several files at once. -@@end menu -@end group -@end example - -In a menu, every line that begins with an @w{@samp{* }} is a -@dfn{menu entry}. (Note the space after the asterisk.) A -line that does not start with an @w{@samp{* }} may also -appear in a menu. Such a line is not a menu entry but is a -menu comment line that appears in the Info file. In -the example above, the line @samp{Larger Units of Text} is a -menu comment line; the two lines starting with @w{@samp{* }} -are menu entries. - -@node Menu Parts, Less Cluttered Menu Entry, Writing a Menu, Menus -@section The Parts of a Menu -@cindex Parts of a menu -@cindex Menu parts -@cindex @code{@@menu} parts - -A menu entry has three parts, only the second of which is -required:@refill - -@enumerate -@item -The menu entry name. - -@item -The name of the node (required). - -@item -A description of the item. -@end enumerate - -The template for a menu entry looks like this:@refill - -@example -* @var{menu-entry-name}: @var{node-name}. @var{description} -@end example - -Follow the menu entry name with a single colon and follow the node name -with tab, comma, period, or newline.@refill - -In Info, a user selects a node with the @kbd{m} (@code{Info-menu}) -command. The menu entry name is what the user types after the @kbd{m} -command.@refill - -The third part of a menu entry is a descriptive phrase or -sentence. Menu entry names and node names are often short; the -description explains to the reader what the node is about. The -description, which is optional, can spread over two or more lines. A -useful description complements the node name rather than repeats -it.@refill - -@node Less Cluttered Menu Entry, Menu Example, Menu Parts, Menus -@comment node-name, next, previous, up -@section Less Cluttered Menu Entry -@cindex Two part menu entry -@cindex Double-colon menu entries -@cindex Menu entries with two colons -@cindex Less cluttered menu entry -@cindex Uncluttered menu entry - -When the menu entry name and node name are the same, you can write -the name immediately after the asterisk and space at the beginning of -the line and follow the name with two colons.@refill - -@need 800 -For example, write - -@example -* Name:: @var{description} -@end example - -@need 800 -@noindent -instead of - -@example -* Name: Name. @var{description} -@end example - -You should use the node name for the menu entry name whenever possible, -since it reduces visual clutter in the menu.@refill - -@node Menu Example, Other Info Files, Less Cluttered Menu Entry, Menus -@comment node-name, next, previous, up -@section A Menu Example -@cindex Menu example -@cindex Example menu - -A menu looks like this in Texinfo:@refill - -@example -@group -@@menu -* menu entry name: Node name. A short description. -* Node name:: This form is preferred. -@@end menu -@end group -@end example - -@need 800 -@noindent -This produces: - -@example -@group -* menu: - -* menu entry name: Node name. A short description. -* Node name:: This form is preferred. -@end group -@end example - -@need 700 -Here is an example as you might see it in a Texinfo file:@refill - -@example -@group -@@menu -Larger Units of Text - -* Files:: All about handling files. -* Multiples: Buffers. Multiple buffers; editing - several files at once. -@@end menu -@end group -@end example - -@need 800 -@noindent -This produces: - -@example -@group -* menu: -Larger Units of Text - -* Files:: All about handling files. -* Multiples: Buffers. Multiple buffers; editing - several files at once. -@end group -@end example - -In this example, the menu has two entries. @samp{Files} is both a menu -entry name and the name of the node referred to by that name. -@samp{Multiples} is the menu entry name; it refers to the node named -@samp{Buffers}. The line @samp{Larger Units of Text} is a comment; it -appears in the menu, but is not an entry.@refill - -Since no file name is specified with either @samp{Files} or -@samp{Buffers}, they must be the names of nodes in the same Info file -(@pxref{Other Info Files, , Referring to Other Info Files}).@refill - -@node Other Info Files, , Menu Example, Menus -@comment node-name, next, previous, up -@section Referring to Other Info Files -@cindex Referring to other Info files -@cindex Nodes in other Info files -@cindex Other Info files' nodes -@cindex Going to other Info files' nodes -@cindex Info; other files' nodes - -You can create a menu entry that enables a reader in Info to go to a -node in another Info file by writing the file name in parentheses just -before the node name. In this case, you should use the three-part menu -entry format, which saves the reader from having to type the file -name.@refill - -@need 800 -The format looks like this:@refill - -@example -@group -@@menu -* @var{first-entry-name}:(@var{filename})@var{nodename}. @var{description} -* @var{second-entry-name}:(@var{filename})@var{second-node}. @var{description} -@@end menu -@end group -@end example - -For example, to refer directly to the @samp{Outlining} and -@samp{Rebinding} nodes in the @cite{Emacs Manual}, you would write a -menu like this:@refill - -@example -@group -@@menu -* Outlining: (emacs)Outline Mode. The major mode for - editing outlines. -* Rebinding: (emacs)Rebinding. How to redefine the - meaning of a key. -@@end menu -@end group -@end example - -If you do not list the node name, but only name the file, then Info -presumes that you are referring to the `Top' node.@refill - -The @file{dir} file that contains the main menu for Info has menu -entries that list only file names. These take you directly to the `Top' -nodes of each Info document. (@xref{Install an Info File}.)@refill - -@need 700 -For example: - -@example -@group -* Info: (info). Documentation browsing system. -* Emacs: (emacs). The extensible, self-documenting - text editor. -@end group -@end example - -@noindent -(The @file{dir} top level directory for the Info system is an Info file, -not a Texinfo file, but a menu entry looks the same in both types of -file.)@refill - -Note that the GNU Emacs Texinfo mode menu updating commands only work -with nodes within the current buffer, so you cannot use them to create -menus that refer to other files. You must write such menus by hand.@refill - -@node Cross References, Marking Text, Menus, Top -@comment node-name, next, previous, up -@chapter Cross References -@cindex Making cross references -@cindex Cross references -@cindex References - -@dfn{Cross references} are used to refer the reader to other parts of the -same or different Texinfo files. In Texinfo, nodes are the -places to which cross references can refer.@refill - -@menu -* References:: What cross references are for. -* Cross Reference Commands:: A summary of the different commands. -* Cross Reference Parts:: A cross reference has several parts. -* xref:: Begin a reference with `See' @dots{} -* Top Node Naming:: How to refer to the beginning of another file. -* ref:: A reference for the last part of a sentence. -* pxref:: How to write a parenthetical cross reference. -* inforef:: How to refer to an Info-only file. -@end menu - -@node References, Cross Reference Commands, , Cross References -@ifinfo -@heading What References Are For -@end ifinfo - -Often, but not always, a printed document should be designed so that -it can be read sequentially. People tire of flipping back and forth -to find information that should be presented to them as they need -it.@refill - -However, in any document, some information will be too detailed for -the current context, or incidental to it; use cross references to -provide access to such information. Also, an on-line help system or a -reference manual is not like a novel; few read such documents in -sequence from beginning to end. Instead, people look up what they -need. For this reason, such creations should contain many cross -references to help readers find other information that they may not -have read.@refill - -In a printed manual, a cross reference results in a page reference, -unless it is to another manual altogether, in which case the cross -reference names that manual.@refill - -In Info, a cross reference results in an entry that you can follow using -the Info @samp{f} command. (@inforef{Help-Adv, Some advanced Info -commands, info}.)@refill - -The various cross reference commands use nodes to define cross -reference locations. This is evident in Info, in which a cross -reference takes you to the specified node. @TeX{} also uses nodes to -define cross reference locations, but the action is less obvious. When -@TeX{} generates a @sc{dvi} file, it records nodes' page numbers and -uses the page numbers in making references. Thus, if you are writing -a manual that will only be printed, and will not be used on-line, you -must nonetheless write @code{@@node} lines to name the places to which -you make cross references.@refill - -@need 800 -@node Cross Reference Commands, Cross Reference Parts, References, Cross References -@comment node-name, next, previous, up -@section Different Cross Reference Commands -@cindex Different cross reference commands - -There are four different cross reference commands:@refill - -@table @code -@item @@xref -Used to start a sentence in the printed manual saying -@w{`See @dots{}'} or an entry in the Info file saying -@samp{*Note @dots{}}. - -@item @@ref -Used within or, more often, at the end of a sentence; same as -@code{@@xref} for Info; produces just the reference in the printed -manual without a preceding `See'.@refill - -@item @@pxref -Used within parentheses to make a reference that suits both an Info -file and a printed book. Starts with a lower case `see' within the -printed manual. (@samp{p} is for `parenthesis'.)@refill - -@item @@inforef -Used to make a reference to an Info file for which there is no printed -manual.@refill -@end table - -@noindent -(The @code{@@cite} command is used to make references to books and -manuals for which there is no corresponding Info file and, therefore, -no node to which to point. @xref{cite, , @code{@@cite}}.)@refill - -@node Cross Reference Parts, xref, Cross Reference Commands, Cross References -@comment node-name, next, previous, up -@section Parts of a Cross Reference -@cindex Cross reference parts -@cindex Parts of a cross reference - -A cross reference command requires only one argument, which is the -name of the node to which it refers. But a cross reference command -may contain up to four additional arguments. By using these -arguments, you can provide a cross reference name for Info, a topic -description or section title for the printed output, the name of a -different Info file, and the name of a different printed -manual.@refill - -Here is a simple cross reference example:@refill - -@example -@@xref@{Node name@}. -@end example - -@noindent -which produces - -@example -*Note Node name::. -@end example - -@noindent -and - -@quotation -See Section @var{nnn} [Node name], page @var{ppp}. -@end quotation - -@need 700 -Here is an example of a full five-part cross reference:@refill - -@example -@group -@@xref@{Node name, Cross Reference Name, Particular Topic, -info-file-name, A Printed Manual@}, for details. -@end group -@end example - -@noindent -which produces - -@example -*Note Cross Reference Name: (info-file-name)Node name, -for details. -@end example - -@noindent -in Info and - -@quotation -See section ``Particular Topic'' in @i{A Printed Manual}, for details. -@end quotation - -@noindent -in a printed book. - -The five possible arguments for a cross reference are:@refill - -@enumerate -@item -The node name (required). This is the node to which the -cross reference takes you. In a printed document, the location of the -node provides the page reference only for references within the same -document.@refill - -@item -The cross reference name for the Info reference, if it is to be different -from the node name. If you include this argument, it argument becomes -the first part of the cross reference. It is usually omitted.@refill - -@item -A topic description or section name. Often, this is the title of the -section. This is used as the name of the reference in the printed -manual. If omitted, the node name is used.@refill - -@item -The name of the Info file in which the reference is located, if it is -different from the current file.@refill - -@item -The name of a printed manual from a different Texinfo file.@refill -@end enumerate - -The template for a full five argument cross reference looks like -this:@refill - -@example -@group -@@xref@{@var{node-name}, @var{cross-reference-name}, @var{title-or-topic}, -@var{info-file-name}, @var{printed-manual-title}@}. -@end group -@end example - -Cross references with one, two, three, four, and five arguments are -described separately following the description of @code{@@xref}.@refill - -Write a node name in a cross reference in exactly the same way as in -the @code{@@node} line, including the same capitalization; otherwise, the -formatters may not find the reference.@refill - -You can write cross reference commands within a paragraph, but note -how Info and @TeX{} format the output of each of the various commands: -write @code{@@xref} at the beginning of a sentence; write -@code{@@pxref} only within parentheses, and so on.@refill - -@node xref, Top Node Naming, Cross Reference Parts, Cross References -@comment node-name, next, previous, up -@section @code{@@xref} -@findex xref -@cindex Cross references using @code{@@xref} -@cindex References using @code{@@xref} - -The @code{@@xref} command generates a cross reference for the -beginning of a sentence. The Info formatting commands convert it into -an Info cross reference, which the Info @samp{f} command can use to -bring you directly to another node. The @TeX{} typesetting commands -convert it into a page reference, or a reference to another book or -manual.@refill - -@menu -* Reference Syntax:: What a reference looks like and requires. -* One Argument:: @code{@@xref} with one argument. -* Two Arguments:: @code{@@xref} with two arguments. -* Three Arguments:: @code{@@xref} with three arguments. -* Four and Five Arguments:: @code{@@xref} with four and five arguments. -@end menu - -@node Reference Syntax, One Argument, , xref -@ifinfo -@subheading What a Reference Looks Like and Requires -@end ifinfo - -Most often, an Info cross reference looks like this:@refill - -@example -*Note @var{node-name}::. -@end example - -@noindent -or like this - -@example -*Note @var{cross-reference-name}: @var{node-name}. -@end example - -@noindent -In @TeX{}, a cross reference looks like this: - -@example -See Section @var{section-number} [@var{node-name}], page @var{page}. -@end example - -@noindent -or like this - -@example -See Section @var{section-number} [@var{title-or-topic}], page @var{page}. -@end example - -The @code{@@xref} command does not generate a period or comma to end -the cross reference in either the Info file or the printed output. -You must write that period or comma yourself; otherwise, Info will not -recognize the end of the reference. (The @code{@@pxref} command works -differently. @xref{pxref, , @code{@@pxref}}.)@refill - -@quotation -@strong{Please note:} A period or comma @strong{must} follow the closing -brace of an @code{@@xref}. It is required to terminate the cross -reference. This period or comma will appear in the output, both in -the Info file and in the printed manual.@refill -@end quotation - -@code{@@xref} must refer to an Info node by name. Use @code{@@node} -to define the node (@pxref{Writing a Node}).@refill - -@code{@@xref} is followed by several arguments inside braces, separated by -commas. Whitespace before and after these commas is ignored.@refill - -A cross reference requires only the name of a node; but it may contain -up to four additional arguments. Each of these variations produces a -cross reference that looks somewhat different.@refill - -@quotation -@strong{Please note:} Commas separate arguments in a cross reference; -avoid including them in the title or other part lest the formatters -mistake them for separators.@refill -@end quotation - -@node One Argument, Two Arguments, Reference Syntax, xref -@subsection @code{@@xref} with One Argument - -The simplest form of @code{@@xref} takes one argument, the name of -another node in the same Info file. The Info formatters produce -output that the Info readers can use to jump to the reference; @TeX{} -produces output that specifies the page and section number for you.@refill - -@need 700 -@noindent -For example, - -@example -@@xref@{Tropical Storms@}. -@end example - -@noindent -produces - -@example -*Note Tropical Storms::. -@end example - -@noindent -and - -@quotation -See Section 3.1 [Tropical Storms], page 24. -@end quotation - -@noindent -(Note that in the preceding example the closing brace is followed by a -period.)@refill - -You can write a clause after the cross reference, like this:@refill - -@example -@@xref@{Tropical Storms@}, for more info. -@end example - -@noindent -which produces - -@example -*Note Tropical Storms::, for more info. -@end example - -@quotation -See Section 3.1 [Tropical Storms], page 24, for more info. -@end quotation - -@noindent -(Note that in the preceding example the closing brace is followed by a -comma, and then by the clause, which is followed by a period.)@refill - -@node Two Arguments, Three Arguments, One Argument, xref -@subsection @code{@@xref} with Two Arguments - -With two arguments, the second is used as the name of the Info cross -reference, while the first is still the name of the node to which the -cross reference points.@refill - -@need 750 -@noindent -The template is like this: - -@example -@@xref@{@var{node-name}, @var{cross-reference-name}@}. -@end example - -@need 700 -@noindent -For example, - -@example -@@xref@{Electrical Effects, Lightning@}. -@end example - -@noindent -produces: - -@example -*Note Lightning: Electrical Effects. -@end example - -@noindent -and - -@quotation -See Section 5.2 [Electrical Effects], page 57. -@end quotation - -@noindent -(Note that in the preceding example the closing brace is followed by a -period; and that the node name is printed, not the cross reference name.)@refill - -You can write a clause after the cross reference, like this:@refill - -@example -@@xref@{Electrical Effects, Lightning@}, for more info. -@end example - -@noindent -which produces -@example -*Note Lightning: Electrical Effects, for more info. -@end example - -@noindent -and - -@quotation -See Section 5.2 [Electrical Effects], page 57, for more info. -@end quotation - -@noindent -(Note that in the preceding example the closing brace is followed by a -comma, and then by the clause, which is followed by a period.)@refill - -@node Three Arguments, Four and Five Arguments, Two Arguments, xref -@subsection @code{@@xref} with Three Arguments - -A third argument replaces the node name in the @TeX{} output. The third -argument should be the name of the section in the printed output, or -else state the topic discussed by that section. Often, you will want to -use initial upper case letters so it will be easier to read when the -reference is printed. Use a third argument when the node name is -unsuitable because of syntax or meaning.@refill - -Remember to avoid placing a comma within the title or topic section of -a cross reference, or within any other section. The formatters divide -cross references into arguments according to the commas; a comma -within a title or other section will divide it into two arguments. In -a reference, you need to write a title such as ``Clouds, Mist, and -Fog'' without the commas.@refill - -Also, remember to write a comma or period after the closing brace of a -@code{@@xref} to terminate the cross reference. In the following -examples, a clause follows a terminating comma.@refill - - -@need 750 -@noindent -The template is like this: - -@example -@group -@@xref@{@var{node-name}, @var{cross-reference-name}, @var{title-or-topic}@}. -@end group -@end example - -@need 700 -@noindent -For example, - -@example -@group -@@xref@{Electrical Effects, Lightning, Thunder and Lightning@}, -for details. -@end group -@end example - -@noindent -produces - -@example -*Note Lightning: Electrical Effects, for details. -@end example - -@noindent -and - -@quotation -See Section 5.2 [Thunder and Lightning], page 57, for details. -@end quotation - -If a third argument is given and the second one is empty, then the -third argument serves both. (Note how two commas, side by side, mark -the empty second argument.)@refill - -@example -@group -@@xref@{Electrical Effects, , Thunder and Lightning@}, -for details. -@end group -@end example - -@noindent -produces - -@example -*Note Thunder and Lightning: Electrical Effects, for details. -@end example - -@noindent -and - -@quotation -See Section 5.2 [Thunder and Lightning], page 57, for details. -@end quotation - -As a practical matter, it is often best to write cross references with -just the first argument if the node name and the section title are the -same, and with the first and third arguments if the node name and title -are different.@refill - -Here are several examples from @cite{The GAWK Manual}:@refill - -@smallexample -@@xref@{Sample Program@}. -@@xref@{Glossary@}. -@@xref@{Case-sensitivity, ,Case-sensitivity in Matching@}. -@@xref@{Close Output, , Closing Output Files and Pipes@}, - for more information. -@@xref@{Regexp, , Regular Expressions as Patterns@}. -@end smallexample - -@node Four and Five Arguments, , Three Arguments, xref -@subsection @code{@@xref} with Four and Five Arguments - -In a cross reference, a fourth argument specifies the name of another -Info file, different from the file in which the reference appears, and -a fifth argument specifies its title as a printed manual.@refill - -Remember that a comma or period must follow the closing brace of an -@code{@@xref} command to terminate the cross reference. In the -following examples, a clause follows a terminating comma.@refill - -@need 800 -@noindent -The template is: - -@example -@group -@@xref@{@var{node-name}, @var{cross-reference-name}, @var{title-or-topic}, -@var{info-file-name}, @var{printed-manual-title}@}. -@end group -@end example - -@need 700 -@noindent -For example, - -@example -@@xref@{Electrical Effects, Lightning, Thunder and Lightning, -weather, An Introduction to Meteorology@}, for details. -@end example - -@noindent -produces - -@example -*Note Lightning: (weather)Electrical Effects, for details. -@end example - -@noindent -The name of the Info file is enclosed in parentheses and precedes -the name of the node. - -@noindent -In a printed manual, the reference looks like this:@refill - -@quotation -See section ``Thunder and Lightning'' in @i{An Introduction to -Meteorology}, for details. -@end quotation - -@noindent -The title of the printed manual is typeset in italics; and the -reference lacks a page number since @TeX{} cannot know to which page a -reference refers when that reference is to another manual.@refill - -Often, you will leave out the second argument when you use the long -version of @code{@@xref}. In this case, the third argument, the topic -description, will be used as the cross reference name in Info.@refill - -@noindent -The template looks like this: - -@example -@@xref@{@var{node-name}, , @var{title-or-topic}, @var{info-file-name}, -@var{printed-manual-title}@}, for details. -@end example - -@noindent -which produces - -@example -*Note @var{title-or-topic}: (@var{info-file-name})@var{node-name}, for details. -@end example - -@noindent -and - -@quotation -See section @var{title-or-topic} in @var{printed-manual-title}, for details. -@end quotation - -@need 700 -@noindent -For example, - -@example -@@xref@{Electrical Effects, , Thunder and Lightning, -weather, An Introduction to Meteorology@}, for details. -@end example - -@noindent -produces - -@example -@group -*Note Thunder and Lightning: (weather)Electrical Effects, -for details. -@end group -@end example - -@noindent -and - -@quotation -See section ``Thunder and Lightning'' in @i{An Introduction to -Meteorology}, for details. -@end quotation - -On rare occasions, you may want to refer to another Info file that -is within a single printed manual---when multiple Texinfo files are -incorporated into the same @TeX{} run but make separate Info files. -In this case, you need to specify only the fourth argument, and not -the fifth.@refill - -@node Top Node Naming, ref, xref, Cross References -@section Naming a `Top' Node -@cindex Naming a `Top' Node in references -@cindex @samp{@r{Top}} node naming for references - -In a cross reference, you must always name a node. This means that in -order to refer to a whole manual, you must identify the `Top' node by -writing it as the first argument to the @code{@@xref} command. (This -is different from the way you write a menu entry; see @ref{Other Info -Files, , Referring to Other Info Files}.) At the same time, to -provide a meaningful section topic or title in the printed cross -reference (instead of the word `Top'), you must write an appropriate -entry for the third argument to the @code{@@xref} command. -@refill - -@noindent -Thus, to make a cross reference to @cite{The GNU Make Manual}, -write:@refill - -@example -@@xref@{Top, , Overview, make, The GNU Make Manual@}. -@end example - -@noindent -which produces - -@example -*Note Overview: (make)Top. -@end example - -@noindent -and - -@quotation -See section ``Overview'' in @i{The GNU Make Manual}. -@end quotation - -@noindent -In this example, @samp{Top} is the name of the first node, and -@samp{Overview} is the name of the first section of the manual.@refill -@node ref, pxref, Top Node Naming, Cross References -@comment node-name, next, previous, up -@section @code{@@ref} -@cindex Cross references using @code{@@ref} -@cindex References using @code{@@ref} -@findex ref - -@code{@@ref} is nearly the same as @code{@@xref} except that it does -not generate a `See' in the printed output, just the reference itself. -This makes it useful as the last part of a sentence.@refill - -@need 700 -@noindent -For example, - -@example -For more information, see @@ref@{Hurricanes@}. -@end example - -@noindent -produces - -@example -For more information, see *Note Hurricanes. -@end example - -@noindent -and - -@quotation -For more information, see Section 8.2 [Hurricanes], page 123. -@end quotation - -The @code{@@ref} command sometimes leads writers to express themselves -in a manner that is suitable for a printed manual but looks awkward -in the Info format. Bear in mind that your audience will be using -both the printed and the Info format.@refill - -@need 800 -@noindent -For example, - -@example -@group -Sea surges are described in @@ref@{Hurricanes@}. -@end group -@end example - -@need 800 -@noindent -produces - -@quotation -Sea surges are described in Section 6.7 [Hurricanes], page 72. -@end quotation - -@need 800 -@noindent -in a printed document, and the following in Info: - -@example -Sea surges are described in *Note Hurricanes::. -@end example - -@quotation -@strong{Caution:} You @emph{must} write a period or comma immediately -after an @code{@@ref} command with two or more arguments. Otherwise, -Info will not find the end of the cross reference entry and its -attempt to follow the cross reference will fail. As a general rule, -you should write a period or comma after every @code{@@ref} command. -This looks best in both the printed and the Info output.@refill -@end quotation - -@node pxref, inforef, ref, Cross References -@comment node-name, next, previous, up -@section @code{@@pxref} -@cindex Cross references using @code{@@pxref} -@cindex References using @code{@@pxref} -@findex pxref - -The parenthetical reference command, @code{@@pxref}, is nearly the -same as @code{@@xref}, but you use it @emph{only} inside parentheses -and you do @emph{not} type a comma or period after the command's -closing brace. The command differs from @code{@@xref} in two -ways:@refill - -@enumerate -@item -@TeX{} typesets the reference for the printed manual with a lower case -`see' rather than an upper case `See'.@refill - -@item -The Info formatting commands automatically end the reference with a -closing colon or period.@refill -@end enumerate - -Because one type of formatting automatically inserts closing -punctuation and the other does not, you should use @code{@@pxref} -@emph{only} inside parentheses as part of another sentence. Also, you -yourself should not insert punctuation after the reference, as you do -with @code{@@xref}.@refill - -@code{@@pxref} is designed so that the output looks right and works -right between parentheses both in printed output and in an Info file. -In a printed manual, a closing comma or period should not follow a -cross reference within parentheses; such punctuation is wrong. But in -an Info file, suitable closing punctuation must follow the cross -reference so Info can recognize its end. @code{@@pxref} spares you -the need to use complicated methods to put a terminator into one form -of the output and not the other.@refill - -@noindent -With one argument, a parenthetical cross reference looks like -this:@refill - -@example -@dots{} storms cause flooding (@@pxref@{Hurricanes@}) @dots{} -@end example - -@need 800 -@noindent -which produces - -@example -@group -@dots{} storms cause flooding (*Note Hurricanes::) @dots{} -@end group -@end example - -@noindent -and - -@quotation -@dots{} storms cause flooding (see Section 6.7 [Hurricanes], page 72) @dots{} -@end quotation - -With two arguments, a parenthetical cross reference has this -template:@refill - -@example -@dots{} (@@pxref@{@var{node-name}, @var{cross-reference-name}@}) @dots{} -@end example - -@noindent -which produces - -@example -@dots{} (*Note @var{cross-reference-name}: @var{node-name}.) @dots{} -@end example - -@noindent -and - -@need 1500 -@quotation -@dots{} (see Section @var{nnn} [@var{node-name}], page @var{ppp}) @dots{} -@end quotation - -@code{@@pxref} can be used with up to five arguments just like -@code{@@xref} (@pxref{xref, , @code{@@xref}}).@refill - -@quotation -@strong{Please note:} Use @code{@@pxref} only as a parenthetical -reference. Do not try to use @code{@@pxref} as a clause in a sentence. -It will look bad in either the Info file, the printed output, or -both.@refill - -Also, parenthetical cross references look best at the ends of sentences. -Although you may write them in the middle of a sentence, that location -breaks up the flow of text.@refill -@end quotation - -@node inforef, , pxref, Cross References -@comment node-name, next, previous, up -@section @code{@@inforef} -@cindex Cross references using @code{@@inforef} -@cindex References using @code{@@inforef} -@findex inforef - -@code{@@inforef} is used for cross references to Info files for which -there are no printed manuals. Even in a printed manual, -@code{@@inforef} generates a reference directing the user to look in -an Info file.@refill - -The command takes either two or three arguments, in the following -order:@refill - -@enumerate -@item -The node name. - -@item -The cross reference name (optional). - -@item -The Info file name. -@end enumerate - -@noindent -Separate the arguments with commas, as with @code{@@xref}. Also, you -must terminate the reference with a comma or period after the -@samp{@}}, as you do with @code{@@xref}.@refill - -@noindent -The template is: - -@example -@@inforef@{@var{node-name}, @var{cross-reference-name}, @var{info-file-name}@}, -@end example - -@need 800 -@noindent -Thus, - -@example -@group -@@inforef@{Expert, Advanced Info commands, info@}, -for more information. -@end group -@end example - -@need 800 -@noindent -produces - -@example -@group -*Note Advanced Info commands: (info)Expert, -for more information. -@end group -@end example - -@need 800 -@noindent -and - -@quotation -See Info file @file{info}, node @samp{Expert}, for more information. -@end quotation - -@need 800 -@noindent -Similarly, - -@example -@group -@@inforef@{Expert, , info@}, for more information. -@end group -@end example - -@need 800 -@noindent -produces - -@example -*Note (info)Expert::, for more information. -@end example - -@need 800 -@noindent -and - -@quotation -See Info file @file{info}, node @samp{Expert}, for more information. -@end quotation - -The converse of @code{@@inforef} is @code{@@cite}, which is used to -refer to printed works for which no Info form exists. @xref{cite, , -@code{@@cite}}.@refill - -@node Marking Text, Quotations and Examples, Cross References, Top -@comment node-name, next, previous, up -@chapter Marking Words and Phrases -@cindex Paragraph, marking text within -@cindex Marking words and phrases -@cindex Words and phrases, marking them -@cindex Marking text within a paragraph - -In Texinfo, you can mark words and phrases in a variety of ways. -The Texinfo formatters use this information to determine how to -highlight the text. -You can specify, for example, whether a word or phrase is a -defining occurrence, a metasyntactic variable, or a symbol used in a -program. Also, you can emphasize text.@refill - -@menu -* Indicating:: How to indicate definitions, files, etc. -* Emphasis:: How to emphasize text. -@end menu - -@node Indicating, Emphasis, , Marking Text -@comment node-name, next, previous, up -@section Indicating Definitions, Commands, etc. -@cindex Highlighting text -@cindex Indicating commands, definitions, etc. - -Texinfo has commands for indicating just what kind of object a piece of -text refers to. For example, metasyntactic variables are marked by -@code{@@var}, and code by @code{@@code}. Since the pieces of text are -labelled by commands that tell what kind of object they are, it is easy -to change the way the Texinfo formatters prepare such text. (Texinfo is -an @emph{intentional} formatting language rather than a @emph{typesetting} -formatting language.)@refill - -For example, in a printed manual, -code is usually illustrated in a typewriter font; -@code{@@code} tells @TeX{} to typeset this text in this font. But it -would be easy to change the way @TeX{} highlights code to use another -font, and this change would not effect how keystroke examples are -highlighted. If straight typesetting commands were used in the body -of the file and you wanted to make a change, you would need to check -every single occurrence to make sure that you were changing code and -not something else that should not be changed.@refill - -@menu -* Useful Highlighting:: Highlighting provides useful information. -* code:: How to indicate code. -* kbd:: How to show keyboard input. -* key:: How to specify keys. -* samp:: How to show a literal sequence of characters. -* var:: How to indicate a metasyntactic variable. -* file:: How to indicate the name of a file. -* dfn:: How to specify a definition. -* cite:: How to refer to a book that is not in Info. -@end menu - -@node Useful Highlighting, code, , Indicating -@ifinfo -@subheading Highlighting Commands are Useful -@end ifinfo - -The highlighting commands can be used to generate useful information -from the file, such as lists of functions or file names. It is -possible, for example, to write a program in Emacs Lisp (or a keyboard -macro) to insert an index entry after every paragraph that contains -words or phrases marked by a specified command. You could do this to -construct an index of functions if you had not already made the -entries.@refill - -The commands serve a variety of purposes:@refill - -@table @code -@item @@code@{@var{sample-code}@} -Indicate text that is a literal example of a piece of a program.@refill - -@item @@kbd@{@var{keyboard-characters}@} -Indicate keyboard input.@refill - -@item @@key@{@var{key-name}@} -Indicate the conventional name for a key on a keyboard.@refill - -@item @@samp@{@var{text}@} -Indicate text that is a literal example of a sequence of characters.@refill - -@item @@var@{@var{metasyntactic-variable}@} -Indicate a metasyntactic variable.@refill - -@item @@file@{@var{file-name}@} -Indicate the name of a file.@refill - -@item @@dfn@{@var{term}@} -Indicate the introductory or defining use of a term.@refill - -@item @@cite@{@var{reference}@} -Indicate the name of a book.@refill - -@ignore -@item @@ctrl@{@var{ctrl-char}@} -Use for an @sc{ascii} control character.@refill -@end ignore -@end table - -@node code, kbd, Useful Highlighting, Indicating -@comment node-name, next, previous, up -@subsection @code{@@code}@{@var{sample-code}@} -@findex code - -Use the @code{@@code} command to indicate text that is a piece of a -program and which consists of entire syntactic tokens. Enclose the -text in braces.@refill - -Thus, you should use @code{@@code} for an expression in a program, for -the name of a variable or function used in a program, or for a -keyword. Also, you should use @code{@@code} for the name of a -program, such as @code{diff}, that is a name used in the machine. (You -should write the name of a program in the ordinary text font if you -regard it as a new English word, such as `Emacs' or `Bison'.)@refill - -Use @code{@@code} for environment variables such as @code{TEXINPUTS}, -and other variables.@refill - -Use @code{@@code} for command names in command languages that -resemble programming languages, such as Texinfo or the shell. -For example, @code{@@code} and @code{@@samp} are produced by writing -@samp{@@code@{@@@@code@}} and @samp{@@code@{@@@@samp@}} in the Texinfo -source, respectively.@refill - -Note, however, that you should not use @code{@@code} for shell options -such as @samp{-c} when such options stand alone. (Use @code{@@samp}.) -Also, an entire shell command often looks better if written using -@code{@@samp} rather than @code{@@code}. In this case, the rule is to -choose the more pleasing format.@refill - -It is incorrect to alter the case of a word inside an @code{@@code} -command when it appears at the beginning of a sentence. Most computer -languages are case sensitive. In C, for example, @code{Printf} is -different from the identifier @code{printf}, and most likely is a -misspelling of it. Even in languages which are not case sensitive, it -is confusing to a human reader to see identifiers spelled in different -ways. Pick one spelling and always use that. If you do not want to -start a sentence with a command written all in lower case, you should -rearrange the sentence.@refill - -Do not use the @code{@@code} command for a string of characters shorter -than a syntactic token. If you are writing about @samp{TEXINPU}, which -is just a part of the name for the @code{TEXINPUTS} environment -variable, you should use @code{@@samp}.@refill - -In particular, you should not use the @code{@@code} command when writing -about the characters used in a token; do not, for example, use -@code{@@code} when you are explaining what letters or printable symbols -can be used in the names of functions. (Use @code{@@samp}.) Also, you -should not use @code{@@code} to mark text that is considered input to -programs unless the input is written in a language that is like a -programming language. For example, you should not use @code{@@code} for -the keystroke commands of GNU Emacs (use @code{@@kbd} instead) although -you may use @code{@@code} for the names of the Emacs Lisp functions that -the keystroke commands invoke.@refill - -In the printed manual, @code{@@code} causes @TeX{} to typeset the -argument in a typewriter face. In the Info file, it causes the Info -formatting commands to use single quotation marks around the text. - -@need 700 -For example, - -@example -Use @@code@{diff@} to compare two files. -@end example - -@noindent -produces this in the printed manual:@refill - -@quotation -Use @code{diff} to compare two files. -@end quotation -@iftex - -@noindent -and this in the Info file:@refill - -@example -Use `diff' to compare two files. -@end example -@end iftex - -@node kbd, key, code, Indicating -@comment node-name, next, previous, up -@subsection @code{@@kbd}@{@var{keyboard-characters}@} -@findex kbd - -Use the @code{@@kbd} command for characters of input to be typed by -users. For example, to refer to the characters @kbd{M-a}, -write@refill - -@example -@@kbd@{M-a@} -@end example - -@noindent -and to refer to the characters @kbd{M-x shell}, write@refill - -@example -@@kbd@{M-x shell@} -@end example - -The @code{@@kbd} command has the same effect as @code{@@code} in Info, -but may produce a different font in a printed manual.@refill - -You can embed another @@-command inside the braces of an @code{@@kbd} -command. Here, for example, is the way to describe a command that -would be described more verbosely as ``press an @samp{r} and then -press the @key{RET} key'':@refill - -@example -@@kbd@{r @@key@{RET@}@} -@end example - -@noindent -This produces: @kbd{r @key{RET}} - -You also use the @code{@@kbd} command if you are spelling out the letters -you type; for example:@refill - -@example -To give the @@code@{logout@} command, -type the characters @@kbd@{l o g o u t @@key@{RET@}@}. -@end example - -@noindent -This produces: - -@quotation -To give the @code{logout} command, -type the characters @kbd{l o g o u t @key{RET}}. -@end quotation - -(Also, this example shows that you can add spaces for clarity. If you -really want to mention a space character as one of the characters of -input, write @kbd{@@key@{SPC@}} for it.)@refill - -@node key, samp, kbd, Indicating -@comment node-name, next, previous, up -@subsection @code{@@key}@{@var{key-name}@} -@findex key - -Use the @code{@@key} command for the conventional name for a key on a -keyboard, as in:@refill - -@example -@@key@{RET@} -@end example - -You can use the @code{@@key} command within the argument of an -@code{@@kbd} command when the sequence of characters to be typed -includes one or more keys that are described by name.@refill - -@need 700 -For example, to produce @kbd{C-x @key{ESC}} you would type:@refill - -@example -@@kbd@{C-x @@key@{ESC@}@} -@end example - -@c bob: this next sentence looks weird, having a semi-colon followed by -@c a colon that ends the "sentence".. --mew -Here is a list of the recommended names for keys; they are all in -upper case:@refill -@cindex Recommended names for keys -@cindex Keys, recommended names -@cindex Names recommended for keys -@cindex Abbreviations for keys - -@quotation -@table @t -@item SPC -Space -@item RET -Return -@item LFD -Linefeed -@item TAB -Tab -@item BS -Backspace -@item ESC -Escape -@item DEL -Delete -@item SFT -Shift -@item CTL -Control -@item META -Meta -@end table -@end quotation - -There are subtleties to handling words like `meta' or `ctl' that are -names of shift keys. When mentioning a character in which the shift -key is used, such as @kbd{Meta-a}, use the @code{@@kbd} command alone; -do not use the @code{@@key} command; but when you are referring to the -shift key in isolation, use the @code{@@key} command. For example, -write @samp{@@kbd@{Meta-a@}} to produce @kbd{Meta-a} and -@samp{@@key@{META@}} to produce @key{META}. This is because -@kbd{Meta-a} refers to keys that you press on a keyboard, but -@key{META} refers to a key without implying that you press it. In -short, use @code{@@kbd} for what you do, and use @code{@@key} for what -you talk about: ``Press @code{@@kbd@{M-a@}} to move point to the -beginning of the sentence. The @code{@@key@{META@}} key is often in the -lower left of the keyboard.''@refill -@cindex META key - -@node samp, var, key, Indicating -@comment node-name, next, previous, up -@subsection @code{@@samp}@{@var{text}@} -@findex samp - -Use the @code{@@samp} command to indicate text that is a literal example -or `sample' of a sequence of characters in a file, string, pattern, etc. -Enclose the text in braces. The argument appears within single -quotation marks in both the Info file and the printed manual; in -addition, it is printed in a fixed-width font.@refill - -@example -To match @@samp@{foo@} at the end of the line, -use the regexp @@samp@{foo$@}. -@end example - -@noindent -produces - -@quotation -To match @samp{foo} at the end of the line, use the regexp -@samp{foo$}.@refill -@end quotation - -Any time you are referring to single characters, you should use -@code{@@samp} unless @code{@@kbd} is more appropriate. Use -@code{@@samp} for the names of command-line options. Also, you may use -@code{@@samp} for entire statements in C and for entire shell -commands---in this case, @code{@@samp} often looks better than -@code{@@code}. Basically, @code{@@samp} is a catchall for whatever is -not covered by @code{@@code}, @code{@@kbd}, or @code{@@key}.@refill - -Only include punctuation marks within braces if they are part of the -string you are specifying. Write punctuation marks outside the braces -if those punctuation marks are part of the English text that surrounds -the string. In the following sentence, for example, the commas and -period are outside of the braces:@refill - -@example -@group -In English, the vowels are @@samp@{a@}, @@samp@{e@}, -@@samp@{i@}, @@samp@{o@}, @@samp@{u@}, and sometimes -@@samp@{y@}. -@end group -@end example - -@noindent -This produces: - -@quotation -In English, the vowels are @samp{a}, @samp{e}, -@samp{i}, @samp{o}, @samp{u}, and sometimes -@samp{y}. -@end quotation - -@node var, file, samp, Indicating -@comment node-name, next, previous, up -@subsection @code{@@var}@{@var{metasyntactic-variable}@} -@findex var - -Use the @code{@@var} command to indicate metasyntactic variables. A -@dfn{metasyntactic variable} is something that stands for another piece of -text. For example, you should use a metasyntactic variable in the -documentation of a function to describe the arguments that are passed -to that function.@refill - -Do not use @code{@@var} for the names of particular variables in -programming languages. These are specific names from a program, so -@code{@@code} is correct for them. For example, the Lisp variable -@code{texinfo-tex-command} is not a metasyntactic variable; it is -properly formatted using @code{@@code}.@refill - -The effect of @code{@@var} in the Info file is to change the case of -the argument to all upper case; in the printed manual, to italicize it. - -@need 700 -For example, - -@example -To delete file @@var@{filename@}, -type @@code@{rm @@var@{filename@}@}. -@end example - -@noindent -produces - -@quotation -To delete file @var{filename}, type @code{rm @var{filename}}. -@end quotation - -@noindent -(Note that @code{@@var} may appear inside @code{@@code}, -@code{@@samp}, @code{@@file}, etc.)@refill - -Write a metasyntactic variable all in lower case without spaces, and -use hyphens to make it more readable. Thus, the Texinfo source for -the illustration of how to begin a Texinfo manual looks like -this:@refill - -@example -@group -\input texinfo -@@@@setfilename @@var@{info-file-name@} -@@@@settitle @@var@{name-of-manual@} -@end group -@end example - -@noindent -This produces: - -@example -@group -\input texinfo -@@setfilename @var{info-file-name} -@@settitle @var{name-of-manual} -@end group -@end example - -In some documentation styles, metasyntactic variables are shown with -angle brackets, for example:@refill - -@example -@dots{}, type rm <filename> -@end example - -@noindent -However, that is not the style that Texinfo uses. (You can, of -course, modify the sources to @TeX{} and the Info formatting commands -to output the @code{<@dots{}>} format if you wish.)@refill - -@node file, dfn, var, Indicating -@comment node-name, next, previous, up -@subsection @code{@@file}@{@var{file-name}@} -@findex file - -Use the @code{@@file} command to indicate text that is the name of a -file, buffer, or directory, or is the name of a node in Info. You can -also use the command for file name suffixes. Do not use @code{@@file} -for symbols in a programming language; use @code{@@code}. - -Currently, @code{@@file} is equivalent to @code{@@samp} in its effects. -For example,@refill - -@example -The @@file@{.el@} files are in -the @@file@{/usr/local/emacs/lisp@} directory. -@end example - -@noindent -produces - -@quotation -The @file{.el} files are in -the @file{/usr/local/emacs/lisp} directory. -@end quotation - -@node dfn, cite, file, Indicating -@comment node-name, next, previous, up -@subsection @code{@@dfn}@{@var{term}@} -@findex dfn - -Use the @code{@@dfn} command to identify the introductory or defining -use of a technical term. Use the command only in passages whose -purpose is to introduce a term which will be used again or which the -reader ought to know. Mere passing mention of a term for the first -time does not deserve @code{@@dfn}. The command generates italics in -the printed manual, and double quotation marks in the Info file. For -example:@refill - -@example -Getting rid of a file is called @@dfn@{deleting@} it. -@end example - -@noindent -produces - -@quotation -Getting rid of a file is called @dfn{deleting} it. -@end quotation - -As a general rule, a sentence containing the defining occurrence of a -term should be a definition of the term. The sentence does not need -to say explicitly that it is a definition, but it should contain the -information of a definition---it should make the meaning clear. - -@node cite, , dfn, Indicating -@comment node-name, next, previous, up -@subsection @code{@@cite}@{@var{reference}@} -@findex cite - -Use the @code{@@cite} command for the name of a book that lacks a -companion Info file. The command produces italics in the printed -manual, and quotation marks in the Info file.@refill - -(If a book is written in Texinfo, it is better to use a cross reference -command since a reader can easily follow such a reference in Info. -@xref{xref, , @code{@@xref}}.)@refill -@ignore - -@c node ctrl, , cite, Indicating -@comment node-name, next, previous, up -@c subsection @code{@@ctrl}@{@var{ctrl-char}@} -@findex ctrl - -The @code{@@ctrl} command is seldom used. It describes an @sc{ascii} -control character by inserting the actual character into the Info -file. - -Usually, in Texinfo, you talk what you type as keyboard entry by -describing it with @code{@@kbd}: thus, @samp{@@kbd@{C-a@}} for -@kbd{C-a}. Use @code{@@kbd} in this way when talking about a control -character that is typed on the keyboard by the user. When talking -about a control character appearing in a file or a string, do not use -@code{@@kbd} since the control character is not typed. Also, do not -use @samp{C-} but spell out @code{control-}, as in @samp{control-a}, -to make it easier for a reader to understand.@refill - -@code{@@ctrl} is an idea from the beginnings of Texinfo which may not -really fit in to the scheme of things. But there may be times when -you want to use the command. The pattern is -@code{@@ctrl@{@var{ch}@}}, where @var{ch} is an @sc{ascii} character -whose control-equivalent is wanted. For example, to specify -@samp{control-f}, you would enter@refill - -@example -@@ctrl@{f@} -@end example - -@noindent -produces - -@quotation -@ctrl{f} -@end quotation - -In the Info file, this generates the specified control character, output -literally into the file. This is done so a user can copy the specified -control character (along with whatever else he or she wants) into another -Emacs buffer and use it. Since the `control-h',`control-i', and -`control-j' characters are formatting characters, they should not be -indicated with @code{@@ctrl}.@refill - -In a printed manual, @code{@@ctrl} generates text to describe or -identify that control character: an uparrow followed by the character -@var{ch}.@refill -@end ignore - -@node Emphasis, , Indicating, Marking Text -@comment node-name, next, previous, up -@section Emphasizing Text -@cindex Emphasizing text - -Usually, Texinfo changes the font to mark words in the text according to -what category the words belong to; an example is the @code{@@code} command. -Most often, this is the best way to mark words. -However, sometimes you will want to emphasize text without indicating a -category. Texinfo has two commands to do this. Also, Texinfo has -several commands that specify the font in which @TeX{} will typeset -text. These commands have no affect on Info and only one of them, -the @code{@@r} command, has any regular use.@refill - -@menu -* emph & strong:: How to emphasize text in Texinfo. -* Smallcaps:: How to use the small caps font. -* Fonts:: Various font commands for printed output. -@end menu - -@node emph & strong, Smallcaps, , Emphasis -@comment node-name, next, previous, up -@subsection @code{@@emph}@{@var{text}@} and @code{@@strong}@{@var{text}@} -@cindex Emphasizing text, font for -@findex emph -@findex strong - -The @code{@@emph} and @code{@@strong} commands are for emphasis; -@code{@@strong} is stronger. In printed output, @code{@@emph} -produces @emph{italics} and @code{@@strong} produces -@strong{bold}.@refill - -@need 800 -For example, - -@example -@group -@@quotation -@@strong@{Caution:@} @@code@{rm * .[^.]*@} removes @@emph@{all@} -files in the directory. -@@end quotation -@end group -@end example - -@iftex -@noindent -produces the following in printed output: - -@quotation -@strong{Caution}: @code{rm * .[^.]*} removes @emph{all} -files in the directory. -@end quotation - -@noindent -and the following in Info: -@end iftex -@ifinfo -@noindent -produces: -@end ifinfo - -@example - *Caution*: `rm * .[^.]*' removes *all* - files in the directory. -@end example - -The @code{@@strong} command is seldom used except to mark what is, in -effect, a typographical element, such as the word `Caution' in the -preceding example. - -In the Info file, both @code{@@emph} and @code{@@strong} put asterisks -around the text.@refill - -@quotation -@strong{Caution:} Do not use @code{@@emph} or @code{@@strong} with the -word @samp{Note}; Info will mistake the combination for a cross -reference. Use a phrase such as @strong{Please note} or -@strong{Caution} instead.@refill -@end quotation - -@node Smallcaps, Fonts, emph & strong, Emphasis -@subsection @code{@@sc}@{@var{text}@}: The Small Caps Font -@cindex Small caps font -@findex sc @r{(small caps font)} - -@iftex -Use the @samp{@@sc} command to set text in the printed output in @sc{a -small caps font} and set text in the Info file in upper case letters.@refill -@end iftex -@ifinfo -Use the @samp{@@sc} command to set text in the printed output in a -small caps font and set text in the Info file in upper case letters.@refill -@end ifinfo - -Write the text between braces in lower case, like this:@refill - -@example -The @@sc@{acm@} and @@sc@{ieee@} are technical societies. -@end example - -@noindent -This produces: - -@display -The @sc{acm} and @sc{ieee} are technical societies. -@end display - -@TeX{} typesets the small caps font in a manner that prevents the -letters from `jumping out at you on the page'. This makes small caps -text easier to read than text in all upper case. The Info formatting -commands set all small caps text in upper case.@refill - -@ifinfo -If the text between the braces of an @code{@@sc} command is upper case, -@TeX{} typesets in full-size capitals. Use full-size capitals -sparingly.@refill -@end ifinfo -@iftex -If the text between the braces of an @code{@@sc} command is upper case, -@TeX{} typesets in @sc{FULL-SIZE CAPITALS}. Use full-size capitals -sparingly.@refill -@end iftex - -You may also use the small caps font for a jargon word such as -@sc{ato} (a @sc{nasa} word meaning `abort to orbit').@refill - -There are subtleties to using the small caps font with a jargon word -such as @sc{cdr}, a word used in Lisp programming. In this case, you -should use the small caps font when the word refers to the second and -subsequent elements of a list (the @sc{cdr} of the list), but you -should use @samp{@@code} when the word refers to the Lisp function of -the same spelling.@refill - -@node Fonts, , Smallcaps, Emphasis -@comment node-name, next, previous, up -@subsection Fonts for Printing, Not Info -@cindex Fonts for printing, not for Info -@findex i @r{(italic font)} -@findex b @r{(bold font)} -@findex t @r{(typewriter font)} -@findex r @r{(Roman font)} - -Texinfo provides four font commands that specify font changes in the -printed manual but have no effect in the Info file. @code{@@i} -requests @i{italic} font (in some versions of @TeX{}, a slanted font -is used), @code{@@b} requests @b{bold} face, @code{@@t} requests the -@t{fixed-width}, typewriter-style font used by @code{@@code}, and @code{@@r} requests a -@r{roman} font, which is the usual font in which text is printed. All -four commands apply to an argument that follows, surrounded by -braces.@refill - -Only the @code{@@r} command has much use: in example programs, you -can use the @code{@@r} command to convert code comments from the -fixed-width font to a roman font. This looks better in printed -output.@refill - -@need 700 -For example, - -@example -@group -@@lisp -(+ 2 2) ; @@r@{Add two plus two.@} -@@end lisp -@end group -@end example - -@noindent -produces - -@lisp -(+ 2 2) ; @r{Add two plus two.} -@end lisp - -If possible, you should avoid using the other three font commands. If -you need to use one, it probably indicates a gap in the Texinfo -language.@refill - -@node Quotations and Examples, Lists and Tables, Marking Text, Top -@comment node-name, next, previous, up -@chapter Quotations and Examples - -Quotations and examples are blocks of text consisting of one or more -whole paragraphs that are set off from the bulk of the text and -treated differently. They are usually indented.@refill - -In Texinfo, you always begin a quotation or example by writing an -@@-command at the beginning of a line by itself, and end it by writing -an @code{@@end} command that is also at the beginning of a line by -itself. For instance, you begin an example by writing @code{@@example} -by itself at the beginning of a line and end the example by writing -@code{@@end example} on a line by itself, at the beginning of that -line.@refill -@findex end - -@menu -* Block Enclosing Commands:: Use different constructs for - different purposes. -* quotation:: How to write a quotation. -* example:: How to write an example in a fixed-width font. -* noindent:: How to prevent paragraph indentation. -* Lisp Example:: How to illustrate Lisp code. -* smallexample & smalllisp:: Forms for the @code{@@smallbook} option. -* display:: How to write an example in the current font. -* format:: How to write an example that does not narrow - the margins. -* exdent:: How to undo the indentation of a line. -* flushleft & flushright:: How to push text flushleft or flushright. -* cartouche:: How to draw cartouches around examples. -@end menu - -@node Block Enclosing Commands, quotation, , Quotations and Examples -@section The Block Enclosing Commands - -Here are commands for quotations and examples:@refill - -@table @code -@item @@quotation -Indicate text that is quoted. The text is filled, indented, and -printed in a roman font by default.@refill - -@item @@example -Illustrate code, commands, and the like. The text is printed -in a fixed-width font, and indented but not filled.@refill - -@item @@lisp -Illustrate Lisp code. The text is printed in a fixed-width font, -and indented but not filled.@refill - -@item @@smallexample -Illustrate code, commands, and the like. Similar to -@code{@@example}, except that in @TeX{} this command typesets text in -a smaller font for the smaller @code{@@smallbook} format than for the -8.5 by 11 inch format.@refill - -@item @@smalllisp -Illustrate Lisp code. Similar to @code{@@lisp}, except that -in @TeX{} this command typesets text in a smaller font for the smaller -@code{@@smallbook} format than for the 8.5 by 11 inch format.@refill - -@item @@display -Display illustrative text. The text is indented but not filled, and -no font is specified (so, by default, the font is roman).@refill - -@item @@format -Print illustrative text. The text is not indented and not filled -and no font is specified (so, by default, the font is roman).@refill -@end table - -The @code{@@exdent} command is used within the above constructs to -undo the indentation of a line. - -The @code{@@flushleft} and @code{@@flushright} commands are used to line -up the left or right margins of unfilled text.@refill - -The @code{@@noindent} command may be used after one of the above -constructs to prevent the following text from being indented as a new -paragraph.@refill - -You can use the @code{@@cartouche} command within one of the above -constructs to highlight the example or quotation by drawing a box with -rounded corners around it. (The @code{@@cartouche} command affects -only the printed manual; it has no effect in the Info file; see -@ref{cartouche, , Drawing Cartouches Around Examples}.)@refill - -@node quotation, example, Block Enclosing Commands, Quotations and Examples -@comment node-name, next, previous, up -@section @code{@@quotation} -@cindex Quotations -@findex quotation - -The text of a quotation is -processed normally except that:@refill - -@itemize @bullet -@item -the margins are closer to the center of the page, so the whole of the -quotation is indented;@refill - -@item -the first lines of paragraphs are indented no more than other -lines;@refill - -@item -in the printed output, interparagraph spacing is reduced.@refill -@end itemize - -@quotation -This is an example of text written between an @code{@@quotation} -command and an @code{@@end quotation} command. An @code{@@quotation} -command is most often used to indicate text that is excerpted from -another (real or hypothetical) printed work.@refill -@end quotation - -Write an @code{@@quotation} command as text on a line by itself. This -line will disappear from the output. Mark the end of the quotation -with a line beginning with and containing only @code{@@end quotation}. -The @code{@@end quotation} line will likewise disappear from the -output. Thus, the following,@refill - -@example -@@quotation -This is -a foo. -@@end quotation -@end example - -@noindent -produces - -@quotation -This is a foo. -@end quotation - -@node example, noindent, quotation, Quotations and Examples -@comment node-name, next, previous, up -@section @code{@@example} -@cindex Examples, formatting them -@cindex Formatting examples -@findex example - -The @code{@@example} command is used to indicate an example that is -not part of the running text, such as computer input or output.@refill - -@example -@group -This is an example of text written between an -@code{@@example} command -and an @code{@@end example} command. -The text is indented but not filled. -@end group - -@group -In the printed manual, the text is typeset in a -fixed-width font, and extra spaces and blank lines are -significant. In the Info file, an analogous result is -obtained by indenting each line with five spaces. -@end group -@end example - -Write an @code{@@example} command at the beginning of a line by itself. -This line will disappear from the output. Mark the end of the example -with an @code{@@end example} command, also written at the beginning of a -line by itself. The @code{@@end example} will disappear from the -output.@refill - -@need 700 -For example, - -@example -@@example -mv foo bar -@@end example -@end example - -@noindent -produces - -@example -mv foo bar -@end example - -Since the lines containing @code{@@example} and @code{@@end example} -will disappear, you should put a blank line before the -@code{@@example} and another blank line after the @code{@@end -example}. (Remember that blank lines between the beginning -@code{@@example} and the ending @code{@@end example} will appear in -the output.)@refill - -@quotation -@strong{Caution:} Do not use tabs in the lines of an example (or anywhere -else in Texinfo, for that matter)! @TeX{} treats tabs as single -spaces, and that is not what they look like. This is a problem with -@TeX{}. (If necessary, in Emacs, you can use @kbd{M-x untabify} to -convert tabs in a region to multiple spaces.)@refill -@end quotation - -Examples are often, logically speaking, ``in the middle'' of a -paragraph, and the text continues after an example should not be -indented. The @code{@@noindent} command prevents a piece of text from -being indented as if it were a new paragraph. -@ifinfo -(@xref{noindent}.) -@end ifinfo - -(The @code{@@code} command is used for examples of code that are -embedded within sentences, not set off from preceding and following -text. @xref{code, , @code{@@code}}.) - -@node noindent, Lisp Example, example, Quotations and Examples -@comment node-name, next, previous, up -@section @code{@@noindent} -@findex noindent - -An example or other inclusion can break a paragraph into segments. -Ordinarily, the formatters indent text that follows an example as a new -paragraph. However, you can prevent this by writing @code{@@noindent} -at the beginning of a line by itself preceding the continuation -text.@refill - -@need 750 -For example: - -@example -@group -@@example -This is an example -@@end example - -@@noindent -This line is not indented. As you can see, the -beginning of the line is fully flush left with the line -that follows after it. (This whole example is between -@@code@{@@@@display@} and @@code@{@@@@end display@}.) -@end group -@end example - -@noindent -produces - -@display -@example -This is an example -@end example -@tex -% Remove extra vskip; this is a kludge to counter the effect of display -\vskip-3.5\baselineskip -@end tex - -@noindent -This line is not indented. As you can see, the -beginning of the line is fully flush left with the line -that follows after it. (This whole example is between -@code{@@display} and @code{@@end display}.) -@end display - -To adjust the number of blank lines properly in the Info file output, -remember that the line containing @code{@@noindent} does not generate a -blank line, and neither does the @code{@@end example} line.@refill - -In the Texinfo source file for this manual, each line that says -`produces' is preceded by a line containing @code{@@noindent}.@refill - -Do not put braces after an @code{@@noindent} command; they are not -necessary, since @code{@@noindent} is a command used outside of -paragraphs (@pxref{Command Syntax}).@refill - -@node Lisp Example, smallexample & smalllisp, noindent, Quotations and Examples -@comment node-name, next, previous, up -@section @code{@@lisp} -@cindex Lisp example -@findex lisp - -The @code{@@lisp} command is used for Lisp code. It is synonymous -with the @code{@@example} command. - -@lisp -This is an example of text written between an -@code{@@lisp} command and an @code{@@end lisp} command. -@end lisp - -Use @code{@@lisp} instead of @code{@@example} so as to preserve -information regarding the nature of the example. This is useful, for -example, if you write a function that evaluates only and all the Lisp -code in a Texinfo file. Then you can use the Texinfo file as a Lisp -library.@footnote{It would be straightforward to extend Texinfo to -work in a similar fashion for C, @sc{fortran}, or other languages.}@refill - -Mark the end of @code{@@lisp} with @code{@@end lisp} on a line by -itself.@refill - -@node smallexample & smalllisp, display, Lisp Example, Quotations and Examples -@comment node-name, next, previous, up -@section @code{@@smallexample} and @code{@@smalllisp} -@cindex Small book example -@cindex Example for a small book -@cindex Lisp example for a small book -@findex smallexample -@findex smalllisp - -In addition to the regular @code{@@example} and @code{@@lisp} commands, -Texinfo has two other ``example-style'' commands. These are the -@code{@@smallexample} and @code{@@smalllisp} commands. Both these -commands are designed for use with the @code{@@smallbook} command that -causes @TeX{} to produce a printed manual in a 7 by 9.25 inch format -rather than the regular 8.5 by 11 inch format.@refill - -In @TeX{}, the @code{@@smallexample} and @code{@@smalllisp} commands -typeset text in a smaller font for the smaller @code{@@smallbook} -format than for the 8.5 by 11 inch format. Consequently, many examples -containing long lines fit in a narrower, @code{@@smallbook} page -without needing to be shortened. Both commands typeset in the normal -font size when you format for the 8.5 by 11 inch size; indeed, -in this situation, the @code{@@smallexample} and @code{@@smalllisp} -commands are defined to be the @code{@@example} and @code{@@lisp} -commands.@refill - -In Info, the @code{@@smallexample} and @code{@@smalllisp} commands are -equivalent to the @code{@@example} and @code{@@lisp} commands, and work -exactly the same.@refill - -Mark the end of @code{@@smallexample} or @code{@@smalllisp} with -@code{@@end smallexample} or @code{@@end smalllisp}, -respectively.@refill - -@iftex -Here is an example written in the small font used by the -@code{@@smallexample} and @code{@@smalllisp} commands: - -@ifclear smallbook -@display -@tex -% Remove extra vskip; this is a kludge to counter the effect of display -\vskip-3\baselineskip -{\ninett -\dots{} to make sure that you have the freedom to -distribute copies of free software (and charge for -this service if you wish), that you receive source -code or can get it if you want it, that you can -change the software or use pieces of it in new free -programs; and that you know you can do these things.} -@end tex -@end display -@end ifclear -@end iftex -@ifset smallbook -@iftex -@smallexample -This is an example of text written between @code{@@smallexample} and -@code{@@end smallexample}. In Info and in an 8.5 by 11 inch manual, -this text appears in its normal size; but in a 7 by 9.25 inch manual, -this text appears in a smaller font. -@end smallexample -@end iftex -@end ifset -@ifinfo -@smallexample -This is an example of text written between @code{@@smallexample} and -@code{@@end smallexample}. In Info and in an 8.5 by 11 inch manual, -this text appears in its normal size; but in a 7 by 9.25 inch manual, -this text appears in a smaller font. -@end smallexample -@end ifinfo - -The @code{@@smallexample} and @code{@@smalllisp} commands make it -easier to prepare smaller format manuals without forcing you to edit -examples by hand to fit them onto narrower pages.@refill - -As a general rule, a printed document looks better if you write all the -examples in a chapter consistently in @code{@@example} or in -@code{@@smallexample}. Only occasionally should you mix the two -formats.@refill - -@xref{smallbook, , Printing ``Small'' Books}, for more information -about the @code{@@smallbook} command.@refill - -@node display, format, smallexample & smalllisp, Quotations and Examples -@comment node-name, next, previous, up -@section @code{@@display} -@cindex Display formatting -@findex display - -The @code{@@display} command begins a kind of example. It is like the -@code{@@example} command -except that, in -a printed manual, @code{@@display} does not select the fixed-width -font. In fact, it does not specify the font at all, so that the text -appears in the same font it would have appeared in without the -@code{@@display} command.@refill - -@display -This is an example of text written between an @code{@@display} command -and an @code{@@end display} command. The @code{@@display} command -indents the text, but does not fill it. -@end display - -@node format, exdent, display, Quotations and Examples -@comment node-name, next, previous, up -@section @code{@@format} -@findex format - -The @code{@@format} command is similar to @code{@@example} except -that, in the printed manual, @code{@@format} does not select the -fixed-width font and does not narrow the margins.@refill - -@format -This is an example of text written between an @code{@@format} command -and an @code{@@end format} command. As you can see -from this example, -the @code{@@format} command does not fill the text. -@end format - -@node exdent, flushleft & flushright, format, Quotations and Examples -@section @code{@@exdent}: Undoing a Line's Indentation -@cindex Indentation undoing -@findex exdent - -The @code{@@exdent} command removes any indentation a line might have. -The command is written at the beginning of a line and applies only to -the text that follows the command that is on the same line. Do not use -braces around the text. In a printed manual, the text on an -@code{@@exdent} line is printed in the roman font.@refill - -@code{@@exdent} is usually used within examples. Thus,@refill - -@example -@group -@@example -This line follows an @@@@example command. -@@exdent This line is exdented. -This line follows the exdented line. -The @@@@end example comes on the next line. -@@end group -@end group -@end example - -@noindent -produces - -@example -@group -This line follows an @@example command. -@exdent This line is exdented. -This line follows the exdented line. -The @@end example comes on the next line. -@end group -@end example - -In practice, the @code{@@exdent} command is rarely used. -Usually, you un-indent text by ending the example and -returning the page to its normal width.@refill - -@node flushleft & flushright, cartouche, exdent, Quotations and Examples -@section @code{@@flushleft} and @code{@@flushright} -@findex flushleft -@findex flushright - -The @code{@@flushleft} and @code{@@flushright} commands line up the -ends of lines on the left and right margins of a page, -but do not fill the text. The commands are written on lines of their -own, without braces. The @code{@@flushleft} and @code{@@flushright} -commands are ended by @code{@@end flushleft} and @code{@@end -flushright} commands on lines of their own.@refill - -@need 800 -For example, - -@example -@group -@@flushleft -This text is -written flushleft. -@@end flushleft -@end group -@end example - -@noindent -produces - -@quotation -@flushleft -This text is -written flushleft. -@end flushleft -@end quotation - - -Flushright produces the type of indentation often used in the return -address of letters.@refill - -@need 800 -@noindent -For example, - -@example -@group -@@flushright -Here is an example of text written -flushright. The @@code@{@@flushright@} command -right justifies every line but leaves the -left end ragged. -@@end flushright -@end group -@end example - -@noindent -produces - -@flushright -Here is an example of text written -flushright. The @code{@@flushright} command -right justifies every line but leaves the -left end ragged. -@end flushright - -@node cartouche, , flushleft & flushright, Quotations and Examples -@section Drawing Cartouches Around Examples -@findex cartouche -@cindex Box with rounded corners - -In a printed manual, the @code{@@cartouche} command draws a box with -rounded corners around its contents. You can use this command to -further highlight an example or quotation. For instance, you could -write a manual in which one type of example is surrounded by a cartouche -for emphasis.@refill - -The @code{@@cartouche} command affects only the printed manual; it has -no effect in the Info file.@refill - -@need 1500 -For example, - -@example -@group -@@example -@@cartouche -% pwd -/usr/local/lib/emacs/info -@@end cartouche -@@end example -@end group -@end example - -@noindent -surrounds the two-line example with a box with rounded corners, in the -printed manual. - -@iftex -In a printed manual, the example looks like this:@refill - -@example -@group -@cartouche -% pwd -/usr/local/lib/emacs/info -@end cartouche -@end group -@end example -@end iftex - -@node Lists and Tables, Indices, Quotations and Examples, Top -@comment node-name, next, previous, up -@chapter Making Lists and Tables -@cindex Making lists and tables -@cindex Lists and tables, making them -@cindex Tables and lists, making them - -Texinfo has several ways of making lists and two-column tables. Lists can -be bulleted or numbered, while two-column tables can highlight the items in -the first column.@refill - -@menu -* Introducing Lists:: Texinfo formats lists for you. -* itemize:: How to construct a simple list. -* enumerate:: How to construct a numbered list. -* Two-column Tables:: How to construct a two-column table. -@end menu - -@ifinfo -@node Introducing Lists, itemize, , Lists and Tables -@heading Introducing Lists -@end ifinfo - -Texinfo automatically indents the text in lists or tables, and numbers -an enumerated list. This last feature is useful if you modify the -list, since you do not need to renumber it yourself.@refill - -Numbered lists and tables begin with the appropriate @@-command at the -beginning of a line, and end with the corresponding @code{@@end} -command on a line by itself. The table and itemized-list commands -also require that you write formatting information on the same line as -the beginning @@-command.@refill - -Begin an enumerated list, for example, with an @code{@@enumerate} -command and end the list with an @code{@@end enumerate} command. -Begin an itemized list with an @code{@@itemize} command, followed on -the same line by a formatting command such as @code{@@bullet}, and end -the list with an @code{@@end itemize} command.@refill -@findex end - -Precede each element of a list with an @code{@@item} or @code{@@itemx} -command.@refill - -@sp 1 -@noindent -Here is an itemized list of the different kinds of table and lists:@refill - -@itemize @bullet -@item -Itemized lists with and without bullets. - -@item -Enumerated lists, using numbers or letters. - -@item -Two-column tables with highlighting. -@end itemize - -@sp 1 -@noindent -Here is an enumerated list with the same items:@refill - -@enumerate -@item -Itemized lists with and without bullets. - -@item -Enumerated lists, using numbers or letters. - -@item -Two-column tables with highlighting. -@end enumerate - -@sp 1 -@noindent -And here is a two-column table with the same items and their -@w{@@-commands}:@refill - -@table @code -@item @@itemize -Itemized lists with and without bullets. - -@item @@enumerate -Enumerated lists, using numbers or letters. - -@item @@table -@itemx @@ftable -@itemx @@vtable -Two-column tables with highlighting. -@end table - -@node itemize, enumerate, Introducing Lists, Lists and Tables -@comment node-name, next, previous, up -@section Making an Itemized List -@cindex Itemization -@findex itemize - -The @code{@@itemize} command produces sequences of indented -paragraphs, with a bullet or other mark inside the left margin -at the beginning of each paragraph for which such a mark is desired.@refill - -Begin an itemized list by writing @code{@@itemize} at the beginning of -a line. Follow the command, on the same line, with a character or a -Texinfo command that generates a mark. Usually, you will write -@code{@@bullet} after @code{@@itemize}, but you can use -@code{@@minus}, or any character or any special symbol that results in -a single character in the Info file. (When you write @code{@@bullet} -or @code{@@minus} after an @code{@@itemize} command, you may omit the -@samp{@{@}}.)@refill - -Write the text of the indented paragraphs themselves after the -@code{@@itemize}, up to another line that says @code{@@end -itemize}.@refill - -Before each paragraph for which a mark in the margin is desired, write -a line that says just @code{@@item}. Do not write any other text on this -line.@refill -@findex item - -Usually, you should put a blank line before an @code{@@item}. This -puts a blank line in the Info file. (@TeX{} inserts the proper -interline whitespace in either case.) Except when the entries are -very brief, these blank lines make the list look better.@refill - -Here is an example of the use of @code{@@itemize}, followed by the -output it produces. Note that @code{@@bullet} produces an @samp{*} in -Info and a round dot in @TeX{}.@refill - -@example -@group -@@itemize @@bullet -@@item -Some text for foo. - -@@item -Some text -for bar. -@@end itemize -@end group -@end example - -@noindent -This produces: - -@quotation -@itemize @bullet -@item -Some text for foo. - -@item -Some text -for bar. -@end itemize -@end quotation - -Itemized lists may be embedded within other itemized lists. Here is a -list marked with dashes embedded in a list marked with bullets:@refill - -@example -@group -@@itemize @@bullet -@@item -First item. - -@@itemize @@minus -@@item -Inner item. - -@@item -Second inner item. -@@end itemize - -@@item -Second outer item. -@@end itemize -@end group -@end example - -@noindent -This produces: - -@quotation -@itemize @bullet -@item -First item. - -@itemize @minus -@item -Inner item. - -@item -Second inner item. -@end itemize - -@item -Second outer item. -@end itemize -@end quotation - -@node enumerate, Two-column Tables, itemize, Lists and Tables -@comment node-name, next, previous, up -@section Making a Numbered or Lettered List -@cindex Enumeration -@findex enumerate - -@code{@@enumerate} is like @code{@@itemize} except that the marks in -the left margin contain successive integers or letters. -(@xref{itemize, , @code{@@itemize}}.)@refill - -Write the @code{@@enumerate} command at the beginning of a line. -The command does not require an argument, but accepts either a number or -a letter as an option. -Without an argument, @code{@@enumerate} starts the list -with the number 1. With a numeric argument, such as 3, -the command starts the list with that number. -With an upper or lower case letter, such as @kbd{a} or @kbd{A}, -the command starts the list with that letter.@refill - -Write the text of the enumerated list in the same way you write an -itemized list: put @code{@@item} on a line of its own before the start of -each paragraph that you want enumerated. Do not write any other text on -the line beginning with @code{@@item}.@refill - -You should put a blank line between entries in the list. -This generally makes it easier to read the Info file.@refill - -@need 1500 -Here is an example of @code{@@enumerate} without an argument:@refill - -@example -@group -@@enumerate -@@item -Underlying causes. - -@@item -Proximate causes. -@@end enumerate -@end group -@end example - -@noindent -This produces: - -@enumerate -@item -Underlying causes. - -@item -Proximate causes. -@end enumerate -@sp 1 -Here is an example with an argument of @kbd{3}:@refill -@sp 1 -@example -@group -@@enumerate 3 -@@item -Predisposing causes. - -@@item -Precipitating causes. - -@@item -Perpetuating causes. -@@end enumerate -@end group -@end example - -@noindent -This produces: - -@enumerate 3 -@item -Predisposing causes. - -@item -Precipitating causes. - -@item -Perpetuating causes. -@end enumerate -@sp 1 -Here is a brief summary of the alternatives. The summary is constructed -using @code{@@enumerate} with an argument of @kbd{a}.@refill -@sp 1 -@enumerate a -@item -@code{@@enumerate} - -Without an argument, produce a numbered list, starting with the number -1.@refill - -@item -@code{@@enumerate @var{positive-integer}} - -With a (positive) numeric argument, start a numbered list with that -number. You can use this to continue a list that you interrupted with -other text.@refill - -@item -@code{@@enumerate @var{upper-case-letter}} - -With an upper case letter as argument, start a list -in which each item is marked -by a letter, beginning with that upper case letter.@refill - -@item -@code{@@enumerate @var{lower-case-letter}} - -With a lower case letter as argument, start a list -in which each item is marked by -a letter, beginning with that lower case letter.@refill -@end enumerate - -You can also nest enumerated lists, as in an outline.@refill - -@node Two-column Tables, , enumerate, Lists and Tables -@comment node-name, next, previous, up -@section Making a Two-column Table -@cindex Tables, making two-column -@findex table - -@code{@@table} is similar to @code{@@itemize}, but the command allows -you to specify a name or heading line for each item. (@xref{itemize, -, @code{@@itemize}}.) The @code{@@table} command is used to produce -two-column tables, and is especially useful for glossaries and -explanatory exhibits.@refill - -@menu -* table:: How to construct a two-column table. -* ftable vtable:: How to construct a two-column table - with automatic indexing. -* itemx:: How to put more entries in the first column. -@end menu - -@ifinfo -@node table, ftable vtable, , Two-column Tables -@subheading Using the @code{@@table} Command - -Use the @code{@@table} command to produce two-column tables.@refill -@end ifinfo - -Write the @code{@@table} command at the beginning of a line and follow -it on the same line with an argument that is a Texinfo command such as -@code{@@code}, @code{@@samp}, @code{@@var}, or @code{@@kbd}. -Although these commands are usually followed by arguments in braces, -in this case you use the command name without an argument because -@code{@@item} will supply the argument. This command will be applied -to the text that goes into the first column of each item and -determines how it will be highlighted. For example, @code{@@samp} -will cause the text in the first column to be highlighted with an -@code{@@samp} command.@refill - -You may also choose to use the @code{@@asis} command as an argument to -@code{@@table}. @code{@@asis} is a command that does nothing; if you use this -command after @code{@@table}, @TeX{} and the Info formatting commands -output the first column entries without added highlighting (`as -is').@refill - -(The @code{@@table} command may work with other commands besides those -listed here. However, you can only use commands -that normally take arguments in braces.)@refill - -Begin each table entry with an @code{@@item} command at the beginning -of a line. Write the first column text on the same line as the -@code{@@item} command. Write the second column text on the line -following the @code{@@item} line and on subsequent lines. (You do not -need to type anything for an empty second column entry.) You may -write as many lines of supporting text as you wish, even several -paragraphs. But only text on the same line as the @code{@@item} will -be placed in the first column.@refill -@findex item - -Normally, you should put a blank line before an @code{@@item} line. -This puts a blank like in the Info file. Except when the entries are -very brief, a blank line looks better.@refill - -@need 1500 -The following table, for example, highlights the text in the first -column with an @code{@@samp} command:@refill - -@example -@group -@@table @@samp -@@item foo -This is the text for -@@samp@{foo@}. - -@@item bar -Text for @@samp@{bar@}. -@@end table -@end group -@end example - -@noindent -This produces: - -@table @samp -@item foo -This is the text for -@samp{foo}. -@item bar -Text for @samp{bar}. -@end table - -If you want to list two or more named items with a single block of -text, use the @code{@@itemx} command. (@xref{itemx, , -@code{@@itemx}}.)@refill - -@node ftable vtable, itemx, table, Two-column Tables -@comment node-name, next, previous, up -@subsection @code{@@ftable} and @code{@@vtable} -@cindex Tables with indexes -@cindex Indexing table entries automatically -@findex ftable -@findex vtable - -The @code{@@ftable} and @code{@@vtable} commands are the same as the -@code{@@table} command except that @code{@@ftable} automatically enters -each of the items in the first column of the table into the index of -functions and @code{@@vtable} automatically enters each of the items in -the first column of the table into the index of variables. This -simplifies the task of creating indices. Only the items on the same -line as the @code{@@item} commands are indexed, and they are indexed in -exactly the form that they appear on that line. @xref{Indices, , -Creating Indices}, for more information about indices.@refill - -Begin a two-column table using @code{@@ftable} or @code{@@vtable} by -writing the @@-command at the beginning of a line, followed on the same -line by an argument that is a Texinfo command such as @code{@@code}, -exactly as you would for an @code{@@table} command; and end the table -with an @code{@@end ftable} or @code{@@end vtable} command on a line by -itself. - -@node itemx, , ftable vtable, Two-column Tables -@comment node-name, next, previous, up -@subsection @code{@@itemx} -@cindex Two named items for @code{@@table} -@findex itemx - -Use the @code{@@itemx} command inside a table when you have two or -more first column entries for the same item, each of which should -appear on a line of its own. Use @code{@@itemx} for all but the first -entry. The @code{@@itemx} command works exactly like @code{@@item} -except that it does not generate extra vertical space above the first -column text.@refill - -@need 1000 -For example, - -@example -@group -@@table @@code -@@item upcase -@@itemx downcase -These two functions accept a character or a string as -argument, and return the corresponding upper case (lower -case) character or string. -@@end table -@end group -@end example - -@noindent -This produces: - -@table @code -@item upcase -@itemx downcase -These two functions accept a character or a string as -argument, and return the corresponding upper case (lower -case) character or string.@refill -@end table - -@noindent -(Note also that this example illustrates multi-line supporting text in -a two-column table.)@refill - -@node Indices, Insertions, Lists and Tables, Top -@comment node-name, next, previous, up -@chapter Creating Indices -@cindex Indices -@cindex Creating indices - -Using Texinfo, you can generate indices without having to sort and -collate entries manually. In an index, the entries are listed in -alphabetical order, together with information on how to find the -discussion of each entry. In a printed manual, this information -consists of page numbers. In an Info file, this information is a menu -entry leading to the first node referenced.@refill - -Texinfo provides several predefined kinds of index: an index -for functions, an index for variables, an index for concepts, and so -on. You can combine indices or use them for other than their -canonical purpose. If you wish, you can define your own indices.@refill - -@menu -* Index Entries:: Choose different words for index entries. -* Predefined Indices:: Use different indices for different kinds - of entry. -* Indexing Commands:: How to make an index entry. -* Combining Indices:: How to combine indices. -* New Indices:: How to define your own indices. -@end menu - -@node Index Entries, Predefined Indices, , Indices -@comment node-name, next, previous, up -@section Making Index Entries -@cindex Index entries, making -@cindex Entries, making index - -When you are making index entries, it is good practice to think of the -different ways people may look for something. Different people -@emph{do not} think of the same words when they look something up. A -helpful index will have items indexed under all the different words -that people may use. For example, one reader may think it obvious that -the two-letter names for indices should be listed under ``Indices, -two-letter names'', since the word ``Index'' is the general concept. -But another reader may remember the specific concept of two-letter -names and search for the entry listed as ``Two letter names for -indices''. A good index will have both entries and will help both -readers.@refill - -Like typesetting, the construction of an index is a highly skilled, -professional art, the subtleties of which are not appreciated until you -need to do it yourself.@refill - -@xref{Printing Indices & Menus}, for information about printing an index -at the end of a book or creating an index menu in an Info file.@refill - -@node Predefined Indices, Indexing Commands, Index Entries, Indices -@comment node-name, next, previous, up -@section Predefined Indices - -Texinfo provides six predefined indices:@refill - -@itemize @bullet -@item -A @dfn{concept index} listing concepts that are discussed.@refill - -@item -A @dfn{function index} listing functions (such as entry points of -libraries).@refill - -@item -A @dfn{variables index} listing variables (such as global variables -of libraries).@refill - -@item -A @dfn{keystroke index} listing keyboard commands.@refill - -@item -A @dfn{program index} listing names of programs.@refill - -@item -A @dfn{data type index} listing data types (such as structures defined in -header files).@refill -@end itemize - -@noindent -Not every manual needs all of these, and most manuals use two or three -of them. This manual has two indices: a -concept index and an @@-command index (that is actually the function -index but is called a command index in the chapter heading). Two or -more indices can be combined into one using the @code{@@synindex} or -@code{@@syncodeindex} commands. @xref{Combining Indices}.@refill - -@node Indexing Commands, Combining Indices, Predefined Indices, Indices -@comment node-name, next, previous, up -@section Defining the Entries of an Index -@cindex Defining indexing entries -@cindex Index entries -@cindex Entries for an index -@cindex Specifying index entries -@cindex Creating index entries - -The data to make an index come from many individual indexing commands -scattered throughout the Texinfo source file. Each command says to add -one entry to a particular index; after formatting, the index will give -the current page number or node name as the reference.@refill - -An index entry consists of an indexing command at the beginning of a -line followed, on the rest of the line, by the entry.@refill - -For example, this section begins with the following five entries for -the concept index:@refill - -@example -@@cindex Defining indexing entries -@@cindex Index entries -@@cindex Entries for an index -@@cindex Specifying index entries -@@cindex Creating index entries -@end example - -Each predefined index has its own indexing command---@code{@@cindex} -for the concept index, @code{@@findex} for the function index, and so -on.@refill - -@cindex Capitalizing index entries -@cindex Index entry capitalization -The usual convention is to capitalize the first word of each index -entry, unless that word is the name of a function, variable, or other -such entity that should not be capitalized. Thus, if you are -documenting Emacs Lisp, you should usually capitalize entries in -the concept index, but not those in the function index. -However, if your -concept index entries are consistently short (one or two words each) -it may look better for each regular entry to start with a lower case -letter. Whichever convention you adapt, please be consistent! - -By default, entries for a concept index are printed in a small roman -font and entries for the other indices are printed in a small -@code{@@code} font. You may change the way part of an entry is -printed with the usual Texinfo commands, such as @code{@@file} for -file names and @code{@@emph} for emphasis (@pxref{Marking -Text}).@refill -@cindex Index font types - -@cindex Predefined indexing commands -@cindex Indexing commands, predefined -The six indexing commands for predefined indices are: - -@table @code -@item @@cindex @var{concept} -@findex cindex -Make an entry in the concept index for @var{concept}.@refill - -@item @@findex @var{function} -@findex findex -Make an entry in the function index for @var{function}.@refill - -@item @@vindex @var{variable} -@findex vindex -Make an entry in the variable index for @var{variable}.@refill - -@item @@kindex @var{keystroke} -@findex kindex -Make an entry in the key index for @var{keystroke}.@refill - -@item @@pindex @var{program} -@findex pindex -Make an entry in the program index for @var{program}.@refill - -@item @@tindex @var{data type} -@findex tindex -Make an entry in the data type index for @var{data type}.@refill -@end table - -@quotation -@strong{Caution:} Do not use a colon in an index entry. In Info, a -colon separates the menu entry name from the node name. An extra -colon confuses Info. -@xref{Menu Parts, , The Parts of a Menu}, -for more information about the structure of a menu entry.@refill -@end quotation - -If you write several identical index entries in different places in a -Texinfo file, the index in the printed manual will list all the pages to -which those entries refer. However, the index in the Info file will -list @strong{only} the node that references the @strong{first} of those -index entries. Therefore, it is best to write indices in which each -entry refers to only one place in the Texinfo file. Fortunately, this -constraint is a feature rather than a loss since it means that the index -will be easy to use. Otherwise, you could create an index that lists -several pages for one entry and your reader would not know to which page -to turn. If you have two identical entries for one topic, change the -topics slightly, or qualify them to indicate the difference.@refill - -You are not actually required to use the predefined indices for their -canonical purposes. For example, suppose you wish to index some C -preprocessor macros. You could put them in the function index along -with actual functions, just by writing @code{@@findex} commands for -them; then, when you print the ``Function Index'' as an unnumbered -chapter, you could give it the title `Function and Macro Index' and -all will be consistent for the reader. Or you could put the macros in -with the data types by writing @code{@@tindex} commands for them, and -give that index a suitable title so the reader will understand. -(@xref{Printing Indices & Menus}.)@refill - -@node Combining Indices, New Indices, Indexing Commands, Indices -@comment node-name, next, previous, up -@section Combining Indices -@cindex Combining indices -@cindex Indices, combining them - -Sometimes you will want to combine two disparate indices such as functions -and concepts, perhaps because you have few enough of one of them that -a separate index for them would look silly.@refill - -You could put functions into the concept index by writing -@code{@@cindex} commands for them instead of @code{@@findex} commands, -and produce a consistent manual by printing the concept index with the -title `Function and Concept Index' and not printing the `Function -Index' at all; but this is not a robust procedure. It works only if -your document is never included as part of another -document that is designed to have a separate function index; if your -document were to be included with such a document, the functions from -your document and those from the other would not end up together. -Also, to make your function names appear in the right font in the -concept index, you would need to enclose every one of them between -the braces of @code{@@code}.@refill - -@menu -* syncodeindex:: How to merge two indices, using @code{@@code} - font for the merged-from index. -* synindex:: How to merge two indices, using the - default font of the merged-to index. -@end menu - -@node syncodeindex, synindex, , Combining Indices -@subsubsection @code{@@syncodeindex} -@findex syncodeindex - -When you want to combine functions and concepts into one index, you -should index the functions with @code{@@findex} and index the concepts -with @code{@@cindex}, and use the @code{@@syncodeindex} command to -redirect the function index entries into the concept index.@refill -@findex syncodeindex - -The @code{@@syncodeindex} command takes two arguments; they are the name -of the index to redirect, and the name of the index to redirect it to. -The template looks like this:@refill - -@example -@@syncodeindex @var{from} @var{to} -@end example - -@cindex Predefined names for indices -@cindex Two letter names for indices -@cindex Indices, two letter names -@cindex Names for indices -For this purpose, the indices are given two-letter names:@refill - -@table @samp -@item cp -concept index -@item fn -function index -@item vr -variable index -@item ky -key index -@item pg -program index -@item tp -data type index -@end table - -Write an @code{@@syncodeindex} command before or shortly after the -end-of-header line at the beginning of a Texinfo file. For example, -to merge a function index with a concept index, write the -following:@refill - -@example -@@syncodeindex fn cp -@end example - -@noindent -This will cause all entries designated for the function index to merge -in with the concept index instead.@refill - -To merge both a variables index and a function index into a concept -index, write the following:@refill - -@example -@group -@@syncodeindex vr cp -@@syncodeindex fn cp -@end group -@end example - -@cindex Fonts for indices -The @code{@@syncodeindex} command puts all the entries from the `from' -index (the redirected index) into the @code{@@code} font, overriding -whatever default font is used by the index to which the entries are -now directed. This way, if you direct function names from a function -index into a concept index, all the function names are printed in the -@code{@@code} font as you would expect.@refill - -@node synindex, , syncodeindex, Combining Indices -@subsubsection @code{@@synindex} -@findex synindex - -The @code{@@synindex} command is nearly the same as the -@code{@@syncodeindex} command, except that it does not put the -`from' index entries into the @code{@@code} font; rather it puts -them in the roman font. Thus, you use @code{@@synindex} when you -merge a concept index into a function index.@refill - -@xref{Printing Indices & Menus}, for information about printing an index -at the end of a book or creating an index menu in an Info file.@refill - -@node New Indices, , Combining Indices, Indices -@section Defining New Indices -@cindex Defining new indices -@cindex Indices, defining new -@cindex New index defining -@findex defindex -@findex defcodeindex - -In addition to the predefined indices, you may use the -@code{@@defindex} and @code{@@defcodeindex} commands to define new -indices. These commands create new indexing @@-commands with which -you mark index entries. The @code{@@defindex }command is used like -this:@refill - -@example -@@defindex @var{name} -@end example - -The name of an index should be a two letter word, such as @samp{au}. -For example:@refill - -@example -@@defindex au -@end example - -This defines a new index, called the @samp{au} index. At the same -time, it creates a new indexing command, @code{@@auindex}, that you -can use to make index entries. Use the new indexing command just as -you would use a predefined indexing command.@refill - -For example, here is a section heading followed by a concept index -entry and two @samp{au} index entries.@refill - -@example -@@section Cognitive Semantics -@@cindex kinesthetic image schemas -@@auindex Johnson, Mark -@@auindex Lakoff, George -@end example - -@noindent -(Evidently, @samp{au} serves here as an abbreviation for ``author''.) -Texinfo constructs the new indexing command by concatenating the name -of the index with @samp{index}; thus, defining an @samp{au} index -leads to the automatic creation of an @code{@@auindex} command.@refill - -Use the @code{@@printindex} command to print the index, as you do with -the predefined indices. For example:@refill - -@example -@group -@@node Author Index, Subject Index, , Top -@@unnumbered Author Index - -@@printindex au -@end group -@end example - -The @code{@@defcodeindex} is like the @code{@@defindex} command, except -that, in the printed output, it prints entries in an @code{@@code} font -instead of a roman font. Thus, it parallels the @code{@@findex} command -rather than the @code{@@cindex} command.@refill - -You should define new indices within or right after the end-of-header -line of a Texinfo file, before any @code{@@synindex} or -@code{@@syncodeindex} commands (@pxref{Header}).@refill - -@node Insertions, Glyphs, Indices, Top -@comment node-name, next, previous, up -@chapter Special Insertions -@cindex Inserting special characters and symbols -@cindex Special insertions - -Texinfo provides several commands for formatting dimensions, for -inserting single characters that have special meaning in Texinfo, such -as braces, and for inserting special graphic symbols that do not -correspond to characters, such as dots and bullets.@refill - -@iftex -These are: - -@itemize @bullet -@item -Braces, @samp{@@} and periods. - -@item -Format a dimension, such as @samp{12@dmn{pt}}. - -@item -Dots and bullets. - -@item -The @TeX{} logo and the copyright symbol. - -@item -A minus sign. -@end itemize -@end iftex - -@menu -* Braces Atsigns Periods:: How to insert braces, @samp{@@} and periods. -* dmn:: How to format a dimension. -* Dots Bullets:: How to insert dots and bullets. -* TeX and copyright:: How to insert the @TeX{} logo - and the copyright symbol. -* minus:: How to insert a minus sign. -@end menu - -@node Braces Atsigns Periods, dmn, , Insertions -@comment node-name, next, previous, up -@section Inserting @samp{@@}, Braces, and Periods -@cindex Inserting @@, braces, and periods -@cindex Braces, inserting -@cindex Periods, inserting -@cindex Single characters, commands to insert -@cindex Commands to insert single characters - -@samp{@@} and curly braces are special characters in Texinfo. To -insert these characters so they appear in text, you must put an @samp{@@} in front -of these characters to prevent Texinfo from misinterpreting them.@refill - -Periods are also special. Depending on whether the period is inside -or at the end of a sentence, less or more space is inserted after a -period in a typeset manual. Since it is not always possible for -Texinfo to determine when a period ends a sentence and when it is used -in an abbreviation, special commands are needed in some circumstances. -(Usually, Texinfo can guess how to handle periods, so you do not need -to use the special commands; you just enter a period as you would if -you were using a typewriter, which means you put two spaces after the -period, question mark, or exclamation mark that ends a -sentence.)@refill - -Do not put braces after any of these commands; they are not -necessary.@refill - -@menu -* Inserting An Atsign:: -* Inserting Braces:: How to insert @samp{@{} and @samp{@}} -* Controlling Spacing:: How to insert the right amount of space - after punctuation within a sentence. -@end menu - -@node Inserting An Atsign, Inserting Braces, , Braces Atsigns Periods -@comment node-name, next, previous, up -@subsection Inserting @samp{@@} with @@@@ -@findex @@ @r{(single @samp{@@})} - -@code{@@@@} stands for a single @samp{@@} in either printed or Info -output.@refill - -Do not put braces after an @code{@@@@} command.@refill - -@node Inserting Braces, Controlling Spacing, Inserting An Atsign, Braces Atsigns Periods -@comment node-name, next, previous, up -@subsection Inserting @samp{@{} and @samp{@}}with @@@{ and @@@} -@findex @{ @r{(single @samp{@{})} -@findex @} @r{(single @samp{@}})} - -@code{@@@{} stands for a single @samp{@{} in either printed or Info -output.@refill - -@code{@@@}} stands for a single @samp{@}} in either printed or Info -output.@refill - -Do not put braces after either an @code{@@@{} or an @code{@@@}} -command.@refill - -@node Controlling Spacing, , Inserting Braces, Braces Atsigns Periods -@comment node-name, next, previous, up -@subsection Spacing After Colons and Periods -@findex : @r{(suppress widening)} - -Use the @code{@@:}@: command after a period, question mark, -exclamation mark, or colon that should not be followed by extra space. -For example, use @code{@@:}@: after periods that end abbreviations -which are not at the ends of sentences. @code{@@:}@: has no effect on -the Info file output.@refill - -@need 700 -For example, - -@example -The s.o.p.@@: has three parts @dots{} -The s.o.p. has three parts @dots{} -@end example - -@noindent -@ifinfo -produces -@end ifinfo -@iftex -produces the following. If you look carefully at this printed output, -you will see a little more whitespace after @samp{s.o.p.} in the second -line.@refill -@end iftex - -@quotation -The s.o.p.@: has three parts @dots{}@* -The s.o.p. has three parts @dots{} -@end quotation - -@noindent -@kbd{@@:} has no effect on the Info output. (@samp{s.o.p} is an acronym -for ``Standard Operating Procedure''.) - -@findex . @r{(true end of sentence)} -Use @code{@@.}@: instead of a period at the end of a sentence that -ends with a single capital letter. Otherwise, @TeX{} will think the -letter is an abbreviation and will not insert the correct -end-of-sentence spacing. Here is an example:@refill - -@example -Give it to M.I.B. and to M.E.W@@. Also, give it to R.J.C@@. -Give it to M.I.B. and to M.E.W. Also, give it to R.J.C. -@end example - -@noindent -@ifinfo -produces -@end ifinfo -@iftex -produces the following. If you look carefully at this printed output, -you will see a little more whitespace after the @samp{W} in the first -line.@refill -@end iftex - -@quotation -Give it to M.I.B. and to M.E.W@. Also, give it to R.J.C@.@* -Give it to M.I.B. and to M.E.W. Also, give it to R.J.C. -@end quotation - -In the Info file output, @code{@@.}@: is equivalent to a simple -@samp{.}.@refill - -The meanings of @code{@@:}@: and @code{@@.}@: in Texinfo are designed -to work well with the Emacs sentence motion commands. This made it -necessary for them to be incompatible with some other formatting -systems that use @@-commands.@refill - -Do not put braces after either an @code{@@:} or an @code{@@.} command.@refill - -@node dmn, Dots Bullets, Braces Atsigns Periods, Insertions -@section @code{@@dmn}@{@var{dimension}@}: Format a Dimension -@cindex Thin space between number, dimension -@cindex Dimension formatting -@cindex Format a dimension -@findex dmn - -At times, you may want to write @samp{12@dmn{pt}} or -@samp{8.5@dmn{in}} with little or no space between the number and the -abbreviation for the dimension. You can use the @code{@@dmn} command -to do this. On seeing the command, @TeX{} inserts just enough space -for proper typesetting; the Info formatting commands insert no space -at all, since the Info file does not require it.@refill - -To use the @code{@@dmn} command, write the number and then follow it -immediately, with no intervening space, by @code{@@dmn}, and then by -the dimension within braces.@refill - -@need 700 -@noindent -For example, - -@example -A4 paper is 8.27@@dmn@{in@} wide. -@end example - -@noindent -produces - -@quotation -A4 paper is 8.27@dmn{in} wide. -@end quotation - -Not everyone uses this style. Instead of writing -@w{@samp{8.27@@dmn@{in@}}} in the Texinfo file, you may write -@w{@samp{8.27 in.}} or @w{@samp{8.27 inches}}. (In these cases, the -formatters may insert a line break between the number and the -dimension. Also, if you write a period after an abbreviation within a -sentence, you should write @samp{@@:} after the period to prevent -@TeX{} from inserting extra whitespace. @xref{Controlling Spacing, , -Spacing After Colons and Periods}.)@refill - -@node Dots Bullets, TeX and copyright, dmn, Insertions -@comment node-name, next, previous, up -@section Inserting Ellipsis, Dots, and Bullets -@cindex Dots, inserting -@cindex Bullets, inserting -@cindex Ellipsis, inserting -@cindex Inserting ellipsis -@cindex Inserting dots -@cindex Special typesetting commands -@cindex Typesetting commands for dots, etc. - -An @dfn{ellipsis} (a line of dots) is not typeset as a string of -periods, so a special command is used for ellipsis in Texinfo. The -@code{@@bullet} command is special, too. Each of these commands is -followed by a pair of braces, @samp{@{@}}, without any whitespace -between the name of the command and the braces. (You need to use braces -with these commands because you can use them next to other text; without -the braces, the formatters would be confused. @xref{Command Syntax, , -@@-Command Syntax}, for further information.)@refill - -@menu -* dots:: How to insert dots @dots{} -* bullet:: How to insert a bullet. -@end menu - -@node dots, bullet, , Dots Bullets -@comment node-name, next, previous, up -@subsection @code{@@dots}@{@} -@findex dots -@cindex Inserting dots -@cindex Dots, inserting - -Use the @code{@@dots@{@}} command to generate an ellipsis, which is -three dots in a row, appropriately spaced, like this: `@dots{}'. Do -not simply write three periods in the input file; that would work for -the Info file output, but would produce the wrong amount of space -between the periods in the printed manual.@refill - -@iftex -Here is an ellipsis: @dots{} - -Here are three periods in a row: ... - -In printed output, the three periods in a row are closer together than -the dots in the ellipsis. -@end iftex - -@node bullet, , dots, Dots Bullets -@comment node-name, next, previous, up -@subsection @code{@@bullet}@{@} -@findex bullet - -Use the @code{@@bullet@{@}} command to generate a large round dot, or -the closest possible thing to one. In Info, an asterisk is used.@refill - -Here is a bullet: @bullet{} - -When you use @code{@@bullet} in @code{@@itemize}, you do not need to -type the braces, because @code{@@itemize} supplies them. @xref{itemize}.@refill - -@node TeX and copyright, minus, Dots Bullets, Insertions -@comment node-name, next, previous, up -@section Inserting @TeX{} and the Copyright Symbol - -The logo `@TeX{}' is typeset in a special fashion and it needs an -@@-command. The copyright symbol, `@copyright{}', is also special. -Each of these commands is followed by a pair of braces, @samp{@{@}}, -without any whitespace between the name of the command and the -braces.@refill - -@menu -* tex:: How to insert the @TeX{} logo. -* copyright symbol:: How to use @code{@@copyright}@{@}. -@end menu - -@node tex, copyright symbol, , TeX and copyright -@comment node-name, next, previous, up -@subsection @code{@@TeX}@{@} -@findex tex (command) - -Use the @code{@@TeX@{@}} command to generate `@TeX{}'. In a printed -manual, this is a special logo that is different from three ordinary -letters. In Info, it just looks like @samp{TeX}. The -@code{@@TeX@{@}} command is unique among Texinfo commands in that the -@key{T} and the @key{X} are in upper case.@refill - -@node copyright symbol, , tex, TeX and copyright -@comment node-name, next, previous, up -@subsection @code{@@copyright}@{@} -@findex copyright - -Use the @code{@@copyright@{@}} command to generate `@copyright{}'. In -a printed manual, this is a @samp{c} inside a circle, and in Info, -this is @samp{(C)}.@refill - -@node minus, , TeX and copyright, Insertions -@section @code{@@minus}@{@}: Inserting a Minus Sign -@findex minus - -Use the @code{@@minus@{@}} command to generate a minus sign. In a -fixed-width font, this is a single hyphen, but in a proportional font, -the symbol is the customary length for a minus sign---a little longer -than a hyphen.@refill - -You can compare the two forms: - -@display -@samp{@minus{}} is a minus sign generated with @samp{@@minus@{@}}, - -`-' is a hyphen generated with the character @samp{-}. -@end display - -@noindent -In the fixed-width font used by Info, @code{@@minus@{@}} is the same -as a hyphen.@refill - -You should not use @code{@@minus@{@}} inside @code{@@code} or -@code{@@example} because the width distinction is not made in the -fixed-width font they use.@refill - -When you use @code{@@minus} to specify the mark beginning each entry in -an itemized list, you do not need to type the braces -(@pxref{itemize}).@refill - -@node Glyphs, Breaks, Insertions, Top -@comment node-name, next, previous, up -@chapter Glyphs for Examples -@cindex Glyphs - -In Texinfo, code is often illustrated in examples that are delimited -by @code{@@example} and @code{@@end example}, or by @code{@@lisp} and -@code{@@end lisp}. In such examples, you can indicate the results of -evaluation or an expansion using @samp{@result{}} or -@samp{@expansion{}}. Likewise, there are commands to insert glyphs -to indicate -printed output, error messages, equivalence of expressions, and the -location of point.@refill - -The glyph-insertion commands do not need to be used within an example, but -most often they are. Every glyph-insertion command is followed by a pair of -left- and right-hand braces.@refill - -@menu -* Glyphs Summary:: -* result:: How to show the result of expression. -* expansion:: How to indicate an expansion. -* Print Glyph:: How to indicate printed output. -* Error Glyph:: How to indicate an error message. -* Equivalence:: How to indicate equivalence. -* Point Glyph:: How to indicate the location of point. -@end menu - -@node Glyphs Summary, result, , Glyphs -@ifinfo -@heading Glyphs Summary - -Here are the different glyph commands:@refill -@end ifinfo - -@table @asis -@item @result{} -@code{@@result@{@}} points to the result of an expression.@refill - -@item @expansion{} -@code{@@expansion@{@}} shows the results of a macro expansion.@refill - -@item @print{} -@code{@@print@{@}} indicates printed output.@refill - -@item @error{} -@code{@@error@{@}} indicates that the following text is an error -message.@refill - -@item @equiv{} -@code{@@equiv@{@}} indicates the exact equivalence of two forms.@refill - -@item @point{} -@code{@@point@{@}} shows the location of point.@refill -@end table - -@node result, expansion, Glyphs Summary, Glyphs -@section @result{}: Indicating Evaluation -@cindex Result of an expression -@cindex Indicating evaluation -@cindex Evaluation glyph -@cindex Value of an expression, indicating - -Use the @code{@@result@{@}} command to indicate the result of -evaluating an expression.@refill - -@iftex -The @code{@@result@{@}} command is displayed as @samp{=>} in Info and -as @samp{@result{}} in the printed output. -@end iftex -@ifinfo -The @code{@@result@{@}} command is displayed as @samp{@result{}} in Info -and as a double stemmed arrow in the printed output.@refill -@end ifinfo - -Thus, the following, - -@lisp -(cdr '(1 2 3)) - @result{} (2 3) -@end lisp - -@noindent -may be read as ``@code{(cdr '(1 2 3))} evaluates to @code{(2 3)}''. - -@node expansion, Print Glyph, result, Glyphs -@section @expansion{}: Indicating an Expansion -@cindex Expansion, indicating it - -When an expression is a macro call, it expands into a new expression. -You can indicate the result of the expansion with the -@code{@@expansion@{@}} command.@refill - -@iftex -The @code{@@expansion@{@}} command is displayed as @samp{==>} in Info and -as @samp{@expansion{}} in the printed output. -@end iftex -@ifinfo -The @code{@@expansion@{@}} command is displayed as @samp{@expansion{}} -in Info and as a long arrow with a flat base in the printed output.@refill -@end ifinfo - -@need 700 -For example, the following - -@example -@group -@@lisp -(third '(a b c)) - @@expansion@{@} (car (cdr (cdr '(a b c)))) - @@result@{@} c -@@end lisp -@end group -@end example - -@noindent -produces - -@lisp -@group -(third '(a b c)) - @expansion{} (car (cdr (cdr '(a b c)))) - @result{} c -@end group -@end lisp - -@noindent -which may be read as: - -@quotation -@code{(third '(a b c))} expands to @code{(car (cdr (cdr '(a b c))))}; -the result of evaluating the expression is @code{c}. -@end quotation - -@noindent -Often, as in this case, an example looks better if the -@code{@@expansion@{@}} and @code{@@result@{@}} commands are indented -five spaces.@refill - -@node Print Glyph, Error Glyph, expansion, Glyphs -@section @print{}: Indicating Printed Output -@cindex Printed output, indicating it - -Sometimes an expression will print output during its execution. You -can indicate the printed output with the @code{@@print@{@}} command.@refill - -@iftex -The @code{@@print@{@}} command is displayed as @samp{-|} in Info and -as @samp{@print{}} in the printed output. -@end iftex -@ifinfo -The @code{@@print@{@}} command is displayed as @samp{@print{}} in Info -and similarly, as a horizontal dash butting against a vertical bar, in -the printed output.@refill -@end ifinfo - -In the following example, the printed text is indicated with -@samp{@print{}}, and the value of the expression follows on the -last line.@refill - -@lisp -@group -(progn (print 'foo) (print 'bar)) - @print{} foo - @print{} bar - @result{} bar -@end group -@end lisp - -@noindent -In a Texinfo source file, this example is written as follows: - -@lisp -@group -@@lisp -(progn (print 'foo) (print 'bar)) - @@print@{@} foo - @@print@{@} bar - @@result@{@} bar -@@end lisp -@end group -@end lisp - -@node Error Glyph, Equivalence, Print Glyph, Glyphs -@section @error{}: Indicating an Error Message -@cindex Error message, indicating it - -A piece of code may cause an error when you evaluate it. You can -designate the error message with the @code{@@error@{@}} command.@refill - -@iftex -The @code{@@error@{@}} command is displayed as @samp{error-->} in Info -and as @samp{@error{}} in the printed output. -@end iftex -@ifinfo -The @code{@@error@{@}} command is displayed as @samp{@error{}} in Info -and as the word `error' in a box in the printed output.@refill -@end ifinfo - -@need 700 -Thus, - -@example -@@lisp -(+ 23 'x) -@@error@{@} Wrong type argument: integer-or-marker-p, x -@@end lisp -@end example - -@noindent -produces - -@lisp -(+ 23 'x) -@error{} Wrong type argument: integer-or-marker-p, x -@end lisp - -@noindent -This indicates that the following error message is printed -when you evaluate the expression: - -@lisp -Wrong type argument: integer-or-marker-p, x -@end lisp - -Note that @samp{@error{}} itself is not part of the error -message. - -@node Equivalence, Point Glyph, Error Glyph, Glyphs -@section @equiv{}: Indicating Equivalence -@cindex Equivalence, indicating it - -Sometimes two expressions produce identical results. You can indicate the -exact equivalence of two forms with the @code{@@equiv@{@}} command.@refill - -@iftex -The @code{@@equiv@{@}} command is displayed as @samp{==} in Info and -as @samp{@equiv{}} in the printed output. -@end iftex -@ifinfo -The @code{@@equiv@{@}} command is displayed as @samp{@equiv{}} in Info -and as a three parallel horizontal lines in the printed output.@refill -@end ifinfo - -Thus, - -@example -@@lisp -(make-sparse-keymap) @@equiv@{@} (list 'keymap) -@@end lisp -@end example - -@noindent -produces - -@lisp -(make-sparse-keymap) @equiv{} (list 'keymap) -@end lisp - -@noindent -This indicates that evaluating @code{(make-sparse-keymap)} produces -identical results to evaluating @code{(list 'keymap)}. - -@c Cannot write point command here because it causes trouble with TOC. -@node Point Glyph, , Equivalence, Glyphs -@section Indicating Point in a Buffer -@cindex Point, indicating it in a buffer - -Sometimes you need to show an example of text in an Emacs buffer. In -such examples, the convention is to include the entire contents of the -buffer in question between two lines of dashes containing the buffer -name.@refill - -You can use the @samp{@@point@{@}} command to show the location of point -in the text in the buffer. (The symbol for point, of course, is not -part of the text in the buffer; it indicates the place @emph{between} -two characters where point is located.)@refill - -@iftex -The @code{@@point@{@}} command is displayed as @samp{-!-} in Info and -as @samp{@point{}} in the printed output. -@end iftex -@ifinfo -The @code{@@point@{@}} command is displayed as @samp{@point{}} in Info -and as a small five pointed star in the printed output.@refill -@end ifinfo - -The following example shows the contents of buffer @file{foo} before -and after evaluating a Lisp command to insert the word @code{changed}.@refill - -@example -@group ----------- Buffer: foo ---------- -This is the @point{}contents of foo. ----------- Buffer: foo ---------- - -@end group -@end example - -@example -@group -(insert "changed ") - @result{} nil ----------- Buffer: foo ---------- -This is the changed @point{}contents of foo. ----------- Buffer: foo ---------- - -@end group -@end example - -In a Texinfo source file, the example is written like this:@refill - -@example -@@example ----------- Buffer: foo ---------- -This is the @@point@{@}contents of foo. ----------- Buffer: foo ---------- - -(insert "changed ") - @@result@{@} nil ----------- Buffer: foo ---------- -This is the changed @@point@{@}contents of foo. ----------- Buffer: foo ---------- -@@end example -@end example - -@node Breaks, Definition Commands, Glyphs, Top -@comment node-name, next, previous, up -@chapter Making and Preventing Breaks -@cindex Making line and page breaks -@cindex Preventing line and page breaks - -Usually, a Texinfo file is processed both by @TeX{} and by one of the -Info formatting commands. Line, paragraph, or page breaks sometimes -occur in the `wrong' place in one or other form of output. You must -ensure that text looks right both in the printed manual and in the -Info file.@refill - -For example, in a printed manual, page breaks may occur awkwardly in -the middle of an example; to prevent this, you can hold text together -using a grouping command that keeps the text from being split across -two pages. Conversely, you may want to force a page break where none -would occur normally. Fortunately, problems like these do not often -arise. When they do, use the break, break prevention, or pagination -commands.@refill - -@menu -* Break Commands:: Cause and prevent splits. -* Line Breaks:: How to force a single line to use two lines. -* w:: How to prevent unwanted line breaks. -* sp:: How to insert blank lines. -* page:: How to force the start of a new page. -* group:: How to prevent unwanted page breaks. -* need:: Another way to prevent unwanted page breaks. -@end menu - -@ifinfo -@node Break Commands, Line Breaks, , Breaks -@heading The Break Commands -@end ifinfo -@iftex -@sp 1 -@end iftex - -The break commands create line and paragraph breaks:@refill - -@table @code -@item @@* -Force a line break. - -@item @@sp @var{n} -Skip @var{n} blank lines.@refill -@end table -@iftex -@sp 1 -@end iftex - -The line-break-prevention command holds text together all on one -line:@refill - -@table @code -@item @@w@{@var{text}@} -Prevent @var{text} from being split and hyphenated across two lines.@refill -@end table -@iftex -@sp 1 -@end iftex - -The pagination commands apply only to printed output, since Info -files do not have pages.@refill - -@table @code -@item @@page -Start a new page in the printed manual.@refill - -@item @@group -Hold text together that must appear on one printed page.@refill - -@item @@need @var{mils} -Start a new printed page if not enough space on this one.@refill -@end table - -@node Line Breaks, w, Break Commands, Breaks -@comment node-name, next, previous, up -@section @code{@@*}: Generate Line Breaks -@findex * @r{(force line break)} -@cindex Line breaks -@cindex Breaks in a line - -The @code{@@*} command forces a line break in both the printed manual and -in Info.@refill - -@need 700 -For example, - -@example -This line @@* is broken @@*in two places. -@end example - -@noindent -produces - -@example -@group -This line - is broken -in two places. -@end group -@end example - -@noindent -(Note that the space after the first @code{@@*} command is faithfully -carried down to the next line.)@refill - -@need 800 -The @code{@@*} command is often used in a file's copyright page:@refill - -@example -@group -This is edition 2.0 of the Texinfo documentation,@@* -and is for @dots{} -@end group -@end example - -@noindent -In this case, the @code{@@*} command keeps @TeX{} from stretching the -line across the whole page in an ugly manner.@refill - -@quotation -@strong{Please note:} Do not write braces after an @code{@@*} command; -they are not needed.@refill - -Do not write an @code{@@refill} command at the end of a paragraph -containing an @code{@@*} command; it will cause the paragraph to be -refilled after the line break occurs, negating the effect of the line -break.@refill -@end quotation - -@node w, sp, Line Breaks, Breaks -@comment node-name, next, previous, up -@section @code{@@w}@{@var{text}@}: Prevent Line Breaks -@findex w @r{(prevent line break)} -@cindex Line breaks, preventing - -@code{@@w@{@var{text}@}} outputs @var{text} and prohibits line breaks -within @var{text}.@refill - -You can use the @code{@@w} command to prevent @TeX{} from automatically -hyphenating a long name or phrase that accidentally falls near the end -of a line.@refill - -@example -You can copy GNU software from @@w@{@@file@{prep.ai.mit.edu@}@}. -@end example - -@noindent -produces - -@quotation -You can copy GNU software from @w{@file{prep.ai.mit.edu}}. -@end quotation - -In the Texinfo file, you must write the @code{@@w} command and its -argument (all the affected text) all on one line.@refill - -@quotation -@strong{Caution:} Do not write an @code{@@refill} command at the end -of a paragraph containing an @code{@@w} command; it will cause the -paragraph to be refilled and may thereby negate the effect of the -@code{@@w} command.@refill -@end quotation - -@node sp, page, w, Breaks -@comment node-name, next, previous, up -@section @code{@@sp} @var{n}: Insert Blank Lines -@findex sp @r{(line spacing)} -@cindex Spaces (blank lines) -@cindex Blank lines -@cindex Line spacing - -A line beginning with and containing only @code{@@sp @var{n}} -generates @var{n} blank lines of space in both the printed manual and -the Info file. @code{@@sp} also forces a paragraph break. For -example,@refill - -@example -@@sp 2 -@end example - -@noindent -generates two blank lines. - -The @code{@@sp} command is most often used in the title page.@refill - -@ignore -@c node br, page, sp, Breaks -@comment node-name, next, previous, up -@c section @code{@@br}: Generate Paragraph Breaks -@findex br @r{(paragraph breaks)} -@cindex Paragraph breaks -@cindex Breaks in a paragraph - -The @code{@@br} command forces a paragraph break. It inserts a blank -line. You can use the command within or at the end of a line. If -used within a line, the @code{@@br@{@}} command must be followed by -left and right braces (as shown here) to mark the end of the -command.@refill - -@need 700 -For example, - -@example -@group -This line @@br@{@}contains and is ended by paragraph breaks@@br -and is followed by another line. -@end group -@end example - -@noindent -produces - -@example -@group -This line - -contains and is ended by paragraph breaks - -and is followed by another line. -@end group -@end example - -The @code{@@br} command is seldom used. -@end ignore - -@node page, group, sp, Breaks -@comment node-name, next, previous, up -@section @code{@@page}: Start a New Page -@cindex Page breaks -@findex page - -A line containing only @code{@@page} starts a new page in a printed -manual. The command has no effect on Info files since they are not -paginated. An @code{@@page} command is often used in the @code{@@titlepage} -section of a Texinfo file to start the copyright page.@refill - -@node group, need, page, Breaks -@comment node-name, next, previous, up -@section @code{@@group}: Prevent Page Breaks -@cindex Group (hold text together vertically) -@cindex Holding text together vertically -@cindex Vertically holding text together -@findex group - -The @code{@@group} command (on a line by itself) is used inside an -@code{@@example} or similar construct to begin an unsplittable vertical -group, which will appear entirely on one page in the printed output. -The group is terminated by a line containing only @code{@@end group}. -These two lines produce no output of their own, and in the Info file -output they have no effect at all.@refill - -@c Once said that these environments -@c turn off vertical spacing between ``paragraphs''. -@c Also, quotation used to work, but doesn't in texinfo-2.72 -Although @code{@@group} would make sense conceptually in a wide -variety of contexts, its current implementation works reliably only -within @code{@@example} and variants, and within @code{@@display}, -@code{@@format}, @code{@@flushleft} and @code{@@flushright}. -@xref{Quotations and Examples}. (What all these commands have in -common is that each line of input produces a line of output.) In -other contexts, @code{@@group} can cause anomalous vertical -spacing.@refill - -@need 750 -This formatting requirement means that you should write: - -@example -@group -@@example -@@group -@dots{} -@@end group -@@end example -@end group -@end example - -@noindent -with the @code{@@group} and @code{@@end group} commands inside the -@code{@@example} and @code{@@end example} commands. - -The @code{@@group} command is most often used to hold an example -together on one page. In this Texinfo manual, more than 100 examples -contain text that is enclosed between @code{@@group} and @code{@@end -group}. - -If you forget to end a group, you may get strange and unfathomable -error messages when you run @TeX{}. This is because @TeX{} keeps -trying to put the rest of the Texinfo file onto the one page and does -not start to generate error messages until it has processed -considerable text. It is a good rule of thumb to look for a missing -@code{@@end group} if you get incomprehensible error messages in -@TeX{}.@refill - -@node need, , group, Breaks -@comment node-name, next, previous, up -@section @code{@@need @var{mils}}: Prevent Page Breaks -@cindex Need space at page bottom -@findex need - -A line containing only @code{@@need @var{n}} starts -a new page in a printed manual if fewer than @var{n} mils (thousandths -of an inch) remain on the current page. Do not use -braces around the argument @var{n}. The @code{@@need} command has no -effect on Info files since they are not paginated.@refill - -@need 800 -This paragraph is preceded by an @code{@@need} command that tells -@TeX{} to start a new page if fewer than 800 mils (eight-tenths -inch) remain on the page. It looks like this:@refill - -@example -@group -@@need 800 -This paragraph is preceded by @dots{} -@end group -@end example - -The @code{@@need} command is useful for preventing orphans (single -lines at the bottoms of printed pages).@refill - -@node Definition Commands, Footnotes, Breaks, Top -@chapter Definition Commands -@cindex Definition commands - -The @code{@@deffn} command and the other @dfn{definition commands} -enable you to describe functions, variables, macros, commands, user -options, special forms and other such artifacts in a uniform -format.@refill - -In the Info file, a definition causes the entity -category---`Function', `Variable', or whatever---to appear at the -beginning of the first line of the definition, followed by the -entity's name and arguments. In the printed manual, the command -causes @TeX{} to print the entity's name and its arguments on the left -margin and print the category next to the right margin. In both -output formats, the body of the definition is indented. Also, the -name of the entity is entered into the appropriate index: -@code{@@deffn} enters the name into the index of functions, -@code{@@defvr} enters it into the index of variables, and so -on.@refill - -A manual need not and should not contain more than one definition for -a given name. An appendix containing a summary should use -@code{@@table} rather than the definition commands.@refill - -@menu -* Def Cmd Template:: How to structure a description using a - definition command. -* Optional Arguments:: How to handle optional and repeated arguments. -* deffnx:: How to group two or more `first' lines. -* Def Cmds in Detail:: All the definition commands. -* Def Cmd Conventions:: Conventions for writing definitions. -* Sample Function Definition:: -@end menu - -@node Def Cmd Template, Optional Arguments, , Definition Commands -@section The Template for a Definition -@cindex Definition template -@cindex Template for a definition - -The @code{@@deffn} command is used for definitions of entities that -resemble functions. To write a definition using the @code{@@deffn} -command, write the @code{@@deffn} command at the beginning of a line -and follow it on the same line by the category of the entity, the name -of the entity itself, and its arguments (if any). Then write the body -of the definition on succeeding lines. (You may embed examples in the -body.) Finally, end the definition with an @code{@@end deffn} command -written on a line of its own. (The other definition commands follow -the same format.)@refill - -The template for a definition looks like this: - -@example -@group -@@deffn @var{category} @var{name} @var{arguments}@dots{} -@var{body-of-definition} -@@end deffn -@end group -@end example - -@need 700 -@noindent -For example, - -@example -@group -@@deffn Command forward-word count -This command moves point forward @@var@{count@} words -(or backward if @@var@{count@} is negative). @dots{} -@@end deffn -@end group -@end example - -@noindent -produces - -@quotation -@deffn Command forward-word count -This function moves point forward @var{count} words -(or backward if @var{count} is negative). @dots{} -@end deffn -@end quotation - -Capitalize the category name like a title. If the name of the -category contains spaces, as in the phrase `Interactive Command', -write braces around it. For example:@refill - -@example -@group -@@deffn @{Interactive Command@} isearch-forward -@dots{} -@@end deffn -@end group -@end example - -@noindent -Otherwise, the second word will be mistaken for the name of the -entity.@refill - -Some of the definition commands are more general than others. The -@code{@@deffn} command, for example, is the general definition command -for functions and the like---for entities that may take arguments. When -you use this command, you specify the category to which the entity -belongs. The @code{@@deffn} command possesses three predefined, -specialized variations, @code{@@defun}, @code{@@defmac}, and -@code{@@defspec}, that specify the category for you: ``Function'', -``Macro'', and ``Special Form'' respectively. The @code{@@defvr} -command also is accompanied by several predefined, specialized -variations for describing particular kinds of variables.@refill - -The template for a specialized definition, such as @code{@@defun}, is -similar to the template for a generalized definition, except that you -do not need to specify the category:@refill - -@example -@group -@@defun @var{name} @var{arguments}@dots{} -@var{body-of-definition} -@@end defun -@end group -@end example - -@noindent -Thus, - -@example -@group -@@defun buffer-end flag -This function returns @@code@{(point-min)@} if @@var@{flag@} -is less than 1, @@code@{(point-max)@} otherwise. -@dots{} -@@end defun -@end group -@end example - -@noindent -produces - -@quotation -@defun buffer-end flag -This function returns @code{(point-min)} if @var{flag} is less than 1, -@code{(point-max)} otherwise. @dots{} -@end defun -@end quotation - -@noindent -@xref{Sample Function Definition, Sample Function Definition, A Sample -Function Definition}, for a more detailed example of a function -definition, including the use of @code{@@example} inside the -definition.@refill - -The other specialized commands work like @code{@@defun}.@refill - -@node Optional Arguments, deffnx, Def Cmd Template, Definition Commands -@section Optional and Repeated Arguments -@cindex Optional and repeated arguments -@cindex Repeated and optional arguments -@cindex Arguments, repeated and optional -@cindex Syntax, optional & repeated arguments -@cindex Meta-syntactic chars for arguments - -Some entities take optional or repeated arguments, which may be -specified by a distinctive glyph that uses square brackets and -ellipses. For @w{example}, a special form often breaks its argument list -into separate arguments in more complicated ways than a -straightforward function.@refill - -@iftex -An argument enclosed within square brackets is optional. -Thus, the phrase -@samp{@code{@r{[}@var{optional-arg}@r{]}}} means that -@var{optional-arg} is optional. -An argument followed by an ellipsis is optional -and may be repeated more than once. -@c This is consistent with Emacs Lisp Reference manual -Thus, @samp{@var{repeated-args}@dots{}} stands for zero or more arguments. -Parentheses are used when several arguments are grouped -into additional levels of list structure in Lisp. -@end iftex -@c The following looks better in Info (no `r', `samp' and `code'): -@ifinfo -An argument enclosed within square brackets is optional. -Thus, [@var{optional-arg}] means that @var{optional-arg} is optional. -An argument followed by an ellipsis is optional -and may be repeated more than once. -@c This is consistent with Emacs Lisp Reference manual -Thus, @var{repeated-args}@dots{} stands for zero or more arguments. -Parentheses are used when several arguments are grouped -into additional levels of list structure in Lisp. -@end ifinfo - -Here is the @code{@@defspec} line of an example of an imaginary -special form:@refill - -@quotation -@defspec foobar (@var{var} [@var{from} @var{to} [@var{inc}]]) @var{body}@dots{} -@end defspec -@tex -\vskip \parskip -@end tex -@end quotation - -@noindent -In this example, the arguments @var{from} and @var{to} are optional, -but must both be present or both absent. If they are present, -@var{inc} may optionally be specified as well. These arguments are -grouped with the argument @var{var} into a list, to distinguish them -from @var{body}, which includes all remaining elements of the -form.@refill - -In a Texinfo source file, this @code{@@defspec} line is written like -this (except it would not be split over two lines, as it is in this -example).@refill - -@example -@group -@@defspec foobar (@@var@{var@} [@@var@{from@} @@var@{to@} - [@@var@{inc@}]]) @@var@{body@}@@dots@{@} -@end group -@end example - -@noindent -The function is listed in the Command and Variable Index under -@samp{foobar}.@refill - -@node deffnx, Def Cmds in Detail, Optional Arguments, Definition Commands -@section Two or More `First' Lines -@cindex Two `First' Lines for @code{@@deffn} -@cindex Grouping two definitions together -@cindex Definitions grouped together -@findex deffnx - -To create two or more `first' or header lines for a definition, follow -the first @code{@@deffn} line by a line beginning with @code{@@deffnx}. -The @code{@@deffnx} command works exactly like @code{@@deffn} -except that it does not generate extra vertical white space between it -and the preceding line.@refill - -@need 1000 -For example, - -@example -@group -@@deffn @{Interactive Command@} isearch-forward -@@deffnx @{Interactive Command@} isearch-backward -These two search commands are similar except @dots{} -@@end deffn -@end group -@end example - -@noindent -produces - -@deffn {Interactive Command} isearch-forward -@deffnx {Interactive Command} isearch-backward -These two search commands are similar except @dots{} -@end deffn - -Each of the other definition commands has an `x' form: @code{@@defunx}, -@code{@@defvrx}, @code{@@deftypefunx}, etc. - -The `x' forms work just like @code{@@itemx}; see @ref{itemx, , @code{@@itemx}}. - -@node Def Cmds in Detail, Def Cmd Conventions, deffnx, Definition Commands -@section The Definition Commands - -Texinfo provides more than a dozen definition commands, all of which -are described in this section.@refill - -The definition commands automatically enter the name of the entity in -the appropriate index: for example, @code{@@deffn}, @code{@@defun}, -and @code{@@defmac} enter function names in the index of functions; -@code{@@defvr} and @code{@@defvar} enter variable names in the index -of variables.@refill - -Although the examples that follow mostly illustrate Lisp, the commands -can be used for other programming languages.@refill - -@menu -* Functions Commands:: Commands for functions and similar entities. -* Variables Commands:: Commands for variables and similar entities. -* Typed Functions:: Commands for functions in typed languages. -* Typed Variables:: Commands for variables in typed languages. -* Abstract Objects:: Commands for object-oriented programming. -* Data Types:: The definition command for data types. -@end menu - -@node Functions Commands, Variables Commands, , Def Cmds in Detail -@subsection Functions and Similar Entities - -This section describes the commands for describing functions and similar -entities:@refill - -@table @code -@findex deffn -@item @@deffn @var{category} @var{name} @var{arguments}@dots{} -The @code{@@deffn} command is the general definition command for -functions, interactive commands, and similar entities that may take -arguments. You must choose a term to describe the category of entity -being defined; for example, ``Function'' could be used if the entity is -a function. The @code{@@deffn} command is written at the beginning of a -line and is followed on the same line by the category of entity being -described, the name of this particular entity, and its arguments, if -any. Terminate the definition with @code{@@end deffn} on a line of its -own.@refill - -@need 750 -For example, here is a definition: - -@example -@group -@@deffn Command forward-char nchars -Move point forward @@var@{nchars@} characters. -@@end deffn -@end group -@end example - -@noindent -This shows a rather terse definition for a ``command'' named -@code{forward-char} with one argument, @var{nchars}. - -@code{@@deffn} prints argument names such as @var{nchars} in italics or -upper case, as if @code{@@var} had been used, because we think of these -names as metasyntactic variables---they stand for the actual argument -values. Within the text of the description, write an argument name -explicitly with @code{@@var} to refer to the value of the argument. In -the example above, we used @samp{@@var@{nchars@}} in this way. - -The template for @code{@@deffn} is: - -@example -@group -@@deffn @var{category} @var{name} @var{arguments}@dots{} -@var{body-of-definition} -@@end deffn -@end group -@end example - -@findex defun -@item @@defun @var{name} @var{arguments}@dots{} -The @code{@@defun} command is the definition command for functions. -@code{@@defun} is equivalent to @samp{@@deffn Function -@dots{}}.@refill - -@need 800 -@noindent -For example, - -@example -@group -@@defun set symbol new-value -Change the value of the symbol @@var@{symbol@} -to @@var@{new-value@}. -@@end defun -@end group -@end example - -@noindent -shows a rather terse definition for a function @code{set} whose -arguments are @var{symbol} and @var{new-value}. The argument names on -the @code{@@defun} line automatically appear in italics or upper case as -if they were enclosed in @code{@@var}. Terminate the definition with -@code{@@end defun} on a line of its own.@refill - -The template is: - -@example -@group -@@defun @var{function-name} @var{arguments}@dots{} -@var{body-of-definition} -@@end defun -@end group -@end example - -@code{@@defun} creates an entry in the index of functions. - -@findex defmac -@item @@defmac @var{name} @var{arguments}@dots{} -The @code{@@defmac} command is the definition command for macros. -@code{@@defmac} is equivalent to @samp{@@deffn Macro @dots{}} and -works like @code{@@defun}.@refill - -@findex defspec -@item @@defspec @var{name} @var{arguments}@dots{} -The @code{@@defspec} command is the definition command for special -forms. (In Lisp, a special form is an entity much like a function.) -@code{@@defspec} is equivalent to @samp{@@deffn @{Special Form@} -@dots{}} and works like @code{@@defun}.@refill -@end table - -@node Variables Commands, Typed Functions, Functions Commands, Def Cmds in Detail -@subsection Variables and Similar Entities - -Here are the commands for defining variables and similar -entities:@refill - -@table @code -@findex defvr -@item @@defvr @var{category} @var{name} -The @code{@@defvr} command is a general definition command for -something like a variable---an entity that records a value. You must -choose a term to describe the category of entity being defined; for -example, ``Variable'' could be used if the entity is a variable. -Write the @code{@@defvr} command at the beginning of a line and -followed it on the same line by the category of the entity and the -name of the entity.@refill - -Capitalize the category name like a title. If the name of the -category contains spaces, as in the name `User Option', write braces -around it. Otherwise, the second word will be mistaken for the name -of the entity, for example: - -@example -@group -@@defvr @{User Option@} fill-column -This buffer-local variable specifies -the maximum width of filled lines. -@dots{} -@@end defvr -@end group -@end example - -Terminate the definition with @code{@@end defvr} on a line of its -own.@refill - -The template is: - -@example -@group -@@defvr @var{category} @var{name} -@var{body-of-definition} -@@end defvr -@end group -@end example - -@code{@@defvr} creates an entry in the index of variables for @var{name}. - -@findex defvar -@item @@defvar @var{name} -The @code{@@defvar} command is the definition command for variables. -@code{@@defvar} is equivalent to @samp{@@defvr Variable -@dots{}}.@refill - -@need 750 -For example: - -@example -@group -@@defvar kill-ring -@dots{} -@@end defvar -@end group -@end example - -The template is: - -@example -@group -@@defvar @var{name} -@var{body-of-definition} -@@end defvar -@end group -@end example - -@code{@@defvar} creates an entry in the index of variables for -@var{name}.@refill - -@findex defopt -@item @@defopt @var{name} -The @code{@@defopt} command is the definition command for user -options. @code{@@defopt} is equivalent to @samp{@@defvr @{User -Option@} @dots{}} and works like @code{@@defvar}.@refill -@end table - -@node Typed Functions, Typed Variables, Variables Commands, Def Cmds in Detail -@subsection Functions in Typed Languages - -The @code{@@deftypefn} command and its variations are for describing -functions in C or any other language in which you must declare types -of variables and functions.@refill - -@table @code -@findex deftypefn -@item @@deftypefn @var{category} @var{data-type} @var{name} @var{arguments}@dots{} -The @code{@@deftypefn} command is the general definition command for -functions and similar entities that may take arguments and that are -typed. The @code{@@deftypefn} command is written at the beginning of -a line and is followed on the same line by the category of entity -being described, the type of the returned value, the name of this -particular entity, and its arguments, if any.@refill - -@need 800 -@noindent -For example, - -@example -@group -@@deftypefn @{Library Function@} int foobar - (int @@var@{foo@}, float @@var@{bar@}) -@dots{} -@@end deftypefn -@end group -@end example - -@need 1000 -@noindent -(where the text before the ``@dots{}'', shown above as two lines, would -actually be a single line in a real Texinfo file) produces the following -in Info: - -@smallexample -@group --- Library Function: int foobar (int FOO, float BAR) -@dots{} -@end group -@end smallexample -@iftex - -In a printed manual, it produces: - -@quotation -@deftypefn {Library Function} int foobar (int @var{foo}, float @var{bar}) -@dots{} -@end deftypefn -@end quotation -@end iftex - -This means that @code{foobar} is a ``library function'' that returns an -@code{int}, and its arguments are @var{foo} (an @code{int}) and -@var{bar} (a @code{float}).@refill - -The argument names that you write in @code{@@deftypefn} are not subject -to an implicit @code{@@var}---since the actual names of the arguments in -@code{@@deftypefn} are typically scattered among data type names and -keywords, Texinfo cannot find them without help. Instead, you must write -@code{@@var} explicitly around the argument names. In the example -above, the argument names are @samp{foo} and @samp{bar}.@refill - -The template for @code{@@deftypefn} is:@refill - -@example -@group -@@deftypefn @var{category} @var{data-type} @var{name} @var{arguments} @dots{} -@var{body-of-description} -@@end deftypefn -@end group -@end example - -@noindent -Note that if the @var{category} or @var{data type} is more than one -word then it must be enclosed in braces to make it a single argument.@refill - -If you are describing a procedure in a language that has packages, -such as Ada, you might consider using @code{@@deftypefn} in a manner -somewhat contrary to the convention described in the preceding -paragraphs.@refill - -@need 800 -@noindent -For example: - -@example -@group -@@deftypefn stacks private push - (@@var@{s@}:in out stack; - @@var@{n@}:in integer) -@dots{} -@@end deftypefn -@end group -@end example - -@noindent -(The @code{@@deftypefn} arguments are shown split into three lines, but -would be a single line in a real Texinfo file.) - -In this instance, the procedure is classified as belonging to the -package @code{stacks} rather than classified as a `procedure' and its -data type is described as @code{private}. (The name of the procedure -is @code{push}, and its arguments are @var{s} and @var{n}.)@refill - -@code{@@deftypefn} creates an entry in the index of functions for -@var{name}.@refill - -@findex deftypefun -@item @@deftypefun @var{data-type} @var{name} @var{arguments}@dots{} -The @code{@@deftypefun} command is the specialized definition command -for functions in typed languages. The command is equivalent to -@samp{@@deftypefn Function @dots{}}.@refill - -@need 800 -@noindent -Thus, - -@smallexample -@group -@@deftypefun int foobar (int @@var@{foo@}, float @@var@{bar@}) -@dots{} -@@end deftypefun -@end group -@end smallexample - -@noindent -produces the following in Info: - -@example -@group --- Function: int foobar (int FOO, float BAR) -@dots{} -@end group -@end example -@iftex - -@need 800 -@noindent -and the following in a printed manual: - -@quotation -@deftypefun int foobar (int @var{foo}, float @var{bar}) -@dots{} -@end deftypefun -@end quotation -@end iftex - -@need 800 -The template is: - -@example -@group -@@deftypefun @var{type} @var{name} @var{arguments}@dots{} -@var{body-of-description} -@@end deftypefun -@end group -@end example - -@code{@@deftypefun} creates an entry in the index of functions for -@var{name}.@refill -@end table - -@node Typed Variables, Abstract Objects, Typed Functions, Def Cmds in Detail -@subsection Variables in Typed Languages - -Variables in typed languages are handled in a manner similar to -functions in typed languages. @xref{Typed Functions}. The general -definition command @code{@@deftypevr} corresponds to -@code{@@deftypefn} and the specialized definition command -@code{@@deftypevar} corresponds to @code{@@deftypefun}.@refill - -@table @code -@findex deftypevr -@item @@deftypevr @var{category} @var{data-type} @var{name} -The @code{@@deftypevr} command is the general definition command for -something like a variable in a typed language---an entity that records -a value. You must choose a term to describe the category of the -entity being defined; for example, ``Variable'' could be used if the -entity is a variable.@refill - -The @code{@@deftypevr} command is written at the beginning of a line -and is followed on the same line by the category of the entity -being described, the data type, and the name of this particular -entity.@refill - -@need 800 -@noindent -For example: - -@example -@group -@@deftypevr @{Global Flag@} int enable -@dots{} -@@end deftypevr -@end group -@end example - -@noindent -produces the following in Info: - -@example -@group --- Global Flag: int enable -@dots{} -@end group -@end example -@iftex - -@noindent -and the following in a printed manual: - -@quotation -@deftypevr {Global Flag} int enable -@dots{} -@end deftypevr -@end quotation -@end iftex - -@need 800 -The template is: - -@example -@@deftypevr @var{category} @var{data-type} @var{name} -@var{body-of-description} -@@end deftypevr -@end example - -@code{@@deftypevr} creates an entry in the index of variables for -@var{name}.@refill - -@findex deftypevar -@item @@deftypevar @var{data-type} @var{name} -The @code{@@deftypevar} command is the specialized definition command -for variables in typed languages. @code{@@deftypevar} is equivalent -to @samp{@@deftypevr Variable @dots{}}.@refill - -@need 800 -@noindent -For example: - -@example -@group -@@deftypevar int fubar -@dots{} -@@end deftypevar -@end group -@end example - -@noindent -produces the following in Info: - -@example -@group --- Variable: int fubar -@dots{} -@end group -@end example -@iftex - -@need 800 -@noindent -and the following in a printed manual: - -@quotation -@deftypevar int fubar -@dots{} -@end deftypevar -@end quotation -@end iftex - -@need 800 -@noindent -The template is: - -@example -@group -@@deftypevar @var{data-type} @var{name} -@var{body-of-description} -@@end deftypevar -@end group -@end example - -@code{@@deftypevar} creates an entry in the index of variables for -@var{name}.@refill -@end table - -@node Abstract Objects, Data Types, Typed Variables, Def Cmds in Detail -@subsection Object-Oriented Programming - -Here are the commands for formatting descriptions about abstract -objects, such as are used in object-oriented programming. A class is -a defined type of abstract object. An instance of a class is a -particular object that has the type of the class. An instance -variable is a variable that belongs to the class but for which each -instance has its own value.@refill - -In a definition, if the name of a class is truly a name defined in the -programming system for a class, then you should write an @code{@@code} -around it. Otherwise, it is printed in the usual text font.@refill - -@table @code -@findex defcv -@item @@defcv @var{category} @var{class} @var{name} -The @code{@@defcv} command is the general definition command for -variables associated with classes in object-oriented programming. The -@code{@@defcv} command is followed by three arguments: the category of -thing being defined, the class to which it belongs, and its -name. Thus,@refill - -@example -@group -@@defcv @{Class Option@} Window border-pattern -@dots{} -@@end defcv -@end group -@end example - -@noindent -illustrates how you would write the first line of a definition of the -@code{border-pattern} class option of the class @code{Window}.@refill - -The template is - -@example -@group -@@defcv @var{category} @var{class} @var{name} -@dots{} -@@end defcv -@end group -@end example - -@code{@@defcv} creates an entry in the index of variables. - -@findex defivar -@item @@defivar @var{class} @var{name} -The @code{@@defivar} command is the definition command for instance -variables in object-oriented programming. @code{@@defivar} is -equivalent to @samp{@@defcv @{Instance Variable@} @dots{}}@refill - -The template is: - -@example -@group -@@defivar @var{class} @var{instance-variable-name} -@var{body-of-definition} -@@end defivar -@end group -@end example - -@code{@@defivar} creates an entry in the index of variables. - -@findex defop -@item @@defop @var{category} @var{class} @var{name} @var{arguments}@dots{} -The @code{@@defop} command is the general definition command for -entities that may resemble methods in object-oriented programming. -These entities take arguments, as functions do, but are associated -with particular classes of objects.@refill - -For example, some systems have constructs called @dfn{wrappers} that -are associated with classes as methods are, but that act more like -macros than like functions. You could use @code{@@defop Wrapper} to -describe one of these.@refill - -Sometimes it is useful to distinguish methods and @dfn{operations}. -You can think of an operation as the specification for a method. -Thus, a window system might specify that all window classes have a -method named @code{expose}; we would say that this window system -defines an @code{expose} operation on windows in general. Typically, -the operation has a name and also specifies the pattern of arguments; -all methods that implement the operation must accept the same -arguments, since applications that use the operation do so without -knowing which method will implement it.@refill - -Often it makes more sense to document operations than methods. For -example, window application developers need to know about the -@code{expose} operation, but need not be concerned with whether a -given class of windows has its own method to implement this operation. -To describe this operation, you would write:@refill - -@example -@@defop Operation windows expose -@end example - -The @code{@@defop} command is written at the beginning of a line and -is followed on the same line by the overall name of the category of -operation, the name of the class of the operation, the name of the -operation, and its arguments, if any.@refill - -@need 800 -@noindent -The template is: - -@example -@group -@@defop @var{category} @var{class} @var{name} @var{arguments}@dots{} -@var{body-of-definition} -@@end defop -@end group -@end example - -@code{@@defop} creates an entry, such as `@code{expose} on -@code{windows}', in the index of functions.@refill - -@findex defmethod -@item @@defmethod @var{class} @var{name} @var{arguments}@dots{} -The @code{@@defmethod} command is the definition command for methods -in object-oriented programming. A method is a kind of function that -implements an operation for a particular class of objects and its -subclasses. In the Lisp Machine, methods actually were functions, but -they were usually defined with @code{defmethod}. - -@code{@@defmethod} is equivalent to @samp{@@defop Method @dots{}}. -The command is written at the beginning of a line and is followed by -the name of the class of the method, the name of the method, and its -arguments, if any.@refill - -@need 800 -@noindent -For example, - -@example -@group -@@defmethod @code{bar-class} bar-method argument -@dots{} -@@end defmethod -@end group -@end example - -@noindent -illustrates the definition for a method called @code{bar-method} of -the class @code{bar-class}. The method takes an argument.@refill - -The template is: - -@example -@group -@@defmethod @var{class} @var{method-name} @var{arguments}@dots{} -@var{body-of-definition} -@@end defmethod -@end group -@end example - -@c !!! reworded to prevent overfull hbox --bob 26 Mar 93 -@code{@@defmethod} creates an entry in the index of functions, such as -`@code{bar-method} on @code{bar-class}'.@refill -@end table - -@node Data Types, , Abstract Objects, Def Cmds in Detail -@subsection Data Types - -Here is the command for data types:@refill - -@table @code -@findex deftp -@item @@deftp @var{category} @var{name} @var{attributes}@dots{} -The @code{@@deftp} command is the generic definition command for data -types. The command is written at the beginning of a line and is -followed on the same line by the category, by the name of the type -(which is a word like @code{int} or @code{float}), and then by names of -attributes of objects of that type. Thus, you could use this command -for describing @code{int} or @code{float}, in which case you could use -@code{data type} as the category. (A data type is a category of -certain objects for purposes of deciding which operations can be -performed on them.)@refill - -In Lisp, for example, @dfn{pair} names a particular data -type, and an object of that type has two slots called the -@sc{car} and the @sc{cdr}. Here is how you would write the first line -of a definition of @code{pair}.@refill - -@example -@group -@@deftp @{Data type@} pair car cdr -@dots{} -@@end deftp -@end group -@end example - -@need 950 -The template is: - -@example -@group -@@deftp @var{category} @var{name-of-type} @var{attributes}@dots{} -@var{body-of-definition} -@@end deftp -@end group -@end example - -@code{@@deftp} creates an entry in the index of data types. -@end table - -@node Def Cmd Conventions, Sample Function Definition, Def Cmds in Detail, Definition Commands -@section Conventions for Writing Definitions -@cindex Definition conventions -@cindex Conventions for writing definitions - -When you write a definition using @code{@@deffn}, @code{@@defun}, or -one of the other definition commands, please take care to use -arguments that indicate the meaning, as with the @var{count} argument -to the @code{forward-word} function. Also, if the name of an argument -contains the name of a type, such as @var{integer}, take care that the -argument actually is of that type.@refill - -@node Sample Function Definition, , Def Cmd Conventions, Definition Commands -@section A Sample Function Definition -@cindex Function definitions -@cindex Command definitions -@cindex Macro definitions -@cindex Sample function definition - -A function definition uses the @code{@@defun} and @code{@@end defun} -commands. The name of the function follows immediately after the -@code{@@defun} command and it is followed, on the same line, by the -parameter list.@refill - -Here is a definition from @cite{The GNU Emacs Lisp Reference Manual}. -(@xref{Calling Functions, , Calling Functions, elisp, The GNU Emacs -Lisp Reference Manual}.) - -@quotation -@defun apply function &rest arguments -@code{apply} calls @var{function} with @var{arguments}, just -like @code{funcall} but with one difference: the last of -@var{arguments} is a list of arguments to give to -@var{function}, rather than a single argument. We also say -that this list is @dfn{appended} to the other arguments. - -@code{apply} returns the result of calling @var{function}. -As with @code{funcall}, @var{function} must either be a Lisp -function or a primitive function; special forms and macros -do not make sense in @code{apply}. - -@example -(setq f 'list) - @result{} list -(apply f 'x 'y 'z) -@error{} Wrong type argument: listp, z -(apply '+ 1 2 '(3 4)) - @result{} 10 -(apply '+ '(1 2 3 4)) - @result{} 10 - -(apply 'append '((a b c) nil (x y z) nil)) - @result{} (a b c x y z) -@end example - -An interesting example of using @code{apply} is found in the description -of @code{mapcar}.@refill -@end defun -@end quotation - -@need 1200 -In the Texinfo source file, this example looks like this: - -@example -@group -@@defun apply function &rest arguments - -@@code@{apply@} calls @@var@{function@} with -@@var@{arguments@}, just like @@code@{funcall@} but with one -difference: the last of @@var@{arguments@} is a list of -arguments to give to @@var@{function@}, rather than a single -argument. We also say that this list is @@dfn@{appended@} -to the other arguments. -@end group - -@group -@@code@{apply@} returns the result of calling -@@var@{function@}. As with @@code@{funcall@}, -@@var@{function@} must either be a Lisp function or a -primitive function; special forms and macros do not make -sense in @@code@{apply@}. -@end group - -@group -@@example -(setq f 'list) - @@result@{@} list -(apply f 'x 'y 'z) -@@error@{@} Wrong type argument: listp, z -(apply '+ 1 2 '(3 4)) - @@result@{@} 10 -(apply '+ '(1 2 3 4)) - @@result@{@} 10 - -(apply 'append '((a b c) nil (x y z) nil)) - @@result@{@} (a b c x y z) -@@end example -@end group - -@group -An interesting example of using @@code@{apply@} is found -in the description of @@code@{mapcar@}.@@refill -@@end defun -@end group -@end example - -@noindent -In this manual, this function is listed in the Command and Variable -Index under @code{apply}.@refill - -Ordinary variables and user options are described using a format like -that for functions except that variables do not take arguments. - -@node Footnotes, Conditionals, Definition Commands, Top -@comment node-name, next, previous, up -@chapter Footnotes -@cindex Footnotes -@findex footnote - -A @dfn{footnote} is for a reference that documents or elucidates the -primary text.@footnote{A footnote should complement or expand upon -the primary text, but a reader should not need to read a footnote to -understand the primary text. For a thorough discussion of footnotes, -see @cite{The Chicago Manual of Style}, which is published by the -University of Chicago Press.}@refill - -In Texinfo, footnotes are created with the @code{@@footnote} command. -This command is followed immediately by a left brace, then by the text -of the footnote, and then by a terminating right brace. The template -is: - -@example -@@footnote@{@var{text}@} -@end example - -Footnotes may be of any length, but are usually short.@refill - -For example, this clause is followed by a sample -footnote@footnote{Here is the sample footnote.}; in the Texinfo -source, it looks like this:@refill - -@example -@dots{}a sample footnote @@footnote@{Here is the sample -footnote.@}; in the Texinfo source@dots{} -@end example - -In a printed manual or book, the reference mark for a footnote is a -small, superscripted number; the text of the footnote is written at -the bottom of the page, below a horizontal line.@refill - -In Info, the reference mark for a footnote is a pair of parentheses -with the footnote number between them, like this: @samp{(1)}.@refill - -Info has two footnote styles, which determine where the text of the -footnote is located:@refill - -@itemize @bullet -@cindex @samp{@r{End}} node footnote style -@item -In the `End' node style, all the footnotes for a single node -are placed at the end of that node. The footnotes are separated from -the rest of the node by a line of dashes with the word -@samp{Footnotes} within it. Each footnote begins with an -@samp{(@var{n})} reference mark.@refill - -@need 700 -@noindent -Here is an example of a single footnote in the end of node style:@refill - -@example -@group - --------- Footnotes --------- - -(1) Here is a sample footnote. -@end group -@end example - -@cindex @samp{@r{Separate}} footnote style -@item -In the `Separate' node style, all the footnotes for a single -node are placed in an automatically constructed node of -their own. In this style, a ``footnote reference'' follows -each @samp{(@var{n})} reference mark in the body of the -node. The footnote reference is actually a cross reference -which you use to reach the footnote node.@refill - -The name of the node containing the footnotes is constructed -by appending @w{@samp{-Footnotes}} to the name of the node -that contains the footnotes. (Consequently, the footnotes' -node for the @file{Footnotes} node is -@w{@file{Footnotes-Footnotes}}!) The footnotes' node has an -`Up' node pointer that leads back to its parent node.@refill - -@noindent -Here is how the first footnote in this manual looks after being -formatted for Info in the separate node style:@refill - -@smallexample -@group -File: texinfo.info Node: Overview-Footnotes, Up: Overview - -(1) Note that the first syllable of "Texinfo" is -pronounced like "speck", not "hex". @dots{} -@end group -@end smallexample -@end itemize - -A Texinfo file may be formatted into an Info file with either footnote -style.@refill - -@findex footnotestyle -Use the @code{@@footnotestyle} command to specify an Info file's -footnote style. Write this command at the beginning of a line followed -by an argument, either @samp{end} for the end node style or -@samp{separate} for the separate node style. - -@need 700 -For example, - -@example -@@footnotestyle end -@end example -@noindent -or -@example -@@footnotestyle separate -@end example - -Write an @code{@@footnotestyle} command before or shortly after the -end-of-header line at the beginning of a Texinfo file. (If you -include the @code{@@footnotestyle} command between the start-of-header -and end-of-header lines, the region formatting commands will format -footnotes as specified.)@refill - -@c !!! changed wording to prevent overfull hbox --bob 26 Mar 93 -If you do not specify a footnote style, the formatting commands use -their default style. Currently, @code{makeinfo} uses the `end' style, -while @code{texinfo-format-buffer} and @code{texinfo-format-region} -use the `separate' style.@refill - -@c !!! note: makeinfo's --footnote-style option overrides footnotestyle -@ignore -If you use @code{makeinfo} to create the Info file, the -@samp{--footnote-style} option determines which style is used, -@samp{end} for the end of node style or @samp{separate} for the -separate node style. Thus, to format the Texinfo manual in the -separate node style, you would use the following shell command:@refill - -@example -makeinfo --footnote-style=separate texinfo.texi -@end example - -@noindent -To format the Texinfo manual in the end of node style, you would -type:@refill - -@example -makeinfo --footnote-style=end texinfo.texi -@end example -@end ignore -@ignore -If you use @code{texinfo-format-buffer} or -@code{texinfo-format-region} to create the Info file, the value of the -@code{texinfo-footnote-style} variable controls the footnote style. -It can be either @samp{"separate"} for the separate node style or -@samp{"end"} for the end of node style. (You can change the value of -this variable with the @kbd{M-x edit-options} command (@pxref{Edit -Options, , Editing Variable Values, emacs, The GNU Emacs Manual}), or -with the @kbd{M-x set-variable} command (@pxref{Examining, , Examining -and Setting Variables, emacs, The GNU Emacs Manual}).@refill - -The @code{texinfo-footnote-style} variable also controls the style if -you use the @kbd{M-x makeinfo-region} or @kbd{M-x makeinfo-buffer} -command in Emacs.@refill -@end ignore -This chapter contains two footnotes.@refill - -@node Conditionals, Format/Print Hardcopy, Footnotes, Top -@comment node-name, next, previous, up -@chapter Conditionally Visible Text -@cindex Conditionally visible text -@cindex Text, conditionally visible -@cindex Visibility of conditional text -@cindex If text conditionally visible -@findex ifinfo -@findex iftex - -Sometimes it is good to use different text for a printed manual and -its corresponding Info file. In this case, you can use the -@dfn{conditional commands} to specify which text is for the printed manual -and which is for the Info file.@refill - -@menu -* Conditional Commands:: How to specify text for Info or @TeX{}. -* Using Ordinary TeX Commands:: You can use any and all @TeX{} commands. -* set clear value:: How to designate which text to format (for - both Info and @TeX{}); and how to set a - flag to a string that you can insert. -@end menu - -@node Conditional Commands, Using Ordinary TeX Commands, , Conditionals -@ifinfo -@heading Using @code{@@ifinfo} and @code{@@iftex} -@end ifinfo - -@code{@@ifinfo} begins segments of text that should be ignored -by @TeX{} when it -typesets the printed manual. The segment of text appears only -in the Info file. -The @code{@@ifinfo} command should appear on a line by itself; end -the Info-only text with a line containing @code{@@end ifinfo} by -itself. At the beginning of a Texinfo file, the Info permissions are -contained within a region marked by @code{@@ifinfo} and @code{@@end -ifinfo}. (@xref{Info Summary and Permissions}.)@refill - -The @code{@@iftex} and @code{@@end iftex} commands are similar to the -@code{@@ifinfo} and @code{@@end ifinfo} commands, except that they -specify text that will appear in the printed manual but not in the Info -file.@refill - -@need 700 -For example, - -@example -@@iftex -This text will appear only in the printed manual. -@@end iftex - -@@ifinfo -However, this text will appear only in Info. -@@end ifinfo -@end example - -@noindent -The preceding example produces the following line: - -@iftex -This text will appear only in the printed manual. -@end iftex - -@ifinfo -However, this text will appear only in Info. -@end ifinfo - -@noindent -Note how you only see one of the two lines, depending on whether you -are reading the Info version or the printed version of this -manual.@refill - -The @code{@@titlepage} command is a special variant of @code{@@iftex} that -is used for making the title and copyright pages of the printed -manual. (@xref{titlepage, , @code{@@titlepage}}.) @refill - -@node Using Ordinary TeX Commands, set clear value, Conditional Commands, Conditionals -@comment node-name, next, previous, up -@section Using Ordinary @TeX{} Commands -@cindex @TeX{} commands, using ordinary -@cindex Ordinary @TeX{} commands, using -@cindex Commands using ordinary @TeX{} -@cindex Plain@TeX{} - -Inside a region delineated by @code{@@iftex} and @code{@@end iftex}, -you can embed some Plain@TeX{} commands. Info will ignore these -commands since they are only in that part of the file which is seen by -@TeX{}. You can write the @TeX{} commands as you would write them in -a normal @TeX{} file, except that you must replace the @samp{\} used -by @TeX{} with an @samp{@@}. For example, in the @code{@@titlepage} -section of a Texinfo file, you can use the @TeX{} command -@code{@@vskip} to format the copyright page. (The @code{@@titlepage} -command causes Info to ignore the region automatically, as it does -with the @code{@@iftex} command.)@refill - -However, many features of Plain@TeX{} will not work, as they are -overridden by features of Texinfo. - -@findex tex -You can enter Plain@TeX{} completely, and use @samp{\} in the @TeX{} -commands, by delineating a region with the @code{@@tex} and @code{@@end -tex} commands. (The @code{@@tex} command also causes Info to ignore the -region, like the @code{@@iftex} -command.)@refill - -@cindex Mathematical expressions -For example, here is a mathematical expression written in -Plain@TeX{}:@refill - -@example -@@tex -$$ \chi^2 = \sum_@{i=1@}^N - \left (y_i - (a + b x_i) - \over \sigma_i\right)^2 $$ -@@end tex -@end example - -@noindent -The output of this example will appear only in a printed manual. If -you are reading this in Info, you will not see anything after this -paragraph. -@iftex -In a printed manual, the above expression looks like -this: -@end iftex - -@tex -$$ \chi^2 = \sum_{i=1}^N - \left(y_i - (a + b x_i) - \over \sigma_i\right)^2 $$ -@end tex - -@node set clear value, , Using Ordinary TeX Commands, Conditionals -@comment node-name, next, previous, up -@section @code{@@set}, @code{@@clear}, and @code{@@value} - -You can direct the Texinfo formatting commands to format or ignore parts -of a Texinfo file with the @code{@@set}, @code{@@clear}, @code{@@ifset}, -and @code{@@ifclear} commands.@refill - -In addition, you can use the @code{@@set @var{flag}} command to set the -value of @var{flag} to a string of characters; and use -@code{@@value@{@var{flag}@}} to insert that string. You can use -@code{@@set}, for example, to set a date and use @code{@@value} to -insert the date in several places in the Texinfo file.@refill - -@menu -* ifset ifclear:: Format a region if a flag is set. -* value:: Replace a flag with a string. -* value Example:: An easy way to update edition information. -@end menu - -@node ifset ifclear, value, , set clear value -@subsection @code{@@ifset} and @code{@@ifclear} - -@findex ifset -When a @var{flag} is set, the Texinfo formatting commands format text -between subsequent pairs of @code{@@ifset @var{flag}} and @code{@@end -ifset} commands. When the @var{flag} is cleared, the Texinfo formatting -commands do @emph{not} format the text. - -Use the @code{@@set @var{flag}} command to turn on, or @dfn{set}, a -@var{flag}; a @dfn{flag} can be any single word. The format for the -command looks like this:@refill -@findex set - -@example -@@set @var{flag} -@end example - -Write the conditionally formatted text between @code{@@ifset @var{flag}} -and @code{@@end ifset} commands, like this:@refill - -@example -@group -@@ifset @var{flag} -@var{conditional-text} -@@end ifset -@end group -@end example - -For example, you can create one document that has two variants, such as -a manual for a `large' and `small' model:@refill - -@example -You can use this machine to dig up shrubs -without hurting them. - -@@set large - -@@ifset large -It can also dig up fully grown trees. -@@end ifset - -Remember to replant promptly @dots{} -@end example - -@noindent -In the example, the formatting commands will format the text between -@code{@@ifset large} and @code{@@end ifset} because the @code{large} -flag is set.@refill - -@findex clear -Use the @code{@@clear @var{flag}} command to turn off, or @dfn{clear}, -a flag. Clearing a flag is the opposite of setting a flag. The -command looks like this:@refill - -@example -@@clear @var{flag} -@end example - -@noindent -Write the command on a line of its own. - -When @var{flag} is cleared, the Texinfo formatting commands do -@emph{not} format the text between @code{@@ifset @var{flag}} and -@code{@@end ifset}; that text is ignored and does not appear in either -printed or Info output.@refill - -For example, if you clear the flag of the preceding example by writing -an @code{@@clear large} command after the @code{@@set large} command -(but before the conditional text), then the Texinfo formatting commands -ignore the text between the @code{@@ifset large} and @code{@@end ifset} -commands. In the formatted output, that text does not appear; in both -printed and Info output, you see only the lines that say, ``You can use -this machine to dig up shrubs without hurting them. Remember to replant -promptly @dots{}''. - -@findex ifclear -If a flag is cleared with an @code{@@clear @var{flag}} command, then -the formatting commands format text between subsequent pairs of -@code{@@ifclear} and @code{@@end ifclear} commands. But if the flag -is set with @code{@@set @var{flag}}, then the formatting commands do -@emph{not} format text between an @code{@@ifclear} and an @code{@@end -ifclear} command; rather, they ignore that text. An @code{@@ifclear} -command looks like this:@refill - -@example -@@ifclear @var{flag} -@end example - -@need 700 -In brief, the commands are:@refill - -@table @code -@item @@set @var{flag} -Tell the Texinfo formatting commands that @var{flag} is set.@refill - -@item @@clear @var{flag} -Tell the Texinfo formatting commands that @var{flag} is cleared.@refill - -@item @@ifset @var{flag} -If @var{flag} is set, tell the Texinfo formatting commands to format -the text up to the following @code{@@end ifset} command.@refill - -If @var{flag} is cleared, tell the Texinfo formatting commands to -ignore text up to the following @code{@@end ifset} command.@refill - -@item @@ifclear @var{flag} -If @var{flag} is set, tell the Texinfo formatting commands to ignore -the text up to the following @code{@@end ifclear} command.@refill - -If @var{flag} is cleared, tell the Texinfo formatting commands to -format the text up to the following @code{@@end ifclear} -command.@refill -@end table - -@node value, value Example, ifset ifclear, set clear value -@subsection @code{@@value} -@findex value - -You can use the @code{@@set} command to specify a value for a flag, -which is expanded by the @code{@@value} command. The value is a string -a characters. - -Write the @code{@@set} command like this: - -@example -@@set foo This is a string. -@end example - -@noindent -This sets the value of @code{foo} to ``This is a string.'' - -The Texinfo formatters replace an @code{@@value@{@var{flag}@}} command with -the string to which @var{flag} is set.@refill - -Thus, when @code{foo} is set as shown above, the Texinfo formatters convert - -@example -@group -@@value@{foo@} -@exdent @r{to} -This is a string. -@end group -@end example - -You can write an @code{@@value} command within a paragraph; but you -must write an @code{@@set} command on a line of its own. - -If you write the @code{@@set} command like this: - -@example -@@set foo -@end example - -@noindent -without specifying a string, the value of @code{foo} is an empty string. - -If you clear a previously set flag with an @code{@@clear @var{flag}} -command, a subsequent @code{@@value@{flag@}} command is invalid and the -string is replaced with an error message that says @samp{@{No value for -"@var{flag}"@}}. - -For example, if you set @code{foo} as follows:@refill - -@example -@@set how-much very, very, very -@end example - -@noindent -then the formatters transform - -@example -@group -It is a @@value@{how-much@} wet day. -@exdent @r{into} -It is a very, very, very wet day. -@end group -@end example - -If you write - -@example -@@clear how-much -@end example - -@noindent -then the formatters transform - -@example -@group -It is a @@value@{how-much@} wet day. -@exdent @r{into} -It is a @{No value for "how-much"@} wet day. -@end group -@end example - -@node value Example, , value, set clear value -@subsection @code{@@value} Example - -You can use the @code{@@value} command to limit the number of places you -need to change when you record an update to a manual. -Here is how it is done in @cite{The GNU Make Manual}: - -@need 1000 -@noindent -Set the flags: - -@example -@group -@@set EDITION 0.35 Beta -@@set VERSION 3.63 Beta -@@set UPDATED 14 August 1992 -@@set UPDATE-MONTH August 1992 -@end group -@end example - -@need 750 -@noindent -Write text for the first @code{@@ifinfo} section, for people reading the -Texinfo file: - -@example -@group -This is Edition @@value@{EDITION@}, -last updated @@value@{UPDATED@}, -of @@cite@{The GNU Make Manual@}, -for @@code@{make@}, Version @@value@{VERSION@}. -@end group -@end example - -@need 1000 -@noindent -Write text for the title page, for people reading the printed manual: -@c List only the month and the year since that looks less fussy on a -@c printed cover than a date that lists the day as well. - -@example -@group -@@title GNU Make -@@subtitle A Program for Directing Recompilation -@@subtitle Edition @@value@{EDITION@}, @dots{} -@@subtitle @@value@{UPDATE-MONTH@} -@end group -@end example - -@noindent -(On a printed cover, a date listing the month and the year looks less -fussy than a date listing the day as well as the month and year.) - -@need 750 -@noindent -Write text for the Top node, for people reading the Info file: - -@example -@group -This is Edition @@value@{EDITION@} -of the @@cite@{GNU Make Manual@}, -last updated @@value@{UPDATED@} -for @@code@{make@} Version @@value@{VERSION@}. -@end group -@end example - -@need 950 -After you format the manual, the text in the first @code{@@ifinfo} -section looks like this: - -@example -@group -This is Edition 0.35 Beta, last updated 14 August 1992, -of `The GNU Make Manual', for `make', Version 3.63 Beta. -@end group -@end example - -When you update the manual, change only the values of the flags; you do -not need to rewrite the three sections. - -@node Format/Print Hardcopy, Create an Info File, Conditionals, Top -@comment node-name, next, previous, up -@chapter Format and Print Hardcopy -@cindex Format and print hardcopy -@cindex Hardcopy, printing it -@cindex Making a printed manual -@cindex Sorting indices -@cindex Indices, sorting -@cindex @TeX{} index sorting -@findex texindex - -There are three major shell commands for making a printed manual from a -Texinfo file: one for converting the Texinfo file into a file that will be -printed, a second for sorting indices, and a third for printing the -formatted document. When you use the shell commands, you can either -work directly in the operating system shell or work within a shell -inside GNU Emacs.@refill - -If you are using GNU Emacs, you can use commands provided by Texinfo -mode instead of shell commands. In addition to the three commands to -format a file, sort the indices, and print the result, Texinfo mode -offers key bindings for commands to recenter the output buffer, show the -print queue, and delete a job from the print queue.@refill - -@menu -* Use TeX:: Use @TeX{} to format for hardcopy. -* Shell Format & Print:: How to format and print a hardcopy manual - with shell commands. -* Within Emacs:: How to format and print from an Emacs shell. -* Texinfo Mode Printing:: How to format and print in Texinfo mode. -* Compile-Command:: How to print using Emacs's compile command. -* Requirements Summary:: @TeX{} formatting requirements summary. -* Preparing for TeX:: What you need to do to use @TeX{}. -* Overfull hboxes:: What are and what to do with overfull hboxes. -* smallbook:: How to print small format books and manuals. -* A4 Paper:: How to print on European A4 paper. -* Cropmarks and Magnification:: How to print marks to indicate the size - of pages and how to print scaled up output. -@end menu - -@node Use TeX, Shell Format & Print, , Format/Print Hardcopy -@ifinfo -@heading Use @TeX{} -@end ifinfo - -The typesetting program called @TeX{} is used for formatting a Texinfo -file. @TeX{} is a very powerful typesetting program and, if used right, -does an exceptionally good job. @xref{Obtaining TeX, , How to Obtain -@TeX{}}, for information on how to obtain @TeX{}.@refill - -The @code{makeinfo}, @code{texinfo-format-region}, and -@code{texinfo-format-buffer} commands read the very same @@-commands -in the Texinfo file as does @TeX{}, but process them differently to -make an Info file; see @ref{Create an Info File}.@refill - -@node Shell Format & Print, Within Emacs, Use TeX, Format/Print Hardcopy -@comment node-name, next, previous, up -@section Format and Print Using Shell Commands - -@cindex DVI file -Format the Texinfo file with the shell command @code{tex} followed by -the name of the Texinfo file. This produces a formatted @sc{dvi} file -as well as several auxiliary files containing indices, cross -references, etc. The @sc{dvi} file (for @dfn{DeVice Independent} -file) can be printed on a wide variety of printers.@refill - -The @code{tex} formatting command itself does not sort the indices; it -writes an output file of unsorted index data. This is a misfeature of -@TeX{}. Hence, to generate a printed index, you first need a sorted -index to work from. The @code{texindex} command sorts indices. (The -source file @file{texindex.c} comes as part of the standard GNU -distribution and is usually installed when Emacs is installed.)@refill -@findex texindex -@ignore -Usage: texindex [-k] [-T tempdir] infile [-o outfile] ... - -Each infile arg can optionally be followed by a `-o outfile' arg; -for each infile that is not followed by a -o arg, the infile name with -`s' (for `sorted') appended is used for the outfile. - --T dir is the directory to put temp files in, instead of /tmp. --k means `keep tempfiles', for debugging. -@end ignore - -The @code{tex} formatting command outputs unsorted index files under -names that obey a standard convention. These names are the name of -your main input file to the @code{tex} formatting command, with -everything after the first period thrown away, and the two letter -names of indices added at the end. For example, the raw index output -files for the input file @file{foo.texinfo} would be @file{foo.cp}, -@file{foo.vr}, @file{foo.fn}, @file{foo.tp}, @file{foo.pg} and -@file{foo.ky}. Those are exactly the arguments to give to -@code{texindex}.@refill - -@need 1000 -Or else, you can use @samp{??} as ``wild-cards'' and give the command in -this form:@refill - -@example -texindex foo.?? -@end example - -@noindent -This command will run @code{texindex} on all the unsorted index files, -including any that you have defined yourself using @code{@@defindex} -or @code{@@defcodeindex}. (You may execute @samp{texindex foo.??} -even if there are similarly named files with two letter extensions -that are not index files, such as @samp{foo.el}. The @code{texindex} -command reports but otherwise ignores such files.)@refill - -For each file specified, @code{texindex} generates a sorted index file -whose name is made by appending @samp{s} to the input file name. The -@code{@@printindex} command knows to look for a file of that name. -@code{texindex} does not alter the raw index output file.@refill - -After you have sorted the indices, you need to rerun the @code{tex} -formatting command on the Texinfo file. This regenerates a formatted -@sc{dvi} file with up-to-date index entries.@footnote{If you use more -than one index and have cross references to an index other than the -first, you must run @code{tex} @emph{three times} to get correct output: -once to generate raw index data; again (after @code{texindex}) to output -the text of the indices and determine their true page numbers; and a -third time to output correct page numbers in cross references to them. -However, cross references to indices are rare.}@refill - -To summarize, this is a three step process: - -@enumerate -@item -Run the @code{tex} formatting command on the Texinfo file. This -generates the formatted @sc{dvi} file as well as the raw index files -with two letter extensions.@refill - -@item -Run the shell command @code{texindex} on the raw index files to sort -them. This creates the corresponding sorted index files.@refill - -@item -Rerun the @code{tex} formatting command on the Texinfo file. This -regenerates a formatted @sc{dvi} file with the index entries in the -correct order. This second run also corrects the page numbers for -the cross references. (The tables of contents are always correct.)@refill -@end enumerate - -You need not run @code{texindex} each time after you run the -@code{tex} formatting. If you do not, on the next run, the @code{tex} -formatting command will use whatever sorted index files happen to -exist from the previous use of @code{texindex}. This is usually -@sc{ok} while you are debugging.@refill - -@findex texi2dvi @r{(shell script)} -Rather than type the @code{tex} and @code{texindex} commands yourself, -you can use @code{texi2dvi}. This shell script is designed to -simplify the @code{tex}---@code{texindex}---@code{tex} sequence by -figuring out whether index files and @sc{dvi} files are up-to-date. -It runs @code{texindex} and @code{tex} only when necessary. - -@need 1000 -The syntax for @code{texi2dvi} is like this (where @samp{%} is the -shell prompt):@refill - -@example -% texi2dvi @var{filename}@dots{} -@end example - -@findex lpr @r{(@sc{dvi} print command)} -Finally, you can print the @sc{dvi} file with the @sc{dvi} print command. -The precise command to use depends on the system; @samp{lpr -d} is -common. The @sc{dvi} print command may require a file name without any -extension or with a @samp{.dvi} extension.@refill - -@need 1200 -The following commands, for example, sort the indices, format, and -print the @cite{Bison Manual} (where @samp{%} is the shell -prompt):@refill - -@example -@group -% tex bison.texinfo -% texindex bison.?? -% tex bison.texinfo -% lpr -d bison.dvi -@end group -@end example - -@noindent -(Remember that the shell commands may be different at your site; but -these are commonly used versions.)@refill - -@node Within Emacs, Texinfo Mode Printing, Shell Format & Print, Format/Print Hardcopy -@comment node-name, next, previous, up -@section From an Emacs Shell @dots{} -@cindex Print, format from Emacs shell -@cindex Format, print from Emacs shell -@cindex Shell, format, print from -@cindex Emacs shell, format, print from -@cindex GNU Emacs shell, format, print from - -You can give formatting and printing commands from a shell within GNU -Emacs. To create a shell within Emacs, type @kbd{M-x shell}. In this -shell, you can format and print the document. @xref{Shell Format & Print, , -How to Format and Print Using Shell Commands}, for details.@refill - -You can switch to and from the shell buffer while @code{tex} is -running and do other editing. If you are formatting a long document -on a slow machine, this can be very convenient.@refill - -You can also use @code{texi2dvi} from an Emacs shell. For example, -here is how to use @code{texi2dvi} to format and print @cite{Using and -Porting GNU CC} from a shell within Emacs (where @samp{%} is the shell -prompt):@refill - -@example -@group -% texi2dvi gcc.texinfo -% lpr -d gcc.dvi -@end group -@end example -@ifinfo - -@xref{Texinfo Mode Printing}, for more information about formatting -and printing in Texinfo mode.@refill -@end ifinfo - -@node Texinfo Mode Printing, Compile-Command, Within Emacs, Format/Print Hardcopy -@section Formatting and Printing in Texinfo Mode -@cindex Region printing in Texinfo mode -@cindex Format and print in Texinfo mode -@cindex Print and format in Texinfo mode - -Texinfo mode provides several predefined key commands for @TeX{} -formatting and printing. These include commands for sorting indices, -looking at the printer queue, killing the formatting job, and -recentering the display of the buffer in which the operations -occur.@refill - -@table @kbd -@item C-c C-t C-r -@itemx M-x texinfo-tex-region -Run @TeX{} on the current region.@refill - -@item C-c C-t C-b -@itemx M-x texinfo-tex-buffer -Run @TeX{} on the current buffer.@refill - -@c !!! changed wording to prevent overfull hbox --bob 26 Mar 93 -@item C-c C-t C-i -@itemx M-x texinfo-texindex -Sort the indices of a Texinfo file that have been formatted with -@code{texinfo-tex-region} or @code{texinfo-tex-buffer}.@refill - -@item C-c C-t C-p -@itemx M-x texinfo-tex-print -Print a @sc{dvi} file that was made with @code{texinfo-tex-region} or -@code{texinfo-tex-buffer}.@refill - -@item C-c C-t C-q -@itemx M-x texinfo-show-tex-print-queue -Show the print queue.@refill - -@item C-c C-t C-d -@itemx M-x texinfo-delete-from-tex-print-queue -Delete a job from the print queue; you will be prompted for the job -number shown by a preceding @kbd{C-c C-t C-q} command -(@code{texinfo-show-tex-print-queue}).@refill - -@c !!! changed wording to prevent overfull hbox --bob 26 Mar 93 -@item C-c C-t C-k -@itemx M-x texinfo-kill-tex-job -Kill either the currently running @TeX{} job that has been started by -@code{texinfo-tex-region} or @code{texinfo-tex-buffer}, or any other -process running in the Texinfo shell buffer.@refill - -@item C-c C-t C-x -@itemx M-x texinfo-quit-tex-job -Quit a @TeX{} formatting job that has stopped because of an error by -sending an @key{x} to it. When you do this, @TeX{} preserves a record -of what it did in a @file{.log} file.@refill - -@item C-c C-t C-l -@itemx M-x texinfo-recenter-tex-output-buffer -Redisplay the shell buffer in which the @TeX{} printing and formatting -commands are run to show its most recent output.@refill -@end table - -Thus, the usual sequence of commands for formatting a buffer is as -follows (with comments to the right):@refill - -@example -@group -C-c C-t C-b @r{Run @TeX{} on the buffer.} -C-c C-t C-i @r{Sort the indices.} -C-c C-t C-b @r{Rerun @TeX{} to regenerate indices.} -C-c C-t C-p @r{Print the @sc{dvi} file.} -C-c C-t C-q @r{Display the printer queue.} -@end group -@end example - -The Texinfo mode @TeX{} formatting commands start a subshell in Emacs -called the @file{*texinfo-tex-shell*}. The @code{texinfo-tex-command}, -@code{texinfo-texindex-command}, and @code{tex-dvi-print-command} -commands are all run in this shell. - -You can watch the commands operate in the @samp{*texinfo-tex-shell*} buffer, -and you can switch to and from and use the @samp{*texinfo-tex-shell*} buffer -as you would any other shell buffer.@refill - -@need 1500 -The formatting and print commands depend on the values of several variables. -The default values are:@refill - -@sp 1 -@example -@group - @r{Variable} @r{Default value} - -texinfo-tex-command "tex" -texinfo-texindex-command "texindex" -texinfo-tex-shell-cd-command "cd" -texinfo-tex-dvi-print-command "lpr -d" -texinfo-show-tex-queue-command "lpq" -texinfo-delete-from-print-queue-command "lprm" -texinfo-start-of-header "%**start" -texinfo-end-of-header "%**end" -texinfo-tex-trailer "@@bye" -@end group -@end example - -@c !!! changed wording to prevent overfull hbox --bob 26 Mar 93 -The default values of both the @code{texinfo-tex-command} and the -@code{texinfo-texindex-command} variables are set in the @file{texnfo-tex.el} -file.@refill - -You can change the values of these variables with the @kbd{M-x -edit-options} command (@pxref{Edit Options, , Editing Variable Values, -emacs, The GNU Emacs Manual}), with the @kbd{M-x set-variable} command -(@pxref{Examining, , Examining and Setting Variables, emacs, The GNU -Emacs Manual}), or with your @file{.emacs} initialization file -(@pxref{Init File, , , emacs, The GNU Emacs Manual}).@refill - -@node Compile-Command, Requirements Summary, Texinfo Mode Printing, Format/Print Hardcopy -@comment node-name, next, previous, up -@section Using the Local Variables List -@cindex Local variables -@cindex Compile command for formatting -@cindex Format with the compile command - -Yet another way to apply the @TeX{} formatting command to a Texinfo -file is to put that command in a @dfn{local variables list} at the end -of the Texinfo file. You can then specify the @TeX{} formatting -command as a @code{compile-command} and have Emacs run the @TeX{} -formatting command by typing @kbd{M-x compile}. This creates a -special shell called the @samp{*compilation buffer*} in which Emacs -runs the compile command. For example, at the end of the -@file{gdb.texinfo} file, after the @code{@@bye}, you would put the -following:@refill - -@example -@@c Local Variables: -@@c compile-command: "tex gdb.texinfo" -@@c End: -@end example - -@noindent -This technique is most often used by programmers who also compile programs -this way; see @ref{Compilation, , , emacs, The GNU Emacs Manual}.@refill - -@node Requirements Summary, Preparing for TeX, Compile-Command, Format/Print Hardcopy -@comment node-name, next, previous, up -@section @TeX{} Formatting Requirements Summary -@cindex Requirements for formatting -@cindex Formatting requirements - -Every Texinfo file that is to be input to @TeX{} must begin with a -@code{\input} command and contain an @code{@@settitle} command:@refill - -@example -\input texinfo -@@settitle @var{name-of-manual} -@end example - -@noindent -The first command instructs @TeX{} to load the macros it needs to -process a Texinfo file and the second command specifies the title of -printed manual.@refill - -@need 1000 -Every Texinfo file must end with a line that terminates @TeX{} -processing and forces out unfinished pages:@refill - -@example -@@bye -@end example - -Strictly speaking, these three lines are all a Texinfo file needs for -@TeX{}, besides the body. (The @code{@@setfilename} line is the only -line that a Texinfo file needs for Info formatting.)@refill - -Usually, the file's first line contains an @samp{@@c -*-texinfo-*-} -comment that causes Emacs to switch to Texinfo mode when you edit the -file. In addition, the beginning usually includes an -@code{@@setfilename} for Info formatting, an @code{@@setchapternewpage} -command, a title page, a copyright page, and permissions. Besides an -@code{@@bye}, the end of a file usually includes indices and a table of -contents.@refill - -@iftex -For more information, see -@ref{setchapternewpage, , @code{@@setchapternewpage}}, -@ref{Headings, ,Page Headings}, -@ref{Titlepage & Copyright Page}, -@ref{Printing Indices & Menus}, and -@ref{Contents}. -@end iftex -@noindent -@ifinfo -For more information, see@* -@ref{setchapternewpage, , @code{@@setchapternewpage}},@* -@ref{Headings, ,Page Headings},@* -@ref{Titlepage & Copyright Page},@* -@ref{Printing Indices & Menus}, and@* -@ref{Contents}. -@end ifinfo - -@node Preparing for TeX, Overfull hboxes, Requirements Summary, Format/Print Hardcopy -@comment node-name, next, previous, up -@section Preparing to Use @TeX{} -@cindex Preparing to use @TeX{} -@cindex @TeX{} input initialization -@cindex @code{TEXINPUTS} environment variable -@vindex TEXINPUTS -@cindex @b{.profile} initialization file -@cindex @b{.cshrc} initialization file -@cindex Initialization file for @TeX{} input - -@TeX{} needs to know where to find the @file{texinfo.tex} file -that you have told it to input with the @samp{\input texinfo} command -at the beginning of the first line. The @file{texinfo.tex} file tells -@TeX{} how to handle @@-commands. (@file{texinfo.tex} is -included in the standard GNU distributions.)@refill - -Usually, the @file{texinfo.tex} file is put in the default directory -that contains @TeX{} macros (the @file{/usr/lib/tex/macros} -directory) when GNU Emacs or other GNU software is installed. -In this case, @TeX{} will -find the file and you do not need to do anything special. -Alternatively, you can put @file{texinfo.tex} in the directory in -which the Texinfo source file is located, and @TeX{} will find it -there.@refill - -However, you may want to specify the location of the @code{\input} file -yourself. One way to do this is to write the complete path for the file -after the @code{\input} command. Another way is to set the -@code{TEXINPUTS} environment variable in your @file{.cshrc} or -@file{.profile} file. The @code{TEXINPUTS} environment variable will tell -@TeX{} where to find the @file{texinfo.tex} file and any other file that -you might want @TeX{} to use.@refill - -Whether you use a @file{.cshrc} or @file{.profile} file depends on -whether you use @code{csh}, @code{sh}, or @code{bash} for your shell -command interpreter. When you use @code{csh}, it looks to the -@file{.cshrc} file for initialization information, and when you use -@code{sh} or @code{bash}, it looks to the @file{.profile} file.@refill - -@need 1000 -In a @file{.cshrc} file, you could use the following @code{csh} command -sequence:@refill - -@example -setenv TEXINPUTS .:/usr/me/mylib:/usr/lib/tex/macros -@end example - -@need 1000 -In a @file{.profile} file, you could use the following @code{sh} command -sequence: - -@example -@group -TEXINPUTS=.:/usr/me/mylib:/usr/lib/tex/macros -export TEXINPUTS -@end group -@end example - -@noindent -This would cause @TeX{} to look for @file{\input} file first in the current -directory, indicated by the @samp{.}, then in a hypothetical user's -@file{me/mylib} directory, and finally in the system library.@refill - -@node Overfull hboxes, smallbook, Preparing for TeX, Format/Print Hardcopy -@comment node-name, next, previous, up -@section Overfull ``hboxes'' -@cindex Overfull @samp{hboxes} -@cindex @samp{hboxes}, overfull -@cindex Final output - -@TeX{} is sometimes unable to typeset a line without extending it into -the right margin. This can occur when @TeX{} comes upon what it -interprets as a long word that it cannot hyphenate, such as an -electronic mail network address or a very long title. When this -happens, @TeX{} prints an error message like this:@refill - -@example -Overfull \hbox (20.76302pt too wide) -@end example - -@noindent -(In @TeX{}, lines are in ``horizontal boxes'', hence the term, ``hbox''. -The backslash, @samp{\}, is the @TeX{} equivalent of @samp{@@}.)@refill - -@TeX{} also provides the line number in the Texinfo source file and -the text of the offending line, which is marked at all the places that -@TeX{} knows how to hyphenate words. -@xref{Debugging with TeX, , Catching Errors with @TeX{} Formatting}, -for more information about typesetting errors.@refill - -If the Texinfo file has an overfull hbox, you can rewrite the sentence -so the overfull hbox does not occur, or you can decide to leave it. A -small excursion into the right margin often does not matter and may not -even be noticeable.@refill - -@cindex Black rectangle in hardcopy -@cindex Rectangle, ugly, black in hardcopy -However, unless told otherwise, @TeX{} will print a large, ugly, black -rectangle beside the line that contains the overful hbox. This is so -you will notice the location of the problem if you are correcting a -draft.@refill - -@need 1000 -@findex finalout -To prevent such a monstrosity from marring your final printout, write -the following in the beginning of the Texinfo file on a line of its own, -before the @code{@@titlepage} command:@refill - -@example -@@finalout -@end example - -@node smallbook, A4 Paper, Overfull hboxes, Format/Print Hardcopy -@comment node-name, next, previous, up -@section Printing ``Small'' Books -@findex smallbook -@cindex Small book size -@cindex Book, printing small -@cindex Page sizes for books -@cindex Size of printed book - -By default, @TeX{} typesets pages for printing in an 8.5 by 11 inch -format. However, you can direct @TeX{} to typeset a document in a 7 by -9.25 inch format that is suitable for bound books by inserting the -following command on a line by itself at the beginning of the Texinfo -file, before the title page:@refill - -@example -@@smallbook -@end example - -@noindent -(Since regular sized books are often about 7 by 9.25 inches, this -command might better have been called the @code{@@regularbooksize} -command, but it came to be called the @code{@@smallbook} command by -comparison to the 8.5 by 11 inch format.)@refill - -If you write the @code{@@smallbook} command between the -start-of-header and end-of-header lines, the Texinfo mode @TeX{} -region formatting command, @code{texinfo-tex-region}, will format the -region in ``small'' book size (@pxref{Start of Header}).@refill - -The Free Software Foundation distributes printed copies of @cite{The GNU -Emacs Manual} and other manuals in the ``small'' book size. -@xref{smallexample & smalllisp, , @code{@@smallexample} and -@code{@@smalllisp}}, for information about commands that make it easier -to produce examples for a smaller manual.@refill - -@node A4 Paper, Cropmarks and Magnification, smallbook, Format/Print Hardcopy -@comment node-name, next, previous, up -@section Printing on A4 Paper -@cindex A4 paper, printing on -@cindex Paper size, European A4 -@cindex European A4 paper -@findex afourpaper - -You can tell @TeX{} to typeset a document for printing on European size -A4 paper with the @code{@@afourpaper} command. Write the command on a -line by itself between @code{@@iftex} and @code{@@end iftex} lines near -the beginning of the Texinfo file, before the title page:@refill - -For example, this is how you would write the header for this manual:@refill - -@example -@group -\input texinfo @@c -*-texinfo-*- -@@c %**start of header -@@setfilename texinfo -@@settitle Texinfo -@@syncodeindex vr fn -@@iftex -@@afourpaper -@@end iftex -@@c %**end of header -@end group -@end example - -@node Cropmarks and Magnification, , A4 Paper, Format/Print Hardcopy -@comment node-name, next, previous, up -@section Cropmarks and Magnification - -@findex cropmarks -@cindex Cropmarks for printing -@cindex Printing cropmarks -You can attempt to direct @TeX{} to print cropmarks at the corners of -pages with the @code{@@cropmarks} command. Write the @code{@@cropmarks} -command on a line by itself between @code{@@iftex} and @code{@@end -iftex} lines near the beginning of the Texinfo file, before the title -page, like this:@refill - -@example -@group -@@iftex -@@cropmarks -@@end iftex -@end group -@end example - -This command is mainly for printers that typeset several pages on one -sheet of film; but you can attempt to use it to mark the corners of a -book set to 7 by 9.25 inches with the @code{@@smallbook} command. -(Printers will not produce cropmarks for regular sized output that is -printed on regular sized paper.) Since different printing machines work -in different ways, you should explore the use of this command with a -spirit of adventure. You may have to redefine the command in the -@file{texinfo.tex} definitions file.@refill - -@findex mag @r{(@TeX{} command)} -@cindex Magnified printing -@cindex Larger or smaller pages -You can attempt to direct @TeX{} to typeset pages larger or smaller than -usual with the @code{\mag} @TeX{} command. Everything that is typeset -is scaled proportionally larger or smaller. (@code{\mag} stands for -``magnification''.) This is @emph{not} a Texinfo @@-command, but is a -Plain@TeX{} command that is prefixed with a backslash. You have to -write this command between @code{@@tex} and @code{@@end tex} -(@pxref{Using Ordinary TeX Commands, , Using Ordinary @TeX{} -Commands}).@refill - -Follow the @code{\mag} command with an @samp{=} and then a number that -is 1000 times the magnification you desire. For example, to print pages -at 1.2 normal size, write the following near the beginning of the -Texinfo file, before the title page:@refill - -@example -@group -@@tex -\mag=1200 -@@end tex -@end group -@end example - -With some printing technologies, you can print normal-sized copies that -look better than usual by using a larger-than-normal master.@refill - -Depending on your system, @code{\mag} may not work or may work only at -certain magnifications. Be prepared to experiment.@refill - -@node Create an Info File, Install an Info File, Format/Print Hardcopy, Top -@comment node-name, next, previous, up -@chapter Creating an Info File -@cindex Creating an Info file -@cindex Info, creating an on-line file -@cindex Formatting a file for Info - -@code{makeinfo} is a utility that converts a Texinfo file into an Info -file; @code{texinfo-format-region} and @code{texinfo-format-buffer} are -GNU Emacs functions that do the same.@refill - -A Texinfo file must possess an @code{@@setfilename} line near its -beginning, otherwise the Info formatting commands will fail.@refill - -For information on installing the Info file in the Info system, see -@ref{Install an Info File}.@refill - -@menu -* makeinfo advantages:: @code{makeinfo} provides better error checking. -* Invoking makeinfo:: How to run @code{makeinfo} from a shell. -* makeinfo options:: Specify fill-column and other options. -* Pointer Validation:: How to check that pointers point somewhere. -* makeinfo in Emacs:: How to run @code{makeinfo} from Emacs. -* texinfo-format commands:: Two Info formatting commands written - in Emacs Lisp are an alternative - to @code{makeinfo}. -* Batch Formatting:: How to format for Info in Emacs Batch mode. -* Tag and Split Files:: How tagged and split files help Info - to run better. -@end menu - -@node makeinfo advantages, Invoking makeinfo, , Create an Info File -@ifinfo -@heading @code{makeinfo} Preferred -@end ifinfo - -The @code{makeinfo} utility creates an Info file from a Texinfo source -file more quickly than either of the Emacs formatting commands and -provides better error messages. We recommend it. @code{makeinfo} is a -C program that is independent of Emacs. You do not need to run Emacs to -use @code{makeinfo}, which means you can use @code{makeinfo} on machines -that are too small to run Emacs. You can run @code{makeinfo} in -any one of three ways: from an operating system shell, from a shell -inside Emacs, or by typing a key command in Texinfo mode in Emacs. -@refill - -The @code{texinfo-format-region} and the @code{texinfo-format-buffer} -commands are useful if you cannot run @code{makeinfo}. Also, in some -circumstances, they format short regions or buffers more quickly than -@code{makeinfo}.@refill - -@node Invoking makeinfo, makeinfo options, makeinfo advantages, Create an Info File -@section Invoking @code{makeinfo} from a Shell - -To create an Info file from a Texinfo file, type @code{makeinfo} -followed by the name of the Texinfo file. Thus, to create the Info -file for Bison, type the following at the shell prompt (where @samp{%} -is the prompt):@refill - -@example -% makeinfo bison.texinfo -@end example - -(You can run a shell inside Emacs by typing @kbd{M-x -shell}.)@refill - -@ifinfo -Sometimes you will want to specify options. For example, if you wish -to discover which version of @code{makeinfo} you are using, -type:@refill - -@example -% makeinfo --version -@end example - -@xref{makeinfo options}, for more information. -@end ifinfo - -@node makeinfo options, Pointer Validation, Invoking makeinfo, Create an Info File -@comment node-name, next, previous, up -@section Options for @code{makeinfo} -@cindex @code{makeinfo} options -@cindex Options for @code{makeinfo} - -The @code{makeinfo} command takes a number of options. Most often, -options are used to set the value of the fill column and specify the -footnote style. Each command line option is a word preceded by -@samp{--}@footnote{@samp{--} has replaced @samp{+}, the old introductory -character, to maintain POSIX.2 compatibility without losing long-named -options.} or a letter preceded by @samp{-}. You can use abbreviations -for the option names as long as they are unique.@refill - -For example, you could use the following command to create an Info -file for @file{bison.texinfo} in which each line is filled to only 68 -columns (where @samp{%} is the prompt):@refill - -@example -% makeinfo --fill-column=68 bison.texinfo -@end example - -You can write two or more options in sequence, like this:@refill - -@example -% makeinfo --no-split --fill-column=70 @dots{} -@end example - -@noindent -This would keep the Info file together as one possibly very long -file and would also set the fill column to 70.@refill - -@iftex -If you wish to discover which version of @code{makeinfo} -you are using, type:@refill - -@example -% makeinfo --version -@end example -@end iftex - -The options are:@refill - -@need 100 -@table @code -@item -D @var{var} -Cause @var{var} to be defined. This is equivalent to -@code{@@set @var{var}} in the Texinfo file. - -@need 150 -@item --error-limit @var{limit} -Set the maximum number of errors that @code{makeinfo} will report -before exiting (on the assumption that continuing would be useless). -The default number of errors that can be reported before -@code{makeinfo} gives up is 100.@refill - -@need 150 -@item --fill-column @var{width} -Specify the maximum number of columns in a line; this is the right-hand -edge of a line. Paragraphs that are filled will be filled to this -width. (Filling is the process of breaking up and connecting lines so -that lines are the same length as or shorter than the number specified -as the fill column. Lines are broken between words.) The default value -for @code{fill-column} is 72. -@refill - -@item --footnote-style @var{style} -Set the footnote style to @var{style}, either @samp{end} for the end -node style or @samp{separate} for the separate node style. The value -set by this option overrides the value set in a Texinfo file by an -@code{@@footnotestyle} command. When the footnote style is -@samp{separate}, @code{makeinfo} makes a new node containing the -footnotes found in the current node. When the footnote style is -@samp{end}, @code{makeinfo} places the footnote references at the end -of the current node.@refill - -@need 150 -@item -I @var{dir} -Add @code{dir} to the directory search list for finding files that are -included using the @code{@@include} command. By default, -@code{makeinfo} searches only the current directory. - -@need 150 -@item --no-headers -Do not include menus or node lines in the output. This results in an -@sc{ascii} file that you cannot read in Info since it does not contain -the requisite nodes or menus; but you can print such a file in a -single, typewriter-like font and produce acceptable output. - -@need 150 -@item --no-split -Suppress the splitting stage of @code{makeinfo}. Normally, large -output files (where the size is greater than 70k bytes) are split into -smaller subfiles, each one approximately 50k bytes. If you specify -@samp{--no-split}, @code{makeinfo} will not split up the output -file.@refill - -@need 100 -@item --no-pointer-validate -@item --no-validate -Suppress the pointer-validation phase of @code{makeinfo}. Normally, -after a Texinfo file is processed, some consistency checks are made to -ensure that cross references can be resolved, etc. -@xref{Pointer Validation}.@refill - -@need 150 -@item --no-warn -Suppress the output of warning messages. This does @emph{not} -suppress the output of error messages, only warnings. You might -want this if the file you are creating has examples of Texinfo cross -references within it, and the nodes that are referenced do not actually -exist.@refill - -@item --no-number-footnotes -Supress automatic footnote numbering. By default, @code{makeinfo} -numbers each footnote sequentially in a single node, resetting the -current footnote number to 1 at the start of each node. - -@need 150 -@item --output @var{file} -@itemx -o @var{file} -Specify that the output should be directed to @var{file} and not to the -file name specified in the @code{@@setfilename} command found in the Texinfo -source. @var{file} can be the special token @samp{-}, which specifies -standard output. - -@need 150 -@item --paragraph-indent @var{indent} -Set the paragraph indentation style to @var{indent}. The value set by -this option overrides the value set in a Texinfo file by an -@code{@@paragraphindent} command. The value of @var{indent} is -interpreted as follows:@refill - -@itemize @bullet -@item -If the value of @var{indent} is @samp{asis}, do not change the -existing indentation at the starts of paragraphs.@refill - -@item -If the value of @var{indent} is zero, delete any existing -indentation.@refill - -@item -If the value of @var{indent} is greater than zero, indent each -paragraph by that number of spaces.@refill -@end itemize - -@need 100 -@item --reference-limit @var{limit} -Set the value of the number of references to a node that -@code{makeinfo} will make without reporting a warning. If a node has more -than this number of references in it, @code{makeinfo} will make the -references but also report a warning.@refill - -@need 150 -@item -U @var{var} -Cause @var{var} to be undefined. This is equivalent to -@code{@@clear @var{var}} in the Texinfo file. - -@need 100 -@item --verbose -Cause @code{makeinfo} to display messages saying what it is doing. -Normally, @code{makeinfo} only outputs messages if there are errors or -warnings.@refill - -@need 100 -@item --version -Report the version number of this copy of @code{makeinfo}.@refill -@end table - -@node Pointer Validation, makeinfo in Emacs, makeinfo options, Create an Info File -@section Pointer Validation -@cindex Pointer validation with @code{makeinfo} -@cindex Validation of pointers - -@c !!! changed wording to prevent overfull hbox --bob 26 Mar 93 -@code{makeinfo} will check the validity of the final Info file unless -you suppress pointer-validation by using the -@samp{--no-pointer-validation} option. Mostly, this means ensuring -that nodes you have referenced really exist. Here is a complete list -of what is checked:@refill - -@enumerate -@item -If a `Next', `Previous', or `Up' node reference is a reference to a -node in the current file and is not an external reference such as to -@file{(dir)}, then the referenced node must exist.@refill - -@item -In every node, if the `Previous' node is different from the `Up' node, -then the `Previous' node must also be pointed to by a `Next' node.@refill - -@item -Every node except the `Top' node must have an `Up' pointer.@refill - -@item -The node referenced by an `Up' pointer must contain a reference to the -current node in some manner other than through a `Next' reference. -This includes menu entries and cross references.@refill - -@item -If the `Next' reference of a node is not the same as the `Next' reference -of the `Up' reference, then the node referenced by the `Next' pointer -must have a `Previous' pointer that points back to the current node. -This rule allows the last node in a section to point to the first node -of the next chapter.@refill -@end enumerate - -@node makeinfo in Emacs, texinfo-format commands, Pointer Validation, Create an Info File -@section Running @code{makeinfo} inside Emacs -@cindex Running @code{makeinfo} in Emacs -@cindex @code{makeinfo} inside Emacs -@cindex Shell, running @code{makeinfo} in - -You can run @code{makeinfo} in GNU Emacs Texinfo mode by using either the -@code{makeinfo-region} or the @code{makeinfo-buffer} commands. In -Texinfo mode, the commands are bound to @kbd{C-c C-m C-r} and @kbd{C-c -C-m C-b} by default.@refill - -@table @kbd -@item C-c C-m C-r -@itemx M-x makeinfo-region -Format the current region for Info.@refill -@findex makeinfo-region - -@item C-c C-m C-b -@itemx M-x makeinfo-buffer -Format the current buffer for Info.@refill -@findex makeinfo-buffer -@end table - -When you invoke either @code{makeinfo-region} or -@code{makeinfo-buffer}, Emacs prompts for a file name, offering the -name of the visited file as the default. You can edit the default -file name in the minibuffer if you wish, before typing @key{RET} to -start the @code{makeinfo} process.@refill - -The Emacs @code{makeinfo-region} and @code{makeinfo-buffer} commands -run the @code{makeinfo} program in a temporary shell buffer. If -@code{makeinfo} finds any errors, Emacs displays the error messages in -the temporary buffer.@refill - -@cindex Errors, parsing -@cindex Parsing errors -@findex next-error -You can parse the error messages by typing @kbd{C-x `} -(@code{next-error}). This causes Emacs to go to and position the -cursor on the line in the Texinfo source that @code{makeinfo} thinks -caused the error. @xref{Compilation, , Running @code{make} or -Compilers Generally, emacs, The GNU Emacs Manual}, for more -information about using the @code{next-error} command.@refill - -In addition, you can kill the shell in which the @code{makeinfo} -command is running or make the shell buffer display its most recent -output.@refill - - -@c !!! changed wording to prevent overfull hbox --bob 26 Mar 93 -@table @kbd -@item C-c C-m C-k -@itemx M-x makeinfo-kill-job -@findex makeinfo-kill-job -Kill the currently running job created by -@code{makeinfo-region} or @code{makeinfo-buffer}.@refill - -@item C-c C-m C-l -@itemx M-x makeinfo-recenter-output-buffer -@findex makeinfo-recenter-output-buffer -Redisplay the @code{makeinfo} shell buffer to display its most recent -output.@refill -@end table - -@noindent -(Note that the parallel commands for killing and recentering a @TeX{} -job are @kbd{C-c C-t C-k} and @kbd{C-c C-t C-l}. @xref{Texinfo Mode -Printing}.)@refill - -You can specify options for @code{makeinfo} by setting the -@code{makeinfo-options} variable with either the @kbd{M-x -edit-options} or the @kbd{M-x set-variable} command, or by setting the -variable in your @file{.emacs} initialization file.@refill - -For example, you could write the following in your @file{.emacs} file:@refill - -@example -@group -(setq makeinfo-options - "--paragraph-indent=0 --no-split - --fill-column=70 --verbose") -@end group -@end example - -@c If you write these three cross references using xref, you see -@c three references to the same named manual, which looks strange. -@iftex -For more information, see @ref{makeinfo options, , Options for -@code{makeinfo}}, as well as ``Editing Variable Values,''``Examining and -Setting Variables,'' and ``Init File'' in the @cite{The GNU Emacs -Manual}. -@end iftex -@noindent -@ifinfo -For more information, see@* -@ref{Edit Options, , Editing Variable Values, emacs, The GNU Emacs Manual},@* -@ref{Examining, , Examining and Setting Variables, emacs, The GNU Emacs Manual},@* -@ref{Init File, , , emacs, The GNU Emacs Manual}, and@* -@ref{makeinfo options, , Options for @code{makeinfo}}. -@end ifinfo - -@node texinfo-format commands, Batch Formatting, makeinfo in Emacs, Create an Info File -@comment node-name, next, previous, up -@section The @code{texinfo-format@dots{}} Commands -@findex texinfo-format-region -@findex texinfo-format-buffer - -In GNU Emacs in Texinfo mode, you can format part or all of a Texinfo -file with the @code{texinfo-format-region} command. This formats the -current region and displays the formatted text in a temporary buffer -called @samp{*Info Region*}.@refill - -Similarly, you can format a buffer with the -@code{texinfo-format-buffer} command. This command creates a new -buffer and generates the Info file in it. Typing @kbd{C-x C-s} will -save the Info file under the name specified by the -@code{@@setfilename} line which must be near the beginning of the -Texinfo file.@refill - -@table @kbd -@item C-c C-e C-r -@itemx @code{texinfo-format-region} -Format the current region for Info. -@findex texinfo-format-region - -@item C-c C-e C-b -@itemx @code{texinfo-format-buffer} -Format the current buffer for Info. -@findex texinfo-format-buffer -@end table - -The @code{texinfo-format-region} and @code{texinfo-format-buffer} -commands provide you with some error checking, and other functions can -provide you with further help in finding formatting errors. These -procedures are described in an appendix; see @ref{Catching Mistakes}. -However, the @code{makeinfo} program is often faster and -provides better error checking (@pxref{makeinfo in Emacs}).@refill - -@node Batch Formatting, Tag and Split Files, texinfo-format commands, Create an Info File -@comment node-name, next, previous, up -@section Batch Formatting -@cindex Batch formatting for Info -@cindex Info batch formatting - -You can format Texinfo files for Info using @code{batch-texinfo-format} -and Emacs Batch mode. You can run Emacs in Batch mode from any shell, -including a shell inside of Emacs. (@xref{Command Switches, , Command -Line Switches and Arguments, emacs, The GNU Emacs Manual}.)@refill - -Here is the command to format all the files that end in @file{.texinfo} -in the current directory (where @samp{%} is the shell prompt):@refill - -@example -% emacs -batch -funcall batch-texinfo-format *.texinfo -@end example - -@noindent -Emacs processes all the files listed on the command line, even if an -error occurs while attempting to format some of them.@refill - -Run @code{batch-texinfo-format} only with Emacs in Batch mode as shown; -it is not interactive. It kills the Batch mode Emacs on completion.@refill - -@code{batch-texinfo-format} is convenient if you lack @code{makeinfo} -and want to format several Texinfo files at once. When you use Batch -mode, you create a new Emacs process. This frees your current Emacs, so -you can continue working in it. (When you run -@code{texinfo-format-region} or @code{texinfo-format-buffer}, you cannot -use that Emacs for anything else until the command finishes.)@refill - -@node Tag and Split Files, , Batch Formatting, Create an Info File -@comment node-name, next, previous, up -@section Tag Files and Split Files -@cindex Making a tag table automatically -@cindex Tag table, making automatically - -If a Texinfo file has more than 30,000 bytes, -@code{texinfo-format-buffer} automatically creates a tag table -for its Info file; @code{makeinfo} always creates a tag table. With -a @dfn{tag table}, Info can jump to new nodes more quickly than it can -otherwise.@refill - -@cindex Indirect subfiles -In addition, if the Texinfo file contains more than about 70,000 -bytes, @code{texinfo-format-buffer} and @code{makeinfo} split the -large Info file into shorter @dfn{indirect} subfiles of about 50,000 -bytes each. Big files are split into smaller files so that Emacs does -not need to make a large buffer to hold the whole of a large Info -file; instead, Emacs allocates just enough memory for the small, split -off file that is needed at the time. This way, Emacs avoids wasting -memory when you run Info. (Before splitting was implemented, Info -files were always kept short and @dfn{include files} were designed as -a way to create a single, large printed manual out of the smaller Info -files. @xref{Include Files}, for more information. Include files are -still used for very large documents, such as @cite{The Emacs Lisp -Reference Manual}, in which each chapter is a separate file.)@refill - -When a file is split, Info itself makes use of a shortened version of -the original file that contains just the tag table and references to -the files that were split off. The split off files are called -@dfn{indirect} files.@refill - -The split off files have names that are created by appending @w{@samp{-1}}, -@w{@samp{-2}}, @w{@samp{-3}} and so on to the file name specified by the -@code{@@setfilename} command. The shortened version of the original file -continues to have the name specified by @code{@@setfilename}.@refill - -At one stage in writing this document, for example, the Info file was saved -as @file{test-texinfo} and that file looked like this:@refill - -@example -@group -Info file: test-texinfo, -*-Text-*- -produced by texinfo-format-buffer -from file: new-texinfo-manual.texinfo - -^_ -Indirect: -test-texinfo-1: 102 -test-texinfo-2: 50422 -test-texinfo-3: 101300 -^_^L -Tag table: -(Indirect) -Node: overview^?104 -Node: info file^?1271 -Node: printed manual^?4853 -Node: conventions^?6855 -@dots{} -@end group -@end example - -@noindent -(But @file{test-texinfo} had far more nodes than are shown here.) Each of -the split off, indirect files, @file{test-texinfo-1}, -@file{test-texinfo-2}, and @file{test-texinfo-3}, is listed in this file -after the line that says @samp{Indirect:}. The tag table is listed after -the line that says @samp{Tag table:}. @refill - -In the list of indirect files, the number following the file name -records the cumulative number of bytes in the preceding indirect files, -not counting the file list itself, the tag table, or the permissions -text in each file. In the tag table, the number following the node name -records the location of the beginning of the node, in bytes from the -beginning.@refill - -If you are using @code{texinfo-format-buffer} to create Info files, -you may want to run the @code{Info-validate} command. (The -@code{makeinfo} command does such a good job on its own, you do not -need @code{Info-validate}.) However, you cannot run the @kbd{M-x -Info-validate} node-checking command on indirect files. For -information on how to prevent files from being split and how to -validate the structure of the nodes, see @ref{Using -Info-validate}.@refill - -@node Install an Info File, Command List, Create an Info File, Top -@comment node-name, next, previous, up -@chapter Installing an Info File -@cindex Installing an Info file -@cindex Info file installation -@cindex @file{dir} directory for Info installation - -Info files are usually kept in the @file{info} -directory. (You can find the location of this directory within Emacs -by typing @kbd{C-h i} to enter Info and then typing @kbd{C-x C-f} to -see the full pathname to the @file{info} directory.) - -@menu -* Directory file:: The top level menu for all Info files. -* New Info File:: Listing a new info file. -* Other Info Directories:: How to specify Info files that are - located in other directories. -@end menu - -@node Directory file, New Info File, , Install an Info File -@ifinfo -@heading The @file{dir} File -@end ifinfo - -For Info to work, the @file{info} directory must contain a file that -serves as a top level directory for the Info system. By convention, -this file is called @file{dir}. The @file{dir} file is itself an Info -file. It contains the top level menu for all the Info files in the -system. The menu looks like this:@refill - -@example -* Menu: - -* Info: (info). Documentation browsing system. -* Emacs: (emacs). The extensible, self-documenting - text editor. -* Texinfo: (texinfo). With one source file, make - either a printed manual using - TeX or an Info file. -@dots{} -@end example - -Each of these menu entries points to the `Top' node of the Info file -that is named in parentheses. (The menu entry does not need to -specify the `Top' node, since Info goes to the `Top' node if no node -name is mentioned. @xref{Other Info Files, , Nodes in Other Info -Files}.)@refill - -Thus, the @samp{Info} entry points to the `Top' node of the -@file{info} file and the @samp{Emacs} entry points to the `Top' node -of the @file{emacs} file.@refill - -In each of the Info files, the `Up' pointer of the `Top' node refers -back to the @code{dir} file. For example, the line for the `Top' -node of the Emacs manual looks like this in Info:@refill - -@example -File: emacs Node: Top, Up: (DIR), Next: Distrib -@end example - -@noindent -(Note that in this case, the @file{dir} file name is written in upper -case letters---it can be written in either upper or lower case. Info -has a feature that it will change the case of the file name to lower -case if it cannot find the name as written.)@refill - -@c !!! Can any file name be written in upper or lower case, -@c or is dir a special case? -@c Yes, apparently so, at least with Gillespie's Info. --rjc 24mar92 -@c -@node New Info File, Other Info Directories, Directory file, Install an Info File -@section Listing a New Info File -@cindex Adding a new info file -@cindex Listing a new info file -@cindex New info file, listing it in @file{dir} file -@cindex Info file, listing new one -@cindex @file{dir} file listing - -To add a new Info file to your system, write a menu entry for it in the -menu in the @file{dir} file in the @file{info} directory. Also, move -the new Info file itself to the @file{info} directory. For example, if -you were adding documentation for GDB, you would write the following new -entry:@refill - -@example -* GDB: (gdb). The source-level C debugger. -@end example - -@noindent -The first part of the menu entry is the menu entry name, followed by a -colon. The second part is the name of the Info file, in parentheses, -followed by a period. The third part is the description.@refill - -Conventionally, the name of an Info file has a @file{.info} extension. -Thus, you might list the name of the file like this: - -@example -* GDB: (gdb.info). The source-level C debugger. -@end example - -@noindent -However, Info will look for a file with a @file{.info} extension if it -does not find the file under the name given in the menu. This means -that you can refer to the file @file{gdb.info} as @file{gdb}, as shown -in the first example. This looks better. - -@node Other Info Directories, , New Info File, Install an Info File -@comment node-name, next, previous, up -@section Info Files in Other Directories -@cindex Installing Info in another directory -@cindex Info installed in another directory -@cindex Another Info directory - -If an Info file is not in the @file{info} directory, there are two -ways to specify its location:@refill - -@itemize @bullet -@item -Write the pathname as the menu's second part, or;@refill - -@item -Specify the @file{info} directory name in an environment variable in -your @file{.profile} or @file{.cshrc} initialization file. (Only you -and others with the same environment variable will be able to find Info -files whose location is specified this way.)@refill -@end itemize - -For example, to reach a test file in the @file{~bob/manuals} -directory, you could add an entry like this to the menu in the -@file{dir} file:@refill - -@example -* Test: (~bob/manuals/info-test). Bob's own test file. -@end example - -@noindent -In this case, the absolute file name of the @file{info-test} file is -written as the second part of the menu entry.@refill - -@vindex INFOPATH -Alternatively, you can tell Info where to look by setting the -@code{INFOPATH} environment variable in your @file{.cshrc} or -@file{.profile} file.@refill - -If you use @code{sh} or @code{bash} for your shell command interpreter, -you must set the @code{INFOPATH} environment variable in the -@file{.profile} initialization file; but if you use @code{csh}, you must -set the variable in the @file{.cshrc} initialization file. The two -files require slightly different command formats.@refill - -@itemize @bullet -@item -In a @file{.cshrc} file, you could set the @code{INFOPATH} -variable as follows:@refill - -@smallexample -setenv INFOPATH .:~bob/manuals:/usr/local/emacs/info -@end smallexample - -@item -In a @file{.profile} file, you would achieve the same effect by -writing:@refill - -@smallexample -INFOPATH=.:~bob/manuals:/usr/local/emacs/info -export INFOPATH -@end smallexample -@end itemize - -@noindent -Either form would cause Info to look first in the current directory, -indicated by the @samp{.}, then in the @file{~bob/manuals} directory, -and finally in the @file{/usr/local/emacs/info} directory (which is -a common location for the standard Info directory).@refill - -@c ================ Appendix starts here ================ - -@node Command List, Tips, Install an Info File, Top -@appendix @@-Command List -@cindex Alphabetical @@-command list -@cindex List of @@-commands -@cindex @@-command list - -Here is an alphabetical list of the @@-commands in Texinfo. Square -brackets, @t{[}@w{ }@t{]}, indicate optional arguments; an ellipsis, -@samp{@dots{}}, indicates repeated text.@refill - -@sp 1 -@table @code -@item @@* -Force a line break. Do not end a paragraph that uses @code{@@*} with -an @code{@@refill} command. @xref{Line Breaks}.@refill - -@item @@. -Stands for a period that really does end a sentence (usually after an -end-of-sentence capital letter). @xref{Controlling Spacing}.@refill - -@item @@: -Indicate to @TeX{} that an immediately preceding period, question -mark, exclamation mark, or colon does not end a sentence. Prevent -@TeX{} from inserting extra whitespace as it does at the end of a -sentence. The command has no effect on the Info file output. -@xref{Controlling Spacing}.@refill - -@item @@@@ -Stands for @samp{@@}. @xref{Braces Atsigns Periods, , Inserting -@samp{@@}}.@refill - -@item @@@{ -Stands for a left-hand brace, @samp{@{}. -@xref{Braces Atsigns Periods, , Inserting @@ braces and periods}.@refill - -@item @@@} -Stands for a right-hand brace, @samp{@}}. -@xref{Braces Atsigns Periods, , Inserting @@ braces and periods}.@refill - -@item @@appendix @var{title} -Begin an appendix. The title appears in the table -of contents of a printed manual. In Info, the title is -underlined with asterisks. @xref{unnumbered & appendix, , The -@code{@@unnumbered} and @code{@@appendix} Commands}.@refill - -@item @@appendixsec @var{title} -@itemx @@appendixsection @var{title} -Begin an appendix section within an appendix. The section title appears -in the table of contents of a printed manual. In Info, the title is -underlined with equal signs. @code{@@appendixsection} is a longer -spelling of the @code{@@appendixsec} command. @xref{unnumberedsec -appendixsec heading, , Section Commands}.@refill - -@item @@appendixsubsec @var{title} -Begin an appendix subsection within an appendix. The title appears -in the table of contents of a printed manual. In Info, the title is -underlined with hyphens. @xref{unnumberedsubsec appendixsubsec -subheading, , Subsection Commands}.@refill - -@item @@appendixsubsubsec @var{title} -Begin an appendix subsubsection within a subappendix. The title -appears in the table of contents of a printed manual. In Info, the -title is underlined with periods. @xref{subsubsection,, The `subsub' -Commands}.@refill - -@item @@asis -Used following @code{@@table}, @code{@@ftable}, and @code{@@vtable} to -print the table's first column without highlighting (``as is''). -@xref{Two-column Tables, , Making a Two-column Table}.@refill - -@item @@author @var{author} -Typeset @var{author} flushleft and underline it. @xref{title -subtitle author, , The @code{@@title} and @code{@@author} -Commands}.@refill - -@item @@b@{@var{text}@} -Print @var{text} in @b{bold} font. No effect in Info. @xref{Fonts}.@refill - -@ignore -@item @@br -Force a paragraph break. If used within a line, follow @code{@@br} -with braces. @xref{br, , @code{@@br}}.@refill -@end ignore - -@item @@bullet@{@} -Generate a large round dot, or the closest possible -thing to one. @xref{bullet, , @code{@@bullet}}.@refill - -@item @@bye -Stop formatting a file. The formatters do not see the contents of a -file following an @code{@@bye} command. @xref{Ending a File}.@refill - -@item @@c @var{comment} -Begin a comment in Texinfo. The rest of the line does not appear in -either the Info file or the printed manual. A synonym for -@code{@@comment}. @xref{Conventions, , General Syntactic -Conventions}.@refill - -@item @@cartouche -Highlight an example or quotation by drawing a box with rounded -corners around it. Pair with @code{@@end cartouche}. No effect in -Info. @xref{cartouche, , Drawing Cartouches Around Examples}.)@refill - -@item @@center @var{line-of-text} -Center the line of text following the command. -@xref{titlefont center sp, , @code{@@center}}.@refill - -@item @@chapheading @var{title} -Print a chapter-like heading in the text, but not in the table of -contents of a printed manual. In Info, the title is underlined with -asterisks. @xref{majorheading & chapheading, , @code{@@majorheading} -and @code{@@chapheading}}.@refill - -@item @@chapter @var{title} -Begin a chapter. The chapter title appears in the table of -contents of a printed manual. In Info, the title is underlined with -asterisks. @xref{chapter, , @code{@@chapter}}.@refill - -@item @@cindex @var{entry} -Add @var{entry} to the index of concepts. @xref{Index Entries, , -Defining the Entries of an Index}.@refill - -@item @@cite@{@var{reference}@} -Highlight the name of a book or other reference that lacks a -companion Info file. @xref{cite, , @code{@@cite}}.@refill - -@item @@clear @var{flag} -Unset @var{flag}, preventing the Texinfo formatting commands from -formatting text between subsequent pairs of @code{@@ifset @var{flag}} -and @code{@@end ifset} commands, and preventing -@code{@@value@{@var{flag}@}} from expanding to the value to which -@var{flag} is set. -@xref{set clear value, , @code{@@set} @code{@@clear} @code{@@value}}.@refill - -@item @@code@{@var{sample-code}@} -Highlight text that is an expression, a syntactically complete token -of a program, or a program name. @xref{code, , @code{@@code}}.@refill - -@item @@comment @var{comment} -Begin a comment in Texinfo. The rest of the line does not appear in -either the Info file or the printed manual. A synonym for @code{@@c}. -@xref{Conventions, , General Syntactic Conventions}.@refill - -@item @@contents -Print a complete table of contents. Has no effect in Info, which uses -menus instead. @xref{Contents, , Generating a Table of -Contents}.@refill - -@item @@copyright@{@} -Generate a copyright symbol. @xref{copyright symbol, , -@code{@@copyright}}.@refill - -@ignore -@item @@ctrl@{@var{ctrl-char}@} -Describe an @sc{ascii} control character. Insert actual control character -into Info file. @xref{ctrl, , @code{@@ctrl}}.@refill -@end ignore - -@item @@defcodeindex @var{index-name} -Define a new index and its indexing command. Print entries in an -@code{@@code} font. @xref{New Indices, , Defining New -Indices}.@refill - -@item @@defcv @var{category} @var{class} @var{name} -Format a description for a variable associated with a class in -object-oriented programming. Takes three arguments: the category of -thing being defined, the class to which it belongs, and its name. -@xref{Definition Commands}.@refill - -@item @@deffn @var{category} @var{name} @var{arguments}@dots{} -Format a description for a function, interactive command, or similar -entity that may take arguments. @code{@@deffn} takes as arguments the -category of entity being described, the name of this particular -entity, and its arguments, if any. @xref{Definition Commands}.@refill - -@item @@defindex @var{index-name} -Define a new index and its indexing command. Print entries in a roman -font. @xref{New Indices, , Defining New Indices}.@refill - -@item @@defivar @var{class} @var{instance-variable-name} -Format a description for an instance variable in object-oriented -programming. The command is equivalent to @samp{@@defcv @{Instance -Variable@} @dots{}}. @xref{Definition Commands}.@refill - -@item @@defmac @var{macro-name} @var{arguments}@dots{} -Format a description for a macro. The command is equivalent to -@samp{@@deffn Macro @dots{}}. @xref{Definition Commands}.@refill - -@item @@defmethod @var{class} @var{method-name} @var{arguments}@dots{} -Format a description for a method in object-oriented programming. The -command is equivalent to @samp{@@defop Method @dots{}}. Takes as -arguments the name of the class of the method, the name of the -method, and its arguments, if any. @xref{Definition Commands}.@refill - -@item @@defop @var{category} @var{class} @var{name} @var{arguments}@dots{} -Format a description for an operation in object-oriented programming. -@code{@@defop} takes as arguments the overall name of the category of -operation, the name of the class of the operation, the name of the -operation, and its arguments, if any. @xref{Definition -Commands}.@refill - -@need 100 -@item @@defopt @var{option-name} -Format a description for a user option. The command is equivalent to -@samp{@@defvr @{User Option@} @dots{}}. @xref{Definition Commands}.@refill - -@need 100 -@item @@defspec @var{special-form-name} @var{arguments}@dots{} -Format a description for a special form. The command is equivalent to -@samp{@@deffn @{Special Form@} @dots{}}. @xref{Definition Commands}.@refill - -@need 200 -@item @@deftp @var{category} @var{name-of-type} @var{attributes}@dots{} -Format a description for a data type. @code{@@deftp} takes as -arguments the category, the name of the type (which is a word like -@samp{int} or @samp{float}), and then the names of attributes of -objects of that -type. @xref{Definition Commands}.@refill - -@item @@deftypefn @var{classification} @var{data-type} @var{name} @var{arguments}@dots{} -Format a description for a function or similar entity that may take -arguments and that is typed. @code{@@deftypefn} takes as arguments -the classification of entity being described, the type, the name of -the entity, and its arguments, if any. @xref{Definition -Commands}.@refill - -@item @@deftypefun @var{data-type} @var{function-name} @var{arguments}@dots{} -Format a description for a function in a typed language. -The command is equivalent to @samp{@@deftypefn Function @dots{}}. -@xref{Definition Commands}.@refill - -@item @@deftypevr @var{classification} @var{data-type} @var{name} -Format a description for something like a variable in a typed -language---an entity that records a value. Takes as arguments the -classification of entity being described, the type, and the name of -the entity. @xref{Definition Commands}.@refill - -@item @@deftypevar @var{data-type} @var{variable-name} -Format a description for a variable in a typed language. The command is -equivalent to @samp{@@deftypevr Variable @dots{}}. @xref{Definition -Commands}.@refill - -@item @@defun @var{function-name} @var{arguments}@dots{} -Format a description for functions. The command is equivalent to -@samp{@@deffn Function @dots{}}. @xref{Definition Commands}.@refill - -@item @@defvar @var{variable-name} -Format a description for variables. The command is equivalent to -@samp{@@defvr Variable @dots{}}. @xref{Definition Commands}.@refill - -@item @@defvr @var{category} @var{name} -Format a description for any kind of variable. @code{@@defvr} takes -as arguments the category of the entity and the name of the entity. -@xref{Definition Commands}.@refill - -@item @@dfn@{@var{term}@} -Highlight the introductory or defining use of a term. -@xref{dfn, , @code{@@dfn}}.@refill - -@need 100 -@item @@display -Begin a kind of example. Indent text, do not fill, do not select a -new font. Pair with @code{@@end display}. @xref{display, , -@code{@@display}}.@refill - -@need 100 -@item @@dmn@{@var{dimension}@} -Format a dimension. Cause @TeX{} to insert a narrow space before -@var{dimension}. No effect in Info. Use for writing a number -followed by an abbreviation of a dimension name, such as -@samp{12@dmn{pt}}, written as @samp{12@@dmn@{pt@}}, with no space -between the number and the @code{@@dmn} command. @xref{dmn, , -@code{@@dmn}}.@refill - -@need 100 -@item @@dots@{@} -Insert an ellipsis: @samp{@dots{}}. -@xref{dots, , @code{@@dots}}.@refill - -@need 100 -@item @@emph@{@var{text}@} -Highlight @var{text}; text is displayed in @emph{italics} in printed -output, and surrounded by asterisks in Info. @xref{Emphasis, , Emphasizing Text}.@refill - -@need 100 -@item @@enumerate [@var{number-or-letter}] -Begin a numbered list, using @code{@@item} for each entry. -Optionally, start list with @var{number-or-letter}. Pair with -@code{@@end enumerate}. @xref{enumerate, , -@code{@@enumerate}}.@refill - -@need 100 -@item @@equiv@{@} -Indicate to the reader the exact equivalence of two forms with a -glyph: @samp{@equiv{}}. @xref{Equivalence}.@refill - -@item @@error@{@} -Indicate to the reader with a glyph that the following text is -an error message: @samp{@error{}}. @xref{Error Glyph}.@refill - -@item @@evenfooting [@var{left}] @@| [@var{center}] @@| [@var{right}] -Specify page footings for even-numbered (left-hand) pages. Not relevant to -Info. @xref{Custom Headings, , How to Make Your Own Headings}.@refill - -@item @@evenheading [@var{left}] @@| [@var{center}] @@| [@var{right}] -Specify page headings for even-numbered (left-hand) pages. Not relevant to -Info. @xref{Custom Headings, , How to Make Your Own Headings}.@refill - -@item @@everyfooting [@var{left}] @@| [@var{center}] @@| [@var{right}] -Specify page footings for every page. Not relevant to Info. @xref{Custom -Headings, , How to Make Your Own Headings}.@refill - -@item @@everyheading [@var{left}] @@| [@var{center}] @@| [@var{right}] -Specify page headings for every page. Not relevant to Info. @xref{Custom -Headings, , How to Make Your Own Headings}.@refill - -@item @@example -Begin an example. Indent text, do not fill, and select fixed-width font. -Pair with @code{@@end example}. @xref{example, , -@code{@@example}}.@refill - -@item @@exdent @var{line-of-text} -Remove any indentation a line might have. @xref{exdent, , -Undoing the Indentation of a Line}.@refill - -@item @@expansion@{@} -Indicate the result of a macro expansion to the reader with a special -glyph: @samp{@expansion{}}. -@xref{expansion, , @expansion{} Indicating an Expansion}.@refill - -@item @@file@{@var{filename}@} -Highlight the name of a file, buffer, node, or directory. @xref{file, , -@code{@@file}}.@refill - -@item @@finalout -Prevent @TeX{} from printing large black warning rectangles beside -over-wide lines. @xref{Overfull hboxes}.@refill - -@need 100 -@item @@findex @var{entry} -Add @var{entry} to the index of functions. @xref{Index Entries, , -Defining the Entries of an Index}.@refill - -@need 200 -@item @@flushleft -Left justify every line but leave the right end ragged. -Leave font as is. Pair with @code{@@end flushleft}. -@xref{flushleft & flushright, , @code{@@flushleft} and -@code{@@flushright}}.@refill - -@need 200 -@item @@flushright -Right justify every line but leave the left end ragged. -Leave font as is. Pair with @code{@@end flushright}. -@xref{flushleft & flushright, , @code{@@flushleft} and -@code{@@flushright}}.@refill - -@need 200 -@item @@footnote@{@var{text-of-footnote}@} -Enter a footnote. Footnote text is printed at the bottom of the page -by @TeX{}; Info may format in either `End' node or `Separate' node style. -@xref{Footnotes}.@refill - -@item @@footnotestyle @var{style} -Specify an Info file's footnote style, either @samp{end} for the end -node style or @samp{separate} for the separate node style. -@xref{Footnotes}.@refill - -@item @@format -Begin a kind of example. Like @code{@@example} or @code{@@display}, -but do not narrow the margins and do not select the fixed-width font. -Pair with @code{@@end format}. @xref{example, , -@code{@@example}}.@refill - -@item @@ftable @var{formatting-command} -Begin a two-column table, using @code{@@item} for each entry. -Automatically enter each of the items in the first column into the -index of functions. Pair with @code{@@end ftable}. The same as -@code{@@table}, except for indexing. @xref{ftable vtable, , -@code{@@ftable} and @code{@@vtable}}.@refill - -@item @@group -Hold text together that must appear on one printed page. Pair with -@code{@@end group}. Not relevant to Info. @xref{group, , -@code{@@group}}.@refill - -@item @@heading @var{title} -Print an unnumbered section-like heading in the text, but not in the -table of contents of a printed manual. In Info, the title is -underlined with equal signs. @xref{unnumberedsec appendixsec heading, -, Section Commands}.@refill - -@item @@headings @var{on-off-single-double} -Turn page headings on or off, or specify single-sided or double-sided -page headings for printing. @code{@@headings on} is synonymous with -@code{@@headings double}. @xref{headings on off, , The -@code{@@headings} Command}.@refill - -@item @@i@{@var{text}@} -Print @var{text} in @i{italic} font. No effect in Info. -@xref{Fonts}.@refill - -@item @@ifclear @var{flag} -If @var{flag} is cleared, the Texinfo formatting commands format text -between @code{@@ifclear @var{flag}} and the following @code{@@end -ifclear} command. -@xref{set clear value, , @code{@@set} @code{@@clear} @code{@@value}}.@refill - -@item @@ifinfo -Begin a stretch of text that will be ignored by @TeX{} when it -typesets the printed manual. The text appears only in the Info file. -Pair with @code{@@end ifinfo}. @xref{Conditionals, , Conditionally -Visible Text}.@refill - -@item @@ifset @var{flag} -If @var{flag} is set, the Texinfo formatting commands format text -between @code{@@ifset @var{flag}} and the following @code{@@end ifset} -command. -@xref{set clear value, , @code{@@set} @code{@@clear} @code{@@value}}.@refill - -@item @@iftex -Begin a stretch of text that will not appear in the Info file, but -will be processed only by @TeX{}. Pair with @code{@@end iftex}. -@xref{Conditionals, , Conditionally Visible Text}.@refill - -@item @@ignore -Begin a stretch of text that will not appear in either the Info file -or the printed output. Pair with @code{@@end ignore}. -@xref{Comments, , Comments and Ignored Text}.@refill - -@item @@include @var{filename} -Incorporate the contents of the file @var{filename} into the Info file -or printed document. @xref{Include Files}.@refill - -@item @@inforef@{@var{node-name}, [@var{entry-name}], @var{info-file-name}@} -Make a cross reference to an Info file for which there is no printed -manual. @xref{inforef, , Cross references using -@code{@@inforef}}.@refill - -@item \input @var{macro-definitions-file} -Use the specified macro definitions file. This command is used only -in the first line of a Texinfo file to cause @TeX{} to make use of the -@file{texinfo} macro definitions file. The backslash in @code{\input} -is used instead of an @code{@@} because @TeX{} does not properly -recognize @code{@@} until after it has read the definitions file. -@xref{Header, , The Texinfo File Header}.@refill - -@item @@item -Indicate the beginning of a marked paragraph for @code{@@itemize} and -@code{@@enumerate}; indicate the beginning of the text of a first column -entry for @code{@@table}, @code{@@ftable}, and @code{@@vtable}. -@xref{Lists and Tables}.@refill - -@item @@itemize @var{mark-generating-character-or-command} -Produce a sequence of indented paragraphs, with a mark inside the left -margin at the beginning of each paragraph. Pair with @code{@@end -itemize}. @xref{itemize, , @code{@@itemize}}.@refill - -@item @@itemx -Like @code{@@item} but do not generate extra vertical space above the -item text. @xref{itemx, , @code{@@itemx}}.@refill - -@item @@kbd@{@var{keyboard-characters}@} -Indicate text that consists of characters of input to be typed by -users. @xref{kbd, , @code{@@kbd}}.@refill - -@item @@key@{@var{key-name}@} -Highlight @var{key-name}, a conventional name for a key on a keyboard. -@xref{key, , @code{@@key}}.@refill - -@item @@kindex @var{entry} -Add @var{entry} to the index of keys. @xref{Index Entries, , Defining the -Entries of an Index}.@refill - -@item @@lisp -Begin an example of Lisp code. Indent text, do not fill, and select -fixed-width font. Pair with @code{@@end lisp}. @xref{Lisp Example, , -@code{@@lisp}}.@refill - -@item @@majorheading @var{title} -Print a chapter-like heading in the text, but not in the table of -contents of a printed manual. Generate more vertical whitespace before -the heading than the @code{@@chapheading} command. In Info, the chapter -heading line is underlined with asterisks. @xref{majorheading & -chapheading, , @code{@@majorheading} and @code{@@chapheading}}.@refill - -@item @@menu -Mark the beginning of a menu of nodes in Info. No effect in a printed -manual. Pair with @code{@@end menu}. @xref{Menus}.@refill - -@item @@minus@{@} -Generate a minus sign. @xref{minus, , @code{@@minus}}.@refill - -@item @@need @var{n} -Start a new page in a printed manual if fewer than @var{n} mils -(thousandths of an inch) remain on the current page. @xref{need, , -@code{@@need}}.@refill - -@item @@node @var{name, next, previous, up} -Define the beginning of a new node in Info, and serve as a locator for -references for @TeX{}. @xref{node, , @code{@@node}}.@refill - -@need 200 -@item @@noindent -Prevent text from being indented as if it were a new paragraph. -@xref{noindent, , @code{@@noindent}}.@refill - -@item @@oddfooting [@var{left}] @@| [@var{center}] @@| [@var{right}] -Specify page footings for odd-numbered (right-hand) pages. Not relevant to -Info. @xref{Custom Headings, , How to Make Your Own Headings}.@refill - -@item @@oddheading [@var{left}] @@| [@var{center}] @@| [@var{right}] -Specify page headings for odd-numbered (right-hand) pages. Not relevant to -Info. @xref{Custom Headings, , How to Make Your Own Headings}.@refill - -@item @@page -Start a new page in a printed manual. No effect in Info. -@xref{page, , @code{@@page}}.@refill - -@item @@paragraphindent @var{indent} -Indent paragraphs by @var{indent} number of spaces; delete indentation -if the value of @var{indent} is 0; and do not change indentation if -@var{indent} is @code{asis}. @xref{paragraphindent, , Paragraph -Indenting}.@refill - -@item @@pindex @var{entry} -Add @var{entry} to the index of programs. @xref{Index Entries, , Defining -the Entries of an Index}.@refill - -@item @@point@{@} -Indicate the position of point in a buffer to the reader with a -glyph: @samp{@point{}}. @xref{Point Glyph, , Indicating -Point in a Buffer}.@refill - -@item @@print@{@} -Indicate printed output to the reader with a glyph: -@samp{@print{}}. @xref{Print Glyph}.@refill - -@item @@printindex @var{index-name} -Print an alphabetized two-column index in a printed manual or generate -an alphabetized menu of index entries for Info. @xref{Printing -Indices & Menus}.@refill - -@item @@pxref@{@var{node-name}, [@var{entry}], [@var{topic-or-title}], [@var{info-file}], [@var{manual}]@} -Make a reference that starts with a lower case `see' in a printed -manual. Use within parentheses only. Do not follow command with a -punctuation mark. The Info formatting commands automatically insert -terminating punctuation as needed, which is why you do not need to -insert punctuation. Only the first argument is mandatory. -@xref{pxref, , @code{@@pxref}}.@refill - -@item @@quotation -Narrow the margins to indicate text that is quoted from another real -or imaginary work. Write command on a line of its own. Pair with -@code{@@end quotation}. @xref{quotation, , -@code{@@quotation}}.@refill - -@need 100 -@item @@r@{@var{text}@} -Print @var{text} in @r{roman} font. No effect in Info. -@xref{Fonts}.@refill - -@need 300 -@item @@ref@{@var{node-name}, [@var{entry}], [@var{topic-or-title}], [@var{info-file}], [@var{manual}]@} -Make a reference. In a printed manual, the reference does not start -with a `See'. Follow command with a punctuation mark. Only the first -argument is mandatory. @xref{ref, , @code{@@ref}}.@refill - -@need 300 -@item @@refill -In Info, refill and indent the paragraph after all the other processing -has been done. No effect on @TeX{}, which always refills. This command -is no longer needed, since all formatters now automatically refill. -@xref{Refilling Paragraphs}.@refill - -@need 300 -@item @@result@{@} -Indicate the result of an expression to the reader with a special -glyph: @samp{@result{}}. @xref{result, , @code{@@result}}.@refill - -@item @@samp@{@var{text}@} -Highlight @var{text} that is a literal example of a sequence of -characters. Used for single characters, for statements, and often for -entire shell commands. @xref{samp, , @code{@@samp}}.@refill - -@item @@sc@{@var{text}@} -Set @var{text} in a printed output in @sc{the small caps font} and -set text in the Info file in uppercase letters. -@xref{Smallcaps}.@refill - -@item @@section @var{title} -Begin a section within a chapter. In a printed manual, the section -title is numbered and appears in the table of contents. In Info, the -title is underlined with equal signs. @xref{section, , -@code{@@section}}.@refill - -@item @@set @var{flag} [@var{string}] -Make @var{flag} active, causing the Texinfo formatting commands to -format text between subsequent pairs of @code{@@ifset @var{flag}} and -@code{@@end ifset} commands. Optionally, set value of @var{flag} to -@var{string}. -@xref{set clear value, , @code{@@set} @code{@@clear} @code{@@value}}.@refill - -@item @@setchapternewpage @var{on-off-odd} -Specify whether chapters start on new pages, and if so, whether on -odd-numbered (right-hand) new pages. @xref{setchapternewpage, , -@code{@@setchapternewpage}}.@refill - -@item @@setfilename @var{info-file-name} -Provide a name for the Info file. @xref{Conventions, , General -Syntactic Conventions}.@refill - -@item @@settitle @var{title} -Provide a title for page headers in a printed manual. -@xref{Conventions, , General Syntactic Conventions}.@refill - -@item @@shortcontents -Print a short table of contents. Not relevant to Info, which uses -menus rather than tables of contents. A synonym for -@code{@@summarycontents}. @xref{Contents, , Generating a Table of -Contents}.@refill - -@need 400 -@item @@smallbook -Cause @TeX{} to produce a printed manual in a 7 by 9.25 inch format -rather than the regular 8.5 by 11 inch format. @xref{smallbook, , -Printing Small Books}. Also, see @ref{smallexample & smalllisp, , -@code{@@smallexample} and @code{@@smalllisp}}.@refill - -@need 400 -@item @@smallexample -Indent text to indicate an example. Do not fill, select fixed-width -font. In @code{@@smallbook} format, print text in a smaller font than -with @code{@@example}. Pair with @code{@@end smallexample}. -@xref{smallexample & smalllisp, , @code{@@smallexample} and -@code{@@smalllisp}}.@refill - -@need 400 -@item @@smalllisp -Begin an example of Lisp code. Indent text, do not fill, select -fixed-width font. In @code{@@smallbook} format, print text in a -smaller font. Pair with @code{@@end smalllisp}. @xref{smallexample & -smalllisp, , @code{@@smallexample} and @code{@@smalllisp}}.@refill - -@need 700 -@item @@sp @var{n} -Skip @var{n} blank lines. @xref{sp, , @code{@@sp}}.@refill - -@need 700 -@item @@strong @var{text} -Emphasize @var{text} by typesetting it in a @strong{bold} font for the -printed manual and by surrounding it with asterisks for Info. -@xref{emph & strong, , Emphasizing Text}.@refill - -@item @@subheading @var{title} -Print an unnumbered subsection-like heading in the text, but not in -the table of contents of a printed manual. In Info, the title is -underlined with hyphens. @xref{unnumberedsubsec appendixsubsec -subheading, , @code{@@unnumberedsubsec} @code{@@appendixsubsec} -@code{@@subheading}}.@refill - -@item @@subsection @var{title} -Begin a subsection within a section. In a printed manual, the -subsection title is numbered and appears in the table of contents. In -Info, the title is underlined with hyphens. @xref{subsection, , -@code{@@subsection}}.@refill - -@item @@subsubheading @var{title} -Print an unnumbered subsubsection-like heading in the text, but not in -the table of contents of a printed manual. In Info, the title is -underlined with periods. @xref{subsubsection, , The `subsub' -Commands}.@refill - -@item @@subsubsection @var{title} -Begin a subsubsection within a subsection. In a printed manual, -the subsubsection title is numbered and appears in the table of -contents. In Info, the title is underlined with periods. -@xref{subsubsection, , The `subsub' Commands}.@refill - -@item @@subtitle @var{title} -In a printed manual, set a subtitle in a normal sized font flush to -the right-hand side of the page. Not relevant to Info, which does not -have title pages. @xref{title subtitle author, , @code{@@title} -@code{@@subtitle} and @code{@@author} Commands}.@refill - -@item @@summarycontents -Print a short table of contents. Not relevant to Info, which uses -menus rather than tables of contents. A synonym for -@code{@@shortcontents}. @xref{Contents, , Generating a Table of -Contents}.@refill - -@need 300 -@item @@syncodeindex @var{from-index} @var{into-index} -Merge the index named in the first argument into the index named in -the second argument, printing the entries from the first index in -@code{@@code} font. @xref{Combining Indices}.@refill - -@need 300 -@item @@synindex @var{from-index} @var{into-index} -Merge the index named in the first argument into the index named in -the second argument. Do not change the font of @var{from-index} -entries. @xref{Combining Indices}.@refill - -@need 100 -@item @@t@{@var{text}@} -Print @var{text} in a @t{fixed-width}, typewriter-like font. -No effect in Info. @xref{Fonts}.@refill - -@need 400 -@item @@table @var{formatting-command} -Begin a two-column table, using @code{@@item} for each entry. Write -each first column entry on the same line as @code{@@item}. First -column entries are printed in the font resulting from -@var{formatting-command}. Pair with @code{@@end table}. -@xref{Two-column Tables, , Making a Two-column Table}. -Also see @ref{ftable vtable, , @code{@@ftable} and @code{@@vtable}}, -and @ref{itemx, , @code{@@itemx}}.@refill - -@item @@TeX@{@} -Insert the logo @TeX{}. @xref{TeX and copyright, , Inserting @TeX{} -and @copyright{}}.@refill - -@item @@tex -Enter @TeX{} completely. Pair with @code{@@end tex}. @xref{Using -Ordinary TeX Commands, , Using Ordinary @TeX{} Commands}.@refill - -@item @@thischapter -In a heading or footing, stands for the number and name of the current -chapter, in the format `Chapter 1: Title'. @xref{Custom -Headings, , How to Make Your Own Headings}.@refill - -@item @@thischaptername -In a heading or footing, stands for the name of the current chapter. -@xref{Custom Headings, , How to Make Your Own Headings}.@refill - -@item @@thisfile -In a heading or footing, stands for the name of the current -@code{@@include} file. Does not insert anything if not within an -@code{@@include} file. @xref{Custom Headings, , How to Make Your Own -Headings}.@refill - -@item @@thispage -In a heading or footing, stands for the current page number. -@xref{Custom Headings, , How to Make Your Own Headings}.@refill - -@ignore -@item @@thissection -In a heading or footing, stands for the title of the current section. -@xref{Custom Headings, , How to Make Your Own Headings}.@refill -@end ignore - -@item @@thistitle -In a heading or footing, stands for the name of the document, as specified -by the @code{@@settitle} command. @xref{Custom Headings, , How to -Make Your Own Headings}.@refill - -@item @@tindex @var{entry} -Add @var{entry} to the index of data types. @xref{Index Entries, , -Defining the Entries of an Index}.@refill - -@item @@title @var{title} -In a printed manual, set a title flush to the left-hand side of the -page in a larger than normal font and underline it with a black rule. -Not relevant to Info, which does not have title pages. @xref{title -subtitle author, , The @code{@@title} @code{@@subtitle} and -@code{@@author} Commands}.@refill - -@need 400 -@item @@titlefont@{@var{text}@} -In a printed manual, print @var{text} in a larger than normal font. -Not relevant to Info, which does not have title pages. -@xref{titlefont center sp, , The @code{@@titlefont} @code{@@center} -and @code{@@sp} Commands}.@refill - -@need 300 -@item @@titlepage -Indicate to Texinfo the beginning of the title page. Write command on -a line of its own. Pair with @code{@@end titlepage}. Nothing between -@code{@@titlepage} and @code{@@end titlepage} appears in Info. -@xref{titlepage, , @code{@@titlepage}}.@refill - -@need 150 -@item @@today@{@} -Insert the current date, in `1 Jan 1900' style. @xref{Custom -Headings, , How to Make Your Own Headings}.@refill - -@item @@top @var{title} -In a Texinfo file to be formatted with @code{makeinfo}, identify the -topmost @code{@@node} line in the file, which must be written on the line -immediately preceding the @code{@@top} command. Used for -@code{makeinfo}'s node pointer insertion feature. The title is -underlined with asterisks. Both the @code{@@node} line and the @code{@@top} -line normally should be enclosed by @code{@@ifinfo} and @code{@@end -ifinfo}. In @TeX{} and @code{texinfo-format-buffer}, the @code{@@top} -command is merely a synonym for @code{@@unnumbered}. @xref{makeinfo -Pointer Creation, , Creating Pointers with @code{makeinfo}}. - -@item @@unnumbered @var{title} -In a printed manual, begin a chapter that appears without chapter -numbers of any kind. The title appears in the table of contents of a -printed manual. In Info, the title is underlined with asterisks. -@xref{unnumbered & appendix, , @code{@@unnumbered} and -@code{@@appendix}}.@refill - -@item @@unnumberedsec @var{title} -In a printed manual, begin a section that appears without section -numbers of any kind. The title appears in the table of contents of a -printed manual. In Info, the title is underlined with equal signs. -@xref{unnumberedsec appendixsec heading, , Section Commands}.@refill - -@item @@unnumberedsubsec @var{title} -In a printed manual, begin an unnumbered subsection within a -chapter. The title appears in the table of contents of a printed -manual. In Info, the title is underlined with hyphens. -@xref{unnumberedsubsec appendixsubsec subheading, , -@code{@@unnumberedsubsec} @code{@@appendixsubsec} -@code{@@subheading}}.@refill - -@item @@unnumberedsubsubsec @var{title} -In a printed manual, begin an unnumbered subsubsection within a -chapter. The title appears in the table of contents of a printed -manual. In Info, the title is underlined with periods. -@xref{subsubsection, , The `subsub' Commands}.@refill - -@item @@value@{@var{flag}@} -Replace @var{flag} with the value to which it is set by @code{@@set -@var{flag}}. -@xref{set clear value, , @code{@@set} @code{@@clear} @code{@@value}}.@refill - -@item @@var@{@var{metasyntactic-variable}@} -Highlight a metasyntactic variable, which is something that stands for -another piece of text. @xref{var, , Indicating Metasyntactic -Variables}.@refill - -@need 400 -@item @@vindex @var{entry} -Add @var{entry} to the index of variables. @xref{Index Entries, , -Defining the Entries of an Index}.@refill - -@need 400 -@item @@vskip @var{amount} -In a printed manual, insert whitespace so as to push text on the -remainder of the page towards the bottom of the page. Used in -formatting the copyright page with the argument @samp{0pt plus -1filll}. (Note spelling of @samp{filll}.) @code{@@vskip} may be used -only in contexts ignored for Info. @xref{Copyright & Permissions, , -The Copyright Page and Printed Permissions}.@refill - -@need 400 -@item @@vtable @var{formatting-command} -Begin a two-column table, using @code{@@item} for each entry. -Automatically enter each of the items in the first column into the -index of variables. Pair with @code{@@end vtable}. The same as -@code{@@table}, except for indexing. @xref{ftable vtable, , -@code{@@ftable} and @code{@@vtable}}.@refill - -@need 400 -@item @@w@{@var{text}@} -Prevent @var{text} from being split across two lines. Do not end a -paragraph that uses @code{@@w} with an @code{@@refill} command. -In the Texinfo file, keep @var{text} on one line. -@xref{w, , @code{@@w}}.@refill - -@need 400 -@item @@xref@{@var{node-name}, [@var{entry}], [@var{topic-or-title}], [@var{info-file}], [@var{manual}]@} -Make a reference that starts with `See' in a printed manual. Follow -command with a punctuation mark. Only the first argument is -mandatory. @xref{xref, , @code{@@xref}}.@refill -@end table - -@node Tips, Sample Texinfo File, Command List, Top -@comment node-name, next, previous, up -@appendix Tips and Hints - -Here are some tips for writing Texinfo documentation:@refill - -@cindex Tips -@cindex Usage tips -@cindex Hints -@itemize @bullet -@item -Write in the present tense, not in the past or the future. - -@item -Write actively! For example, write ``We recommend that @dots{}'' rather -than ``It is recommended that @dots{}''. - -@item -Use 70 or 72 as your fill column. Longer lines are hard to read. - -@item -Include a copyright notice and copying permissions. -@end itemize - -@subsubheading Index, index, index! - -Write many index entries, in different ways. -Readers like indices; they are helpful and convenient. - -Although it is easiest to write index entries as you write the body of -the text, some people prefer to write entries afterwards. In either -case, write an entry before the paragraph to which it applies. This -way, an index entry points to the first page of a paragraph that is -split across pages. - -Here are more hints we have found valuable: - -@itemize @bullet -@item -Write each index entry differently, so each entry refers to a different -place in the document. The index of an Info file lists only one -location for each entry. - -@item -Write index entries only where a topic is discussed significantly. For -example, it is not useful to index ``debugging information'' in a -chapter on reporting bugs. Someone who wants to know about debugging -information will certainly not find it in that chapter. - -@item -Consistently capitalize the first word of every index entry, or else use -lower case. According to convention, you should capitalize the first -word of an index entry. However, this practice may make an index look -crowded. Some writers prefer lower case. Regardless of which you -prefer, choose one style and stick to it. Mixing the two styles looks -bad. - -@item -Always capitalize or use upper case for those words in an index for -which this is proper, such as names of countries or acronyms. - -@item -Write the indexing commands that refer to a whole section immediately -after the section command, and write the indexing commands that refer to -the paragraph before the paragraph. - -@need 1000 -In the example that follows, a blank line comes after the index -entry for ``Leaping'': - -@example -@group -@@section The Dog and the Fox -@@cindex Jumping, in general -@@cindex Leaping - -@@cindex Dog, lazy, jumped over -@@cindex Lazy dog jumped over -@@cindex Fox, jumps over dog -@@cindex Quick fox jumps over dog -The quick brown fox jumps over the lazy dog. -@end group -@end example - -@noindent -(Note that the example shows entries for the same concept that are -written in different ways---@samp{Lazy dog}, and @samp{Dog, lazy}---so -readers can look up the concept in different ways.) -@end itemize - -@subsubheading Blank lines - -@itemize @bullet -@item -Insert a blank line between a sectioning command and the first following -sentence or paragraph, or between the indexing commands associated with -the sectioning command and the first following sentence or paragraph, as -shown in the tip on indexing. Otherwise, a formatter may fold title and -paragraph together. - -@item -Always insert a blank line before an @code{@@table} command and after an -@code{@@end table} command; but never insert a blank line after an -@code{@@table} command or before an @code{@@end table} command. - -@need 1000 -For example, - -@example -@group -Types of fox: - -@@table @@samp -@@item Quick -Jump over lazy dogs. -@end group - -@group -@@item Brown -Also jump over lazy dogs. -@@end table - -@end group -@group -@@noindent -On the other hand, @dots{} -@end group -@end example - -Insert blank lines before and after @code{@@itemize} @dots{} @code{@@end -itemize} and @code{@@enumerate} @dots{} @code{@@end enumerate} in the -same way. -@end itemize - -@subsubheading Complete phrases - -Complete phrases are easier to read than @dots{} - -@itemize @bullet -@item -Write entries in an itemized list as complete sentences; or at least, as -complete phrases. Incomplete expressions @dots{} awkward @dots{} like -this. - -@item -Write the prefatory sentence or phrase for a multi-item list or table as -a complete expression. Do not write ``You can set:''; instead, write -``You can set these variables:''. The former expression sounds cut off. -@end itemize - -@subsubheading Editions, dates and versions - -Write the edition and version numbers and date in three places in every -manual: - -@enumerate -@item -In the first @code{@@ifinfo} section, for people reading the Texinfo file. - -@item -In the @code{@@titlepage} section, for people reading the printed manual. - -@item -In the `Top' node, for people reading the Info file. -@end enumerate - -@noindent -Also, it helps to write a note before the first @code{@@ifinfo} -section to explain what you are doing. - -@need 800 -@noindent -For example: - -@example -@group -@@c ===> NOTE! <== -@@c Specify the edition and version numbers and date -@@c in *three* places: -@@c 1. First ifinfo section 2. title page 3. top node -@@c To find the locations, search for !!set -@end group - -@group -@@ifinfo -@@c !!set edition, date, version -This is Edition 4.03, January 1992, -of the @@cite@{GDB Manual@} for GDB Version 4.3. -@dots{} -@end group -@end example - -@noindent ----or use @code{@@set} and @code{@@value} -(@pxref{value Example, , @code{@@value} Example}). - -@subsubheading Definition Commands - -Definition commands are @code{@@deffn}, @code{@@defun}, -@code{@@defmac}, and the like, and enable you to write descriptions in -a uniform format.@refill - -@itemize @bullet -@item -Write just one definition command for each entity you define with a -definition command. The automatic indexing feature creates an index -entry that leads the reader to the definition. - -@item -Use @code{@@table} @dots{} @code{@@end table} in an appendix that -contains a summary of functions, not @code{@@deffn} or other definition -commands. -@end itemize - -@subsubheading Capitalization - -@itemize @bullet -@item -Capitalize @samp{Texinfo}; it is a name. Do not write the @samp{x} or -@samp{i} in upper case. - -@item -Capitalize @samp{Info}; it is a name. - -@item -Write @TeX{} using the @code{@@TeX@{@}} command. Note the uppercase -@samp{T} and @samp{X}. This command causes the formatters to -typeset the name according to the wishes of Donald Knuth, who wrote -@TeX{}. -@end itemize - -@subsubheading Spaces - -Do not use spaces to format a Texinfo file, except inside of -@code{@@example} @dots{} @code{@@end example} and similar commands. - -@need 700 -For example, @TeX{} fills the following: - -@example -@group - @@kbd@{C-x v@} - @@kbd@{M-x vc-next-action@} - Perform the next logical operation - on the version-controlled file - corresponding to the current buffer. -@end group -@end example - -@need 950 -@noindent -so it looks like this: - -@iftex -@quotation - @kbd{C-x v} - @kbd{M-x vc-next-action} - Perform the next logical operation on the version-controlled file - corresponding to the current buffer. -@end quotation -@end iftex -@ifinfo -@quotation -`C-x v' `M-x vc-next-action' Perform the next logical operation on the -version-controlled file corresponding to the current buffer. -@end quotation -@end ifinfo - -@noindent -In this case, the text should be formatted with -@code{@@table}, @code{@@item}, and @code{@@itemx}, to create a table. - -@subsubheading @@code, @@samp, @@var, and @samp{---} - -@itemize @bullet -@item -Use @code{@@code} around Lisp symbols, including command names. -For example, - -@example -The main function is @@code@{vc-next-action@}, @dots{} -@end example - -@item -Avoid putting letters such as @samp{s} immediately after an -@samp{@@code}. Such letters look bad. - -@item -Use @code{@@var} around meta-variables. Do not write angle brackets -around them. - -@item -Use three hyphens in a row, @samp{---}, to indicate a long dash. @TeX{} -typesets these as a long dash and the Info formatters reduce three -hyphens to two. -@end itemize - -@subsubheading Periods Outside of Quotes - -Place periods and other punctuation marks @emph{outside} of quotations, -unless the punctuation is part of the quotation. This practice goes against -convention, but enables the reader to distinguish between the contents -of the quotation and the whole passage. - -For example, you should write the following sentence with the period -outside the end quotation marks: - -@example -Evidently, @samp{au} is an abbreviation for ``author''. -@end example - -@noindent -since @samp{au} does @emph{not} serve as an abbreviation for -@samp{author.} (with a period following the word). - -@subsubheading Introducing New Terms - -@itemize @bullet -@item -Introduce new terms so that a user who does not know them can understand -them from context; or write a definition for the term. - -For example, in the following, the terms ``check in'', ``register'' and -``delta'' are all appearing for the first time; the example sentence should be -rewritten so they are understandable. - -@quotation -The major function assists you in checking in a file to your -version control system and registering successive sets of changes to -it as deltas. -@end quotation - -@item -Use the @code{@@dfn} command around a word being introduced, to indicate -that the user should not expect to know the meaning already, and should -expect to learn the meaning from this passage. -@end itemize - -@subsubheading @@pxref - -@c !!! maybe include this in the tips on pxref -@ignore -By the way, it is okay to use pxref with something else in front of -it within the parens, as long as the pxref is followed by the close -paren, and the material inside the parents is not part of a larger -sentence. Also, you can use xref inside parens as part of a complete -sentence so long as you terminate the cross reference with punctuation. -@end ignore -Absolutely never use @code{@@pxref} except in the special context for -which it is designed: inside parentheses, with the closing parenthesis -following immediately after the closing brace. One formatter -automatically inserts closing punctuation and the other does not. This -means that the output looks right both in printed output and in an Info -file, but only when the command is used inside parentheses. - -@subsubheading Invoking from a Shell - -You can invoke programs such as Emacs, GCC, and GAWK from a shell. -The documentation for each program should contain a section that -describes this. Unfortunately, if the node names and titles for these -sections are all different, readers find it hard to search for the -section.@refill - -Name such sections with a phrase beginning with the word -@w{`Invoking @dots{}'}, as in `Invoking Emacs'; this way -users can find the section easily. - -@subsubheading @sc{ansi c} Syntax - -When you use @code{@@example} to describe a C function's calling -conventions, use the @sc{ansi c} syntax, like this:@refill - -@example -void dld_init (char *@@var@{path@}); -@end example - -@noindent -And in the subsequent discussion, refer to the argument values by -writing the same argument names, again highlighted with -@code{@@var}.@refill - -@need 800 -Avoid the obsolete style that looks like this:@refill - -@example -#include <dld.h> - -dld_init (path) -char *path; -@end example - -Also, it is best to avoid writing @code{#include} above the -declaration just to indicate that the function is declared in a -header file. The practice may give the misimpression that the -@code{#include} belongs near the declaration of the function. Either -state explicitly which header file holds the declaration or, better -yet, name the header file used for a group of functions at the -beginning of the section that describes the functions.@refill - -@subsubheading Bad Examples - -Here are several examples of bad writing to avoid: - -In this example, say, `` @dots{} you must @code{@@dfn}@{check -in@} the new version.'' That flows better. - -@quotation -When you are done editing the file, you must perform a -@code{@@dfn}@{check in@}. -@end quotation - -In the following example, say, ``@dots{} makes a unified interface such as VC -mode possible.'' - -@quotation -SCCS, RCS and other version-control systems all perform similar -functions in broadly similar ways (it is this resemblance which makes -a unified control mode like this possible). -@end quotation - -And in this example, you should specify what `it' refers to: - -@quotation -If you are working with other people, it assists in coordinating -everyone's changes so they do not step on each other. -@end quotation - -@subsubheading And Finally @dots{} - -@itemize @bullet -@item -Pronounce @TeX{} as if the @samp{X} were a Greek `chi', as the last -sound in the name `Bach'. But pronounce Texinfo as in `speck': -@samp{teckinfo}. - -@item -Write notes for yourself at the very end of a Texinfo file after the -@code{@@bye}. None of the formatters process text after the -@code{@@bye}; it is as if the text were within @code{@@ignore} @dots{} -@code{@@end ignore}. -@end itemize - -@node Sample Texinfo File, Sample Permissions, Tips, Top -@comment node-name, next, previous, up -@appendix A Sample Texinfo File -@cindex Sample Texinfo file, no comments - -Here is a complete, short sample Texinfo file, without any commentary. -You can see this file, with comments, in the first chapter. -@xref{Short Sample, , A Short Sample Texinfo File}. - -@sp 1 -@example -\input texinfo @@c -*-texinfo-*- -@@c %**start of header -@@setfilename sample.info -@@settitle Sample Document -@@c %**end of header - -@@setchapternewpage odd - -@@ifinfo -This is a short example of a complete Texinfo file. - -Copyright 1990 Free Software Foundation, Inc. -@@end ifinfo - -@@titlepage -@@sp 10 -@@comment The title is printed in a large font. -@@center @@titlefont@{Sample Title@} - -@@c The following two commands start the copyright page. -@@page -@@vskip 0pt plus 1filll -Copyright @@copyright@{@} 1990 Free Software Foundation, Inc. -@@end titlepage - -@@node Top, First Chapter, (dir), (dir) -@@comment node-name, next, previous, up - -@@menu -* First Chapter:: The first chapter is the - only chapter in this sample. -* Concept Index:: This index has two entries. -@@end menu - -@@node First Chapter, Concept Index, Top, Top -@@comment node-name, next, previous, up -@@chapter First Chapter -@@cindex Sample index entry - -This is the contents of the first chapter. -@@cindex Another sample index entry - -Here is a numbered list. - -@@enumerate -@@item -This is the first item. - -@@item -This is the second item. -@@end enumerate - -The @@code@{makeinfo@} and @@code@{texinfo-format-buffer@} -commands transform a Texinfo file such as this into -an Info file; and @@TeX@{@} typesets it for a printed -manual. - -@@node Concept Index, , First Chapter, Top -@@comment node-name, next, previous, up -@@unnumbered Concept Index - -@@printindex cp - -@@contents -@@bye -@end example - -@node Sample Permissions, Include Files, Sample Texinfo File, Top -@appendix Sample Permissions -@cindex Permissions -@cindex Copying permissions - -Texinfo files should contain sections that tell the readers that they -have the right to copy and distribute the Texinfo file, the Info file, -and the printed manual.@refill - -Also, if you are writing a manual about software, you should explain -that the software is free and either include the GNU General Public -License (GPL) or provide a reference to it. @xref{Distrib, , -Distribution, emacs, The GNU Emacs Manual}, for an example of the text -that could be used in the software ``Distribution'', ``General Public -License'', and ``NO WARRANTY'' sections of a document. @xref{Copying, -, Texinfo Copying Conditions}, for an example of a brief explanation -of how the copying conditions provide you with rights. @refill - -@menu -* Inserting Permissions:: How to put permissions in your document. -* ifinfo Permissions:: Sample @samp{ifinfo} copying permissions. -* Titlepage Permissions:: Sample Titlepage copying permissions. -@end menu - -@node Inserting Permissions, ifinfo Permissions, , Sample Permissions -@ifinfo -@appendixsec Inserting Permissions -@end ifinfo - -In a Texinfo file, the first @code{@@ifinfo} section usually begins -with a line that says what the file documents. This is what a person -reading the unprocessed Texinfo file or using the advanced Info -command @kbd{g *} sees first. @inforef{Expert, Advanced Info -commands, info}, for more information. (A reader using the regular -Info commands usually starts reading at the first node and skips -this first section, which is not in a node.)@refill - -In the @code{@@ifinfo} section, the summary sentence is followed by a -copyright notice and then by the copying permission notice. One of -the copying permission paragraphs is enclosed in @code{@@ignore} and -@code{@@end ignore} commands. This paragraph states that the Texinfo -file can be processed through @TeX{} and printed, provided the printed -manual carries the proper copying permission notice. This paragraph -is not made part of the Info file since it is not relevant to the Info -file; but it is a mandatory part of the Texinfo file since it permits -people to process the Texinfo file in @TeX{} and print the -results.@refill - -In the printed manual, the Free Software Foundation copying permission -notice follows the copyright notice and publishing information and is -located within the region delineated by the @code{@@titlepage} and -@code{@@end titlepage} commands. The copying permission notice is exactly -the same as the notice in the @code{@@ifinfo} section except that the -paragraph enclosed in @code{@@ignore} and @code{@@end ignore} commands is -not part of the notice.@refill - -To make it simple to insert a permission notice into each section of -the Texinfo file, sample permission notices for each section are -reproduced in full below.@refill - -Note that you may need to specify the correct name of a section -mentioned in the permission notice. For example, in @cite{The GDB -Manual}, the name of the section referring to the General Public -License is called the ``GDB General Public License'', but in the -sample shown below, that section is referred to generically as the -``GNU General Public License''. If the Texinfo file does not carry a -copy of the General Public License, leave out the reference to it, but -be sure to include the rest of the sentence.@refill - -@node ifinfo Permissions, Titlepage Permissions, Inserting Permissions, Sample Permissions -@comment node-name, next, previous, up -@appendixsec @samp{ifinfo} Copying Permissions -@cindex @samp{ifinfo} permissions - -In the @code{@@ifinfo} section of a Texinfo file, the standard Free -Software Foundation permission notice reads as follows:@refill - -@example -This file documents @dots{} - -Copyright 1992 Free Software Foundation, Inc. - -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 a 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 also that the sections -entitled ``Copying'' and ``GNU General Public License'' -are included exactly as in the original, and 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 example - -@node Titlepage Permissions, , ifinfo Permissions, Sample Permissions -@comment node-name, next, previous, up -@appendixsec Titlepage Copying Permissions -@cindex Titlepage permissions - -In the @code{@@titlepage} section of a Texinfo file, the standard Free -Software Foundation copying permission notice follows the copyright -notice and publishing information. The standard phrasing is as -follows:@refill - -@example -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 sections -entitled ``Copying'' and ``GNU General Public License'' -are included exactly as in the original, and 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 example - -@node Include Files, Headings, Sample Permissions, Top -@comment node-name, next, previous, up -@appendix Include Files -@cindex Include files - -When @TeX{} or an Info formatting command sees an @code{@@include} -command in a Texinfo file, it processes the contents of the file named -by the command and incorporates them into the @sc{dvi} or Info file being -created. Index entries from the included file are incorporated into -the indices of the output file.@refill - -Include files let you keep a single large document as a collection of -conveniently small parts.@refill - -@menu -* Using Include Files:: How to use the @code{@@include} command. -* texinfo-multiple-files-update:: How to create and update nodes and - menus when using included files. -* Include File Requirements:: What @code{texinfo-multiple-files-update} expects. -* Sample Include File:: A sample outer file with included files - within it; and a sample included file. -* Include Files Evolution:: How use of the @code{@@include} command - has changed over time. -@end menu - -@node Using Include Files, texinfo-multiple-files-update, , Include Files -@appendixsec How to Use Include Files -@findex include - -To include another file within a Texinfo file, write the -@code{@@include} command at the beginning of a line and follow it on -the same line by the name of a file to be included. For -example:@refill - -@example -@@include buffers.texi -@end example - -An included file should simply be a segment of text that you expect to -be included as is into the overall or @dfn{outer} Texinfo file; it -should not contain the standard beginning and end parts of a Texinfo -file. In particular, you should not start an included file with a -line saying @samp{\input texinfo}; if you do, that phrase is inserted -into the output file as is. Likewise, you should not end an included -file with an @code{@@bye} command; nothing after @code{@@bye} is -formatted.@refill - -In the past, you were required to write an @code{@@setfilename} line at the -beginning of an included file, but no longer. Now, it does not matter -whether you write such a line. If an @code{@@setfilename} line exists -in an included file, it is ignored.@refill - -Conventionally, an included file begins with an @code{@@node} line that -is followed by an @code{@@chapter} line. Each included file is one -chapter. This makes it easy to use the regular node and menu creating -and updating commands to create the node pointers and menus within the -included file. However, the simple Emacs node and menu creating and -updating commands do not work with multiple Texinfo files. Thus you -cannot use these commands to fill in the `Next', `Previous', and `Up' -pointers of the @code{@@node} line that begins the included file. Also, -you cannot use the regular commands to create a master menu for the -whole file. Either you must insert the menus and the `Next', -`Previous', and `Up' pointers by hand, or you must use the GNU Emacs -Texinfo mode command, @code{texinfo-multiple-files-update}, that is -designed for @code{@@include} files.@refill - -@node texinfo-multiple-files-update, Include File Requirements, Using Include Files, Include Files -@appendixsec @code{texinfo-multiple-files-update} -@findex texinfo-multiple-files-update - -@c !!! changed wording to prevent overfull hbox --bob 26 Mar 93 -GNU Emacs Texinfo mode provides a command to handle included files -called @code{texinfo-multiple-files-update}. This command creates or -updates `Next', `Previous', and `Up' pointers of included files as -well as those in the outer or overall Texinfo file, and it creates or -updates a main menu in the outer file. Depending whether you call it -with optional arguments, the command updates only the pointers in the -first @code{@@node} line of the included files or all of them:@refill - -@table @kbd -@item M-x texinfo-multiple-files-update -Called without any arguments:@refill - -@itemize @minus -@item -Create or update the `Next', `Previous', and `Up' pointers of the -first @code{@@node} line in each file included in an outer or overall -Texinfo file.@refill - -@item -Create or update the `Top' level node pointers of the outer or -overall file.@refill - -@item -Create or update a main menu in the outer file.@refill -@end itemize - -@item C-u M-x texinfo-multiple-files-update -Called with @kbd{C-u} as a prefix argument: - -@itemize @minus{} -@item -Create or update pointers in the first @code{@@node} line in each -included file. - -@item -Create or update the `Top' level node pointers of the outer file. - -@item -Create and insert a master menu in the outer file. The master menu -is made from all the menus in all the included files.@refill -@end itemize - -@item C-u 8 M-x texinfo-multiple-files-update -Called with a numeric prefix argument, such as @kbd{C-u 8}: - -@itemize @minus -@item -Create or update @strong{all} the `Next', `Previous', and `Up' pointers -of all the included files.@refill - -@item -Create or update @strong{all} the menus of all the included -files.@refill - -@item -Create or update the `Top' level node pointers of the outer or -overall file.@refill - -@item -And then create a master menu in the outer file. This is similar to -invoking @code{texinfo-master-menu} with an argument when you are -working with just one file.@refill -@end itemize -@end table - -Note the use of the prefix argument in interactive use: with a regular -prefix argument, just @w{@kbd{C-u}}, the -@code{texinfo-multiple-files-update} command inserts a master menu; -with a numeric prefix argument, such as @kbd{C-u 8}, the command -updates @strong{every} pointer and menu in @strong{all} the files and then inserts a -master menu.@refill - -@node Include File Requirements, Sample Include File, texinfo-multiple-files-update, Include Files -@appendixsec Include File Requirements -@cindex Include file requirements -@cindex Requirements for include files - -If you plan to use the @code{texinfo-multiple-files-update} command, -the outer Texinfo file that lists included files within it should -contain nothing but the beginning and end parts of a Texinfo file, and -a number of @code{@@include} commands listing the included files. It -should not even include indices, which should be listed in an included -file of their own.@refill - -Moreover, each of the included files must contain exactly one highest -level node (conventionally, @code{@@chapter} or equivalent), -and this node must be the first node in the included file. -Furthermore, each of these highest level nodes in each included file -must be at the same hierarchical level in the file structure. -Usually, each is an @code{@@chapter}, an @code{@@appendix}, or an -@code{@@unnumbered} node. Thus, normally, each included file contains -one, and only one, chapter or equivalent-level node.@refill - -The outer file should contain only @emph{one} node, the `Top' node. It -should @emph{not} contain any nodes besides the single `Top' node. The -@code{texinfo-multiple-files-update} command will not process -them.@refill - -@node Sample Include File, Include Files Evolution, Include File Requirements, Include Files -@appendixsec Sample File with @code{@@include} -@cindex Sample @code{@@include} file -@cindex Include file sample -@cindex @code{@@include} file sample - -Here is an example of a complete outer Texinfo file with @code{@@include} files -within it before running @code{texinfo-multiple-files-update}, which -would insert a main or master menu:@refill - -@example -@group -\input texinfo @@c -*-texinfo-*- -@c %**start of header -@@setfilename include-example.info -@@settitle Include Example -@c %**end of header -@end group - -@group -@@setchapternewpage odd -@@titlepage -@@sp 12 -@@center @@titlefont@{Include Example@} -@@sp 2 -@@center by Whom Ever -@end group - -@group -@@page -@@vskip 0pt plus 1filll -Copyright @@copyright@{@} 1990 Free Software Foundation, Inc. -@@end titlepage -@end group - -@group -@@ifinfo -@@node Top, First, (dir), (dir) -@@top Master Menu -@@end ifinfo -@end group - -@group -@@include foo.texinfo -@@include bar.texinfo -@@include concept-index.texinfo -@end group - -@group -@@summarycontents -@@contents - -@@bye -@end group -@end example - -An included file, such as @file{foo.texinfo}, might look like -this:@refill - -@example -@group -@@node First, Second, , Top -@@chapter First Chapter - -Contents of first chapter @dots{} -@end group -@end example - -The full contents of @file{concept-index.texinfo} might be as simple as this: - -@example -@group -@@node Concept Index, , Second, Top -@@unnumbered Concept Index - -@@printindex cp -@end group -@end example - -The outer Texinfo source file for @cite{The GNU Emacs Lisp Reference -Manual} is named @file{elisp.texi}. This outer file contains a master -menu with 417 entries and a list of 41 @code{@@include} -files.@refill - -@node Include Files Evolution, , Sample Include File, Include Files -@comment node-name, next, previous, up -@appendixsec Evolution of Include Files - -When Info was first created, it was customary to create many small -Info files on one subject. Each Info file was formatted from its own -Texinfo source file. This custom meant that Emacs did not need to -make a large buffer to hold the whole of a large Info file when -someone wanted information; instead, Emacs allocated just enough -memory for the small Info file that contained the particular -information sought. This way, Emacs could avoid wasting memory.@refill - -References from one file to another were made by referring to the file -name as well as the node name. (@xref{Other Info Files, , Referring to -Other Info Files}. Also, see @ref{Four and Five Arguments, , -@code{@@xref} with Four and Five Arguments}.)@refill - -Include files were designed primarily as a way to create a single, -large printed manual out of several smaller Info files. In a printed -manual, all the references were within the same document, so @TeX{} -could automatically determine the references' page numbers. The Info -formatting commands used include files only for creating joint -indices; each of the individual Texinfo files had to be formatted for -Info individually. (Each, therefore, required its own -@code{@@setfilename} line.)@refill - -However, because large Info files are now split automatically, it is -no longer necessary to keep them small.@refill - -Nowadays, multiple Texinfo files are used mostly for large documents, -such as @cite{The GNU Emacs Lisp Reference Manual}, and for projects -in which several different people write different sections of a -document simultaneously.@refill - -In addition, the Info formatting commands have been extended to work -with the @code{@@include} command so as to create a single large Info -file that is split into smaller files if necessary. This means that -you can write menus and cross references without naming the different -Texinfo files.@refill - -@node Headings, Catching Mistakes, Include Files, Top -@comment node-name, next, previous, up -@appendix Page Headings -@cindex Headings -@cindex Footings -@cindex Page numbering -@cindex Page headings -@cindex Formatting headings and footings - -Most printed manuals contain headings along the top of every page -except the title and copyright pages. Some manuals also contain -footings. (Headings and footings have no meaning to Info, which is -not paginated.)@refill - -@menu -* Headings Introduced:: Conventions for using page headings. -* Heading Format:: Standard page heading formats. -* Heading Choice:: How to specify the type of page heading. -* Custom Headings:: How to create your own headings and footings. -@end menu - -@node Headings Introduced, Heading Format, , Headings -@ifinfo -@heading Headings Introduced -@end ifinfo - -Texinfo provides standard page heading formats for manuals that are printed -on one side of each sheet of paper and for manuals that are printed on -both sides of the paper. Usually, you will use one or other of these -formats, but you can specify your own format, if you wish.@refill - -In addition, you can specify whether chapters should begin on a new -page, or merely continue the same page as the previous chapter; and if -chapters begin on new pages, you can specify whether they must be -odd-numbered pages.@refill - -By convention, a book is printed on both sides of each sheet of paper. -When you open a book, the right-hand page is odd-numbered, and -chapters begin on right-hand pages---a preceding left-hand page is -left blank if necessary. Reports, however, are often printed on just -one side of paper, and chapters begin on a fresh page immediately -following the end of the preceding chapter. In short or informal -reports, chapters often do not begin on a new page at all, but are -separated from the preceding text by a small amount of whitespace.@refill - -The @code{@@setchapternewpage} command controls whether chapters begin -on new pages, and whether one of the standard heading formats is used. -In addition, Texinfo has several heading and footing commands that you -can use to generate your own heading and footing formats.@refill - -In Texinfo, headings and footings are single lines at the tops and -bottoms of pages; you cannot create multiline headings or footings. -Each header or footer line is divided into three parts: a left part, a -middle part, and a right part. Any part, or a whole line, may be left -blank. Text for the left part of a header or footer line is set -flushleft; text for the middle part is centered; and, text for the -right part is set flushright.@refill - -@node Heading Format, Heading Choice, Headings Introduced, Headings -@comment node-name, next, previous, up -@appendixsec Standard Heading Formats - -Texinfo provides two standard heading formats, one for manuals printed -on one side of each sheet of paper, and the other for manuals printed -on both sides of the paper. - -By default, nothing is specified for the footing of a Texinfo file, -so the footing remains blank.@refill - -The standard format for single-sided printing consists of a header -line in which the left-hand part contains the name of the chapter, the -central part is blank, and the right-hand part contains the page -number.@refill - -@need 950 -A single-sided page looks like this: - -@example -@group - _______________________ - | | - | chapter page number | - | | - | Start of text ... | - | ... | - | | - -@end group -@end example - -The standard format for two-sided printing depends on whether the page -number is even or odd. By convention, even-numbered pages are on the -left- and odd-numbered pages are on the right. (@TeX{} will adjust the -widths of the left- and right-hand margins. Usually, widths are -correct, but during double-sided printing, it is wise to check that -pages will bind properly---sometimes a printer will produce output in -which the even-numbered pages have a larger right-hand margin than the -odd-numbered pages.)@refill - -In the standard double-sided format, the left part of the left-hand -(even-numbered) page contains the page number, the central part is -blank, and the right part contains the title (specified by the -@code{@@settitle} command). The left part of the right-hand -(odd-numbered) page contains the name of the chapter, the central part -is blank, and the right part contains the page number.@refill - -@need 750 -Two pages, side by side as in an open book, look like this:@refill - -@example -@group - _______________________ _______________________ - | | | | - | page number title | | chapter page number | - | | | | - | Start of text ... | | More text ... | - | ... | | ... | - | | | | - -@end group -@end example - -@noindent -The chapter name is preceded by the word @samp{Chapter}, the chapter -number and a colon. This makes it easier to keep track of where you -are in the manual.@refill - -@node Heading Choice, Custom Headings, Heading Format, Headings -@comment node-name, next, previous, up -@appendixsec Specifying the Type of Heading - -@TeX{} does not begin to generate page headings for a standard Texinfo -file until it reaches the @code{@@end titlepage} command. Thus, the -title and copyright pages are not numbered. The @code{@@end -titlepage} command causes @TeX{} to begin to generate page headings -according to a standard format specified by the -@code{@@setchapternewpage} command that precedes the -@code{@@titlepage} section.@refill - -@need 1000 -There are four possibilities:@refill - -@table @asis -@item No @code{@@setchapternewpage} command -Cause @TeX{} to specify the single-sided heading format, with chapters -on new pages. This is the same as @code{@@setchapternewpage on}.@refill - -@item @code{@@setchapternewpage on} -Specify the single-sided heading format, with chapters on new pages.@refill - -@item @code{@@setchapternewpage off} -Cause @TeX{} to start a new chapter on the same page as the last page of -the preceding chapter, after skipping some vertical whitespace. Also -cause @TeX{} to typeset for single-sided printing. (You can override -the headers format with the @code{@@headings double} command; see -@ref{headings on off, , The @code{@@headings} Command}.)@refill - -@item @code{@@setchapternewpage odd} -Specify the double-sided heading format, with chapters on new pages.@refill -@end table - -@noindent -Texinfo lacks an @code{@@setchapternewpage even} command.@refill - -@node Custom Headings, , Heading Choice, Headings -@comment node-name, next, previous, up -@appendixsec How to Make Your Own Headings - -You can use the standard headings provided with Texinfo or specify -your own.@refill - -@c Following paragraph is verbose to prevent overfull hboxes. -Texinfo provides six commands for specifying headings and -footings. The @code{@@everyheading} command and -@code{@@everyfooting} command generate page headers and footers -that are the same for both even- and odd-numbered pages. -The @code{@@evenheading} command and @code{@@evenfooting} -command generate headers and footers for even-numbered -(left-hand) pages; and the @code{@@oddheading} command and -@code{@@oddfooting} command generate headers and footers for -odd-numbered (right-hand) pages.@refill - -Write custom heading specifications in the Texinfo file immediately -after the @code{@@end titlepage} command. Enclose your specifications -between @code{@@iftex} and @code{@@end iftex} commands since the -@code{texinfo-format-buffer} command may not recognize them. Also, -you must cancel the predefined heading commands with the -@code{@@headings off} command before defining your own -specifications.@refill - -@need 1000 -Here is how to tell @TeX{} to place the chapter name at the left, the -page number in the center, and the date at the right of every header -for both even- and odd-numbered pages:@refill - -@example -@group -@@iftex -@@headings off -@@everyheading @@thischapter @@| @@thispage @@| @@today@{@} -@@end iftex -@end group -@end example - -@noindent -You need to divide the left part from the central part and the central -part from the right had part by inserting @samp{@@|} between parts. -Otherwise, the specification command will not be able to tell where -the text for one part ends and the next part begins.@refill - -Each part can contain text or @@-commands. The text -is printed as if the part were within an ordinary paragraph in the -body of the page. The @@-commands replace -themselves with the page number, date, chapter name, or -whatever.@refill - -@need 950 -Here are the six heading and footing commands:@refill - -@findex everyheading -@findex everyfooting -@table @code -@item @@everyheading @var{left} @@| @var{center} @@| @var{right} -@itemx @@everyfooting @var{left} @@| @var{center} @@| @var{right} - -The `every' commands specify the format for both even- and odd-numbered -pages. These commands are for documents that are printed on one side -of each sheet of paper, or for documents in which you want symmetrical -headers or footers.@refill - -@findex evenheading -@findex evenfooting -@findex oddheading -@findex oddfooting -@item @@evenheading @var{left} @@| @var{center} @@| @var{right} -@itemx @@oddheading @var{left} @@| @var{center} @@| @var{right} - -@itemx @@evenfooting @var{left} @@| @var{center} @@| @var{right} -@itemx @@oddfooting @var{left} @@| @var{center} @@| @var{right} - -The `even' and `odd' commands specify the format for even-numbered -pages and odd-numbered pages. These commands are for books and -manuals that are printed on both sides of each sheet of paper.@refill -@end table - -Use the @samp{@@this@dots{}} series of @@-commands to -provide the names of chapters -and sections and the page number. You can use the -@samp{@@this@dots{}} commands in the left, center, or right portions -of headers and footers, or anywhere else in a Texinfo file so long as -they are between @code{@@iftex} and @code{@@end iftex} commands.@refill - -@need 1000 -Here are the @samp{@@this@dots{}} commands:@refill - -@table @code -@findex thispage -@item @@thispage -Expands to the current page number.@refill -@c !!! Karl Berry says that `thissection' fails on page breaks. -@ignore -@item @@thissection -Expands to the name of the current section.@refill -@end ignore - -@findex thischaptername -@item @@thischaptername -Expands to the name of the current chapter.@refill - -@findex thischapter -@item @@thischapter -Expands to the number and name of the current -chapter, in the format `Chapter 1: Title'.@refill - -@findex thistitle -@item @@thistitle -Expands to the name of the document, as specified by the -@code{@@settitle} command.@refill - -@findex thisfile -@item @@thisfile -For @code{@@include} files only: expands to the name of the current -@code{@@include} file. If the current Texinfo source file is not an -@code{@@include} file, this command has no effect. This command does -@emph{not} provide the name of the current Texinfo source file unless -it is an @code{@@include} file. (@xref{Include Files}, for more -information about @code{@@include} files.)@refill -@end table - -@noindent -You can also use the @code{@@today@{@}} command, which expands to the -current date, in `1 Jan 1900' format.@refill -@findex today - -Other @@-commands and text are printed in a header or footer just as -if they were in the body of a page. It is useful to incorporate text, -particularly when you are writing drafts:@refill - -@example -@group -@@iftex -@@headings off -@@everyheading @@emph@{Draft!@} @@| @@thispage @@| @@thischapter -@@everyfooting @@| @@| Version: 0.27: @@today@{@} -@@end iftex -@end group -@end example - -Beware of overlong titles: they may overlap another part of the -header or footer and blot it out.@refill - -@node Catching Mistakes, Refilling Paragraphs, Headings, Top -@comment node-name, next, previous, up -@appendix Formatting Mistakes -@cindex Structure, catching mistakes in -@cindex Nodes, catching mistakes -@cindex Catching mistakes -@cindex Correcting mistakes -@cindex Mistakes, catching -@cindex Problems, catching -@cindex Debugging the Texinfo structure - -Besides mistakes in the content of your documentation, there -are two kinds of mistake you can make with Texinfo: you can make mistakes -with @@-commands, and you can make mistakes with the structure of the -nodes and chapters.@refill - -Emacs has two tools for catching the @@-command mistakes and two for -catching structuring mistakes.@refill - -For finding problems with @@-commands, you can run @TeX{} or a region -formatting command on the region that has a problem; indeed, you can -run these commands on each region as you write it.@refill - -For finding problems with the structure of nodes and chapters, you can use -@kbd{C-c C-s} (@code{texinfo-show-structure}) and the related @code{occur} -command and you can use the @kbd{M-x Info-validate} command.@refill - -@menu -* makeinfo preferred:: @code{makeinfo} finds errors. -* Debugging with Info:: How to catch errors with Info formatting. -* Debugging with TeX:: How to catch errors with @TeX{} formatting. -* Using texinfo-show-structure:: How to use @code{texinfo-show-structure}. -* Using occur:: How to list all lines containing a pattern. -* Running Info-Validate:: How to find badly referenced nodes. -@end menu - -@node makeinfo preferred, Debugging with Info, , Catching Mistakes -@ifinfo -@heading @code{makeinfo} Find Errors -@end ifinfo - -@c !!! changed wording to prevent overfull hbox --bob 26 Mar 93 -The @code{makeinfo} program does an excellent job of catching errors -and reporting them---far better than either the -@code{texinfo-format-region} or the @code{texinfo-format-buffer} -command. In addition, the various functions for automatically -creating and updating node pointers and menus remove many -opportunities for human error.@refill - -If you can, use the updating commands to create and insert pointers -and menus. These prevent many errors. Then use @code{makeinfo} (or -its Texinfo mode manifestations, @code{makeinfo-region} and -@code{makeinfo-buffer}) to format your file and check for other -errors. This is the best way to work with Texinfo. But if you -cannot use @code{makeinfo}, or your problem is very puzzling, then you -may want to use the tools described in this appendix.@refill - -@node Debugging with Info, Debugging with TeX, makeinfo preferred, Catching Mistakes -@comment node-name, next, previous, up -@appendixsec Catching Errors with Info Formatting -@cindex Catching errors with Info formatting -@cindex Debugging with Info formatting - -After you have written part of a Texinfo file, you can use the -@code{texinfo-format-region} or the @code{makeinfo-region} command to -see whether the region formats properly.@refill - -Most likely, however, you are reading this section because for some -reason you cannot use the @code{makeinfo-region} command; therefore, the -rest of this section presumes that you are using -@code{texinfo-format-region}.@refill - -@c !!! changed wording to prevent overfull hbox --bob 26 Mar 93 -If you make a mistake with an @@-command, -@code{texinfo-format-region} will stop processing at or after the -error and display an error message. To see where in the buffer the -error occurred, switch to the @samp{*Info Region*} buffer; the cursor -will be in a position that is after the location of the error. Also, -the text will not be formatted after the place where the error -occurred (or more precisely, where it was detected).@refill - -For example, if you accidentally end a menu with the command @code{@@end -menus} with an `s' on the end, instead of with @code{@@end menu}, you -will see an error message that says:@refill - -@example -@@end menus is not handled by texinfo -@end example - -@noindent -The cursor will stop at the point in the buffer where the error -occurs, or not long after it. The buffer will look like this:@refill - -@example -@group ----------- Buffer: *Info Region* ---------- -* Menu: - -* Using texinfo-show-structure:: How to use - `texinfo-show-structure' - to catch mistakes. -* Running Info-Validate:: How to check for - unreferenced nodes. -@@end menus -@point{} ----------- Buffer: *Info Region* ---------- -@end group -@end example - -The @code{texinfo-format-region} command sometimes provides slightly -odd error messages. For example, the following cross reference fails to format:@refill - -@example -(@@xref@{Catching Mistakes, for more info.) -@end example - -@noindent -In this case, @code{texinfo-format-region} detects the missing closing -brace but displays a message that says @samp{Unbalanced parentheses} -rather than @samp{Unbalanced braces}. This is because the formatting -command looks for mismatches between braces as if they were -parentheses.@refill - -Sometimes @code{texinfo-format-region} fails to detect mistakes. For -example, in the following, the closing brace is swapped with the -closing parenthesis:@refill - -@example -(@@xref@{Catching Mistakes), for more info.@} -@end example - -@noindent -Formatting produces: -@example -(*Note for more info.: Catching Mistakes) -@end example - -The only way for you to detect this error is to realize that the -reference should have looked like this:@refill - -@example -(*Note Catching Mistakes::, for more info.) -@end example - -Incidentally, if you are reading this node in Info and type @kbd{f -@key{RET}} (@code{Info-follow-reference}), you will generate an error -message that says: - -@example -No such node: "Catching Mistakes) The only way @dots{} -@end example - -@noindent -This is because Info perceives the example of the error as the first -cross reference in this node and if you type a @key{RET} immediately -after typing the Info @kbd{f} command, Info will attempt to go to the -referenced node. If you type @kbd{f catch @key{TAB} @key{RET}}, Info -will complete the node name of the correctly written example and take -you to the `Catching Mistakes' node. (If you try this, you can return -from the `Catching Mistakes' node by typing @kbd{l} -(@code{Info-last}).) - -@c !!! section on using Elisp debugger ignored. -@ignore -Sometimes @code{texinfo-format-region} will stop long after the -original error; this is because it does not discover the problem until -then. In this case, you will need to backtrack.@refill - -@c menu -@c * Using the Emacs Lisp Debugger:: How to use the Emacs Lisp debugger. -@c end menu - -@c node Using the Emacs Lisp Debugger -@c appendixsubsec Using the Emacs Lisp Debugger -@c index Using the Emacs Lisp debugger -@c index Emacs Lisp debugger -@c index Debugger, using the Emacs Lisp - -If an error is especially elusive, you can turn on the Emacs Lisp -debugger and look at the backtrace; this tells you where in the -@code{texinfo-format-region} function the problem occurred. You can -turn on the debugger with the command:@refill - -@example -M-x set-variable @key{RET} debug-on-error @key{RET} t @key{RET} -@end example - -@noindent -and turn it off with - -@example -M-x set-variable @key{RET} debug-on-error @key{RET} nil @key{RET} -@end example - -Often, when you are using the debugger, it is easier to follow what is -going on if you use the Emacs Lisp files that are not byte-compiled. -The byte-compiled sources send octal numbers to the debugger that may -look mysterious. To use the uncompiled source files, load -@file{texinfmt.el} and @file{texinfo.el} with the @kbd{M-x load-file} -command.@refill - -The debugger will not catch an error if @code{texinfo-format-region} -does not detect one. In the example shown above, -@code{texinfo-format-region} did not find the error when the whole -list was formatted, but only when part of the list was formatted. -When @code{texinfo-format-region} did not find an error, the debugger -did not find one either. @refill - -However, when @code{texinfo-format-region} did report an error, it -invoked the debugger. This is the backtrace it produced:@refill - -@example ----------- Buffer: *Backtrace* ---------- -Signalling: (search-failed "[@},]") - re-search-forward("[@},]") - (while ...) - (let ...) - texinfo-format-parse-args() - (let ...) - texinfo-format-xref() - funcall(texinfo-format-xref) - (if ...) - (let ...) - (if ...) - (while ...) - texinfo-format-scan() - (save-excursion ...) - (let ...) - texinfo-format-region(103370 103631) -* call-interactively(texinfo-format-region) ----------- Buffer: *Backtrace* ---------- -@end example - -The backtrace is read from the bottom up. -@code{texinfo-format-region} was called interactively; and it, in -turn, called various functions, including @code{texinfo-format-scan}, -@code{texinfo-format-xref} and @code{texinfo-format-parse-args}. -Inside the function @code{texinfo-format-parse-args}, the function -@code{re-search-forward} was called; it was this function that could -not find the missing right-hand brace.@refill - -@xref{Lisp Debug, , Debugging Emacs Lisp, emacs, The GNU Emacs -Manual}, for more information.@refill -@end ignore - -@node Debugging with TeX, Using texinfo-show-structure, Debugging with Info, Catching Mistakes -@comment node-name, next, previous, up -@appendixsec Catching Errors with @TeX{} Formatting -@cindex Catching errors with @TeX{} formatting -@cindex Debugging with @TeX{} formatting - -You can also catch mistakes when you format a file with @TeX{}.@refill - -@c !!! changed wording to prevent overfull hbox --bob 26 Mar 93 -Usually, you do this after you have run -@code{texinfo-format-buffer} (or, better, @code{makeinfo-buffer}) on -the same file, because @code{texinfo-format-buffer} sometimes displays -error messages that make more sense than @TeX{}. (@xref{Debugging -with Info}, for more information.)@refill - -For example, @TeX{} was run on a Texinfo file, part of which is shown -here:@refill - -@example ----------- Buffer: texinfo.texi ---------- -name of the texinfo file as an extension. The -@@samp@{??@} are `wildcards' that cause the shell to -substitute all the raw index files. (@@xref@{sorting -indices, for more information about sorting -indices.)@@refill ----------- Buffer: texinfo.texi ---------- -@end example - -@noindent -(The cross reference lacks a closing brace.) -@TeX{} produced the following output, after which it stopped:@refill - -@example ----------- Buffer: *texinfo-tex-shell* ---------- -Runaway argument? -@{sorting indices, for more information about sorting -indices.) @@refill @@ETC. -! Paragraph ended before @@xref was complete. -<to be read again> - @@par -l.27 - -? ----------- Buffer: *texinfo-tex-shell* ---------- -@end example - -In this case, @TeX{} produced an accurate and -understandable error message: - -@example -Paragraph ended before @@xref was complete. -@end example - -@noindent -@samp{@@par} is an internal @TeX{} command of no relevance to Texinfo. -@samp{l.27} means that @TeX{} detected the problem on line 27 of the -Texinfo file. The @samp{?} is the prompt @TeX{} uses in this -circumstance.@refill - -Unfortunately, @TeX{} is not always so helpful, and sometimes you must -truly be a Sherlock Holmes to discover what went wrong.@refill - -In any case, if you run into a problem like this, you can do one of three -things.@refill - -@enumerate -@item -You can tell @TeX{} to continue running and ignore just this error by -typing @key{RET} at the @samp{?} prompt.@refill - -@item -You can tell @TeX{} to continue running and to ignore all errors as best -it can by typing @kbd{r @key{RET}} at the @samp{?} prompt.@refill - -This is often the best thing to do. However, beware: the one error -may produce a cascade of additional error messages as its consequences -are felt through the rest of the file. (To stop @TeX{} when it is -producing such an avalanche of error messages, type @kbd{C-d} (or -@kbd{C-c C-d}, if you are running a shell inside Emacs Version 18.))@refill - -@item -You can tell @TeX{} to stop this run by typing @kbd{x @key{RET}} -at the @samp{?} prompt.@refill -@end enumerate - -Please note that if you are running @TeX{} inside Emacs, you need to -switch to the shell buffer and line at which @TeX{} offers the @samp{?} -prompt.@refill - -Sometimes @TeX{} will format a file without producing error messages even -though there is a problem. This usually occurs if a command is not ended -but @TeX{} is able to continue processing anyhow. For example, if you fail -to end an itemized list with the @code{@@end itemize} command, @TeX{} will -write a @sc{dvi} file that you can print out. The only error message that -@TeX{} will give you is the somewhat mysterious comment that@refill - -@example -(@@end occurred inside a group at level 1) -@end example - -@noindent -However, if you print the @sc{dvi} file, you will find that the text -of the file that follows the itemized list is entirely indented as if -it were part of the last item in the itemized list. The error message -is the way @TeX{} says that it expected to find an @code{@@end} -command somewhere in the file; but that it could not determine where -it was needed.@refill - -Another source of notoriously hard-to-find errors is a missing -@code{@@end group} command. If you ever are stumped by -incomprehensible errors, look for a missing @code{@@end group} command -first.@refill - -If the Texinfo file lacks header lines, -@TeX{} may stop in the -beginning of its run and display output that looks like the following. -The @samp{*} indicates that @TeX{} is waiting for input.@refill - -@example -This is TeX, Version 2.0 for Berkeley UNIX -(preloaded format=plain-cm 87.10.25) -(test.texinfo [1]) -* -@end example - -@noindent -In this case, simply type @kbd{\end @key{RET}} after the asterisk. Then -write the header lines in the Texinfo file and run the @TeX{} command -again. (Note the use of the backslash, @samp{\}. @TeX{} uses @samp{\} -instead of @samp{@@}; and in this circumstance, you are working -directly with @TeX{}, not with Texinfo.)@refill - -@node Using texinfo-show-structure, Using occur, Debugging with TeX, Catching Mistakes -@comment node-name, next, previous, up -@appendixsec Using @code{texinfo-show-structure} -@cindex Showing the structure of a file -@findex texinfo-show-structure - -It is not always easy to keep track of the nodes, chapters, sections, and -subsections of a Texinfo file. This is especially true if you are revising -or adding to a Texinfo file that someone else has written.@refill - -In GNU Emacs, in Texinfo mode, the @code{texinfo-show-structure} -command lists all the lines that begin with the @@-commands that -specify the structure: @code{@@chapter}, @code{@@section}, -@code{@@appendix}, and so on. With an argument (@w{@kbd{C-u}} -as prefix argument, if interactive), -the command also shows the @code{@@node} lines. The -@code{texinfo-show-structure} command is bound to @kbd{C-c C-s} in -Texinfo mode, by default.@refill - -The lines are displayed in a buffer called the @samp{*Occur*} buffer. -For example, when @code{texinfo-show-structure} was run on an earlier -version of this appendix, it produced the following:@refill - -@smallexample -Lines matching "^@@\\(chapter \\|sect\\|sub\\|unnum\\|major\\| -heading \\|appendix\\)" in buffer texinfo.texi. - 4:@@appendix Formatting Mistakes - 52:@@appendixsec Catching Errors with Info Formatting -222:@@appendixsec Catching Errors with @@TeX@{@} Formatting -338:@@appendixsec Using @@code@{texinfo-show-structure@} -407:@@appendixsubsec Using @@code@{occur@} -444:@@appendixsec Finding Badly Referenced Nodes -513:@@appendixsubsec Running @@code@{Info-validate@} -573:@@appendixsubsec Splitting a File Manually -@end smallexample - -This says that lines 4, 52, and 222 of @file{texinfo.texi} begin with -the @code{@@appendix}, @code{@@appendixsec}, and @code{@@appendixsec} -commands respectively. If you move your cursor into the @samp{*Occur*} -window, you can position the cursor over one of the lines and use the -@kbd{C-c C-c} command (@code{occur-mode-goto-occurrence}), to jump to -the corresponding spot in the Texinfo file. @xref{Other Repeating -Search, , Using Occur, emacs, The GNU Emacs Manual}, for more -information about @code{occur-mode-goto-occurrence}.@refill - -The first line in the @samp{*Occur*} window describes the @dfn{regular -expression} specified by @var{texinfo-heading-pattern}. This regular -expression is the pattern that @code{texinfo-show-structure} looks for. -@xref{Regexps, , Using Regular Expressions, emacs, The GNU Emacs Manual}, -for more information.@refill - -When you invoke the @code{texinfo-show-structure} command, Emacs will -display the structure of the whole buffer. If you want to see the -structure of just a part of the buffer, of one chapter, for example, -use the @kbd{C-x n} (@code{narrow-to-region}) command to mark the -region. (@xref{Narrowing, , , emacs, The GNU Emacs Manual}.) This is -how the example used above was generated. (To see the whole buffer -again, use @kbd{C-x w} (@code{widen}).)@refill - -If you call @code{texinfo-show-structure} with a prefix argument by -typing @w{@kbd{C-u C-c C-s}}, it will list lines beginning with -@code{@@node} as well as the lines beginning with the @@-sign commands -for @code{@@chapter}, @code{@@section}, and the like.@refill - -You can remind yourself of the structure of a Texinfo file by looking at -the list in the @samp{*Occur*} window; and if you have mis-named a node -or left out a section, you can correct the mistake.@refill - -@node Using occur, Running Info-Validate, Using texinfo-show-structure, Catching Mistakes -@comment node-name, next, previous, up -@appendixsec Using @code{occur} -@cindex Occurrences, listing with @code{@@occur} -@findex occur - -Sometimes the @code{texinfo-show-structure} command produces too much -information. Perhaps you want to remind yourself of the overall structure -of a Texinfo file, and are overwhelmed by the detailed list produced by -@code{texinfo-show-structure}. In this case, you can use the @code{occur} -command directly. To do this, type@refill - -@example -@kbd{M-x occur} -@end example - -@noindent -and then, when prompted, type a @dfn{regexp}, a regular expression for -the pattern you want to match. (@xref{Regexps, , Regular Expressions, -emacs, The GNU Emacs Manual}.) The @code{occur} command works from -the current location of the cursor in the buffer to the end of the -buffer. If you want to run @code{occur} on the whole buffer, place -the cursor at the beginning of the buffer.@refill - -For example, to see all the lines that contain the word -@samp{@@chapter} in them, just type @samp{@@chapter}. This will -produce a list of the chapters. It will also list all the sentences -with @samp{@@chapter} in the middle of the line.@refill - -If you want to see only those lines that start with the word -@samp{@@chapter}, type @samp{^@@chapter} when prompted by -@code{occur}. If you want to see all the lines that end with a word -or phrase, end the last word with a @samp{$}; for example, -@samp{catching mistakes$}. This can be helpful when you want to see -all the nodes that are part of the same chapter or section and -therefore have the same `Up' pointer.@refill - -@xref{Other Repeating Search, , Using Occur, emacs , The GNU Emacs Manual}, -for more information.@refill - -@node Running Info-Validate, , Using occur, Catching Mistakes -@comment node-name, next, previous, up -@appendixsec Finding Badly Referenced Nodes -@findex Info-validate -@cindex Nodes, checking for badly referenced -@cindex Checking for badly referenced nodes -@cindex Looking for badly referenced nodes -@cindex Finding badly referenced nodes -@cindex Badly referenced nodes - -You can use the @code{Info-validate} command to check whether any of -the `Next', `Previous', `Up' or other node pointers fail to point to a -node. This command checks that every node pointer points to an -existing node. The @code{Info-validate} command works only on Info -files, not on Texinfo files.@refill - -The @code{makeinfo} program validates pointers automatically, so you -do not need to use the @code{Info-validate} command if you are using -@code{makeinfo}. You only may need to use @code{Info-validate} if you -are unable to run @code{makeinfo} and instead must create an Info file -using @code{texinfo-format-region} or @code{texinfo-format-buffer}, or -if you write an Info file from scratch.@refill - -@menu -* Using Info-validate:: How to run @code{Info-validate}. -* Unsplit:: How to create an unsplit file. -* Tagifying:: How to tagify a file. -* Splitting:: How to split a file manually. -@end menu - -@node Using Info-validate, Unsplit, , Running Info-Validate -@appendixsubsec Running @code{Info-validate} -@cindex Running @code{Info-validate} -@cindex Info validating a large file -@cindex Validating a large file - -To use @code{Info-validate}, visit the Info file you wish to check and -type:@refill - -@example -M-x Info-validate -@end example - -@noindent -(Note that the @code{Info-validate} command requires an upper case -`I'. You may also need to create a tag table before running -@code{Info-validate}. @xref{Tagifying}.)@refill - -If your file is valid, you will receive a message that says ``File appears -valid''. However, if you have a pointer that does not point to a node, -error messages will be displayed in a buffer called @samp{*problems in -info file*}.@refill - -For example, @code{Info-validate} was run on a test file that contained -only the first node of this manual. One of the messages said:@refill - -@example -In node "Overview", invalid Next: Texinfo Mode -@end example - -@noindent -This meant that the node called @samp{Overview} had a `Next' pointer that -did not point to anything (which was true in this case, since the test file -had only one node in it).@refill - -Now suppose we add a node named @samp{Texinfo Mode} to our test case -but we do not specify a `Previous' for this node. Then we will get -the following error message:@refill - -@example -In node "Texinfo Mode", should have Previous: Overview -@end example - -@noindent -This is because every `Next' pointer should be matched by a -`Previous' (in the node where the `Next' points) which points back.@refill - -@code{Info-validate} also checks that all menu entries and cross references -point to actual nodes.@refill - -Note that @code{Info-validate} requires a tag table and does not work -with files that have been split. (The @code{texinfo-format-buffer} -command automatically splits large files.) In order to use -@code{Info-validate} on a large file, you must run -@code{texinfo-format-buffer} with an argument so that it does not split -the Info file; and you must create a tag table for the unsplit -file.@refill - -@node Unsplit, Tagifying, Using Info-validate, Running Info-Validate -@comment node-name, next, previous, up -@appendixsubsec Creating an Unsplit File -@cindex Creating an unsplit file -@cindex Unsplit file creation - -You can run @code{Info-validate} only on a single Info file that has a -tag table. The command will not work on the indirect subfiles that -are generated when a master file is split. If you have a large file -(longer than 70,000 bytes or so), you need to run the -@code{texinfo-format-buffer} or @code{makeinfo-buffer} command in such -a way that it does not create indirect subfiles. You will also need -to create a tag table for the Info file. After you have done this, -you can run @code{Info-validate} and look for badly referenced -nodes.@refill - -@c !!! broke into two paragraphs to prevent overfull hbox --bob 26 Mar 93 -The first step is to create an unsplit Info file. - -To prevent @code{texinfo-format-buffer} from splitting a Texinfo file -into smaller Info files, give a prefix to the @kbd{M-x -texinfo-format-buffer} command:@refill - -@example -C-u M-x texinfo-format-buffer -@end example - -@noindent -or else - -@example -C-u C-c C-e C-b -@end example - -@noindent -When you do this, Texinfo will not split the file and will not create -a tag table for it. @refill -@cindex Making a tag table manually -@cindex Tag table, making manually - -@node Tagifying, Splitting, Unsplit, Running Info-Validate -@appendixsubsec Tagifying a File - -After creating an unsplit Info file, you must create a tag table for -it. Visit the Info file you wish to tagify and type:@refill - -@example -M-x Info-tagify -@end example - -@noindent -(Note the upper case @key{I} in @code{Info-tagify}.) This creates an -Info file with a tag table that you can validate.@refill - -The third step is to validate the Info file:@refill - -@example -M-x Info-validate -@end example - -@noindent -(Note the upper case @key{I} in @code{Info-validate}.) -In brief, the steps are:@refill - -@example -@group -C-u M-x texinfo-format-buffer -M-x Info-tagify -M-x Info-validate -@end group -@end example - -@c !!! changed wording to prevent overfull hbox --bob 26 Mar 93 -After you have validated the node structure, you will be able to rerun -@code{texinfo-format-buffer} in the normal way so it will construct a -tag table and split the file automatically, or you can make the tag -table and split the file manually.@refill - -@node Splitting, , Tagifying, Running Info-Validate -@comment node-name, next, previous, up -@appendixsubsec Splitting a File Manually -@cindex Splitting an Info file manually -@cindex Info file, splitting manually - -You should split a large file or else let the -@code{texinfo-format-buffer} or @code{makeinfo-buffer} command do it -for you automatically. (Generally you will let one of the formatting -commands do this job for you. @xref{Create an Info File}.)@refill - -The split-off files are called the indirect subfiles.@refill - -Info files are split to save memory. With smaller files, Emacs does not -have make such a large buffer to hold the information.@refill - -If an Info file has more than 30 nodes, you should also make a tag -table for it. @xref{Using Info-validate}, for information -about creating a tag table. (Again, tag tables are usually created -automatically by the formatting command; you only need to create a tag -table yourself if you are doing the job manually. Most likely, you -will do this for a large, unsplit file on which you have run -@code{Info-validate}.)@refill - -@c Info-split is autoloaded in `loaddefs.el' in Emacs 18.51 -@ignore -Before running @code{Info-split}, you need to load the @code{info} library -into Emacs by giving the command @kbd{M-x load-library @key{RET} info -@key{RET}}. -@end ignore - -Visit the Info file you wish to tagify and split and type the two -commands:@refill - -@example -M-x Info-tagify -M-x Info-split -@end example - -@noindent -(Note that the @samp{I} in @samp{Info} is upper case.)@refill - -When you use the @code{Info-split} command, the buffer is modified into a -(small) Info file which lists the indirect subfiles. This file should be -saved in place of the original visited file. The indirect subfiles are -written in the same directory the original file is in, with names generated -by appending @samp{-} and a number to the original file name.@refill - -The primary file still functions as an Info file, but it contains just -the tag table and a directory of subfiles.@refill - -@node Refilling Paragraphs, Command Syntax, Catching Mistakes, Top -@comment node-name, next, previous, up -@appendix Refilling Paragraphs -@cindex Refilling paragraphs -@cindex Filling paragraphs -@findex refill - -The @code{@@refill} command refills and, optionally, indents the first -line of a paragraph.@footnote{Perhaps the command should have been -called the @code{@@refillandindent} command, but @code{@@refill} is -shorter and the name was chosen before indenting was possible.} The -@code{@@refill} command is no longer important, but we describe it here -because you once needed it. You will see it in many old Texinfo -files.@refill - -@c !!! changed wording to prevent overfull hbox --bob 26 Mar 93 -Without refilling, paragraphs containing long @@-constructs may look -bad after formatting because the formatter removes @@-commands and -shortens some lines more than others. In the past, neither -@code{texinfo-format-region} nor -@code{texinfo-format-buffer} refilled paragraphs -automatically. The @code{@@refill} command had to be written at the -end of every paragraph to cause these formatters to fill them. (Both -@TeX{} and @code{makeinfo} have always refilled paragraphs -automatically.) Now, all the Info formatters automatically fill and -indent those paragraphs that need to be filled and indented.@refill - -@c !!! changed wording to prevent overfull hbox --bob 26 Mar 93 -The @code{@@refill} command causes both the @code{texinfo-format-region} -command and the -@code{texinfo-format-buffer} command to refill a paragraph in the Info file -@emph{after} all the other processing has been done. For this reason, -you can not use @code{@@refill} with a paragraph containing either -@code{@@*} or @code{@@w@{ @dots{} @}} since the refilling action will -override those two commands.@refill - -The @code{texinfo-format-region} and @code{texinfo-format-buffer} -commands now automatically append @code{@@refill} to the end of each -paragraph that should be filled. They do not append @code{@@refill} to -the ends of paragraphs that contain @code{@@*} or @w{@code{@@w@{ @dots{}@}}} -and therefore do not refill or indent them.@refill - -@node Command Syntax, Obtaining TeX, Refilling Paragraphs, Top -@comment node-name, next, previous, up -@appendix @@-Command Syntax -@cindex @@-command syntax - -The character @samp{@@} is used to start special Texinfo commands. -(It has the same meaning that @samp{\} has in Plain@TeX{}.) Texinfo -has four types of @@-command:@refill - -@table @asis -@item 1. Non-alphabetic commands. -These commands consist of an @@ followed by a punctuation mark or other -character that is not part of the alphabet. Non-alphabetic commands -are almost always part of the text within a paragraph, and never take -any argument. The two characters (@@ and the other one) are complete -in themselves; none is followed by braces. The non-alphabetic -commands are: @code{@@.}, @code{@@:}, @code{@@*}, @code{@@@@}, -@code{@@@{}, and @code{@@@}}.@refill - -@item 2. Alphabetic commands that do not require arguments. -These commands start with @@ followed by a word followed by left- and -right-hand braces. These commands insert special symbols in the -document; they do not require arguments. For example, -@code{@@dots@{@}} @result{} @samp{@dots{}}, @code{@@equiv@{@}} -@result{} @samp{@equiv{}}, @code{@@TeX@{@}} @result{} `@TeX{}', -and @code{@@bullet@{@}} @result{} @samp{@bullet{}}.@refill - -@item 3. Alphabetic commands that require arguments within braces. -These commands start with @@ followed by a letter or a word, followed by an -argument within braces. For example, the command @code{@@dfn} indicates -the introductory or defining use of a term; it is used as follows: @samp{In -Texinfo, @@@@-commands are @@dfn@{mark-up@} commands.}@refill - -@item 4. Alphabetic commands that occupy an entire line. -These commands occupy an entire line. The line starts with @@, -followed by the name of the command (a word); for example, @code{@@center} -or @code{@@cindex}. If no argument is needed, the word is followed by -the end of the line. If there is an argument, it is separated from -the command name by a space. Braces are not used.@refill -@end table - -@cindex Braces and argument syntax -Thus, the alphabetic commands fall into classes that have -different argument syntaxes. You cannot tell to which class a command -belongs by the appearance of its name, but you can tell by the -command's meaning: if the command stands for a glyph, it is in -class 2 and does not require an argument; if it makes sense to use the -command together with other text as part of a paragraph, the command -is in class 3 and must be followed by an argument in braces; -otherwise, it is in class 4 and uses the rest of the line as its -argument.@refill - -The purpose of having a different syntax for commands of classes 3 and -4 is to make Texinfo files easier to read, and also to help the GNU -Emacs paragraph and filling commands work properly. There is only one -exception to this rule: the command @code{@@refill}, which is always -used at the end of a paragraph immediately following the final period -or other punctuation character. @code{@@refill} takes no argument and -does @emph{not} require braces. @code{@@refill} never confuses the -Emacs paragraph commands because it cannot appear at the beginning of -a line.@refill - -@node Obtaining TeX, New Features, Command Syntax, Top -@appendix How to Obtain @TeX{} -@cindex Obtaining @TeX{} -@cindex @TeX{}, how to obtain - -@c !!! Here is information about obtaining TeX. Update it whenever. -@c Last updated by RJC on 6 October 1992 -@c based on message from elisabet@@.u.washington.edu -@TeX{} is freely redistributable. You can obtain @TeX{} for Unix -systems from the University of Washington for a distribution -fee.@refill - -To order a full distribution, send $200.00 for a 1/2-inch 9-track 1600 -bpi (@code{tar} or @code{cpio}) tape reel, or $210.00 for a 1/4-inch -4-track QIC-24 (@code{tar} or @code{cpio}) cartridge, to:@refill - -@display -Northwest Computing Support Center -DR-10, Thomson Hall 35 -University of Washington -Seattle, Washington 98195 -@end display - -@noindent -Please make checks payable to the University of Washington.@refill - -Prepaid orders are preferred but purchase orders are acceptable; -however, purchase orders carry an extra charge of $10.00, to pay for -processing.@refill - -Overseas sites: please add to the base cost $20.00 for shipment via -air parcel post, or $30.00 for shipment via courier.@refill - -Please check with the Northwest Computing Support Center at the -University of Washington for current prices and formats:@refill - -@example -@group -@r{telephone:} (206) 543-6259 -@r{email:} elisabet@@u.washington.edu -@end group -@end example - -@node New Features, Command and Variable Index, Obtaining TeX, Top -@appendix Second Edition Features - -@tex -% Widen the space for the first column so three control-character -% strings fit in the first column. Switched back to default .8in -% value at end of chapter. -\global\tableindent=1.0in -@end tex - -The second edition of the Texinfo manual describes more than 20 new -Texinfo mode commands and more than 50 previously undocumented Texinfo -@@-commands. This edition is more than twice the length of the first -edition.@refill - -Here is a brief description of the new commands.@refill - -@menu -* New Texinfo Mode Commands:: The updating commands are especially useful. -* New Commands:: Many newly described @@-commands. -@end menu - -@node New Texinfo Mode Commands, New Commands, , New Features -@appendixsec New Texinfo Mode Commands - -Texinfo mode provides commands and features especially designed for -working with Texinfo files. More than 20 new commands have been -added, including commands for automatically creating and updating -both nodes and menus. This is a tedious task when done by hand.@refill - -The keybindings are intended to be somewhat mnemonic.@refill - -@subheading Update all nodes and menus - -The @code{texinfo-master-menu} command is the primary command: - -@table @kbd -@item C-c C-u m -@itemx M-x texinfo-master-menu -Create or update a master menu. -With @kbd{C-u} as a prefix argument, -first create or update all nodes -and regular menus. -@end table - -@subheading Update Pointers - -@noindent -Create or update `Next', `Previous', and `Up' node pointers.@refill - -@noindent -@xref{Updating Nodes and Menus}. - -@table @kbd -@item C-c C-u C-n -@itemx M-x texinfo-update-node -Update a node. - -@item C-c C-u C-e -@itemx M-x texinfo-every-node-update -Update every node in the buffer. -@end table - -@subheading Update Menus - -@noindent -Create or update menus.@refill - -@noindent -@xref{Updating Nodes and Menus}. - -@table @kbd -@item C-c C-u C-m -@itemx M-x texinfo-make-menu -Make or update a menu. - -@item C-c C-u C-a -@itemx M-x texinfo-all-menus-update -Make or update all the menus in a buffer. -With @kbd{C-u} as a prefix argument, -first update all the nodes. -@end table - -@subheading Insert Title as Description - -@noindent -Insert a node's chapter or section title in the space for the -description in a menu entry line; position point so you can edit the -insert. (This command works somewhat differently than the other -insertion commands, which insert only a predefined string.)@refill - -@noindent -@xref{Inserting, Inserting Frequently Used Commands}. - -@table @kbd -@item C-c C-c C-d -Insert title. -@end table - -@subheading Format for Info - -@noindent -Provide keybindings both for the Info formatting commands that are -written in Emacs Lisp and for @code{makeinfo} that is written in -C.@refill - -@noindent -@xref{Info Formatting}. - -@noindent -Use the Emacs lisp @code{texinfo-format@dots{}} commands: - -@table @kbd -@item C-c C-e C-r -Format the region. - -@item C-c C-e C-b -Format the buffer. -@end table - -@noindent -Use @code{makeinfo}: - -@table @kbd -@item C-c C-m C-r -Format the region. - -@item C-c C-m C-b -Format the buffer. - -@item C-c C-m C-l -Recenter the @code{makeinfo} output buffer. - -@item C-c C-m C-k -Kill the @code{makeinfo} formatting job. -@end table - -@subheading Typeset and Print - -@noindent -Typeset and print Texinfo documents from within Emacs.@refill - -@ifinfo -@noindent -@xref{Printing}. -@end ifinfo -@iftex -@noindent -@xref{Printing, , Formatting and Printing}. -@end iftex - -@table @kbd -@item C-c C-t C-r -Run @TeX{} on the region. - -@item C-c C-t C-b -Run @TeX{} on the buffer. - -@item C-c C-t C-i -Run @code{texindex}. - -@item C-c C-t C-p -Print the @sc{dvi} file. - -@item C-c C-t C-q -Show the print queue. - -@item C-c C-t C-d -Delete a job from the print queue. - -@item C-c C-t C-k -Kill the current @TeX{} formatting job. - -@item C-c C-t C-x -Quit a currently stopped @TeX{} formatting job. - -@item C-c C-t C-l -Recenter the output buffer. -@end table - -@subheading Other Updating Commands - -@noindent -The ``other updating commands'' do not have standard keybindings because -they are used less frequently.@refill - -@noindent -@xref{Other Updating Commands}. - -@table @kbd -@item M-x texinfo-insert-node-lines -Insert missing @code{@@node} lines using -section titles as node names. - -@item M-x texinfo-multiple-files-update -Update a multi-file document. -With a numeric prefix, such as @kbd{C-u 8}, -update @strong{every} pointer and -menu in @strong{all} the files and -then insert a master menu. - -@item M-x texinfo-indent-menu-description -Indent descriptions in menus. - -@item M-x texinfo-sequential-node-update -Insert node pointers in strict sequence. -@end table - -@node New Commands, , New Texinfo Mode Commands, New Features -@appendixsec New Texinfo @@-Commands - -The second edition of the Texinfo manual describes more than 50 -commands that were not described in the first edition. A third or so -of these commands existed in Texinfo but were not documented in the -manual; the others are new. Here is a listing, with brief -descriptions of them:@refill - -@subheading Indexing - -@noindent -Create your own index, and merge indices.@refill - -@noindent -@xref{Indices}. - -@table @kbd -@item @@defindex @var{index-name} -Define a new index and its indexing command. -See also the @code{@@defcodeindex} command. - -@c written verbosely to avoid overful hbox -@item @@synindex @var{from-index} @var{into-index} -Merge the @var{from-index} index into the @var{into-index} index. -See also the @code{@@syncodeindex} command. -@end table - -@subheading Definitions - -@noindent -Describe functions, variables, macros, -commands, user options, special forms, and other such artifacts in a -uniform format.@refill - -@noindent -@xref{Definition Commands}. - -@table @kbd -@item @@deffn @var{category} @var{name} @var{arguments}@dots{} -Format a description for functions, interactive -commands, and similar entities. - -@item @@defvr, @@defop, @dots{} -15 other related commands. -@end table - -@subheading Glyphs - -@noindent -Indicate the results of evaluation, expansion, -printed output, an error message, equivalence of expressions, and the -location of point.@refill - -@noindent -@xref{Glyphs}. - -@table @kbd -@item @@equiv@{@} -@itemx @equiv{} -Equivalence: - -@item @@error@{@} -@itemx @error{} -Error message - -@item @@expansion@{@} -@itemx @expansion{} -Macro expansion - -@item @@point@{@} -@itemx @point{} -Position of point - -@item @@print@{@} -@itemx @print{} -Printed output - -@item @@result@{@} -@itemx @result{} -Result of an expression -@end table - -@subheading Page Headings - -@noindent -Customize page headings. - -@noindent -@xref{Headings}. - -@table @kbd -@item @@headings @var{on-off-single-double} -Headings on or off, single, or double-sided. - -@item @@evenfooting [@var{left}] @@| [@var{center}] @@| [@var{right}] -Footings for even-numbered (left-hand) pages. - -@item @@evenheading, @@everyheading, @@oddheading, @dots{} -Five other related commands. - -@item @@thischapter -Insert name of chapter and chapter number. - -@item @@thischaptername, @@thisfile, @@thistitle, @@thispage -Related commands. -@end table - -@subheading Formatting - -@noindent -Format blocks of text. - -@noindent -@xref{Quotations and Examples}, and@* -@ref{Lists and Tables, , Making Lists and Tables}. - -@table @kbd -@item @@cartouche -Draw rounded box surrounding text (not in Info). - -@item @@enumerate @var{optional-arg} -Enumerate a list with letters or numbers. - -@item @@exdent @var{line-of-text} -Remove indentation. - -@item @@flushleft -Left justify. - -@item @@flushright -Right justify. - -@item @@format -Do not narrow nor change font. - -@item @@ftable @var{formatting-command} -@itemx @@vtable @var{formatting-command} -Two-column table with indexing. - -@item @@lisp -For an example of Lisp code. - -@item @@smallexample -@itemx @@smalllisp -Like @@table and @@lisp @r{but for} @@smallbook. -@end table - -@subheading Conditionals - -@noindent -Conditionally format text. - -@noindent -@xref{set clear value, , @code{@@set} @code{@@clear} @code{@@value}}.@refill - -@table @kbd -@item @@set @var{flag} [@var{string}] -Set a flag. Optionally, set value -of @var{flag} to @var{string}. - -@item @@clear @var{flag} -Clear a flag. - -@item @@value@{@var{flag}@} -Replace with value to which @var{flag} is set. - -@item @@ifset @var{flag} -Format, if @var{flag} is set. - -@item @@ifclear @var{flag} -Ignore, if @var{flag} is set. -@end table - -@subheading @@heading series for Titles - -@noindent -Produce unnumbered headings that do not appear in a table of contents. - -@noindent -@xref{Structuring}. - -@table @kbd -@item @@heading @var{title} -Unnumbered section-like heading not listed -in the table of contents of a printed manual. - -@item @@chapheading, @@majorheading, @@subheading, @@subsubheading -Related commands. -@end table - -@need 1000 -@subheading Font commands - -@need 1000 -@noindent -@xref{Smallcaps}, and @* -@ref{Fonts}. - -@table @kbd -@item @@r@{@var{text}@} -Print in roman font. - -@item @@sc@{@var{text}@} -Print in @sc{small caps} font. -@end table - -@subheading Miscellaneous - -@noindent -See @ref{title subtitle author, , @code{@@title} @code{@@subtitle} and @code{@@author} Commands},@* -see @ref{Overfull hboxes},@* -see @ref{Footnotes},@* -see @ref{dmn, , Format a Dimension},@* -see @ref{minus, , Inserting a Minus Sign},@* -see @ref{paragraphindent, , Paragraph Indenting},@* -see @ref{Cross Reference Commands},@* -see @ref{title subtitle author, , @code{@@title} @code{@@subtitle} and @code{@@author}}, and@* -see @ref{Custom Headings, , How to Make Your Own Headings}. - -@need 700 -@table @kbd -@item @@author @var{author} -Typeset author's name. - -@item @@finalout -Produce cleaner printed output. - -@item @@footnotestyle -Specify footnote style. - -@item @@dmn@{@var{dimension}@} -Format a dimension. - -@item @@minus@{@} -Generate a minus sign. - -@item @@paragraphindent -Specify paragraph indentation. - -@item @@ref@{@var{node-name}, @r{[}@var{entry}@r{]}, @r{[}@var{topic-or-title}@r{]}, @r{[}@var{info-file}@r{]}, @r{[}@var{manual}@r{]}@} -Make a reference. In the printed manual, the -reference does not start with the word `see'. - -@item @@title @var{title} -Typeset @var{title} in the alternative -title page format. - -@item @@subtitle @var{subtitle} -Typeset @var{subtitle} in the alternative -title page format. - -@item @@today@{@} -Insert the current date. -@end table -@tex -% Switch width of first column of tables back to default value -\global\tableindent=.8in -@end tex - -@node Command and Variable Index, Concept Index, New Features, Top -@comment node-name, next, previous, up -@unnumbered Command and Variable Index - -This is an alphabetical list of all the @@-commands and several -variables. To make the list easier to use, the commands are listed -without their preceding @samp{@@}.@refill - -@printindex fn - -@node Concept Index, , Command and Variable Index, Top -@comment node-name, next, previous, up -@unnumbered Concept Index - -@printindex cp - -@summarycontents -@contents -@bye diff --git a/gnu/usr.bin/texinfo/info-files/Makefile b/gnu/usr.bin/texinfo/info-files/Makefile deleted file mode 100644 index fcccc6a..0000000 --- a/gnu/usr.bin/texinfo/info-files/Makefile +++ /dev/null @@ -1,12 +0,0 @@ -# -# Makefile for INFO files -# - -INFOFILES= dir -NOOBJ= noobj - -install: - ${INSTALL} -c -g ${BINGRP} -o ${BINOWN} -m 444 ${INFOFILES} \ - ${DESTDIR}${INFODIR} - -.include <bsd.prog.mk> diff --git a/gnu/usr.bin/texinfo/info-files/dir b/gnu/usr.bin/texinfo/info-files/dir deleted file mode 100644 index 6c7f900..0000000 --- a/gnu/usr.bin/texinfo/info-files/dir +++ /dev/null @@ -1,54 +0,0 @@ --*- Text -*- -This is the file .../info/dir, which contains the topmost node of the -Info hierarchy. The first time you invoke Info you start off -looking at that node, which is (dir)Top. - -File: dir Node: Top This is the top of the INFO tree - This (the Directory node) gives a menu of major topics. - Typing "d" returns here, "q" exits, "?" lists all INFO commands, "h" - gives a primer for first-timers, "mTexinfo<Return>" visits Texinfo topic, - etc. - --- PLEASE ADD DOCUMENTATION TO THIS TREE. (See INFO topic first.) --- - -* Menu: The list of major topics begins on the next line. - -System utilities: - -* AMD: (amdref). AMD Reference Manual. -* CVS: (cvs). CVS Reference Manual. -* CVS-CLIENT: (cvsclient). CVS client/server Reference Manual. -* DIFF: (diff). DIFF/PATCH Reference Manual. -* DC: (dc). The GNU desk calculator. -* GAWK: (gawk). The GNU AWK language interpreter manual. -* Info: (info). Manual for this documentation browsing system. - -* Send-PR: (send-pr). Manual for the system used to send problem - reports or contributions back to the FreeBSD - maintainers. - -* UUCP: (uucp). UUCP Administration manual. - - -Documentation tools: - -* Makeinfo: (makeinfo). GNU Makeinfo guide. -* PTX: (ptx). GNU permuted index generator. -* Texi: (texi). GNU TexInfo guide. - - -Programming & development tools: - -* GDB annotation: (annotate). Annotations for the GNU Debugger (GDB). -* AS: (as-all). The GNU Assembler manual. -* comerr: (com_err). The Common Error Description library. -* CPP: (cpp). The GNU C pre-processor manual. -* GCC: (gcc). The GNU C/C++ compiler manual. -* GXX Internals: (gxxint). Guide to the internals of the GNU C++ compiler. -* GDB: (gdb). The GNU Debugger (C & C++) manual. -* GDB Internals: (gdbint). Guide to the internals of GDB. -* GMP: (gmp). The GNU MP Math library. -* History: (history). The GNU History library. -* Readline: (readline). The GNU Readline library -* Regex: (regex). The GNU regular expression library. -* Renovate: (reno). The GNU C++ Renovation Project documentation. -* STABS: (stabs). All about the stab debugging information format. diff --git a/gnu/usr.bin/texinfo/info/Makefile b/gnu/usr.bin/texinfo/info/Makefile index 2374d29..9edb4d2 100644 --- a/gnu/usr.bin/texinfo/info/Makefile +++ b/gnu/usr.bin/texinfo/info/Makefile @@ -1,26 +1,30 @@ # -# Bmakefile for GNU info -# # $id$ # +INFOSRCDIR= ${.CURDIR}/../../../../contrib/texinfo/info +TXIDIR= ${.CURDIR}/../../../../contrib/texinfo/libtxi +LIBTXI= ${.CURDIR}/../libtxi/libtxi.a +BINDIR= /usr/bin + PROG= info -SRCS+= dir.c display.c dribble.c echo_area.c filesys.c info-utils.c info.c -SRCS+= infodoc.c infomap.c m-x.c nodes.c search.c session.c signals.c -SRCS+= terminal.c tilde.c window.c indices.c doc.c nodemenu.c -SRCS+= footnotes.c variables.c gc.c xmalloc.c getopt1.c getopt.c +SRCS+= dir.c display.c doc.c echo_area.c filesys.c info-utils.c info.c infodoc.c infomap.c +SRCS+= m-x.c nodes.c search.c session.c signals.c terminal.c tilde.c window.c indices.c +SRCS+= xmalloc.c nodemenu.c footnotes.c dribble.c variables.c gc.c man.c clib.c -CFLAGS+= -I${.CURDIR} -CFLAGS+= -DNAMED_FUNCTIONS=1 -DSTDC_HEADERS=1 -DHAVE_STRERROR -CFLAGS+= -DHAVE_UNISTD_H=1 -DHAVE_STRING_H=1 -DHAVE_VARARGS_H=1 -CFLAGS+= -DHAVE_SYS_FCNTL_H=1 -DHAVE_SETVBUF=1 -DHAVE_GETCWD=1 -DHAVE_BZERO=1 -CFLAGS+= -DHAVE_RINDEX=1 -DHAVE_VFPRINTF=1 -DHAVE_VSPRINTF=1 -CFLAGS+= -DHAVE_SYS_TIME_H=1 -DDEFAULT_INFOPATH='"${INFODIR}"' +# $(INFODIR) is defined in /usr/share/mk/bsd.own.mk +CFLAGS+= -DHANDLE_MAN_PAGES -DNAMED_FUNCTIONS=1 +CFLAGS+= -DDEFAULT_INFOPATH=\"${INFODIR}:/usr/local/info:.\" +CFLAGS+= -DSTDC_HEADERS=1 -DHAVE_UNISTD_H=1 -DHAVE_TERMIOS_H=1 -DHAVE_STRINGS_H=1 -DHAVE_STRING_H=1 +CFLAGS+= -DHAVE_VARARGS_H=1 -DHAVE_SYS_TIME_H=1 -DHAVE_SYS_FCNTL_H=1 -DHAVE_SYS_FILE_H=1 +CFLAGS+= -DHAVE_ALLOCA=1 -DHAVE_SETVBUF=1 -DHAVE_GETCWD=1 -DHAVE_MEMSET=1 -DHAVE_BZERO=1 +CFLAGS+= -DHAVE_STRCHR=1 -DHAVE_STRCASECMP=1 -DHAVE_VFPRINTF=1 -DHAVE_VSPRINTF=1 -DHAVE_STRERROR=1 +CFLAGS+= -DHAVE_SIGPROCMASK=1 -DHAVE_SIGSETMASK=1 -I../libtxi -I$(TXIDIR) -LDADD+= -ltermcap -DPADD+= ${LIBTERMCAP} +LDADD+= -ltermcap -L../libtxi -ltxi +DPADD+= ${LIBTERMCAP} ${LIBTXI} -.include "../../Makefile.inc" -.include <bsd.prog.mk> +.PATH: $(INFOSRCDIR) +.include <bsd.prog.mk> diff --git a/gnu/usr.bin/texinfo/info/dir.c b/gnu/usr.bin/texinfo/info/dir.c deleted file mode 100644 index 3820813..0000000 --- a/gnu/usr.bin/texinfo/info/dir.c +++ /dev/null @@ -1,224 +0,0 @@ -/* dir.c -- How to build a special "dir" node from "localdir" files. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include <stdio.h> -#include <sys/types.h> -#include <sys/stat.h> -#include <sys/file.h> -#include <sys/errno.h> -#include "info-utils.h" -#include "filesys.h" -#include "tilde.h" - -/* The "dir" node can be built from the contents of a file called "dir", - with the addition of the menus of every file called "localdir" found in - INFOPATH. */ - -static void add_menu_to_file_buffer (), insert_text_into_fb_at_binding (); - -void -maybe_build_dir_node (dirname, from_files_named) - char *dirname; - char *from_files_named; -{ - FILE_BUFFER *dir_buffer; - - /* See if the file has already been loaded and exists. */ - dir_buffer = info_find_file (dirname); - - /* If there is no "dir" in the current info path, we cannot build one - from nothing. */ - if (!dir_buffer) - return; - - /* If this directory has already been built, return now. */ - if (dir_buffer->flags & N_CannotGC) - return; - - dir_buffer->flags |= N_CannotGC; - - /* For every file named FROM_FILES_NAMED in the search path, add the - contents of that file's menu to our "dir" node. */ - { - struct stat finfo; - char *this_dir; - int namelen, path_index; - int update_tags = 0; - - namelen = strlen (from_files_named); - path_index = 0; - - /* Using each element of the path, check for "localdir". Do not check - for "localdir.info.Z" or anything else. Only files explictly named - "localdir" are eligible. This is a design decision. There can be - an info file name "localdir.info" which contains information on the - setting up of "localdir" files. */ - while (this_dir = extract_colon_unit (infopath, &path_index)) - { - char *fullpath; - int statable; - - /* Expand a leading tilde if one is present. */ - if (*this_dir == '~') - { - char *tilde_expanded_dirname; - - tilde_expanded_dirname = tilde_expand_word (this_dir); - free (this_dir); - this_dir = tilde_expanded_dirname; - } - - fullpath = (char *)xmalloc (3 + strlen (this_dir) + namelen); - strcpy (fullpath, this_dir); - if (fullpath[strlen (fullpath) - 1] != '/') - strcat (fullpath, "/"); - strcat (fullpath, from_files_named); - - statable = (stat (fullpath, &finfo) == 0); - - if (statable && S_ISREG (finfo.st_mode)) - { - long filesize; - char *contents; - - contents = filesys_read_info_file (fullpath, &filesize, &finfo); - - if (contents) - { - update_tags++; - add_menu_to_file_buffer (contents, filesize, dir_buffer); - free (contents); - } - } - - free (fullpath); - free (this_dir); - } - if (update_tags) - build_tags_and_nodes (dir_buffer); - } -} - -/* Given CONTENTS and FB (a file buffer), add the menu found in CONTENTS - to the menu found in FB->contents. Second argument SIZE is the total - size of CONTENTS. */ -static void -add_menu_to_file_buffer (contents, size, fb) - char *contents; - long size; - FILE_BUFFER *fb; -{ - SEARCH_BINDING contents_binding, fb_binding; - long contents_offset, fb_offset; - - contents_binding.buffer = contents; - contents_binding.start = 0; - contents_binding.end = size; - contents_binding.flags = S_FoldCase | S_SkipDest; - - fb_binding.buffer = fb->contents; - fb_binding.start = 0; - fb_binding.end = fb->filesize; - fb_binding.flags = S_FoldCase | S_SkipDest; - - /* Move to the start of the menus in CONTENTS and FB. */ - contents_offset = search_forward (INFO_MENU_LABEL, &contents_binding); - fb_offset = search_forward (INFO_MENU_LABEL, &fb_binding); - - /* If there is no menu in CONTENTS, quit now. */ - if (contents_offset == -1) - return; - - /* If there is no menu in FB, make one. */ - if (fb_offset == -1) - { - /* Find the start of the second node in this file buffer. If there - is only one node, we will be adding the contents to the end of - this node. */ - fb_offset = find_node_separator (&fb_binding); - - /* If not even a single node separator, give up. */ - if (fb_offset == -1) - return; - - fb_binding.start = fb_offset; - fb_binding.start += - skip_node_separator (fb_binding.buffer + fb_binding.start); - - /* Try to find the next node separator. */ - fb_offset = find_node_separator (&fb_binding); - - /* If found one, consider that the start of the menu. Otherwise, the - start of this menu is the end of the file buffer (i.e., fb->size). */ - if (fb_offset != -1) - fb_binding.start = fb_offset; - else - fb_binding.start = fb_binding.end; - - insert_text_into_fb_at_binding - (fb, &fb_binding, INFO_MENU_LABEL, strlen (INFO_MENU_LABEL)); - - fb_binding.buffer = fb->contents; - fb_binding.start = 0; - fb_binding.end = fb->filesize; - fb_offset = search_forward (INFO_MENU_LABEL, &fb_binding); - if (fb_offset == -1) - abort (); - } - - /* CONTENTS_OFFSET and FB_OFFSET point to the starts of the menus that - appear in their respective buffers. Add the remainder of CONTENTS - to the end of FB's menu. */ - fb_binding.start = fb_offset; - fb_offset = find_node_separator (&fb_binding); - if (fb_offset != -1) - fb_binding.start = fb_offset; - else - fb_binding.start = fb_binding.end; - - insert_text_into_fb_at_binding - (fb, &fb_binding, contents + contents_offset, size - contents_offset); -} - -static void -insert_text_into_fb_at_binding (fb, binding, text, textlen) - FILE_BUFFER *fb; - SEARCH_BINDING *binding; - char *text; - int textlen; -{ - char *contents; - long start, end; - - start = binding->start; - end = fb->filesize; - - contents = (char *)xmalloc (fb->filesize + textlen + 1); - memcpy (contents, fb->contents, start); - memcpy (contents + start, text, textlen); - memcpy (contents + start + textlen, fb->contents + start, end - start); - free (fb->contents); - fb->contents = contents; - fb->filesize += textlen; - fb->finfo.st_size = fb->filesize; -} diff --git a/gnu/usr.bin/texinfo/info/display.c b/gnu/usr.bin/texinfo/info/display.c deleted file mode 100644 index 1a348fe..0000000 --- a/gnu/usr.bin/texinfo/info/display.c +++ /dev/null @@ -1,561 +0,0 @@ -/* display.c -- How to display Info windows. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include <stdio.h> -#include <ctype.h> -#include <sys/types.h> -#include <sys/stat.h> -#include "display.h" - -extern int info_any_buffered_input_p (); /* Found in session.c. */ - -static void free_display (); -static DISPLAY_LINE **make_display (); - -/* An array of display lines which tell us what is currently visible on - the display. */ -DISPLAY_LINE **the_display = (DISPLAY_LINE **)NULL; - -/* Non-zero means do no output. */ -int display_inhibited = 0; - -/* Initialize THE_DISPLAY to WIDTH and HEIGHT, with nothing in it. */ -void -display_initialize_display (width, height) - int width, height; -{ - free_display (the_display); - the_display = make_display (width, height); - display_clear_display (the_display); -} - -/* Clear all of the lines in DISPLAY making the screen blank. */ -void -display_clear_display (display) - DISPLAY_LINE **display; -{ - register int i; - register DISPLAY_LINE *display_line; - - for (i = 0; display_line = display[i]; i++) - { - display[i]->text[0] = '\0'; - display[i]->textlen = 0; - display[i]->inverse = 0; - } -} - -/* Non-zero if we didn't completely redisplay a window. */ -int display_was_interrupted_p = 0; - -/* Update the windows pointed to by WINDOW in the_display. This actually - writes the text on the screen. */ -void -display_update_display (window) - WINDOW *window; -{ - register WINDOW *win; - - display_was_interrupted_p = 0; - - /* For every window in the list, check contents against the display. */ - for (win = window; win; win = win->next) - { - /* Only re-display visible windows which need updating. */ - if (((win->flags & W_WindowVisible) == 0) || - ((win->flags & W_UpdateWindow) == 0) || - (win->height == 0)) - continue; - - display_update_one_window (win); - if (display_was_interrupted_p) - break; - } - - /* Always update the echo area. */ - display_update_one_window (the_echo_area); -} - -/* Display WIN on the_display. Unlike display_update_display (), this - function only does one window. */ -void -display_update_one_window (win) - WINDOW *win; -{ - register char *nodetext; /* Current character to display. */ - register char *last_node_char; /* Position of the last character in node. */ - register int i; /* General use index. */ - char *printed_line; /* Buffer for a printed line. */ - int pl_index = 0; /* Index into PRINTED_LINE. */ - int line_index = 0; /* Number of lines done so far. */ - DISPLAY_LINE **display = the_display; - - /* If display is inhibited, that counts as an interrupted display. */ - if (display_inhibited) - display_was_interrupted_p = 1; - - /* If the window has no height, or display is inhibited, quit now. */ - if (!win->height || display_inhibited) - return; - - /* If the window's first row doesn't appear in the_screen, then it - cannot be displayed. This can happen when the_echo_area is the - window to be displayed, and the screen has shrunk to less than one - line. */ - if ((win->first_row < 0) || (win->first_row > the_screen->height)) - return; - - /* Print each line in the window into our local buffer, and then - check the contents of that buffer against the display. If they - differ, update the display. */ - printed_line = (char *)xmalloc (1 + win->width); - - if (!win->node || !win->line_starts) - goto done_with_node_display; - - nodetext = win->line_starts[win->pagetop]; - last_node_char = win->node->contents + win->node->nodelen; - - for (; nodetext < last_node_char; nodetext++) - { - char *rep, *rep_carried_over, rep_temp[2]; - int replen; - - if (isprint (*nodetext)) - { - rep_temp[0] = *nodetext; - replen = 1; - rep_temp[1] = '\0'; - rep = rep_temp; - } - else - { - if (*nodetext == '\r' || *nodetext == '\n') - { - replen = win->width - pl_index; - } - else - { - rep = printed_representation (*nodetext, pl_index); - replen = strlen (rep); - } - } - - /* If this character can be printed without passing the width of - the line, then stuff it into the line. */ - if (replen + pl_index < win->width) - { - /* Optimize if possible. */ - if (replen == 1) - { - printed_line[pl_index++] = *rep; - } - else - { - for (i = 0; i < replen; i++) - printed_line[pl_index++] = rep[i]; - } - } - else - { - DISPLAY_LINE *entry; - - /* If this character cannot be printed in this line, we have - found the end of this line as it would appear on the screen. - Carefully print the end of the line, and then compare. */ - if (*nodetext == '\n' || *nodetext == '\r' || *nodetext == '\t') - { - printed_line[pl_index] = '\0'; - rep_carried_over = (char *)NULL; - } - else - { - /* The printed representation of this character extends into - the next line. Remember the offset of the last character - printed out of REP so that we can carry the character over - to the next line. */ - for (i = 0; pl_index < (win->width - 1);) - printed_line[pl_index++] = rep[i++]; - - rep_carried_over = rep + i; - - /* If printing the last character in this window couldn't - possibly cause the screen to scroll, place a backslash - in the rightmost column. */ - if (1 + line_index + win->first_row < the_screen->height) - { - if (win->flags & W_NoWrap) - printed_line[pl_index++] = '$'; - else - printed_line[pl_index++] = '\\'; - } - printed_line[pl_index] = '\0'; - } - - /* We have the exact line as it should appear on the screen. - Check to see if this line matches the one already appearing - on the screen. */ - entry = display[line_index + win->first_row]; - - /* If the screen line is inversed, then we have to clear - the line from the screen first. Why, I don't know. */ - if (entry->inverse) - { - terminal_goto_xy (0, line_index + win->first_row); - terminal_clear_to_eol (); - entry->inverse = 0; - entry->text[0] = '\0'; - entry->textlen = 0; - } - - /* Find the offset where these lines differ. */ - for (i = 0; i < pl_index; i++) - if (printed_line[i] != entry->text[i]) - break; - - /* If the lines are not the same length, or if they differed - at all, we must do some redrawing. */ - if ((i != pl_index) || (pl_index != entry->textlen)) - { - /* Move to the proper point on the terminal. */ - terminal_goto_xy (i, line_index + win->first_row); - - /* If there is any text to print, print it. */ - if (i != pl_index) - terminal_put_text (printed_line + i); - - /* If the printed text didn't extend all the way to the edge - of the window, and text was appearing between here and the - edge of the window, clear from here to the end of the line. */ - if ((pl_index < win->width && pl_index < entry->textlen) || - (entry->inverse)) - terminal_clear_to_eol (); - - fflush (stdout); - - /* Update the display text buffer. */ - strcpy (entry->text + i, printed_line + i); - entry->textlen = pl_index; - - /* Lines showing node text are not in inverse. Only modelines - have that distinction. */ - entry->inverse = 0; - } - - /* We have done at least one line. Increment our screen line - index, and check against the bottom of the window. */ - if (++line_index == win->height) - break; - - /* A line has been displayed, and the screen reflects that state. - If there is typeahead pending, then let that typeahead be read - now, instead of continuing with the display. */ - if (info_any_buffered_input_p ()) - { - free (printed_line); - display_was_interrupted_p = 1; - return; - } - - /* Reset PL_INDEX to the start of the line. */ - pl_index = 0; - - /* If there are characters from REP left to print, stuff them - into the buffer now. */ - if (rep_carried_over) - for (; rep[pl_index]; pl_index++) - printed_line[pl_index] = rep[pl_index]; - - /* If this window has chosen not to wrap lines, skip to the end - of the physical line in the buffer, and start a new line here. */ - if (pl_index && (win->flags & W_NoWrap)) - { - char *begin; - - pl_index = 0; - printed_line[0] = '\0'; - - begin = nodetext; - - while ((nodetext < last_node_char) && (*nodetext != '\n')) - nodetext++; - } - } - } - - done_with_node_display: - /* We have reached the end of the node or the end of the window. If it - is the end of the node, then clear the lines of the window from here - to the end of the window. */ - for (; line_index < win->height; line_index++) - { - DISPLAY_LINE *entry = display[line_index + win->first_row]; - - /* If this line has text on it then make it go away. */ - if (entry && entry->textlen) - { - entry->textlen = 0; - entry->text[0] = '\0'; - - terminal_goto_xy (0, line_index + win->first_row); - terminal_clear_to_eol (); - } - } - - /* Finally, if this window has a modeline it might need to be redisplayed. - Check the window's modeline against the one in the display, and update - if necessary. */ - if ((win->flags & W_InhibitMode) == 0) - { - window_make_modeline (win); - line_index = win->first_row + win->height; - - /* This display line must both be in inverse, and have the same - contents. */ - if ((!display[line_index]->inverse) || - (strcmp (display[line_index]->text, win->modeline) != 0)) - { - terminal_goto_xy (0, line_index); - terminal_begin_inverse (); - terminal_put_text (win->modeline); - terminal_end_inverse (); - strcpy (display[line_index]->text, win->modeline); - display[line_index]->inverse = 1; - display[line_index]->textlen = strlen (win->modeline); - fflush (stdout); - } - } - - /* Okay, this window doesn't need updating anymore. */ - win->flags &= ~W_UpdateWindow; - free (printed_line); - fflush (stdout); -} - -/* Scroll the region of the_display starting at START, ending at END, and - moving the lines AMOUNT lines. If AMOUNT is less than zero, the lines - are moved up in the screen, otherwise down. Actually, it is possible - for no scrolling to take place in the case that the terminal doesn't - support it. This doesn't matter to us. */ -void -display_scroll_display (start, end, amount) - int start, end, amount; -{ - register int i, last; - DISPLAY_LINE *temp; - - /* If this terminal cannot do scrolling, give up now. */ - if (!terminal_can_scroll) - return; - - /* If there isn't anything displayed on the screen because it is too - small, quit now. */ - if (!the_display[0]) - return; - - /* If there is typeahead pending, then don't actually do any scrolling. */ - if (info_any_buffered_input_p ()) - return; - - /* Do it on the screen. */ - terminal_scroll_terminal (start, end, amount); - - /* Now do it in the display buffer so our contents match the screen. */ - if (amount > 0) - { - last = end + amount; - - /* Shift the lines to scroll right into place. */ - for (i = 0; i < (end - start); i++) - { - temp = the_display[last - i]; - the_display[last - i] = the_display[end - i]; - the_display[end - i] = temp; - } - - /* The lines have been shifted down in the buffer. Clear all of the - lines that were vacated. */ - for (i = start; i != (start + amount); i++) - { - the_display[i]->text[0] = '\0'; - the_display[i]->textlen = 0; - the_display[i]->inverse = 0; - } - } - - if (amount < 0) - { - last = start + amount; - for (i = 0; i < (end - start); i++) - { - temp = the_display[last + i]; - the_display[last + i] = the_display[start + i]; - the_display[start + i] = temp; - } - - /* The lines have been shifted up in the buffer. Clear all of the - lines that are left over. */ - for (i = end + amount; i != end; i++) - { - the_display[i]->text[0] = '\0'; - the_display[i]->textlen = 0; - the_display[i]->inverse = 0; - } - } -} - -/* Try to scroll lines in WINDOW. OLD_PAGETOP is the pagetop of WINDOW before - having had its line starts recalculated. OLD_STARTS is the list of line - starts that used to appear in this window. OLD_COUNT is the number of lines - that appear in the OLD_STARTS array. */ -void -display_scroll_line_starts (window, old_pagetop, old_starts, old_count) - WINDOW *window; - int old_pagetop, old_count; - char **old_starts; -{ - register int i, old, new; /* Indices into the line starts arrays. */ - int last_new, last_old; /* Index of the last visible line. */ - int old_first, new_first; /* Index of the first changed line. */ - int unchanged_at_top = 0; - int already_scrolled = 0; - - /* Locate the first line which was displayed on the old window. */ - old_first = old_pagetop; - new_first = window->pagetop; - - /* Find the last line currently visible in this window. */ - last_new = window->pagetop + (window->height - 1); - if (last_new > window->line_count) - last_new = window->line_count - 1; - - /* Find the last line which used to be currently visible in this window. */ - last_old = old_pagetop + (window->height - 1); - if (last_old > old_count) - last_old = old_count - 1; - - for (old = old_first, new = new_first; - old < last_old && new < last_new; - old++, new++) - if (old_starts[old] != window->line_starts[new]) - break; - else - unchanged_at_top++; - - /* Loop through the old lines looking for a match in the new lines. */ - for (old = old_first + unchanged_at_top; old < last_old; old++) - { - for (new = new_first; new < last_new; new++) - if (old_starts[old] == window->line_starts[new]) - { - /* Find the extent of the matching lines. */ - for (i = 0; (old + i) < last_old; i++) - if (old_starts[old + i] != window->line_starts[new + i]) - break; - - /* Scroll these lines if there are enough of them. */ - { - int start, end, amount; - - start = (window->first_row - + ((old + already_scrolled) - old_pagetop)); - amount = new - (old + already_scrolled); - end = window->first_row + window->height; - - /* If we are shifting the block of lines down, then the last - AMOUNT lines will become invisible. Thus, don't bother - scrolling them. */ - if (amount > 0) - end -= amount; - - if ((end - start) > 0) - { - display_scroll_display (start, end, amount); - - /* Some lines have been scrolled. Simulate the scrolling - by offsetting the value of the old index. */ - old += i; - already_scrolled += amount; - } - } - } - } -} - -/* Move the screen cursor to directly over the current character in WINDOW. */ -void -display_cursor_at_point (window) - WINDOW *window; -{ - int vpos, hpos; - - vpos = window_line_of_point (window) - window->pagetop + window->first_row; - hpos = window_get_cursor_column (window); - terminal_goto_xy (hpos, vpos); -} - -/* **************************************************************** */ -/* */ -/* Functions Static to this File */ -/* */ -/* **************************************************************** */ - -/* Make a DISPLAY_LINE ** with width and height. */ -static DISPLAY_LINE ** -make_display (width, height) - int width, height; -{ - register int i; - DISPLAY_LINE **display; - - display = (DISPLAY_LINE **)xmalloc ((1 + height) * sizeof (DISPLAY_LINE *)); - - for (i = 0; i < height; i++) - { - display[i] = (DISPLAY_LINE *)xmalloc (sizeof (DISPLAY_LINE)); - display[i]->text = (char *)xmalloc (1 + width); - display[i]->textlen = 0; - display[i]->inverse = 0; - } - display[i] = (DISPLAY_LINE *)NULL; - return (display); -} - -/* Free the storage allocated to DISPLAY. */ -static void -free_display (display) - DISPLAY_LINE **display; -{ - register int i; - register DISPLAY_LINE *display_line; - - if (!display) - return; - - for (i = 0; display_line = display[i]; i++) - { - free (display_line->text); - free (display_line); - } - free (display); -} diff --git a/gnu/usr.bin/texinfo/info/display.h b/gnu/usr.bin/texinfo/info/display.h deleted file mode 100644 index f025403..0000000 --- a/gnu/usr.bin/texinfo/info/display.h +++ /dev/null @@ -1,76 +0,0 @@ -/* display.h -- How the display in Info is done. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#ifndef _DISPLAY_H_ -#define _DISPLAY_H_ - -#include "info-utils.h" -#include "terminal.h" - -typedef struct { - char *text; /* Text of the line as it appears. */ - int textlen; /* Printable Length of TEXT. */ - int inverse; /* Non-zero means this line is inverse. */ -} DISPLAY_LINE; - -/* An array of display lines which tell us what is currently visible on - the display. */ -extern DISPLAY_LINE **the_display; - -/* Non-zero means do no output. */ -extern int display_inhibited; - -/* Non-zero if we didn't completely redisplay a window. */ -extern int display_was_interrupted_p; - -/* Initialize THE_DISPLAY to WIDTH and HEIGHT, with nothing in it. */ -extern void display_initialize_display (); - -/* Clear all of the lines in DISPLAY making the screen blank. */ -extern void display_clear_display (); - -/* Update the windows pointed to by WINDOWS in THE_DISPLAY. This actually - writes the text on the screen. */ -extern void display_update_display (); - -/* Display WIN on THE_DISPLAY. Unlike display_update_display (), this - function only does one window. */ -extern void display_update_one_window (); - -/* Move the screen cursor to directly over the current character in WINDOW. */ -extern void display_cursor_at_point (); - -/* Scroll the region of the_display starting at START, ending at END, and - moving the lines AMOUNT lines. If AMOUNT is less than zero, the lines - are moved up in the screen, otherwise down. Actually, it is possible - for no scrolling to take place in the case that the terminal doesn't - support it. This doesn't matter to us. */ -extern void display_scroll_display (); - -/* Try to scroll lines in WINDOW. OLD_PAGETOP is the pagetop of WINDOW before - having had its line starts recalculated. OLD_STARTS is the list of line - starts that used to appear in this window. OLD_COUNT is the number of lines - that appear in the OLD_STARTS array. */ -extern void display_scroll_line_starts (); - -#endif /* !_DISPLAY_H_ */ diff --git a/gnu/usr.bin/texinfo/info/doc.c b/gnu/usr.bin/texinfo/info/doc.c deleted file mode 100644 index b4cd81f..0000000 --- a/gnu/usr.bin/texinfo/info/doc.c +++ /dev/null @@ -1,128 +0,0 @@ -/* doc.c -- Generated structure containing function names and doc strings. - - This file was automatically made from various source files with the - command "./makedoc". DO NOT EDIT THIS FILE, only "./makedoc.c". - Source files groveled to make this file include: - - ./session.c - ./echo_area.c - ./infodoc.c - ./m-x.c - ./indices.c - ./nodemenu.c - ./footnotes.c - ./variables.c - - An entry in the array FUNCTION_DOC_ARRAY is made for each command - found in the above files; each entry consists of a function pointer, - a string which is the user-visible name of the function, - and a string which documents its purpose. */ - -#include "doc.h" -#include "funs.h" - -FUNCTION_DOC function_doc_array[] = { - -/* Commands found in "./session.c". */ - { info_next_line, "next-line", "Move down to the next line" }, - { info_prev_line, "prev-line", "Move up to the previous line" }, - { info_end_of_line, "end-of-line", "Move to the end of the line" }, - { info_beginning_of_line, "beginning-of-line", "Move to the start of the line" }, - { info_forward_char, "forward-char", "Move forward a character" }, - { info_backward_char, "backward-char", "Move backward a character" }, - { info_forward_word, "forward-word", "Move forward a word" }, - { info_backward_word, "backward-word", "Move backward a word" }, - { info_global_next_node, "global-next-node", "Move forwards or down through node structure" }, - { info_global_prev_node, "global-prev-node", "Move backwards or up through node structure" }, - { info_scroll_forward, "scroll-forward", "Scroll forward in this window" }, - { info_scroll_backward, "scroll-backward", "Scroll backward in this window" }, - { info_beginning_of_node, "beginning-of-node", "Move to the start of this node" }, - { info_end_of_node, "end-of-node", "Move to the end of this node" }, - { info_next_window, "next-window", "Select the next window" }, - { info_prev_window, "prev-window", "Select the previous window" }, - { info_split_window, "split-window", "Split the current window" }, - { info_delete_window, "delete-window", "Delete the current window" }, - { info_keep_one_window, "keep-one-window", "Delete all other windows" }, - { info_scroll_other_window, "scroll-other-window", "Scroll the other window" }, - { info_grow_window, "grow-window", "Grow (or shrink) this window" }, - { info_tile_windows, "tile-windows", "Divide the available screen space among the visible windows" }, - { info_toggle_wrap, "toggle-wrap", "Toggle the state of line wrapping in the current window" }, - { info_next_node, "next-node", "Select the `Next' node" }, - { info_prev_node, "prev-node", "Select the `Prev' node" }, - { info_up_node, "up-node", "Select the `Up' node" }, - { info_last_node, "last-node", "Select the last node in this file" }, - { info_first_node, "first-node", "Select the first node in this file" }, - { info_history_node, "history-node", "Select the most recently selected node" }, - { info_last_menu_item, "last-menu-item", "Select the last item in this node's menu" }, - { info_menu_digit, "menu-digit", "Select this menu item" }, - { info_menu_item, "menu-item", "Read a menu item and select its node" }, - { info_xref_item, "xref-item", "Read a footnote or cross reference and select its node" }, - { info_find_menu, "find-menu", "Move to the start of this node's menu" }, - { info_visit_menu, "visit-menu", "Visit as many menu items at once as possible" }, - { info_goto_node, "goto-node", "Read a node name and select it" }, - { info_top_node, "top-node", "Select the node `Top' in this file" }, - { info_dir_node, "dir-node", "Select the node `(dir)'" }, - { info_kill_node, "kill-node", "Kill this node" }, - { info_view_file, "view-file", "Read the name of a file and select it" }, - { info_print_node, "print-node", "Pipe the contents of this node through INFO_PRINT_COMMAND" }, - { info_search, "search", "Read a string and search for it" }, - { isearch_forward, "isearch-forward", "Search interactively for a string as you type it" }, - { isearch_backward, "isearch-backward", "Search interactively for a string as you type it" }, - { info_move_to_prev_xref, "move-to-prev-xref", "Move to the previous cross reference" }, - { info_move_to_next_xref, "move-to-next-xref", "Move to the next cross reference" }, - { info_select_reference_this_line, "select-reference-this-line", "Select reference or menu item appearing on this line" }, - { info_abort_key, "abort-key", "Cancel current operation" }, - { info_move_to_window_line, "move-to-window-line", "Move to the cursor to a specific line of the window" }, - { info_redraw_display, "redraw-display", "Redraw the display" }, - { info_quit, "quit", "Quit using Info" }, - { info_do_lowercase_version, "do-lowercase-version", "" }, - { info_add_digit_to_numeric_arg, "add-digit-to-numeric-arg", "Add this digit to the current numeric argument" }, - { info_universal_argument, "universal-argument", "Start (or multiply by 4) the current numeric argument" }, - { info_numeric_arg_digit_loop, "numeric-arg-digit-loop", "" }, -/* Commands found in "./echo_area.c". */ - { ea_forward, "echo-area-forward", "Move forward a character" }, - { ea_backward, "echo-area-backward", "Move backward a character" }, - { ea_beg_of_line, "echo-area-beg-of-line", "Move to the start of this line" }, - { ea_end_of_line, "echo-area-end-of-line", "Move to the end of this line" }, - { ea_forward_word, "echo-area-forward-word", "Move forward a word" }, - { ea_backward_word, "echo-area-backward-word", "Move backward a word" }, - { ea_delete, "echo-area-delete", "Delete the character under the cursor" }, - { ea_rubout, "echo-area-rubout", "Delete the character behind the cursor" }, - { ea_abort, "echo-area-abort", "Cancel or quit operation" }, - { ea_newline, "echo-area-newline", "Accept (or force completion of) this line" }, - { ea_quoted_insert, "echo-area-quoted-insert", "Insert next character verbatim" }, - { ea_insert, "echo-area-insert", "Insert this character" }, - { ea_tab_insert, "echo-area-tab-insert", "Insert a TAB character" }, - { ea_transpose_chars, "echo-area-transpose-chars", "Transpose characters at point" }, - { ea_yank, "echo-area-yank", "Yank back the contents of the last kill" }, - { ea_yank_pop, "echo-area-yank-pop", "Yank back a previous kill" }, - { ea_kill_line, "echo-area-kill-line", "Kill to the end of the line" }, - { ea_backward_kill_line, "echo-area-backward-kill-line", "Kill to the beginning of the line" }, - { ea_kill_word, "echo-area-kill-word", "Kill the word following the cursor" }, - { ea_backward_kill_word, "echo-area-backward-kill-word", "Kill the word preceding the cursor" }, - { ea_possible_completions, "echo-area-possible-completions", "List possible completions" }, - { ea_complete, "echo-area-complete", "Insert completion" }, - { ea_scroll_completions_window, "echo-area-scroll-completions-window", "Scroll the completions window" }, -/* Commands found in "./infodoc.c". */ - { info_get_help_window, "get-help-window", "Display help message" }, - { info_get_info_help_node, "get-info-help-node", "Visit Info node `(info)Help'" }, - { describe_key, "describe-key", "Print documentation for KEY" }, - { info_where_is, "where-is", "Show what to type to execute a given command" }, -/* Commands found in "./m-x.c". */ - { describe_command, "describe-command", "Read the name of an Info command and describe it" }, - { info_execute_command, "execute-command", "Read a command name in the echo area and execute it" }, - { set_screen_height, "set-screen-height", "Set the height of the displayed window" }, -/* Commands found in "./indices.c". */ - { info_index_search, "index-search", "Look up a string in the index for this file" }, - { info_next_index_match, "next-index-match", "Go to the next matching index item from the last `\\[index-search]' command" }, - { info_index_apropos, "index-apropos", "Grovel all known info file's indices for a string and build a menu" }, -/* Commands found in "./nodemenu.c". */ - { list_visited_nodes, "list-visited-nodes", "Make a window containing a menu of all of the currently visited nodes" }, - { select_visited_node, "select-visited-node", "Select a node which has been previously visited in a visible window" }, -/* Commands found in "./footnotes.c". */ - { info_show_footnotes, "show-footnotes", "Show the footnotes associated with this node in another window" }, -/* Commands found in "./variables.c". */ - { describe_variable, "describe-variable", "Explain the use of a variable" }, - { set_variable, "set-variable", "Set the value of an Info variable" }, - { (VFunction *)NULL, (char *)NULL, (char *)NULL } -}; diff --git a/gnu/usr.bin/texinfo/info/doc.h b/gnu/usr.bin/texinfo/info/doc.h deleted file mode 100644 index 03d82e0..0000000 --- a/gnu/usr.bin/texinfo/info/doc.h +++ /dev/null @@ -1,58 +0,0 @@ -/* doc.h -- Structure associating function pointers with documentation. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#ifndef _DOC_H_ -#define _DOC_H_ - -#if !defined (NULL) -# define NULL 0x0 -#endif /* !NULL */ - -#if !defined (__FUNCTION_DEF) -# define __FUNCTION_DEF -typedef int Function (); -typedef void VFunction (); -#endif /* _FUNCTION_DEF */ - -typedef struct { - VFunction *func; -#if defined (NAMED_FUNCTIONS) - char *func_name; -#endif /* NAMED_FUNCTIONS */ - char *doc; -} FUNCTION_DOC; - -extern FUNCTION_DOC function_doc_array[]; - -extern char *function_documentation (); -extern char *key_documentation (); -extern char *pretty_keyname (); -extern char *replace_in_documentation (); -extern void info_document_key (); -extern void dump_map_to_message_buffer (); - -#if defined (NAMED_FUNCTIONS) -extern char *function_name (); -extern VFunction *named_function (); -#endif /* NAMED_FUNCTIONS */ -#endif /* !_DOC_H_ */ diff --git a/gnu/usr.bin/texinfo/info/dribble.c b/gnu/usr.bin/texinfo/info/dribble.c deleted file mode 100644 index 3a63a15..0000000 --- a/gnu/usr.bin/texinfo/info/dribble.c +++ /dev/null @@ -1,71 +0,0 @@ -/* dribble.c -- Dribble files for Info. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include <stdio.h> -#include "dribble.h" - -/* When non-zero, it is a stream to write all input characters to for the - duration of this info session. */ -FILE *info_dribble_file = (FILE *)NULL; - -/* Open a dribble file named NAME, perhaps closing an already open one. - This sets the global variable INFO_DRIBBLE_FILE to the open stream. */ -void -open_dribble_file (name) - char *name; -{ - /* Perhaps close existing dribble file. */ - close_dribble_file (); - - info_dribble_file = fopen (name, "w"); - -#if defined (HAVE_SETVBUF) - if (info_dribble_file) -# if defined (SETVBUF_REVERSED) - setvbuf (info_dribble_file, _IONBF, (char *)NULL, 1); -# else - setvbuf (info_dribble_file, (char *)NULL, _IONBF, 1); -# endif /* !SETVBUF_REVERSED */ -#endif /* HAVE_SETVBUF */ -} - -/* If there is a dribble file already open, close it. */ -void -close_dribble_file () -{ - if (info_dribble_file) - { - fflush (info_dribble_file); - fclose (info_dribble_file); - info_dribble_file = (FILE *)NULL; - } -} - -/* Write some output to our existing dribble file. */ -void -dribble (byte) - unsigned char byte; -{ - if (info_dribble_file) - fwrite (&byte, sizeof (unsigned char), 1, info_dribble_file); -} diff --git a/gnu/usr.bin/texinfo/info/dribble.h b/gnu/usr.bin/texinfo/info/dribble.h deleted file mode 100644 index 85bd732..0000000 --- a/gnu/usr.bin/texinfo/info/dribble.h +++ /dev/null @@ -1,41 +0,0 @@ -/* dribble.h -- Functions and vars declared in dribble.c. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#ifndef _DRIBBLE_H_ -#define _DRIBBLE_H_ - -/* When non-zero, it is a stream to write all input characters to for the - duration of this info session. */ -extern FILE *info_dribble_file; - -/* Open a dribble file named NAME, perhaps closing an already open one. - This sets the global variable INFO_DRIBBLE_FILE to the open stream. */ -extern void open_dribble_file (); - -/* If there is a dribble file already open, close it. */ -extern void close_dribble_file (); - -/* Write some output to our existing dribble file. */ -extern void dribble (); - -#endif /* !_DRIBBLE_H_ */ diff --git a/gnu/usr.bin/texinfo/info/echo_area.c b/gnu/usr.bin/texinfo/info/echo_area.c deleted file mode 100644 index a116cc6..0000000 --- a/gnu/usr.bin/texinfo/info/echo_area.c +++ /dev/null @@ -1,1500 +0,0 @@ -/* echo_area.c -- How to read a line in the echo area. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include "info.h" - -/* Non-zero means that C-g was used to quit reading input. */ -int info_aborted_echo_area = 0; - -/* Non-zero means that the echo area is being used to read input. */ -int echo_area_is_active = 0; - -/* The address of the last command executed in the echo area. */ -VFunction *ea_last_executed_command = (VFunction *)NULL; - -/* Non-zero means that the last command executed while reading input - killed some text. */ -int echo_area_last_command_was_kill = 0; - -/* Variables which hold on to the current state of the input line. */ -static char input_line[1 + EA_MAX_INPUT]; -static char *input_line_prompt; -static int input_line_point; -static int input_line_beg; -static int input_line_end; -static NODE input_line_node = { - (char *)NULL, (char *)NULL, (char *)NULL, input_line, EA_MAX_INPUT, 0 -}; - -static void echo_area_initialize_node (); -static void push_echo_area (), pop_echo_area (); -static int echo_area_stack_depth (), echo_area_stack_contains_completions_p (); - -static void ea_kill_text (); - -/* Non-zero means we force the user to complete. */ -static int echo_area_must_complete_p = 0; -static int completions_window_p (); - -/* If non-null, this is a window which was specifically created to display - possible completions output. We remember it so we can delete it when - appropriate. */ -static WINDOW *echo_area_completions_window = (WINDOW *)NULL; - -/* Variables which keep track of the window which was active prior to - entering the echo area. */ -static WINDOW *calling_window = (WINDOW *)NULL; -static NODE *calling_window_node = (NODE *)NULL; -static long calling_window_point = 0; -static long calling_window_pagetop = 0; - -/* Remember the node and pertinent variables of the calling window. */ -static void -remember_calling_window (window) - WINDOW *window; -{ - /* Only do this if the calling window is not the completions window, or, - if it is the completions window and there is no other window. */ - if (!completions_window_p (window) || - ((window == windows) && !(window->next))) - { - calling_window = window; - calling_window_node = window->node; - calling_window_point = window->point; - calling_window_pagetop = window->pagetop; - } -} - -/* Restore the caller's window so that it shows the node that it was showing - on entry to info_read_xxx_echo_area (). */ -static void -restore_calling_window () -{ - register WINDOW *win, *compwin = (WINDOW *)NULL; - - /* If the calling window is still visible, and it is the window that - we used for completions output, then restore the calling window. */ - for (win = windows; win; win = win->next) - { - if (completions_window_p (win)) - compwin = win; - - if (win == calling_window && win == compwin) - { - window_set_node_of_window (calling_window, calling_window_node); - calling_window->point = calling_window_point; - calling_window->pagetop = calling_window_pagetop; - compwin = (WINDOW *)NULL; - break; - } - } - - /* Delete the completions window if it is still present, it isn't the - last window on the screen, and there aren't any prior echo area reads - pending which created a completions window. */ - if (compwin) - { - if ((compwin != windows || windows->next) && - !echo_area_stack_contains_completions_p ()) - { - WINDOW *next; - int pagetop, start, end, amount; - - next = compwin->next; - if (next) - { - start = next->first_row; - end = start + next->height; - amount = - (compwin->height + 1); - pagetop = next->pagetop; - } - - info_delete_window_internal (compwin); - - /* This is not necessary because info_delete_window_internal () - calls echo_area_inform_of_deleted_window (), which does the - right thing. */ -#if defined (UNNECESSARY) - echo_area_completions_window = (WINDOW *)NULL; -#endif /* UNNECESSARY */ - - if (next) - { - display_scroll_display (start, end, amount); - next->pagetop = pagetop; - display_update_display (windows); - } - } - } -} - -/* Set up a new input line with PROMPT. */ -static void -initialize_input_line (prompt) - char *prompt; -{ - input_line_prompt = prompt; - if (prompt) - strcpy (input_line, prompt); - else - input_line[0] = '\0'; - - input_line_beg = input_line_end = input_line_point = strlen (prompt); -} - -static char * -echo_area_after_read () -{ - char *return_value; - - if (info_aborted_echo_area) - { - info_aborted_echo_area = 0; - return_value = (char *)NULL; - } - else - { - if (input_line_beg == input_line_end) - return_value = savestring (""); - else - { - int line_len = input_line_end - input_line_beg; - return_value = (char *) xmalloc (1 + line_len); - strncpy (return_value, &input_line[input_line_beg], line_len); - return_value[line_len] = '\0'; - } - } - return (return_value); -} - -/* Read a line of text in the echo area. Return a malloc ()'ed string, - or NULL if the user aborted out of this read. WINDOW is the currently - active window, so that we can restore it when we need to. PROMPT, if - non-null, is a prompt to print before reading the line. */ -char * -info_read_in_echo_area (window, prompt) - WINDOW *window; - char *prompt; -{ - char *line; - - /* If the echo area is already active, remember the current state. */ - if (echo_area_is_active) - push_echo_area (); - - /* Initialize our local variables. */ - initialize_input_line (prompt); - - /* Initialize the echo area for the first (but maybe not the last) time. */ - echo_area_initialize_node (); - - /* Save away the original node of this window, and the window itself, - so echo area commands can temporarily use this window. */ - remember_calling_window (window); - - /* Let the rest of Info know that the echo area is active. */ - echo_area_is_active++; - active_window = the_echo_area; - - /* Read characters in the echo area. */ - info_read_and_dispatch (); - - echo_area_is_active--; - - /* Restore the original active window and show point in it. */ - active_window = calling_window; - restore_calling_window (); - display_cursor_at_point (active_window); - fflush (stdout); - - /* Get the value of the line. */ - line = echo_area_after_read (); - - /* If there is a previous loop waiting for us, restore it now. */ - if (echo_area_is_active) - pop_echo_area (); - - /* Return the results to the caller. */ - return (line); -} - -/* (re) Initialize the echo area node. */ -static void -echo_area_initialize_node () -{ - register int i; - - for (i = input_line_end; i < sizeof (input_line); i++) - input_line[i] = ' '; - - input_line[i - 1] = '\n'; - window_set_node_of_window (the_echo_area, &input_line_node); - input_line[input_line_end] = '\n'; -} - -/* Prepare to read characters in the echo area. This can initialize the - echo area node, but its primary purpose is to side effect the input - line buffer contents. */ -void -echo_area_prep_read () -{ - if (the_echo_area->node != &input_line_node) - echo_area_initialize_node (); - - the_echo_area->point = input_line_point; - input_line[input_line_end] = '\n'; - display_update_one_window (the_echo_area); - display_cursor_at_point (active_window); -} - - -/* **************************************************************** */ -/* */ -/* Echo Area Movement Commands */ -/* */ -/* **************************************************************** */ - -DECLARE_INFO_COMMAND (ea_forward, "Move forward a character") -{ - if (count < 0) - ea_backward (window, -count, key); - else - { - input_line_point += count; - if (input_line_point > input_line_end) - input_line_point = input_line_end; - } -} - -DECLARE_INFO_COMMAND (ea_backward, "Move backward a character") -{ - if (count < 0) - ea_forward (window, -count, key); - else - { - input_line_point -= count; - if (input_line_point < input_line_beg) - input_line_point = input_line_beg; - } -} - -DECLARE_INFO_COMMAND (ea_beg_of_line, "Move to the start of this line") -{ - input_line_point = input_line_beg; -} - -DECLARE_INFO_COMMAND (ea_end_of_line, "Move to the end of this line") -{ - input_line_point = input_line_end; -} - -#define alphabetic(c) (islower (c) || isupper (c) || isdigit (c)) - -/* Move forward a word in the input line. */ -DECLARE_INFO_COMMAND (ea_forward_word, "Move forward a word") -{ - int c; - - if (count < 0) - ea_backward_word (window, -count, key); - else - { - while (count--) - { - if (input_line_point == input_line_end) - return; - - /* If we are not in a word, move forward until we are in one. - Then, move forward until we hit a non-alphabetic character. */ - c = input_line[input_line_point]; - - if (!alphabetic (c)) - { - while (++input_line_point < input_line_end) - { - c = input_line[input_line_point]; - if (alphabetic (c)) - break; - } - } - - if (input_line_point == input_line_end) - return; - - while (++input_line_point < input_line_end) - { - c = input_line[input_line_point]; - if (!alphabetic (c)) - break; - } - } - } -} - -DECLARE_INFO_COMMAND (ea_backward_word, "Move backward a word") -{ - int c; - - if (count < 0) - ea_forward_word (window, -count, key); - else - { - while (count--) - { - if (input_line_point == input_line_beg) - return; - - /* Like ea_forward_word (), except that we look at the - characters just before point. */ - - c = input_line[input_line_point - 1]; - - if (!alphabetic (c)) - { - while (--input_line_point) - { - c = input_line[input_line_point - 1]; - if (alphabetic (c)) - break; - } - } - - while (input_line_point != input_line_beg) - { - c = input_line[input_line_point - 1]; - if (!alphabetic (c)) - break; - else - --input_line_point; - } - } - } -} - -DECLARE_INFO_COMMAND (ea_delete, "Delete the character under the cursor") -{ - register int i; - - if (count < 0) - ea_rubout (window, -count, key); - else - { - if (input_line_point == input_line_end) - return; - - if (info_explicit_arg || count > 1) - { - int orig_point; - - orig_point = input_line_point; - ea_forward (window, count, key); - ea_kill_text (orig_point, input_line_point); - input_line_point = orig_point; - } - else - { - for (i = input_line_point; i < input_line_end; i++) - input_line[i] = input_line[i + 1]; - - input_line_end--; - } - } -} - -DECLARE_INFO_COMMAND (ea_rubout, "Delete the character behind the cursor") -{ - if (count < 0) - ea_delete (window, -count, key); - else - { - int start; - - if (input_line_point == input_line_beg) - return; - - start = input_line_point; - ea_backward (window, count, key); - - if (info_explicit_arg || count > 1) - ea_kill_text (start, input_line_point); - else - ea_delete (window, count, key); - } -} - -DECLARE_INFO_COMMAND (ea_abort, "Cancel or quit operation") -{ - /* If any text, just discard it, and restore the calling window's node. - If no text, quit. */ - if (input_line_end != input_line_beg) - { - terminal_ring_bell (); - input_line_end = input_line_point = input_line_beg; - if (calling_window->node != calling_window_node) - restore_calling_window (); - } - else - info_aborted_echo_area = 1; -} - -DECLARE_INFO_COMMAND (ea_newline, "Accept (or force completion of) this line") -{ - /* Stub does nothing. Simply here to see if it has been executed. */ -} - -DECLARE_INFO_COMMAND (ea_quoted_insert, "Insert next character verbatim") -{ - unsigned char character; - - character = info_get_another_input_char (); - ea_insert (window, count, character); -} - -DECLARE_INFO_COMMAND (ea_insert, "Insert this character") -{ - register int i; - - if ((input_line_end + 1) == EA_MAX_INPUT) - { - terminal_ring_bell (); - return; - } - - for (i = input_line_end + 1; i != input_line_point; i--) - input_line[i] = input_line[i - 1]; - - input_line[input_line_point] = key; - input_line_point++; - input_line_end++; -} - -DECLARE_INFO_COMMAND (ea_tab_insert, "Insert a TAB character") -{ - ea_insert (window, count, '\t'); -} - -/* Transpose the characters at point. If point is at the end of the line, - then transpose the characters before point. */ -DECLARE_INFO_COMMAND (ea_transpose_chars, "Transpose characters at point") -{ - /* Handle conditions that would make it impossible to transpose - characters. */ - if (!count || !input_line_point || (input_line_end - input_line_beg) < 2) - return; - - while (count) - { - int t; - if (input_line_point == input_line_end) - { - t = input_line[input_line_point - 1]; - - input_line[input_line_point - 1] = input_line[input_line_point - 2]; - input_line[input_line_point - 2] = t; - } - else - { - t = input_line[input_line_point]; - - input_line[input_line_point] = input_line[input_line_point - 1]; - input_line[input_line_point - 1] = t; - - if (count < 0 && input_line_point != input_line_beg) - input_line_point--; - else - input_line_point++; - } - - if (count < 0) - count++; - else - count--; - } -} - -/* **************************************************************** */ -/* */ -/* Echo Area Killing and Yanking */ -/* */ -/* **************************************************************** */ - -static char **kill_ring = (char **)NULL; -static int kill_ring_index = 0; /* Number of kills appearing in KILL_RING. */ -static int kill_ring_slots = 0; /* Number of slots allocated to KILL_RING. */ -static int kill_ring_loc = 0; /* Location of current yank pointer. */ - -/* The largest number of kills that we remember at one time. */ -static int max_retained_kills = 15; - -DECLARE_INFO_COMMAND (ea_yank, "Yank back the contents of the last kill") -{ - register int i; - register char *text; - - if (!kill_ring_index) - { - inform_in_echo_area ("Kill ring is empty"); - return; - } - - text = kill_ring[kill_ring_loc]; - - for (i = 0; text[i]; i++) - ea_insert (window, 1, text[i]); -} - -/* If the last command was yank, or yank_pop, and the text just before - point is identical to the current kill item, then delete that text - from the line, rotate the index down, and yank back some other text. */ -DECLARE_INFO_COMMAND (ea_yank_pop, "Yank back a previous kill") -{ - register int len; - - if (((ea_last_executed_command != ea_yank) && - (ea_last_executed_command != ea_yank_pop)) || - (kill_ring_index == 0)) - return; - - len = strlen (kill_ring[kill_ring_loc]); - - /* Delete the last yanked item from the line. */ - { - register int i, counter; - - counter = input_line_end - input_line_point; - - for (i = input_line_point - len; counter; i++, counter--) - input_line[i] = input_line[i + len]; - - input_line_end -= len; - input_line_point -= len; - } - - /* Get a previous kill, and yank that. */ - kill_ring_loc--; - if (kill_ring_loc < 0) - kill_ring_loc = kill_ring_index - 1; - - ea_yank (window, count, key); -} - -/* Delete the text from point to end of line. */ -DECLARE_INFO_COMMAND (ea_kill_line, "Kill to the end of the line") -{ - if (count < 0) - { - ea_kill_text (input_line_point, input_line_beg); - input_line_point = input_line_beg; - } - else - ea_kill_text (input_line_point, input_line_end); -} - -/* Delete the text from point to beg of line. */ -DECLARE_INFO_COMMAND (ea_backward_kill_line, - "Kill to the beginning of the line") -{ - if (count < 0) - ea_kill_text (input_line_point, input_line_end); - else - { - ea_kill_text (input_line_point, input_line_beg); - input_line_point = input_line_beg; - } -} - -/* Delete from point to the end of the current word. */ -DECLARE_INFO_COMMAND (ea_kill_word, "Kill the word following the cursor") -{ - int orig_point = input_line_point; - - if (count < 0) - ea_backward_kill_word (window, -count, key); - else - { - ea_forward_word (window, count, key); - - if (input_line_point != orig_point) - ea_kill_text (orig_point, input_line_point); - - input_line_point = orig_point; - } -} - -/* Delete from point to the start of the current word. */ -DECLARE_INFO_COMMAND (ea_backward_kill_word, - "Kill the word preceding the cursor") -{ - int orig_point = input_line_point; - - if (count < 0) - ea_kill_word (window, -count, key); - else - { - ea_backward_word (window, count, key); - - if (input_line_point != orig_point) - ea_kill_text (orig_point, input_line_point); - } -} - -/* The way to kill something. This appends or prepends to the last - kill, if the last command was a kill command. If FROM is less - than TO, then the killed text is appended to the most recent kill, - otherwise it is prepended. If the last command was not a kill command, - then a new slot is made for this kill. */ -static void -ea_kill_text (from, to) - int from, to; -{ - register int i, counter, distance; - int killing_backwards, slot; - char *killed_text; - - killing_backwards = (from > to); - - /* If killing backwards, reverse the values of FROM and TO. */ - if (killing_backwards) - { - int temp = from; - from = to; - to = temp; - } - - /* Remember the text that we are about to delete. */ - distance = to - from; - killed_text = (char *)xmalloc (1 + distance); - strncpy (killed_text, &input_line[from], distance); - killed_text[distance] = '\0'; - - /* Actually delete the text from the line. */ - counter = input_line_end - to; - - for (i = from; counter; i++, counter--) - input_line[i] = input_line[i + distance]; - - input_line_end -= distance; - - /* If the last command was a kill, append or prepend the killed text to - the last command's killed text. */ - if (echo_area_last_command_was_kill) - { - char *old, *new; - - slot = kill_ring_loc; - old = kill_ring[slot]; - new = (char *)xmalloc (1 + strlen (old) + strlen (killed_text)); - - if (killing_backwards) - { - /* Prepend TEXT to current kill. */ - strcpy (new, killed_text); - strcat (new, old); - } - else - { - /* Append TEXT to current kill. */ - strcpy (new, old); - strcat (new, killed_text); - } - - free (old); - free (killed_text); - kill_ring[slot] = new; - } - else - { - /* Try to store the kill in a new slot, unless that would cause there - to be too many remembered kills. */ - slot = kill_ring_index; - - if (slot == max_retained_kills) - slot = 0; - - if (slot + 1 > kill_ring_slots) - kill_ring = (char **) xrealloc - (kill_ring, - (kill_ring_slots += max_retained_kills) * sizeof (char *)); - - if (slot != kill_ring_index) - free (kill_ring[slot]); - else - kill_ring_index++; - - kill_ring[slot] = killed_text; - - kill_ring_loc = slot; - } - - /* Notice that the last command was a kill. */ - echo_area_last_command_was_kill++; -} - -/* **************************************************************** */ -/* */ -/* Echo Area Completion */ -/* */ -/* **************************************************************** */ - -/* Pointer to an array of REFERENCE to complete over. */ -static REFERENCE **echo_area_completion_items = (REFERENCE **)NULL; - -/* Sorted array of REFERENCE * which is the possible completions found in - the variable echo_area_completion_items. If there is only one element, - it is the only possible completion. */ -static REFERENCE **completions_found = (REFERENCE **)NULL; -static int completions_found_index = 0; -static int completions_found_slots = 0; - -/* The lowest common denominator found while completing. */ -static REFERENCE *LCD_completion; - -/* Internal functions used by the user calls. */ -static void build_completions (), completions_must_be_rebuilt (); - -/* Variable which holds the output of completions. */ -static NODE *possible_completions_output_node = (NODE *)NULL; - -static char *compwin_name = "*Completions*"; - -/* Return non-zero if WINDOW is a window used for completions output. */ -static int -completions_window_p (window) - WINDOW *window; -{ - int result = 0; - - if (internal_info_node_p (window->node) && - (strcmp (window->node->nodename, compwin_name) == 0)) - result = 1; - - return (result); -} - -/* Workhorse for completion readers. If FORCE is non-zero, the user cannot - exit unless the line read completes, or is empty. */ -char * -info_read_completing_internal (window, prompt, completions, force) - WINDOW *window; - char *prompt; - REFERENCE **completions; - int force; -{ - char *line; - - /* If the echo area is already active, remember the current state. */ - if (echo_area_is_active) - push_echo_area (); - - echo_area_must_complete_p = force; - - /* Initialize our local variables. */ - initialize_input_line (prompt); - - /* Initialize the echo area for the first (but maybe not the last) time. */ - echo_area_initialize_node (); - - /* Save away the original node of this window, and the window itself, - so echo area commands can temporarily use this window. */ - remember_calling_window (window); - - /* Save away the list of items to complete over. */ - echo_area_completion_items = completions; - completions_must_be_rebuilt (); - - active_window = the_echo_area; - echo_area_is_active++; - - /* Read characters in the echo area. */ - while (1) - { - info_read_and_dispatch (); - - line = echo_area_after_read (); - - /* Force the completion to take place if the user hasn't accepted - a default or aborted, and if FORCE is active. */ - if (force && line && *line && completions) - { - register int i; - - build_completions (); - - /* If there is only one completion, then make the line be that - completion. */ - if (completions_found_index == 1) - { - free (line); - line = savestring (completions_found[0]->label); - break; - } - - /* If one of the completions matches exactly, then that is okay, so - return the current line. */ - for (i = 0; i < completions_found_index; i++) - if (stricmp (completions_found[i]->label, line) == 0) - { - free (line); - line = savestring (completions_found[i]->label); - break; - } - - /* If no match, go back and try again. */ - if (i == completions_found_index) - { - inform_in_echo_area ("Not complete"); - continue; - } - } - break; - } - echo_area_is_active--; - - /* Restore the original active window and show point in it. */ - active_window = calling_window; - restore_calling_window (); - display_cursor_at_point (active_window); - fflush (stdout); - - echo_area_completion_items = (REFERENCE **)NULL; - completions_must_be_rebuilt (); - - /* If there is a previous loop waiting for us, restore it now. */ - if (echo_area_is_active) - pop_echo_area (); - - return (line); -} - -/* Read a line in the echo area with completion over COMPLETIONS. */ -char * -info_read_completing_in_echo_area (window, prompt, completions) - WINDOW *window; - char *prompt; - REFERENCE **completions; -{ - return (info_read_completing_internal (window, prompt, completions, 1)); -} - -/* Read a line in the echo area allowing completion over COMPLETIONS, but - not requiring it. */ -char * -info_read_maybe_completing (window, prompt, completions) - WINDOW *window; - char *prompt; - REFERENCE **completions; -{ - return (info_read_completing_internal (window, prompt, completions, 0)); -} - -DECLARE_INFO_COMMAND (ea_possible_completions, "List possible completions") -{ - if (!echo_area_completion_items) - { - ea_insert (window, count, key); - return; - } - - build_completions (); - - if (!completions_found_index) - { - terminal_ring_bell (); - inform_in_echo_area ("No completions"); - } - else if ((completions_found_index == 1) && (key != '?')) - { - inform_in_echo_area ("Sole completion"); - } - else - { - register int i, l; - int limit, count, max_label = 0; - - initialize_message_buffer (); - printf_to_message_buffer - ("There %s %d ", completions_found_index == 1 ? "is" : "are", - completions_found_index); - printf_to_message_buffer - ("completion%s:\n", completions_found_index == 1 ? "" : "s"); - - /* Find the maximum length of a label. */ - for (i = 0; i < completions_found_index; i++) - { - int len = strlen (completions_found[i]->label); - if (len > max_label) - max_label = len; - } - - max_label += 4; - - /* Find out how many columns we should print in. */ - limit = calling_window->width / max_label; - if (limit != 1 && (limit * max_label == calling_window->width)) - limit--; - - /* Avoid a possible floating exception. If max_label > width then - the limit will be 0 and a divide-by-zero fault will result. */ - if (limit == 0) - limit = 1; - - /* How many iterations of the printing loop? */ - count = (completions_found_index + (limit - 1)) / limit; - - /* Watch out for special case. If the number of completions is less - than LIMIT, then just do the inner printing loop. */ - if (completions_found_index < limit) - count = 1; - - /* Print the sorted items, up-and-down alphabetically. */ - for (i = 0; i < count; i++) - { - register int j; - - for (j = 0, l = i; j < limit; j++) - { - if (l >= completions_found_index) - break; - else - { - char *label; - int printed_length, k; - - label = completions_found[l]->label; - printed_length = strlen (label); - printf_to_message_buffer ("%s", label); - - if (j + 1 < limit) - { - for (k = 0; k < max_label - printed_length; k++) - printf_to_message_buffer (" "); - } - } - l += count; - } - printf_to_message_buffer ("\n"); - } - - /* Make a new node to hold onto possible completions. Don't destroy - dangling pointers. */ - { - NODE *temp; - - temp = message_buffer_to_node (); - add_gcable_pointer (temp->contents); - name_internal_node (temp, compwin_name); - possible_completions_output_node = temp; - } - - /* Find a suitable window for displaying the completions output. - First choice is an existing window showing completions output. - If there is only one window, and it is large, make another - (smaller) window, and use that one. Otherwise, use the caller's - window. */ - { - WINDOW *compwin; - - compwin = get_internal_info_window (compwin_name); - - if (!compwin) - { - /* If we can split the window to display most of the completion - items, then do so. */ - if (calling_window->height > (count * 2)) - { - int start, end, pagetop; - - active_window = calling_window; - - /* Perhaps we can scroll this window on redisplay. */ - start = calling_window->first_row; - pagetop = calling_window->pagetop; - - compwin = - window_make_window (possible_completions_output_node); - active_window = the_echo_area; - window_change_window_height - (compwin, -(compwin->height - (count + 2))); - - window_adjust_pagetop (calling_window); - remember_calling_window (calling_window); - -#if defined (SPLIT_BEFORE_ACTIVE) - /* If the pagetop hasn't changed, scrolling the calling - window is a reasonable thing to do. */ - if (pagetop == calling_window->pagetop) - { - end = start + calling_window->height; - display_scroll_display - (start, end, calling_window->prev->height + 1); - } -#else /* !SPLIT_BEFORE_ACTIVE */ - /* If the pagetop has changed, set the new pagetop here. */ - if (pagetop != calling_window->pagetop) - { - int newtop = calling_window->pagetop; - calling_window->pagetop = pagetop; - set_window_pagetop (calling_window, newtop); - } -#endif /* !SPLIT_BEFORE_ACTIVE */ - - echo_area_completions_window = compwin; - remember_window_and_node (compwin, compwin->node); - } - else - compwin = calling_window; - } - - if (compwin->node != possible_completions_output_node) - { - window_set_node_of_window - (compwin, possible_completions_output_node); - remember_window_and_node (compwin, compwin->node); - } - - display_update_display (windows); - } - } -} - -DECLARE_INFO_COMMAND (ea_complete, "Insert completion") -{ - if (!echo_area_completion_items) - { - ea_insert (window, count, key); - return; - } - - /* If KEY is SPC, and we are not forcing completion to take place, simply - insert the key. */ - if (!echo_area_must_complete_p && key == SPC) - { - ea_insert (window, count, key); - return; - } - - if (ea_last_executed_command == ea_complete) - { - /* If the keypress is a SPC character, and we have already tried - completing once, and there are several completions, then check - the batch of completions to see if any continue with a space. - If there are some, insert the space character and continue. */ - if (key == SPC && completions_found_index > 1) - { - register int i, offset; - - offset = input_line_end - input_line_beg; - - for (i = 0; i < completions_found_index; i++) - if (completions_found[i]->label[offset] == ' ') - break; - - if (completions_found[i]) - ea_insert (window, 1, ' '); - else - { - ea_possible_completions (window, count, key); - return; - } - } - else - { - ea_possible_completions (window, count, key); - return; - } - } - - input_line_point = input_line_end; - build_completions (); - - if (!completions_found_index) - terminal_ring_bell (); - else if (LCD_completion->label[0] == '\0') - ea_possible_completions (window, count, key); - else - { - register int i; - input_line_point = input_line_end = input_line_beg; - for (i = 0; LCD_completion->label[i]; i++) - ea_insert (window, 1, LCD_completion->label[i]); - } -} - -/* Utility REFERENCE used to store possible LCD. */ -static REFERENCE LCD_reference = { (char *)NULL, (char *)NULL, (char *)NULL }; - -static void remove_completion_duplicates (); - -/* Variables which remember the state of the most recent call - to build_completions (). */ -static char *last_completion_request = (char *)NULL; -static REFERENCE **last_completion_items = (REFERENCE **)NULL; - -/* How to tell the completion builder to reset internal state. */ -static void -completions_must_be_rebuilt () -{ - maybe_free (last_completion_request); - last_completion_request = (char *)NULL; - last_completion_items = (REFERENCE **)NULL; -} - -/* Build a list of possible completions from echo_area_completion_items, - and the contents of input_line. */ -static void -build_completions () -{ - register int i, len; - register REFERENCE *entry; - char *request; - int informed_of_lengthy_job = 0; - - /* If there are no items to complete over, exit immediately. */ - if (!echo_area_completion_items) - { - completions_found_index = 0; - LCD_completion = (REFERENCE *)NULL; - return; - } - - /* Check to see if this call to build completions is the same as the last - call to build completions. */ - len = input_line_end - input_line_beg; - request = (char *)xmalloc (1 + len); - strncpy (request, &input_line[input_line_beg], len); - request[len] = '\0'; - - if (last_completion_request && last_completion_items && - last_completion_items == echo_area_completion_items && - (strcmp (last_completion_request, request) == 0)) - { - free (request); - return; - } - - maybe_free (last_completion_request); - last_completion_request = request; - last_completion_items = echo_area_completion_items; - - /* Always start at the beginning of the list. */ - completions_found_index = 0; - LCD_completion = (REFERENCE *)NULL; - - for (i = 0; entry = echo_area_completion_items[i]; i++) - { - if (strnicmp (request, entry->label, len) == 0) - add_pointer_to_array (entry, completions_found_index, - completions_found, completions_found_slots, - 20, REFERENCE *); - - if (!informed_of_lengthy_job && completions_found_index > 100) - { - informed_of_lengthy_job = 1; - window_message_in_echo_area ("Building completions..."); - } - } - - if (!completions_found_index) - return; - - /* Sort and prune duplicate entries from the completions array. */ - remove_completion_duplicates (); - - /* If there is only one completion, just return that. */ - if (completions_found_index == 1) - { - LCD_completion = completions_found[0]; - return; - } - - /* Find the least common denominator. */ - { - long shortest = 100000; - - for (i = 1; i < completions_found_index; i++) - { - register int j; - int c1, c2; - - for (j = 0; - (c1 = info_tolower (completions_found[i - 1]->label[j])) && - (c2 = info_tolower (completions_found[i]->label[j])); - j++) - if (c1 != c2) - break; - - if (shortest > j) - shortest = j; - } - - maybe_free (LCD_reference.label); - LCD_reference.label = (char *)xmalloc (1 + shortest); - strncpy (LCD_reference.label, completions_found[0]->label, shortest); - LCD_reference.label[shortest] = '\0'; - LCD_completion = &LCD_reference; - } - - if (informed_of_lengthy_job) - echo_area_initialize_node (); -} - -/* Function called by qsort. */ -static int -compare_references (entry1, entry2) - REFERENCE **entry1, **entry2; -{ - return (stricmp ((*entry1)->label, (*entry2)->label)); -} - -/* Prune duplicate entries from COMPLETIONS_FOUND. */ -static void -remove_completion_duplicates () -{ - register int i, j; - REFERENCE **temp; - int newlen; - - if (!completions_found_index) - return; - - /* Sort the items. */ - qsort (completions_found, completions_found_index, sizeof (REFERENCE *), - compare_references); - - for (i = 0, newlen = 1; i < completions_found_index - 1; i++) - { - if (strcmp (completions_found[i]->label, - completions_found[i + 1]->label) == 0) - completions_found[i] = (REFERENCE *)NULL; - else - newlen++; - } - - /* We have marked all the dead slots. It is faster to copy the live slots - twice than to prune the dead slots one by one. */ - temp = (REFERENCE **)xmalloc ((1 + newlen) * sizeof (REFERENCE *)); - for (i = 0, j = 0; i < completions_found_index; i++) - if (completions_found[i]) - temp[j++] = completions_found[i]; - - for (i = 0; i < newlen; i++) - completions_found[i] = temp[i]; - - completions_found[i] = (REFERENCE *)NULL; - completions_found_index = newlen; - free (temp); -} - -/* Scroll the "other" window. If there is a window showing completions, scroll - that one, otherwise scroll the window which was active on entering the read - function. */ -DECLARE_INFO_COMMAND (ea_scroll_completions_window, "Scroll the completions window") -{ - WINDOW *compwin; - int old_pagetop; - - compwin = get_internal_info_window (compwin_name); - - if (!compwin) - compwin = calling_window; - - old_pagetop = compwin->pagetop; - - /* Let info_scroll_forward () do the work, and print any messages that - need to be displayed. */ - info_scroll_forward (compwin, count, key); -} - -/* Function which gets called when an Info window is deleted while the - echo area is active. WINDOW is the window which has just been deleted. */ -void -echo_area_inform_of_deleted_window (window) - WINDOW *window; -{ - /* If this is the calling_window, forget what we remembered about it. */ - if (window == calling_window) - { - if (active_window != the_echo_area) - remember_calling_window (active_window); - else - remember_calling_window (windows); - } - - /* If this window was the echo_area_completions_window, then notice that - the window has been deleted. */ - if (window == echo_area_completions_window) - echo_area_completions_window = (WINDOW *)NULL; -} - -/* **************************************************************** */ -/* */ -/* Pushing and Popping the Echo Area */ -/* */ -/* **************************************************************** */ - -/* Push and Pop the echo area. */ -typedef struct { - char *line; - char *prompt; - REFERENCE **comp_items; - int point, beg, end; - int must_complete; - NODE node; - WINDOW *compwin; -} PUSHED_EA; - -static PUSHED_EA **pushed_echo_areas = (PUSHED_EA **)NULL; -static int pushed_echo_areas_index = 0; -static int pushed_echo_areas_slots = 0; - -/* Pushing the echo_area has a side effect of zeroing the completion_items. */ -static void -push_echo_area () -{ - PUSHED_EA *pushed; - - pushed = (PUSHED_EA *)xmalloc (sizeof (PUSHED_EA)); - pushed->line = savestring (input_line); - pushed->prompt = input_line_prompt; - pushed->point = input_line_point; - pushed->beg = input_line_beg; - pushed->end = input_line_end; - pushed->node = input_line_node; - pushed->comp_items = echo_area_completion_items; - pushed->must_complete = echo_area_must_complete_p; - pushed->compwin = echo_area_completions_window; - - add_pointer_to_array (pushed, pushed_echo_areas_index, pushed_echo_areas, - pushed_echo_areas_slots, 4, PUSHED_EA *); - - echo_area_completion_items = (REFERENCE **)NULL; -} - -static void -pop_echo_area () -{ - PUSHED_EA *popped; - - popped = pushed_echo_areas[--pushed_echo_areas_index]; - - strcpy (input_line, popped->line); - free (popped->line); - input_line_prompt = popped->prompt; - input_line_point = popped->point; - input_line_beg = popped->beg; - input_line_end = popped->end; - input_line_node = popped->node; - echo_area_completion_items = popped->comp_items; - echo_area_must_complete_p = popped->must_complete; - echo_area_completions_window = popped->compwin; - completions_must_be_rebuilt (); - - /* If the completion window no longer exists, forget about it. */ - if (echo_area_completions_window) - { - register WINDOW *win; - - for (win = windows; win; win = win->next) - if (echo_area_completions_window == win) - break; - - /* If the window wasn't found, then it has already been deleted. */ - if (!win) - echo_area_completions_window = (WINDOW *)NULL; - } - - free (popped); -} - -static int -echo_area_stack_depth () -{ - return (pushed_echo_areas_index); -} - -/* Returns non-zero if any of the prior stacked calls to read in the echo - area produced a completions window. */ -static int -echo_area_stack_contains_completions_p () -{ - register int i; - - for (i = 0; i < pushed_echo_areas_index; i++) - if (pushed_echo_areas[i]->compwin) - return (1); - - return (0); -} - -/* **************************************************************** */ -/* */ -/* Error Messages While Reading in Echo Area */ -/* */ -/* **************************************************************** */ - -#if defined (HAVE_SYS_TIME_H) -# include <sys/time.h> -# define HAVE_STRUCT_TIMEVAL -#endif /* HAVE_SYS_TIME_H */ - -static void -pause_or_input () -{ -#if defined (FD_SET) - struct timeval timer; - fd_set readfds; - int ready; - - FD_ZERO (&readfds); - FD_SET (fileno (stdin), &readfds); - timer.tv_sec = 2; - timer.tv_usec = 750; - ready = select (1, &readfds, (fd_set *)NULL, (fd_set *)NULL, &timer); -#endif /* FD_SET */ -} - -/* Print MESSAGE right after the end of the current line, and wait - for input or 2.75 seconds, whichever comes first. Then flush the - informational message that was printed. */ -void -inform_in_echo_area (message) - char *message; -{ - register int i; - char *text; - - text = savestring (message); - for (i = 0; text[i] && text[i] != '\n'; i++); - text[i] = '\0'; - - echo_area_initialize_node (); - sprintf (&input_line[input_line_end], "%s[%s]\n", - echo_area_is_active ? " ": "", text); - free (text); - the_echo_area->point = input_line_point; - display_update_one_window (the_echo_area); - display_cursor_at_point (active_window); - fflush (stdout); - pause_or_input (); - echo_area_initialize_node (); -} diff --git a/gnu/usr.bin/texinfo/info/echo_area.h b/gnu/usr.bin/texinfo/info/echo_area.h deleted file mode 100644 index 3b06078..0000000 --- a/gnu/usr.bin/texinfo/info/echo_area.h +++ /dev/null @@ -1,63 +0,0 @@ -/* echo_area.h -- Functions used in reading information from the echo area. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#ifndef _ECHO_AREA_H_ -#define _ECHO_AREA_H_ - -#define EA_MAX_INPUT 256 - -extern int echo_area_is_active, info_aborted_echo_area; - -/* Non-zero means that the last command executed while reading input - killed some text. */ -extern int echo_area_last_command_was_kill; - -extern void inform_in_echo_area (), echo_area_inform_of_deleted_window (); -extern void echo_area_prep_read (); -extern VFunction *ea_last_executed_command; - -/* Read a line of text in the echo area. Return a malloc ()'ed string, - or NULL if the user aborted out of this read. WINDOW is the currently - active window, so that we can restore it when we need to. PROMPT, if - non-null, is a prompt to print before reading the line. */ -extern char *info_read_in_echo_area (); - -/* Read a line in the echo area with completion over COMPLETIONS. - Takes arguments of WINDOW, PROMPT, and COMPLETIONS, a REFERENCE **. */ -char *info_read_completing_in_echo_area (); - -/* Read a line in the echo area allowing completion over COMPLETIONS, but - not requiring it. Takes arguments of WINDOW, PROMPT, and COMPLETIONS, - a REFERENCE **. */ -extern char *info_read_maybe_completing (); - -extern void ea_insert (), ea_quoted_insert (); -extern void ea_beg_of_line (), ea_backward (), ea_delete (), ea_end_of_line (); -extern void ea_forward (), ea_abort (), ea_rubout (), ea_complete (); -extern void ea_newline (), ea_kill_line (), ea_transpose_chars (); -extern void ea_yank (), ea_tab_insert (), ea_possible_completions (); -extern void ea_backward_word (), ea_kill_word (), ea_forward_word (); -extern void ea_yank_pop (), ea_backward_kill_word (); -extern void ea_scroll_completions_window (); - -#endif /* _ECHO_AREA_H_ */ diff --git a/gnu/usr.bin/texinfo/info/filesys.c b/gnu/usr.bin/texinfo/info/filesys.c deleted file mode 100644 index 17004a4..0000000 --- a/gnu/usr.bin/texinfo/info/filesys.c +++ /dev/null @@ -1,625 +0,0 @@ -/* filesys.c -- File system specific functions for hacking this system. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include <stdio.h> -#include <sys/types.h> -#include <sys/stat.h> -#include <sys/file.h> -#include <sys/errno.h> -#include "general.h" -#include "tilde.h" -#include "filesys.h" - -#if !defined (O_RDONLY) -#if defined (HAVE_SYS_FCNTL_H) -#include <sys/fcntl.h> -#else /* !HAVE_SYS_FCNTL_H */ -#include <fcntl.h> -#endif /* !HAVE_SYS_FCNTL_H */ -#endif /* !O_RDONLY */ - -#if !defined (errno) -extern int errno; -#endif /* !errno */ - -/* Found in info-utils.c. */ -extern char *filename_non_directory (); - -#if !defined (BUILDING_LIBRARY) -/* Found in session.c */ -extern int info_windows_initialized_p; - -/* Found in window.c. */ -extern void message_in_echo_area (), unmessage_in_echo_area (); -#endif /* !BUILDING_LIBRARY */ - -/* Local to this file. */ -static char *info_file_in_path (), *lookup_info_filename (); -static void remember_info_filename (), maybe_initialize_infopath (); - -#if !defined (NULL) -# define NULL 0x0 -#endif /* !NULL */ - -typedef struct { - char *suffix; - char *decompressor; -} COMPRESSION_ALIST; - -static char *info_suffixes[] = { - "", - ".info", - "-info", - (char *)NULL -}; - -static COMPRESSION_ALIST compress_suffixes[] = { - { ".Z", "uncompress" }, - { ".Y", "unyabba" }, - { ".gz", "gunzip" }, - { ".z", "gunzip" }, - { (char *)NULL, (char *)NULL } -}; - -/* The path on which we look for info files. You can initialize this - from the environment variable INFOPATH if there is one, or you can - call info_add_path () to add paths to the beginning or end of it. - You can call zap_infopath () to make the path go away. */ -char *infopath = (char *)NULL; -static int infopath_size = 0; - -/* Expand the filename in PARTIAL to make a real name for this operating - system. This looks in INFO_PATHS in order to find the correct file. - If it can't find the file, it returns NULL. */ -static char *local_temp_filename = (char *)NULL; -static int local_temp_filename_size = 0; - -char * -info_find_fullpath (partial) - char *partial; -{ - int initial_character; - char *temp; - - filesys_error_number = 0; - - maybe_initialize_infopath (); - - if (partial && (initial_character = *partial)) - { - char *expansion; - - expansion = lookup_info_filename (partial); - - if (expansion) - return (expansion); - - /* If we have the full path to this file, we still may have to add - various extensions to it. I guess we have to stat this file - after all. */ - if (initial_character == '/') - temp = info_file_in_path (partial + 1, "/"); - else if (initial_character == '~') - { - expansion = tilde_expand_word (partial); - if (*expansion == '/') - { - temp = info_file_in_path (expansion + 1, "/"); - free (expansion); - } - else - temp = expansion; - } - else if (initial_character == '.' && - (partial[1] == '/' || (partial[1] == '.' && partial[2] == '/'))) - { - if (local_temp_filename_size < 1024) - local_temp_filename = (char *)xrealloc - (local_temp_filename, (local_temp_filename_size = 1024)); -#if defined (HAVE_GETCWD) - if (!getcwd (local_temp_filename, local_temp_filename_size)) -#else /* !HAVE_GETCWD */ - if (!getwd (local_temp_filename)) -#endif /* !HAVE_GETCWD */ - { - filesys_error_number = errno; - return (partial); - } - - strcat (local_temp_filename, "/"); - strcat (local_temp_filename, partial); - return (local_temp_filename); - } - else - temp = info_file_in_path (partial, infopath); - - if (temp) - { - remember_info_filename (partial, temp); - if (strlen (temp) > local_temp_filename_size) - local_temp_filename = (char *) xrealloc - (local_temp_filename, - (local_temp_filename_size = (50 + strlen (temp)))); - strcpy (local_temp_filename, temp); - free (temp); - return (local_temp_filename); - } - } - return (partial); -} - -/* Scan the list of directories in PATH looking for FILENAME. If we find - one that is a regular file, return it as a new string. Otherwise, return - a NULL pointer. */ -static char * -info_file_in_path (filename, path) - char *filename, *path; -{ - struct stat finfo; - char *temp_dirname; - int statable, dirname_index; - - dirname_index = 0; - - while (temp_dirname = extract_colon_unit (path, &dirname_index)) - { - register int i, pre_suffix_length; - char *temp; - - /* Expand a leading tilde if one is present. */ - if (*temp_dirname == '~') - { - char *expanded_dirname; - - expanded_dirname = tilde_expand_word (temp_dirname); - free (temp_dirname); - temp_dirname = expanded_dirname; - } - - temp = (char *)xmalloc (30 + strlen (temp_dirname) + strlen (filename)); - strcpy (temp, temp_dirname); - if (temp[(strlen (temp)) - 1] != '/') - strcat (temp, "/"); - strcat (temp, filename); - - pre_suffix_length = strlen (temp); - - free (temp_dirname); - - for (i = 0; info_suffixes[i]; i++) - { - strcpy (temp + pre_suffix_length, info_suffixes[i]); - - statable = (stat (temp, &finfo) == 0); - - /* If we have found a regular file, then use that. Else, if we - have found a directory, look in that directory for this file. */ - if (statable) - { - if (S_ISREG (finfo.st_mode)) - { - return (temp); - } - else if (S_ISDIR (finfo.st_mode)) - { - char *newpath, *filename_only, *newtemp; - - newpath = savestring (temp); - filename_only = filename_non_directory (filename); - newtemp = info_file_in_path (filename_only, newpath); - - free (newpath); - if (newtemp) - { - free (temp); - return (newtemp); - } - } - } - else - { - /* Add various compression suffixes to the name to see if - the file is present in compressed format. */ - register int j, pre_compress_suffix_length; - - pre_compress_suffix_length = strlen (temp); - - for (j = 0; compress_suffixes[j].suffix; j++) - { - strcpy (temp + pre_compress_suffix_length, - compress_suffixes[j].suffix); - - statable = (stat (temp, &finfo) == 0); - if (statable && (S_ISREG (finfo.st_mode))) - return (temp); - } - } - } - free (temp); - } - return ((char *)NULL); -} - -/* Given a string containing units of information separated by colons, - return the next one pointed to by IDX, or NULL if there are no more. - Advance IDX to the character after the colon. */ -char * -extract_colon_unit (string, idx) - char *string; - int *idx; -{ - register int i, start; - - i = start = *idx; - if ((i >= strlen (string)) || !string) - return ((char *) NULL); - - while (string[i] && string[i] != ':') - i++; - if (i == start) - { - return ((char *) NULL); - } - else - { - char *value = (char *) xmalloc (1 + (i - start)); - strncpy (value, &string[start], (i - start)); - value[i - start] = '\0'; - if (string[i]) - ++i; - *idx = i; - return (value); - } -} - -/* A structure which associates a filename with its expansion. */ -typedef struct { - char *filename; - char *expansion; -} FILENAME_LIST; - -/* An array of remembered arguments and results. */ -static FILENAME_LIST **names_and_files = (FILENAME_LIST **)NULL; -static int names_and_files_index = 0; -static int names_and_files_slots = 0; - -/* Find the result for having already called info_find_fullpath () with - FILENAME. */ -static char * -lookup_info_filename (filename) - char *filename; -{ - if (filename && names_and_files) - { - register int i; - for (i = 0; names_and_files[i]; i++) - { - if (strcmp (names_and_files[i]->filename, filename) == 0) - return (names_and_files[i]->expansion); - } - } - return (char *)NULL;; -} - -/* Add a filename and its expansion to our list. */ -static void -remember_info_filename (filename, expansion) - char *filename, *expansion; -{ - FILENAME_LIST *new; - - if (names_and_files_index + 2 > names_and_files_slots) - { - int alloc_size; - names_and_files_slots += 10; - - alloc_size = names_and_files_slots * sizeof (FILENAME_LIST *); - - names_and_files = - (FILENAME_LIST **) xrealloc (names_and_files, alloc_size); - } - - new = (FILENAME_LIST *)xmalloc (sizeof (FILENAME_LIST)); - new->filename = savestring (filename); - new->expansion = expansion ? savestring (expansion) : (char *)NULL; - - names_and_files[names_and_files_index++] = new; - names_and_files[names_and_files_index] = (FILENAME_LIST *)NULL; -} - -static void -maybe_initialize_infopath () -{ - if (!infopath_size) - { - infopath = (char *) - xmalloc (infopath_size = (1 + strlen (DEFAULT_INFOPATH))); - - strcpy (infopath, DEFAULT_INFOPATH); - } -} - -/* Add PATH to the list of paths found in INFOPATH. 2nd argument says - whether to put PATH at the front or end of INFOPATH. */ -void -info_add_path (path, where) - char *path; - int where; -{ - int len; - - if (!infopath) - { - infopath = (char *)xmalloc (infopath_size = 200 + strlen (path)); - infopath[0] = '\0'; - } - - len = strlen (path) + strlen (infopath); - - if (len + 2 >= infopath_size) - infopath = (char *)xrealloc (infopath, (infopath_size += (2 * len) + 2)); - - if (!*infopath) - strcpy (infopath, path); - else if (where == INFOPATH_APPEND) - { - strcat (infopath, ":"); - strcat (infopath, path); - } - else if (where == INFOPATH_PREPEND) - { - char *temp = savestring (infopath); - strcpy (infopath, path); - strcat (infopath, ":"); - strcat (infopath, temp); - free (temp); - } -} - -/* Make INFOPATH have absolutely nothing in it. */ -void -zap_infopath () -{ - if (infopath) - free (infopath); - - infopath = (char *)NULL; - infopath_size = 0; -} - -/* Read the contents of PATHNAME, returning a buffer with the contents of - that file in it, and returning the size of that buffer in FILESIZE. - FINFO is a stat struct which has already been filled in by the caller. - If the file cannot be read, return a NULL pointer. */ -char * -filesys_read_info_file (pathname, filesize, finfo) - char *pathname; - long *filesize; - struct stat *finfo; -{ - *filesize = filesys_error_number = 0; - - if (compressed_filename_p (pathname)) - return (filesys_read_compressed (pathname, filesize, finfo)); - else - { - int descriptor; - char *contents; - - descriptor = open (pathname, O_RDONLY, 0666); - - /* If the file couldn't be opened, give up. */ - if (descriptor < 0) - { - filesys_error_number = errno; - return ((char *)NULL); - } - - /* Try to read the contents of this file. */ - contents = (char *)xmalloc (1 + finfo->st_size); - if ((read (descriptor, contents, finfo->st_size)) != finfo->st_size) - { - filesys_error_number = errno; - close (descriptor); - free (contents); - return ((char *)NULL); - } - - close (descriptor); - - *filesize = finfo->st_size; - return (contents); - } -} - -/* Typically, pipe buffers are 4k. */ -#define BASIC_PIPE_BUFFER (4 * 1024) - -/* We use some large multiple of that. */ -#define FILESYS_PIPE_BUFFER_SIZE (16 * BASIC_PIPE_BUFFER) - -char * -filesys_read_compressed (pathname, filesize, finfo) - char *pathname; - long *filesize; - struct stat *finfo; -{ - FILE *stream; - char *command, *decompressor; - char *contents = (char *)NULL; - - *filesize = filesys_error_number = 0; - - decompressor = filesys_decompressor_for_file (pathname); - - if (!decompressor) - return ((char *)NULL); - - command = (char *)xmalloc (10 + strlen (pathname) + strlen (decompressor)); - sprintf (command, "%s < %s", decompressor, pathname); - -#if !defined (BUILDING_LIBRARY) - if (info_windows_initialized_p) - { - char *temp; - - temp = (char *)xmalloc (5 + strlen (command)); - sprintf (temp, "%s...", command); - message_in_echo_area ("%s", temp); - free (temp); - } -#endif /* !BUILDING_LIBRARY */ - - stream = popen (command, "r"); - free (command); - - /* Read chunks from this file until there are none left to read. */ - if (stream) - { - int offset, size; - char *chunk; - - offset = size = 0; - chunk = (char *)xmalloc (FILESYS_PIPE_BUFFER_SIZE); - - while (1) - { - int bytes_read; - - bytes_read = fread (chunk, 1, FILESYS_PIPE_BUFFER_SIZE, stream); - - if (bytes_read + offset >= size) - contents = (char *)xrealloc - (contents, size += (2 * FILESYS_PIPE_BUFFER_SIZE)); - - memcpy (contents + offset, chunk, bytes_read); - offset += bytes_read; - if (bytes_read != FILESYS_PIPE_BUFFER_SIZE) - break; - } - - free (chunk); - pclose (stream); - contents = (char *)xrealloc (contents, offset + 1); - *filesize = offset; - } - else - { - filesys_error_number = errno; - } - -#if !defined (BUILDING_LIBARARY) - if (info_windows_initialized_p) - unmessage_in_echo_area (); -#endif /* !BUILDING_LIBRARY */ - return (contents); -} - -/* Return non-zero if FILENAME belongs to a compressed file. */ -int -compressed_filename_p (filename) - char *filename; -{ - char *decompressor; - - /* Find the final extension of this filename, and see if it matches one - of our known ones. */ - decompressor = filesys_decompressor_for_file (filename); - - if (decompressor) - return (1); - else - return (0); -} - -/* Return the command string that would be used to decompress FILENAME. */ -char * -filesys_decompressor_for_file (filename) - char *filename; -{ - register int i; - char *extension = (char *)NULL; - - /* Find the final extension of FILENAME, and see if it appears in our - list of known compression extensions. */ - for (i = strlen (filename) - 1; i > 0; i--) - if (filename[i] == '.') - { - extension = filename + i; - break; - } - - if (!extension) - return ((char *)NULL); - - for (i = 0; compress_suffixes[i].suffix; i++) - if (strcmp (extension, compress_suffixes[i].suffix) == 0) - return (compress_suffixes[i].decompressor); - - return ((char *)NULL); -} - -/* The number of the most recent file system error. */ -int filesys_error_number = 0; - -#if !defined (HAVE_STRERROR) -extern const char * const sys_errlist[]; -extern int sys_nerr; - -char * -strerror (num) - int num; -{ - if (num >= sys_nerr) - return (""); - else - return (sys_errlist[num]); -} -#endif /* !HAVE_STRERROR */ - -/* A function which returns a pointer to a static buffer containing - an error message for FILENAME and ERROR_NUM. */ -static char *errmsg_buf = (char *)NULL; -static int errmsg_buf_size = 0; - -char * -filesys_error_string (filename, error_num) - char *filename; - int error_num; -{ - int len; - char *result; - - if (error_num == 0) - return ((char *)NULL); - - result = strerror (error_num); - - len = 4 + strlen (filename) + strlen (result); - if (len >= errmsg_buf_size) - errmsg_buf = (char *)xrealloc (errmsg_buf, (errmsg_buf_size = 2 + len)); - - sprintf (errmsg_buf, "%s: %s", filename, result); - return (errmsg_buf); -} - diff --git a/gnu/usr.bin/texinfo/info/filesys.h b/gnu/usr.bin/texinfo/info/filesys.h deleted file mode 100644 index 9ee4a71..0000000 --- a/gnu/usr.bin/texinfo/info/filesys.h +++ /dev/null @@ -1,84 +0,0 @@ -/* filesys.h -- External declarations of functions and vars in filesys.c. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#ifndef _FILESYS_H_ -#define _FILESYS_H_ - -/* The path on which we look for info files. You can initialize this - from the environment variable INFOPATH if there is one, or you can - call info_add_path () to add paths to the beginning or end of it. */ -extern char *infopath; - -/* Make INFOPATH have absolutely nothing in it. */ -extern void zap_infopath (); - -/* Add PATH to the list of paths found in INFOPATH. 2nd argument says - whether to put PATH at the front or end of INFOPATH. */ -extern void info_add_path (); - -/* Defines that are passed along with the pathname to info_add_path (). */ -#define INFOPATH_PREPEND 0 -#define INFOPATH_APPEND 1 - -/* Expand the filename in PARTIAL to make a real name for this operating - system. This looks in INFO_PATHS in order to find the correct file. - If it can't find the file, it returns NULL. */ -extern char *info_find_fullpath (); - -/* Read the contents of PATHNAME, returning a buffer with the contents of - that file in it, and returning the size of that buffer in FILESIZE. - FINFO is a stat struct which has already been filled in by the caller. - If the file cannot be read, return a NULL pointer. */ -extern char *filesys_read_info_file (); -extern char *filesys_read_compressed (); - -/* Return the command string that would be used to decompress FILENAME. */ -extern char *filesys_decompressor_for_file (); -extern int compressed_filename_p (); - -/* A function which returns a pointer to a static buffer containing - an error message for FILENAME and ERROR_NUM. */ -extern char *filesys_error_string (); - -/* The number of the most recent file system error. */ -extern int filesys_error_number; - -/* Given a string containing units of information separated by colons, - return the next one pointed to by IDX, or NULL if there are no more. - Advance IDX to the character after the colon. */ -extern char *extract_colon_unit (); - -/* The default value of INFOPATH. */ -#if !defined (DEFAULT_INFOPATH) -# define DEFAULT_INFOPATH "/usr/gnu/info:/local/gnu/info:/usr/gnu/lib/info:/usr/gnu/lib/emacs/info:/usr/local/gnu/info:/usr/local/gnu/lib/info:/usr/local/gnu/lib/emacs/info:/usr/local/lib/info:/usr/local/lib/emacs/info:/usr/local/emacs/info:." -#endif /* !DEFAULT_INFOPATH */ - -#if !defined (S_ISREG) && defined (S_IFREG) -# define S_ISREG(m) (((m) & S_IFMT) == S_IFREG) -#endif /* !S_ISREG && S_IFREG */ - -#if !defined (S_ISDIR) && defined (S_IFDIR) -# define S_ISDIR(m) (((m) & S_IFMT) == S_IFDIR) -#endif /* !S_ISDIR && S_IFDIR */ - -#endif /* !_FILESYS_H_ */ diff --git a/gnu/usr.bin/texinfo/info/footnotes.c b/gnu/usr.bin/texinfo/info/footnotes.c deleted file mode 100644 index 9fd0f95..0000000 --- a/gnu/usr.bin/texinfo/info/footnotes.c +++ /dev/null @@ -1,264 +0,0 @@ -/* footnotes.c -- Some functions for manipulating footnotes. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include "info.h" - -/* Non-zero means attempt to show footnotes when displaying a new window. */ -int auto_footnotes_p = 1; - -static char *footnote_nodename = "*Footnotes*"; - -#define FOOTNOTE_HEADER_FORMAT \ - "*** Footnotes appearing in the node \"%s\" ***\n" - -/* Find the window currently showing footnotes. */ -static WINDOW * -find_footnotes_window () -{ - WINDOW *win; - - /* Try to find an existing window first. */ - for (win = windows; win; win = win->next) - if (internal_info_node_p (win->node) && - (strcmp (win->node->nodename, footnote_nodename) == 0)) - break; - - return (win); -} - -/* Manufacture a node containing the footnotes of this node, and - return the manufactured node. If NODE has no footnotes, return a - NULL pointer. */ -NODE * -make_footnotes_node (node) - NODE *node; -{ - NODE *fn_node, *result = (NODE *)NULL; - long fn_start; - - /* Make the initial assumption that the footnotes appear as simple - text within this windows node. */ - fn_node = node; - - /* See if this node contains the magic footnote label. */ - fn_start = - info_search_in_node (FOOTNOTE_LABEL, node, 0, (WINDOW *)NULL, 1); - - /* If it doesn't, check to see if it has an associated footnotes node. */ - if (fn_start == -1) - { - REFERENCE **refs; - - refs = info_xrefs_of_node (node); - - if (refs) - { - register int i; - char *refname; - - refname = (char *)xmalloc - (1 + strlen ("-Footnotes") + strlen (node->nodename)); - - strcpy (refname, node->nodename); - strcat (refname, "-Footnotes"); - - for (i = 0; refs[i]; i++) - if (strcmp (refs[i]->nodename, refname) == 0) - { - char *filename; - - filename = node->parent; - if (!filename) - filename = node->filename; - - fn_node = info_get_node (filename, refname); - - if (fn_node) - fn_start = 0; - - break; - } - - free (refname); - info_free_references (refs); - } - } - - /* If we never found the start of a footnotes area, quit now. */ - if (fn_start == -1) - return ((NODE *)NULL); - - /* Make the new node. */ - result = (NODE *)xmalloc (sizeof (NODE)); - result->flags = 0; - - /* Get the size of the footnotes appearing within this node. */ - { - char *header; - long text_start = fn_start; - - header = (char *)xmalloc - (1 + strlen (node->nodename) + strlen (FOOTNOTE_HEADER_FORMAT)); - sprintf (header, FOOTNOTE_HEADER_FORMAT, node->nodename); - - /* Move the start of the displayed text to right after the first line. - This effectively skips either "---- footno...", or "File: foo...". */ - while (text_start < fn_node->nodelen) - if (fn_node->contents[text_start++] == '\n') - break; - - result->nodelen = strlen (header) + fn_node->nodelen - text_start; - - /* Set the contents of this node. */ - result->contents = (char *)xmalloc (1 + result->nodelen); - sprintf (result->contents, "%s", header); - memcpy (result->contents + strlen (header), - fn_node->contents + text_start, fn_node->nodelen - text_start); - - name_internal_node (result, footnote_nodename); - free (header); - } - -#if defined (NOTDEF) - /* If the footnotes were gleaned from the node that we were called with, - shorten the calling node's display length. */ - if (fn_node == node) - narrow_node (node, 0, fn_start); -#endif /* NOTDEF */ - - return (result); -} - -/* Create or delete the footnotes window depending on whether footnotes - exist in WINDOW's node or not. Returns FN_FOUND if footnotes were found - and displayed. Returns FN_UNFOUND if there were no footnotes found - in WINDOW's node. Returns FN_UNABLE if there were footnotes, but the - window to show them couldn't be made. */ -int -info_get_or_remove_footnotes (window) - WINDOW *window; -{ - WINDOW *fn_win; - NODE *new_footnotes; - - fn_win = find_footnotes_window (); - - /* If we are in the footnotes window, change nothing. */ - if (fn_win == window) - return (FN_FOUND); - - /* Try to find footnotes for this window's node. */ - new_footnotes = make_footnotes_node (window->node); - - /* If there was a window showing footnotes, and there are no footnotes - for the current window, delete the old footnote window. */ - if (fn_win && !new_footnotes) - { - if (windows->next) - info_delete_window_internal (fn_win); - } - - /* If there are footnotes for this window's node, but no window around - showing footnotes, try to make a new window. */ - if (new_footnotes && !fn_win) - { - WINDOW *old_active; - WINDOW *last, *win; - - /* Always make this window be the last one appearing in the list. Find - the last window in the chain. */ - for (win = windows, last = windows; win; last = win, win = win->next); - - /* Try to split this window, and make the split window the one to - contain the footnotes. */ - old_active = active_window; - active_window = last; - fn_win = window_make_window (new_footnotes); - active_window = old_active; - - if (!fn_win) - { - free (new_footnotes->contents); - free (new_footnotes); - - /* If we are hacking automatic footnotes, and there are footnotes - but we couldn't display them, print a message to that effect. */ - if (auto_footnotes_p) - inform_in_echo_area ("Footnotes could not be displayed"); - return (FN_UNABLE); - } - } - - /* If there are footnotes, and there is a window to display them, - make that window be the number of lines appearing in the footnotes. */ - if (new_footnotes && fn_win) - { - window_set_node_of_window (fn_win, new_footnotes); - - window_change_window_height - (fn_win, fn_win->line_count - fn_win->height); - - remember_window_and_node (fn_win, new_footnotes); - add_gcable_pointer (new_footnotes->contents); - } - - if (!new_footnotes) - return (FN_UNFOUND); - else - return (FN_FOUND); -} - -/* Show the footnotes associated with this node in another window. */ -DECLARE_INFO_COMMAND (info_show_footnotes, - "Show the footnotes associated with this node in another window") -{ - int result; - - /* A negative argument means just make the window go away. */ - if (count < 0) - { - WINDOW *fn_win = find_footnotes_window (); - - /* If there is an old footnotes window, and it isn't the only window - on the screen, delete it. */ - if (fn_win && windows->next) - info_delete_window_internal (fn_win); - } - else - { - int result; - - result = info_get_or_remove_footnotes (window); - - switch (result) - { - case FN_UNFOUND: - info_error (NO_FOOT_NODE); - break; - - case FN_UNABLE: - info_error (WIN_TOO_SMALL); - break; - } - } -} diff --git a/gnu/usr.bin/texinfo/info/footnotes.h b/gnu/usr.bin/texinfo/info/footnotes.h deleted file mode 100644 index 71c9d93..0000000 --- a/gnu/usr.bin/texinfo/info/footnotes.h +++ /dev/null @@ -1,46 +0,0 @@ -/* footnotes.h -- Some functions for manipulating footnotes. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#ifndef _FOOTNOTES_H_ -#define _FOOTNOTES_H_ - -/* Magic string which indicates following text is footnotes. */ -#define FOOTNOTE_LABEL "---------- Footnotes ----------" - -#define FN_FOUND 0 -#define FN_UNFOUND 1 -#define FN_UNABLE 2 - - -/* Create or delete the footnotes window depending on whether footnotes - exist in WINDOW's node or not. Returns FN_FOUND if footnotes were found - and displayed. Returns FN_UNFOUND if there were no footnotes found - in WINDOW's node. Returns FN_UNABLE if there were footnotes, but the - window to show them couldn't be made. */ -extern int info_get_or_remove_footnotes (); - -/* Non-zero means attempt to show footnotes when displaying a new window. */ -extern int auto_footnotes_p; - -#endif /* !_FOOTNOTES_H_ */ - diff --git a/gnu/usr.bin/texinfo/info/funs.h b/gnu/usr.bin/texinfo/info/funs.h deleted file mode 100644 index 1474f0d..0000000 --- a/gnu/usr.bin/texinfo/info/funs.h +++ /dev/null @@ -1,110 +0,0 @@ -/* funs.h -- Generated declarations for Info commands. */ - -/* Functions declared in "./session.c". */ -extern void info_next_line (); -extern void info_prev_line (); -extern void info_end_of_line (); -extern void info_beginning_of_line (); -extern void info_forward_char (); -extern void info_backward_char (); -extern void info_forward_word (); -extern void info_backward_word (); -extern void info_global_next_node (); -extern void info_global_prev_node (); -extern void info_scroll_forward (); -extern void info_scroll_backward (); -extern void info_beginning_of_node (); -extern void info_end_of_node (); -extern void info_next_window (); -extern void info_prev_window (); -extern void info_split_window (); -extern void info_delete_window (); -extern void info_keep_one_window (); -extern void info_scroll_other_window (); -extern void info_grow_window (); -extern void info_tile_windows (); -extern void info_toggle_wrap (); -extern void info_next_node (); -extern void info_prev_node (); -extern void info_up_node (); -extern void info_last_node (); -extern void info_first_node (); -extern void info_history_node (); -extern void info_last_menu_item (); -extern void info_menu_digit (); -extern void info_menu_item (); -extern void info_xref_item (); -extern void info_find_menu (); -extern void info_visit_menu (); -extern void info_goto_node (); -extern void info_top_node (); -extern void info_dir_node (); -extern void info_kill_node (); -extern void info_view_file (); -extern void info_print_node (); -extern void info_search (); -extern void isearch_forward (); -extern void isearch_backward (); -extern void info_move_to_prev_xref (); -extern void info_move_to_next_xref (); -extern void info_select_reference_this_line (); -extern void info_abort_key (); -extern void info_move_to_window_line (); -extern void info_redraw_display (); -extern void info_quit (); -extern void info_do_lowercase_version (); -extern void info_add_digit_to_numeric_arg (); -extern void info_universal_argument (); -extern void info_numeric_arg_digit_loop (); - -/* Functions declared in "./echo_area.c". */ -extern void ea_forward (); -extern void ea_backward (); -extern void ea_beg_of_line (); -extern void ea_end_of_line (); -extern void ea_forward_word (); -extern void ea_backward_word (); -extern void ea_delete (); -extern void ea_rubout (); -extern void ea_abort (); -extern void ea_newline (); -extern void ea_quoted_insert (); -extern void ea_insert (); -extern void ea_tab_insert (); -extern void ea_transpose_chars (); -extern void ea_yank (); -extern void ea_yank_pop (); -extern void ea_kill_line (); -extern void ea_backward_kill_line (); -extern void ea_kill_word (); -extern void ea_backward_kill_word (); -extern void ea_possible_completions (); -extern void ea_complete (); -extern void ea_scroll_completions_window (); - -/* Functions declared in "./infodoc.c". */ -extern void info_get_help_window (); -extern void info_get_info_help_node (); -extern void describe_key (); -extern void info_where_is (); - -/* Functions declared in "./m-x.c". */ -extern void describe_command (); -extern void info_execute_command (); -extern void set_screen_height (); - -/* Functions declared in "./indices.c". */ -extern void info_index_search (); -extern void info_next_index_match (); -extern void info_index_apropos (); - -/* Functions declared in "./nodemenu.c". */ -extern void list_visited_nodes (); -extern void select_visited_node (); - -/* Functions declared in "./footnotes.c". */ -extern void info_show_footnotes (); - -/* Functions declared in "./variables.c". */ -extern void describe_variable (); -extern void set_variable (); diff --git a/gnu/usr.bin/texinfo/info/gc.c b/gnu/usr.bin/texinfo/info/gc.c deleted file mode 100644 index 6a50e81..0000000 --- a/gnu/usr.bin/texinfo/info/gc.c +++ /dev/null @@ -1,95 +0,0 @@ -/* gc.c -- Functions to remember and garbage collect unused node contents. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include "info.h" - -/* Array of pointers to the contents of gc-able nodes. A pointer on this - list can be garbage collected when no info window contains a node whose - contents member match the pointer. */ -static char **gcable_pointers = (char **)NULL; -static int gcable_pointers_index = 0; -static int gcable_pointers_slots = 0; - -/* Add POINTER to the list of garbage collectible pointers. A pointer - is not actually garbage collected until no info window contains a node - whose contents member is equal to the pointer. */ -void -add_gcable_pointer (pointer) - char *pointer; -{ - gc_pointers (); - add_pointer_to_array (pointer, gcable_pointers_index, gcable_pointers, - gcable_pointers_slots, 10, char *); -} - -/* Grovel the list of info windows and gc-able pointers finding those - node->contents which are collectible, and free them. */ -void -gc_pointers () -{ - register int i, j, k; - INFO_WINDOW *iw; - char **new = (char **)NULL; - int new_index = 0; - int new_slots = 0; - - if (!info_windows || !gcable_pointers_index) - return; - - for (i = 0; iw = info_windows[i]; i++) - { - for (j = 0; j < iw->nodes_index; j++) - { - NODE *node = iw->nodes[j]; - - /* If this node->contents appears in our list of gcable_pointers, - it is not gc-able, so save it. */ - for (k = 0; k < gcable_pointers_index; k++) - if (gcable_pointers[k] == node->contents) - { - add_pointer_to_array - (node->contents, new_index, new, new_slots, 10, char *); - break; - } - } - } - - /* We have gathered all of the pointers which need to be saved. Free any - of the original pointers which do not appear in the new list. */ - for (i = 0; i < gcable_pointers_index; i++) - { - for (j = 0; j < new_index; j++) - if (gcable_pointers[i] == new[j]) - break; - - /* If we got all the way through the new list, then the old pointer - can be garbage collected. */ - if (new && !new[j]) - free (gcable_pointers[i]); - } - - free (gcable_pointers); - gcable_pointers = new; - gcable_pointers_slots = new_slots; - gcable_pointers_index = new_index; -} diff --git a/gnu/usr.bin/texinfo/info/gc.h b/gnu/usr.bin/texinfo/info/gc.h deleted file mode 100644 index a521ae6..0000000 --- a/gnu/usr.bin/texinfo/info/gc.h +++ /dev/null @@ -1,36 +0,0 @@ -/* gc.h -- Functions for garbage collecting unused node contents. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#ifndef _GC_H_ -#define _GC_H_ - -/* Add POINTER to the list of garbage collectible pointers. A pointer - is not actually garbage collected until no info window contains a node - whose contents member is equal to the pointer. */ -extern void add_gcable_pointer (); - -/* Grovel the list of info windows and gc-able pointers finding those - node->contents which are collectible, and free them. */ -extern void gc_pointers (); - -#endif /* !_GC_H_ */ diff --git a/gnu/usr.bin/texinfo/info/general.h b/gnu/usr.bin/texinfo/info/general.h deleted file mode 100644 index 605a75a..0000000 --- a/gnu/usr.bin/texinfo/info/general.h +++ /dev/null @@ -1,81 +0,0 @@ -/* general.h -- Some generally useful defines. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#if !defined (_GENERAL_H_) -#define _GENERAL_H_ - -extern void *xmalloc (), *xrealloc (); - -#if defined (HAVE_UNISTD_H) -# include <unistd.h> -#endif /* HAVE_UNISTD_H */ - -#if defined (HAVE_STRING_H) -# include <string.h> -#else -# include <strings.h> -#endif /* !HAVE_STRING_H */ - -#if !defined (savestring) -# define savestring(x) (char *)strcpy ((char *)xmalloc (1 + strlen (x)), x) -#endif /* !savestring */ - -#define info_toupper(x) (islower (x) ? toupper (x) : x) -#define info_tolower(x) (isupper (x) ? tolower (x) : x) - -#if !defined (whitespace) -# define whitespace(c) ((c == ' ') || (c == '\t')) -#endif /* !whitespace */ - -#if !defined (whitespace_or_newline) -# define whitespace_or_newline(c) (whitespace (c) || (c == '\n')) -#endif /* !whitespace_or_newline */ - -#if !defined (__FUNCTION_DEF) -# define __FUNCTION_DEF -typedef int Function (); -typedef void VFunction (); -#endif /* _FUNCTION_DEF */ - -/* Add POINTER to the list of pointers found in ARRAY. SLOTS is the number - of slots that have already been allocated. INDEX is the index into the - array where POINTER should be added. GROW is the number of slots to grow - ARRAY by, in the case that it needs growing. TYPE is a cast of the type - of object stored in ARRAY (e.g., NODE_ENTRY *. */ -#define add_pointer_to_array(pointer, idx, array, slots, grow, type) \ - do { \ - if (idx + 2 >= slots) \ - array = (type *)(xrealloc (array, (slots += grow) * sizeof (type))); \ - array[idx++] = (type)pointer; \ - array[idx] = (type)NULL; \ - } while (0) - -#define maybe_free(x) do { if (x) free (x); } while (0) - -#if !defined (HAVE_BZERO) -# define zero_mem(mem, length) memset (mem, 0, length) -#else -# define zero_mem(mem, length) bzero (mem, length) -#endif /* !BZERO_MISSING */ - -#endif /* !_GENERAL_H_ */ diff --git a/gnu/usr.bin/texinfo/info/getopt.c b/gnu/usr.bin/texinfo/info/getopt.c deleted file mode 100644 index a59a013..0000000 --- a/gnu/usr.bin/texinfo/info/getopt.c +++ /dev/null @@ -1,731 +0,0 @@ -/* Getopt for GNU. - NOTE: getopt is now part of the C library, so if you don't know what - "Keep this file name-space clean" means, talk to roland@gnu.ai.mit.edu - before changing it! - - Copyright (C) 1987, 88, 89, 90, 91, 92, 1993 - Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */ - -/* NOTE!!! AIX requires this to be the first thing in the file. - Do not put ANYTHING before it! */ -#if !defined (__GNUC__) && defined (_AIX) - #pragma alloca -#endif - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#ifdef __GNUC__ -#define alloca __builtin_alloca -#else /* not __GNUC__ */ -#if defined (HAVE_ALLOCA_H) || (defined(sparc) && (defined(sun) || (!defined(USG) && !defined(SVR4) && !defined(__svr4__)))) -#include <alloca.h> -#else -#ifndef _AIX -char *alloca (); -#endif -#endif /* alloca.h */ -#endif /* not __GNUC__ */ - -#if !__STDC__ && !defined(const) && IN_GCC -#define const -#endif - -/* This tells Alpha OSF/1 not to define a getopt prototype in <stdio.h>. */ -#ifndef _NO_PROTO -#define _NO_PROTO -#endif - -#include <stdio.h> - -/* Comment out all this code if we are using the GNU C Library, and are not - actually compiling the library itself. This code is part of the GNU C - Library, but also included in many other GNU distributions. Compiling - and linking in this code is a waste when using the GNU C library - (especially if it is a shared library). Rather than having every GNU - program understand `configure --with-gnu-libc' and omit the object files, - it is simpler to just do this in the source for each such file. */ - -#if defined (_LIBC) || !defined (__GNU_LIBRARY__) - - -/* This needs to come after some library #include - to get __GNU_LIBRARY__ defined. */ -#ifdef __GNU_LIBRARY__ -#undef alloca -/* Don't include stdlib.h for non-GNU C libraries because some of them - contain conflicting prototypes for getopt. */ -#include <stdlib.h> -#else /* Not GNU C library. */ -#define __alloca alloca -#endif /* GNU C library. */ - -/* If GETOPT_COMPAT is defined, `+' as well as `--' can introduce a - long-named option. Because this is not POSIX.2 compliant, it is - being phased out. */ -/* #define GETOPT_COMPAT */ - -/* This version of `getopt' appears to the caller like standard Unix `getopt' - but it behaves differently for the user, since it allows the user - to intersperse the options with the other arguments. - - As `getopt' works, it permutes the elements of ARGV so that, - when it is done, all the options precede everything else. Thus - all application programs are extended to handle flexible argument order. - - Setting the environment variable POSIXLY_CORRECT disables permutation. - Then the behavior is completely standard. - - GNU application programs can use a third alternative mode in which - they can distinguish the relative order of options and other arguments. */ - -#include "getopt.h" - -/* For communication from `getopt' to the caller. - When `getopt' finds an option that takes an argument, - the argument value is returned here. - Also, when `ordering' is RETURN_IN_ORDER, - each non-option ARGV-element is returned here. */ - -char *optarg = 0; - -/* Index in ARGV of the next element to be scanned. - This is used for communication to and from the caller - and for communication between successive calls to `getopt'. - - On entry to `getopt', zero means this is the first call; initialize. - - When `getopt' returns EOF, this is the index of the first of the - non-option elements that the caller should itself scan. - - Otherwise, `optind' communicates from one call to the next - how much of ARGV has been scanned so far. */ - -/* XXX 1003.2 says this must be 1 before any call. */ -int optind = 0; - -/* The next char to be scanned in the option-element - in which the last option character we returned was found. - This allows us to pick up the scan where we left off. - - If this is zero, or a null string, it means resume the scan - by advancing to the next ARGV-element. */ - -static char *nextchar; - -/* Callers store zero here to inhibit the error message - for unrecognized options. */ - -int opterr = 1; - -/* Set to an option character which was unrecognized. - This must be initialized on some systems to avoid linking in the - system's own getopt implementation. */ - -int optopt = '?'; - -/* Describe how to deal with options that follow non-option ARGV-elements. - - If the caller did not specify anything, - the default is REQUIRE_ORDER if the environment variable - POSIXLY_CORRECT is defined, PERMUTE otherwise. - - REQUIRE_ORDER means don't recognize them as options; - stop option processing when the first non-option is seen. - This is what Unix does. - This mode of operation is selected by either setting the environment - variable POSIXLY_CORRECT, or using `+' as the first character - of the list of option characters. - - PERMUTE is the default. We permute the contents of ARGV as we scan, - so that eventually all the non-options are at the end. This allows options - to be given in any order, even with programs that were not written to - expect this. - - RETURN_IN_ORDER is an option available to programs that were written - to expect options and other ARGV-elements in any order and that care about - the ordering of the two. We describe each non-option ARGV-element - as if it were the argument of an option with character code 1. - Using `-' as the first character of the list of option characters - selects this mode of operation. - - The special argument `--' forces an end of option-scanning regardless - of the value of `ordering'. In the case of RETURN_IN_ORDER, only - `--' can cause `getopt' to return EOF with `optind' != ARGC. */ - -static enum -{ - REQUIRE_ORDER, PERMUTE, RETURN_IN_ORDER -} ordering; - -#ifdef __GNU_LIBRARY__ -/* We want to avoid inclusion of string.h with non-GNU libraries - because there are many ways it can cause trouble. - On some systems, it contains special magic macros that don't work - in GCC. */ -#include <string.h> -#define my_index strchr -#define my_bcopy(src, dst, n) memcpy ((dst), (src), (n)) -#else - -/* Avoid depending on library functions or files - whose names are inconsistent. */ - -char *getenv (); - -static char * -my_index (str, chr) - const char *str; - int chr; -{ - while (*str) - { - if (*str == chr) - return (char *) str; - str++; - } - return 0; -} - -static void -my_bcopy (from, to, size) - const char *from; - char *to; - int size; -{ - int i; - for (i = 0; i < size; i++) - to[i] = from[i]; -} -#endif /* GNU C library. */ - -/* Handle permutation of arguments. */ - -/* Describe the part of ARGV that contains non-options that have - been skipped. `first_nonopt' is the index in ARGV of the first of them; - `last_nonopt' is the index after the last of them. */ - -static int first_nonopt; -static int last_nonopt; - -/* Exchange two adjacent subsequences of ARGV. - One subsequence is elements [first_nonopt,last_nonopt) - which contains all the non-options that have been skipped so far. - The other is elements [last_nonopt,optind), which contains all - the options processed since those non-options were skipped. - - `first_nonopt' and `last_nonopt' are relocated so that they describe - the new indices of the non-options in ARGV after they are moved. */ - -static void -exchange (argv) - char **argv; -{ - int nonopts_size = (last_nonopt - first_nonopt) * sizeof (char *); - char **temp = (char **) __alloca (nonopts_size); - - /* Interchange the two blocks of data in ARGV. */ - - my_bcopy ((char *) &argv[first_nonopt], (char *) temp, nonopts_size); - my_bcopy ((char *) &argv[last_nonopt], (char *) &argv[first_nonopt], - (optind - last_nonopt) * sizeof (char *)); - my_bcopy ((char *) temp, - (char *) &argv[first_nonopt + optind - last_nonopt], - nonopts_size); - - /* Update records for the slots the non-options now occupy. */ - - first_nonopt += (optind - last_nonopt); - last_nonopt = optind; -} - -/* Scan elements of ARGV (whose length is ARGC) for option characters - given in OPTSTRING. - - If an element of ARGV starts with '-', and is not exactly "-" or "--", - then it is an option element. The characters of this element - (aside from the initial '-') are option characters. If `getopt' - is called repeatedly, it returns successively each of the option characters - from each of the option elements. - - If `getopt' finds another option character, it returns that character, - updating `optind' and `nextchar' so that the next call to `getopt' can - resume the scan with the following option character or ARGV-element. - - If there are no more option characters, `getopt' returns `EOF'. - Then `optind' is the index in ARGV of the first ARGV-element - that is not an option. (The ARGV-elements have been permuted - so that those that are not options now come last.) - - OPTSTRING is a string containing the legitimate option characters. - If an option character is seen that is not listed in OPTSTRING, - return '?' after printing an error message. If you set `opterr' to - zero, the error message is suppressed but we still return '?'. - - If a char in OPTSTRING is followed by a colon, that means it wants an arg, - so the following text in the same ARGV-element, or the text of the following - ARGV-element, is returned in `optarg'. Two colons mean an option that - wants an optional arg; if there is text in the current ARGV-element, - it is returned in `optarg', otherwise `optarg' is set to zero. - - If OPTSTRING starts with `-' or `+', it requests different methods of - handling the non-option ARGV-elements. - See the comments about RETURN_IN_ORDER and REQUIRE_ORDER, above. - - Long-named options begin with `--' instead of `-'. - Their names may be abbreviated as long as the abbreviation is unique - or is an exact match for some defined option. If they have an - argument, it follows the option name in the same ARGV-element, separated - from the option name by a `=', or else the in next ARGV-element. - When `getopt' finds a long-named option, it returns 0 if that option's - `flag' field is nonzero, the value of the option's `val' field - if the `flag' field is zero. - - The elements of ARGV aren't really const, because we permute them. - But we pretend they're const in the prototype to be compatible - with other systems. - - LONGOPTS is a vector of `struct option' terminated by an - element containing a name which is zero. - - LONGIND returns the index in LONGOPT of the long-named option found. - It is only valid when a long-named option has been found by the most - recent call. - - If LONG_ONLY is nonzero, '-' as well as '--' can introduce - long-named options. */ - -int -_getopt_internal (argc, argv, optstring, longopts, longind, long_only) - int argc; - char *const *argv; - const char *optstring; - const struct option *longopts; - int *longind; - int long_only; -{ - int option_index; - - optarg = 0; - - /* Initialize the internal data when the first call is made. - Start processing options with ARGV-element 1 (since ARGV-element 0 - is the program name); the sequence of previously skipped - non-option ARGV-elements is empty. */ - - if (optind == 0) - { - first_nonopt = last_nonopt = optind = 1; - - nextchar = NULL; - - /* Determine how to handle the ordering of options and nonoptions. */ - - if (optstring[0] == '-') - { - ordering = RETURN_IN_ORDER; - ++optstring; - } - else if (optstring[0] == '+') - { - ordering = REQUIRE_ORDER; - ++optstring; - } - else if (getenv ("POSIXLY_CORRECT") != NULL) - ordering = REQUIRE_ORDER; - else - ordering = PERMUTE; - } - - if (nextchar == NULL || *nextchar == '\0') - { - if (ordering == PERMUTE) - { - /* If we have just processed some options following some non-options, - exchange them so that the options come first. */ - - if (first_nonopt != last_nonopt && last_nonopt != optind) - exchange ((char **) argv); - else if (last_nonopt != optind) - first_nonopt = optind; - - /* Now skip any additional non-options - and extend the range of non-options previously skipped. */ - - while (optind < argc - && (argv[optind][0] != '-' || argv[optind][1] == '\0') -#ifdef GETOPT_COMPAT - && (longopts == NULL - || argv[optind][0] != '+' || argv[optind][1] == '\0') -#endif /* GETOPT_COMPAT */ - ) - optind++; - last_nonopt = optind; - } - - /* Special ARGV-element `--' means premature end of options. - Skip it like a null option, - then exchange with previous non-options as if it were an option, - then skip everything else like a non-option. */ - - if (optind != argc && !strcmp (argv[optind], "--")) - { - optind++; - - if (first_nonopt != last_nonopt && last_nonopt != optind) - exchange ((char **) argv); - else if (first_nonopt == last_nonopt) - first_nonopt = optind; - last_nonopt = argc; - - optind = argc; - } - - /* If we have done all the ARGV-elements, stop the scan - and back over any non-options that we skipped and permuted. */ - - if (optind == argc) - { - /* Set the next-arg-index to point at the non-options - that we previously skipped, so the caller will digest them. */ - if (first_nonopt != last_nonopt) - optind = first_nonopt; - return EOF; - } - - /* If we have come to a non-option and did not permute it, - either stop the scan or describe it to the caller and pass it by. */ - - if ((argv[optind][0] != '-' || argv[optind][1] == '\0') -#ifdef GETOPT_COMPAT - && (longopts == NULL - || argv[optind][0] != '+' || argv[optind][1] == '\0') -#endif /* GETOPT_COMPAT */ - ) - { - if (ordering == REQUIRE_ORDER) - return EOF; - optarg = argv[optind++]; - return 1; - } - - /* We have found another option-ARGV-element. - Start decoding its characters. */ - - nextchar = (argv[optind] + 1 - + (longopts != NULL && argv[optind][1] == '-')); - } - - if (longopts != NULL - && ((argv[optind][0] == '-' - && (argv[optind][1] == '-' || long_only)) -#ifdef GETOPT_COMPAT - || argv[optind][0] == '+' -#endif /* GETOPT_COMPAT */ - )) - { - const struct option *p; - char *s = nextchar; - int exact = 0; - int ambig = 0; - const struct option *pfound = NULL; - int indfound; - - while (*s && *s != '=') - s++; - - /* Test all options for either exact match or abbreviated matches. */ - for (p = longopts, option_index = 0; p->name; - p++, option_index++) - if (!strncmp (p->name, nextchar, s - nextchar)) - { - if (s - nextchar == strlen (p->name)) - { - /* Exact match found. */ - pfound = p; - indfound = option_index; - exact = 1; - break; - } - else if (pfound == NULL) - { - /* First nonexact match found. */ - pfound = p; - indfound = option_index; - } - else - /* Second nonexact match found. */ - ambig = 1; - } - - if (ambig && !exact) - { - if (opterr) - fprintf (stderr, "%s: option `%s' is ambiguous\n", - argv[0], argv[optind]); - nextchar += strlen (nextchar); - optind++; - return '?'; - } - - if (pfound != NULL) - { - option_index = indfound; - optind++; - if (*s) - { - /* Don't test has_arg with >, because some C compilers don't - allow it to be used on enums. */ - if (pfound->has_arg) - optarg = s + 1; - else - { - if (opterr) - { - if (argv[optind - 1][1] == '-') - /* --option */ - fprintf (stderr, - "%s: option `--%s' doesn't allow an argument\n", - argv[0], pfound->name); - else - /* +option or -option */ - fprintf (stderr, - "%s: option `%c%s' doesn't allow an argument\n", - argv[0], argv[optind - 1][0], pfound->name); - } - nextchar += strlen (nextchar); - return '?'; - } - } - else if (pfound->has_arg == 1) - { - if (optind < argc) - optarg = argv[optind++]; - else - { - if (opterr) - fprintf (stderr, "%s: option `%s' requires an argument\n", - argv[0], argv[optind - 1]); - nextchar += strlen (nextchar); - return optstring[0] == ':' ? ':' : '?'; - } - } - nextchar += strlen (nextchar); - if (longind != NULL) - *longind = option_index; - if (pfound->flag) - { - *(pfound->flag) = pfound->val; - return 0; - } - return pfound->val; - } - /* Can't find it as a long option. If this is not getopt_long_only, - or the option starts with '--' or is not a valid short - option, then it's an error. - Otherwise interpret it as a short option. */ - if (!long_only || argv[optind][1] == '-' -#ifdef GETOPT_COMPAT - || argv[optind][0] == '+' -#endif /* GETOPT_COMPAT */ - || my_index (optstring, *nextchar) == NULL) - { - if (opterr) - { - if (argv[optind][1] == '-') - /* --option */ - fprintf (stderr, "%s: unrecognized option `--%s'\n", - argv[0], nextchar); - else - /* +option or -option */ - fprintf (stderr, "%s: unrecognized option `%c%s'\n", - argv[0], argv[optind][0], nextchar); - } - nextchar = (char *) ""; - optind++; - return '?'; - } - } - - /* Look at and handle the next option-character. */ - - { - char c = *nextchar++; - char *temp = my_index (optstring, c); - - /* Increment `optind' when we start to process its last character. */ - if (*nextchar == '\0') - ++optind; - - if (temp == NULL || c == ':') - { - if (opterr) - { -#if 0 - if (c < 040 || c >= 0177) - fprintf (stderr, "%s: unrecognized option, character code 0%o\n", - argv[0], c); - else - fprintf (stderr, "%s: unrecognized option `-%c'\n", argv[0], c); -#else - /* 1003.2 specifies the format of this message. */ - fprintf (stderr, "%s: illegal option -- %c\n", argv[0], c); -#endif - } - optopt = c; - return '?'; - } - if (temp[1] == ':') - { - if (temp[2] == ':') - { - /* This is an option that accepts an argument optionally. */ - if (*nextchar != '\0') - { - optarg = nextchar; - optind++; - } - else - optarg = 0; - nextchar = NULL; - } - else - { - /* This is an option that requires an argument. */ - if (*nextchar != '\0') - { - optarg = nextchar; - /* If we end this ARGV-element by taking the rest as an arg, - we must advance to the next element now. */ - optind++; - } - else if (optind == argc) - { - if (opterr) - { -#if 0 - fprintf (stderr, "%s: option `-%c' requires an argument\n", - argv[0], c); -#else - /* 1003.2 specifies the format of this message. */ - fprintf (stderr, "%s: option requires an argument -- %c\n", - argv[0], c); -#endif - } - optopt = c; - if (optstring[0] == ':') - c = ':'; - else - c = '?'; - } - else - /* We already incremented `optind' once; - increment it again when taking next ARGV-elt as argument. */ - optarg = argv[optind++]; - nextchar = NULL; - } - } - return c; - } -} - -int -getopt (argc, argv, optstring) - int argc; - char *const *argv; - const char *optstring; -{ - return _getopt_internal (argc, argv, optstring, - (const struct option *) 0, - (int *) 0, - 0); -} - -#endif /* _LIBC or not __GNU_LIBRARY__. */ - -#ifdef TEST - -/* Compile with -DTEST to make an executable for use in testing - the above definition of `getopt'. */ - -int -main (argc, argv) - int argc; - char **argv; -{ - int c; - int digit_optind = 0; - - while (1) - { - int this_option_optind = optind ? optind : 1; - - c = getopt (argc, argv, "abc:d:0123456789"); - if (c == EOF) - break; - - switch (c) - { - case '0': - case '1': - case '2': - case '3': - case '4': - case '5': - case '6': - case '7': - case '8': - case '9': - if (digit_optind != 0 && digit_optind != this_option_optind) - printf ("digits occur in two different argv-elements.\n"); - digit_optind = this_option_optind; - printf ("option %c\n", c); - break; - - case 'a': - printf ("option a\n"); - break; - - case 'b': - printf ("option b\n"); - break; - - case 'c': - printf ("option c with value `%s'\n", optarg); - break; - - case '?': - break; - - default: - printf ("?? getopt returned character code 0%o ??\n", c); - } - } - - if (optind < argc) - { - printf ("non-option ARGV-elements: "); - while (optind < argc) - printf ("%s ", argv[optind++]); - printf ("\n"); - } - - exit (0); -} - -#endif /* TEST */ diff --git a/gnu/usr.bin/texinfo/info/getopt.h b/gnu/usr.bin/texinfo/info/getopt.h deleted file mode 100644 index 45541f5..0000000 --- a/gnu/usr.bin/texinfo/info/getopt.h +++ /dev/null @@ -1,129 +0,0 @@ -/* Declarations for getopt. - Copyright (C) 1989, 1990, 1991, 1992, 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */ - -#ifndef _GETOPT_H -#define _GETOPT_H 1 - -#ifdef __cplusplus -extern "C" { -#endif - -/* For communication from `getopt' to the caller. - When `getopt' finds an option that takes an argument, - the argument value is returned here. - Also, when `ordering' is RETURN_IN_ORDER, - each non-option ARGV-element is returned here. */ - -extern char *optarg; - -/* Index in ARGV of the next element to be scanned. - This is used for communication to and from the caller - and for communication between successive calls to `getopt'. - - On entry to `getopt', zero means this is the first call; initialize. - - When `getopt' returns EOF, this is the index of the first of the - non-option elements that the caller should itself scan. - - Otherwise, `optind' communicates from one call to the next - how much of ARGV has been scanned so far. */ - -extern int optind; - -/* Callers store zero here to inhibit the error message `getopt' prints - for unrecognized options. */ - -extern int opterr; - -/* Set to an option character which was unrecognized. */ - -extern int optopt; - -/* Describe the long-named options requested by the application. - The LONG_OPTIONS argument to getopt_long or getopt_long_only is a vector - of `struct option' terminated by an element containing a name which is - zero. - - The field `has_arg' is: - no_argument (or 0) if the option does not take an argument, - required_argument (or 1) if the option requires an argument, - optional_argument (or 2) if the option takes an optional argument. - - If the field `flag' is not NULL, it points to a variable that is set - to the value given in the field `val' when the option is found, but - left unchanged if the option is not found. - - To have a long-named option do something other than set an `int' to - a compiled-in constant, such as set a value from `optarg', set the - option's `flag' field to zero and its `val' field to a nonzero - value (the equivalent single-letter option character, if there is - one). For long options that have a zero `flag' field, `getopt' - returns the contents of the `val' field. */ - -struct option -{ -#if __STDC__ - const char *name; -#else - char *name; -#endif - /* has_arg can't be an enum because some compilers complain about - type mismatches in all the code that assumes it is an int. */ - int has_arg; - int *flag; - int val; -}; - -/* Names for the values of the `has_arg' field of `struct option'. */ - -#define no_argument 0 -#define required_argument 1 -#define optional_argument 2 - -#if __STDC__ -#if defined(__GNU_LIBRARY__) -/* Many other libraries have conflicting prototypes for getopt, with - differences in the consts, in stdlib.h. To avoid compilation - errors, only prototype getopt for the GNU C library. */ -extern int getopt (int argc, char *const *argv, const char *shortopts); -#else /* not __GNU_LIBRARY__ */ -extern int getopt (); -#endif /* not __GNU_LIBRARY__ */ -extern int getopt_long (int argc, char *const *argv, const char *shortopts, - const struct option *longopts, int *longind); -extern int getopt_long_only (int argc, char *const *argv, - const char *shortopts, - const struct option *longopts, int *longind); - -/* Internal only. Users should not call this directly. */ -extern int _getopt_internal (int argc, char *const *argv, - const char *shortopts, - const struct option *longopts, int *longind, - int long_only); -#else /* not __STDC__ */ -extern int getopt (); -extern int getopt_long (); -extern int getopt_long_only (); - -extern int _getopt_internal (); -#endif /* not __STDC__ */ - -#ifdef __cplusplus -} -#endif - -#endif /* _GETOPT_H */ diff --git a/gnu/usr.bin/texinfo/info/getopt1.c b/gnu/usr.bin/texinfo/info/getopt1.c deleted file mode 100644 index a32615c..0000000 --- a/gnu/usr.bin/texinfo/info/getopt1.c +++ /dev/null @@ -1,176 +0,0 @@ -/* getopt_long and getopt_long_only entry points for GNU getopt. - Copyright (C) 1987, 88, 89, 90, 91, 92, 1993 - Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */ - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif - -#include "getopt.h" - -#if !__STDC__ && !defined(const) && IN_GCC -#define const -#endif - -#include <stdio.h> - -/* Comment out all this code if we are using the GNU C Library, and are not - actually compiling the library itself. This code is part of the GNU C - Library, but also included in many other GNU distributions. Compiling - and linking in this code is a waste when using the GNU C library - (especially if it is a shared library). Rather than having every GNU - program understand `configure --with-gnu-libc' and omit the object files, - it is simpler to just do this in the source for each such file. */ - -#if defined (_LIBC) || !defined (__GNU_LIBRARY__) - - -/* This needs to come after some library #include - to get __GNU_LIBRARY__ defined. */ -#ifdef __GNU_LIBRARY__ -#include <stdlib.h> -#else -char *getenv (); -#endif - -#ifndef NULL -#define NULL 0 -#endif - -int -getopt_long (argc, argv, options, long_options, opt_index) - int argc; - char *const *argv; - const char *options; - const struct option *long_options; - int *opt_index; -{ - return _getopt_internal (argc, argv, options, long_options, opt_index, 0); -} - -/* Like getopt_long, but '-' as well as '--' can indicate a long option. - If an option that starts with '-' (not '--') doesn't match a long option, - but does match a short option, it is parsed as a short option - instead. */ - -int -getopt_long_only (argc, argv, options, long_options, opt_index) - int argc; - char *const *argv; - const char *options; - const struct option *long_options; - int *opt_index; -{ - return _getopt_internal (argc, argv, options, long_options, opt_index, 1); -} - - -#endif /* _LIBC or not __GNU_LIBRARY__. */ - -#ifdef TEST - -#include <stdio.h> - -int -main (argc, argv) - int argc; - char **argv; -{ - int c; - int digit_optind = 0; - - while (1) - { - int this_option_optind = optind ? optind : 1; - int option_index = 0; - static struct option long_options[] = - { - {"add", 1, 0, 0}, - {"append", 0, 0, 0}, - {"delete", 1, 0, 0}, - {"verbose", 0, 0, 0}, - {"create", 0, 0, 0}, - {"file", 1, 0, 0}, - {0, 0, 0, 0} - }; - - c = getopt_long (argc, argv, "abc:d:0123456789", - long_options, &option_index); - if (c == EOF) - break; - - switch (c) - { - case 0: - printf ("option %s", long_options[option_index].name); - if (optarg) - printf (" with arg %s", optarg); - printf ("\n"); - break; - - case '0': - case '1': - case '2': - case '3': - case '4': - case '5': - case '6': - case '7': - case '8': - case '9': - if (digit_optind != 0 && digit_optind != this_option_optind) - printf ("digits occur in two different argv-elements.\n"); - digit_optind = this_option_optind; - printf ("option %c\n", c); - break; - - case 'a': - printf ("option a\n"); - break; - - case 'b': - printf ("option b\n"); - break; - - case 'c': - printf ("option c with value `%s'\n", optarg); - break; - - case 'd': - printf ("option d with value `%s'\n", optarg); - break; - - case '?': - break; - - default: - printf ("?? getopt returned character code 0%o ??\n", c); - } - } - - if (optind < argc) - { - printf ("non-option ARGV-elements: "); - while (optind < argc) - printf ("%s ", argv[optind++]); - printf ("\n"); - } - - exit (0); -} - -#endif /* TEST */ diff --git a/gnu/usr.bin/texinfo/info/indices.c b/gnu/usr.bin/texinfo/info/indices.c deleted file mode 100644 index 12029f6..0000000 --- a/gnu/usr.bin/texinfo/info/indices.c +++ /dev/null @@ -1,667 +0,0 @@ -/* indices.c -- Commands for dealing with an Info file Index. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include "info.h" -#include "indices.h" - -/* User-visible variable controls the output of info-index-next. */ -int show_index_match = 1; - -/* In the Info sense, an index is a menu. This variable holds the last - parsed index. */ -static REFERENCE **index_index = (REFERENCE **)NULL; - -/* The offset of the most recently selected index element. */ -static int index_offset = 0; - -/* Variable which holds the last string searched for. */ -static char *index_search = (char *)NULL; - -/* A couple of "globals" describing where the initial index was found. */ -static char *initial_index_filename = (char *)NULL; -static char *initial_index_nodename = (char *)NULL; - -/* A structure associating index names with index offset ranges. */ -typedef struct { - char *name; /* The nodename of this index. */ - int first; /* The index in our list of the first entry. */ - int last; /* The index in our list of the last entry. */ -} INDEX_NAME_ASSOC; - -/* An array associating index nodenames with index offset ranges. */ -static INDEX_NAME_ASSOC **index_nodenames = (INDEX_NAME_ASSOC **)NULL; -static int index_nodenames_index = 0; -static int index_nodenames_slots = 0; - -/* Add the name of NODE, and the range of the associated index elements - (passed in ARRAY) to index_nodenames. */ -static void -add_index_to_index_nodenames (array, node) - REFERENCE **array; - NODE *node; -{ - register int i, last; - INDEX_NAME_ASSOC *assoc; - - for (last = 0; array[last]; last++); - assoc = (INDEX_NAME_ASSOC *)xmalloc (sizeof (INDEX_NAME_ASSOC)); - assoc->name = savestring (node->nodename); - - if (!index_nodenames_index) - { - assoc->first = 0; - assoc->last = last; - } - else - { - for (i = 0; index_nodenames[i + 1]; i++); - assoc->first = 1 + index_nodenames[i]->last; - assoc->last = assoc->first + last; - } - add_pointer_to_array - (assoc, index_nodenames_index, index_nodenames, index_nodenames_slots, - 10, INDEX_NAME_ASSOC *); -} - -/* Find and return the indices of WINDOW's file. The indices are defined - as the first node in the file containing the word "Index" and any - immediately following nodes whose names also contain "Index". All such - indices are concatenated and the result returned. If WINDOW's info file - doesn't have any indices, a NULL pointer is returned. */ -REFERENCE ** -info_indices_of_window (window) - WINDOW *window; -{ - FILE_BUFFER *fb; - - fb = file_buffer_of_window (window); - - return (info_indices_of_file_buffer (fb)); -} - -REFERENCE ** -info_indices_of_file_buffer (file_buffer) - FILE_BUFFER *file_buffer; -{ - register int i; - REFERENCE **result = (REFERENCE **)NULL; - - /* No file buffer, no indices. */ - if (!file_buffer) - return ((REFERENCE **)NULL); - - /* Reset globals describing where the index was found. */ - maybe_free (initial_index_filename); - maybe_free (initial_index_nodename); - initial_index_filename = (char *)NULL; - initial_index_nodename = (char *)NULL; - - if (index_nodenames) - { - for (i = 0; index_nodenames[i]; i++) - { - free (index_nodenames[i]->name); - free (index_nodenames[i]); - } - - index_nodenames_index = 0; - index_nodenames[0] = (INDEX_NAME_ASSOC *)NULL; - } - - /* Grovel the names of the nodes found in this file. */ - if (file_buffer->tags) - { - TAG *tag; - - for (i = 0; tag = file_buffer->tags[i]; i++) - { - if (string_in_line ("Index", tag->nodename) != -1) - { - NODE *node; - REFERENCE **menu; - - /* Found one. Get its menu. */ - node = info_get_node (tag->filename, tag->nodename); - if (!node) - continue; - - /* Remember the filename and nodename of this index. */ - initial_index_filename = savestring (file_buffer->filename); - initial_index_nodename = savestring (tag->nodename); - - menu = info_menu_of_node (node); - - /* If we have a menu, add this index's nodename and range - to our list of index_nodenames. */ - if (menu) - { - add_index_to_index_nodenames (menu, node); - - /* Concatenate the references found so far. */ - result = info_concatenate_references (result, menu); - } - free (node); - } - } - } - - /* If there is a result, clean it up so that every entry has a filename. */ - for (i = 0; result && result[i]; i++) - if (!result[i]->filename) - result[i]->filename = savestring (file_buffer->filename); - - return (result); -} - -DECLARE_INFO_COMMAND (info_index_search, - "Look up a string in the index for this file") -{ - FILE_BUFFER *fb; - char *line; - - /* Reset the index offset, since this is not the info-index-next command. */ - index_offset = 0; - - /* The user is selecting a new search string, so flush the old one. */ - maybe_free (index_search); - index_search = (char *)NULL; - - /* If this window's file is not the same as the one that we last built an - index for, build and remember an index now. */ - fb = file_buffer_of_window (window); - if (!initial_index_filename || - (strcmp (initial_index_filename, fb->filename) != 0)) - { - info_free_references (index_index); - window_message_in_echo_area ("Finding index entries..."); - index_index = info_indices_of_file_buffer (fb); - } - - /* If there is no index, quit now. */ - if (!index_index) - { - info_error ("No indices found."); - return; - } - - /* Okay, there is an index. Let the user select one of the members of it. */ - line = - info_read_maybe_completing (window, "Index entry: ", index_index); - - window = active_window; - - /* User aborted? */ - if (!line) - { - info_abort_key (active_window, 1, 0); - return; - } - - /* Empty line means move to the Index node. */ - if (!*line) - { - free (line); - - if (initial_index_filename && initial_index_nodename) - { - NODE *node; - - node = - info_get_node (initial_index_filename, initial_index_nodename); - set_remembered_pagetop_and_point (window); - window_set_node_of_window (window, node); - remember_window_and_node (window, node); - window_clear_echo_area (); - return; - } - } - - /* The user typed either a completed index label, or a partial string. - Find an exact match, or, failing that, the first index entry containing - the partial string. So, we just call info_next_index_match () with minor - manipulation of INDEX_OFFSET. */ - { - int old_offset; - - /* Start the search right after/before this index. */ - if (count < 0) - { - register int i; - for (i = 0; index_index[i]; i++); - index_offset = i; - } - else - index_offset = -1; - - old_offset == index_offset; - - /* The "last" string searched for is this one. */ - index_search = line; - - /* Find it, or error. */ - info_next_index_match (window, count, 0); - - /* If the search failed, return the index offset to where it belongs. */ - if (index_offset == old_offset) - index_offset = 0; - } -} - -DECLARE_INFO_COMMAND (info_next_index_match, - "Go to the next matching index item from the last `\\[index-search]' command") -{ - register int i; - int partial, dir; - NODE *node; - - /* If there is no previous search string, the user hasn't built an index - yet. */ - if (!index_search) - { - info_error ("No previous index search string."); - return; - } - - /* If there is no index, that is an error. */ - if (!index_index) - { - info_error ("No index entries."); - return; - } - - /* The direction of this search is controlled by the value of the - numeric argument. */ - if (count < 0) - dir = -1; - else - dir = 1; - - /* Search for the next occurence of index_search. First try to find - an exact match. */ - partial = 0; - - for (i = index_offset + dir; (i > -1) && (index_index[i]); i += dir) - if (strcmp (index_search, index_index[i]->label) == 0) - break; - - /* If that failed, look for the next substring match. */ - if ((i < 0) || (!index_index[i])) - { - for (i = index_offset + dir; (i > -1) && (index_index[i]); i += dir) - if (string_in_line (index_search, index_index[i]->label) != -1) - break; - - if ((i > -1) && (index_index[i])) - partial = string_in_line (index_search, index_index[i]->label); - } - - /* If that failed, print an error. */ - if ((i < 0) || (!index_index[i])) - { - info_error ("No %sindex entries containing \"%s\".", - index_offset > 0 ? "more " : "", index_search); - return; - } - - /* Okay, we found the next one. Move the offset to the current entry. */ - index_offset = i; - - /* Report to the user on what we have found. */ - { - register int j; - char *name = "CAN'T SEE THIS"; - char *match; - - for (j = 0; index_nodenames[j]; j++) - { - if ((i >= index_nodenames[j]->first) && - (i <= index_nodenames[j]->last)) - { - name = index_nodenames[j]->name; - break; - } - } - - /* If we had a partial match, indicate to the user which part of the - string matched. */ - match = savestring (index_index[i]->label); - - if (partial && show_index_match) - { - int j, ls, start, upper; - - ls = strlen (index_search); - start = partial - ls; - upper = isupper (match[start]) ? 1 : 0; - - for (j = 0; j < ls; j++) - if (upper) - match[j + start] = info_tolower (match[j + start]); - else - match[j + start] = info_toupper (match[j + start]); - } - - { - char *format; - - format = replace_in_documentation - ("Found \"%s\" in %s. (`\\[next-index-match]' tries to find next.)"); - - window_message_in_echo_area (format, match, name); - } - - free (match); - } - - /* Select the node corresponding to this index entry. */ - node = info_get_node (index_index[i]->filename, index_index[i]->nodename); - - if (!node) - { - info_error (CANT_FILE_NODE, - index_index[i]->filename, index_index[i]->nodename); - return; - } - - set_remembered_pagetop_and_point (window); - window_set_node_of_window (window, node); - remember_window_and_node (window, node); - - - /* Try to find an occurence of LABEL in this node. */ - { - long start, loc; - - start = window->line_starts[1] - window->node->contents; - loc = info_target_search_node (node, index_index[i]->label, start); - - if (loc != -1) - { - window->point = loc; - window_adjust_pagetop (window); - } - } -} - -/* **************************************************************** */ -/* */ -/* Info APROPOS: Search every known index. */ -/* */ -/* **************************************************************** */ - -/* For every menu item in DIR, search the indices of that file for - SEARCH_STRING. */ -REFERENCE ** -apropos_in_all_indices (search_string, inform) - char *search_string; - int inform; -{ - register int i, dir_index; - REFERENCE **all_indices = (REFERENCE **)NULL; - REFERENCE **dir_menu = (REFERENCE **)NULL; - NODE *dir_node; - int printed = 0; - - dir_node = info_get_node ("dir", "Top"); - if (dir_node) - dir_menu = info_menu_of_node (dir_node); - - if (!dir_menu) - return; - - /* For every menu item in DIR, get the associated node's file buffer and - read the indices of that file buffer. Gather all of the indices into - one large one. */ - for (dir_index = 0; dir_menu[dir_index]; dir_index++) - { - REFERENCE **this_index, *this_item; - NODE *this_node; - FILE_BUFFER *this_fb; - - this_item = dir_menu[dir_index]; - - if (!this_item->filename) - { - if (dir_node->parent) - this_item->filename = savestring (dir_node->parent); - else - this_item->filename = savestring (dir_node->filename); - } - - /* Find this node. If we cannot find it, try using the label of the - entry as a file (i.e., "(LABEL)Top"). */ - this_node = info_get_node (this_item->filename, this_item->nodename); - - if (!this_node && this_item->nodename && - (strcmp (this_item->label, this_item->nodename) == 0)) - this_node = info_get_node (this_item->label, "Top"); - - if (!this_node) - continue; - - /* Get the file buffer associated with this node. */ - { - char *files_name; - - files_name = this_node->parent; - if (!files_name) - files_name = this_node->filename; - - this_fb = info_find_file (files_name); - - if (this_fb && inform) - message_in_echo_area ("Scanning indices of \"%s\"...", files_name); - - this_index = info_indices_of_file_buffer (this_fb); - free (this_node); - - if (this_fb && inform) - unmessage_in_echo_area (); - } - - if (this_index) - { - /* Remember the filename which contains this set of references. */ - for (i = 0; this_index && this_index[i]; i++) - if (!this_index[i]->filename) - this_index[i]->filename = savestring (this_fb->filename); - - /* Concatenate with the other indices. */ - all_indices = info_concatenate_references (all_indices, this_index); - } - } - - info_free_references (dir_menu); - - /* Build a list of the references which contain SEARCH_STRING. */ - if (all_indices) - { - REFERENCE *entry, **apropos_list = (REFERENCE **)NULL; - int apropos_list_index = 0; - int apropos_list_slots = 0; - - for (i = 0; (entry = all_indices[i]); i++) - { - if (string_in_line (search_string, entry->label) != -1) - { - add_pointer_to_array - (entry, apropos_list_index, apropos_list, apropos_list_slots, - 100, REFERENCE *); - } - else - { - maybe_free (entry->label); - maybe_free (entry->filename); - maybe_free (entry->nodename); - free (entry); - } - } - - free (all_indices); - all_indices = apropos_list; - } - return (all_indices); -} - -#define APROPOS_NONE \ - "No available info files reference \"%s\" in their indices." - -void -info_apropos (string) - char *string; -{ - REFERENCE **apropos_list; - - apropos_list = apropos_in_all_indices (string, 0); - - if (!apropos_list) - { - info_error (APROPOS_NONE, string); - } - else - { - register int i; - REFERENCE *entry; - - for (i = 0; (entry = apropos_list[i]); i++) - fprintf (stderr, "\"(%s)%s\" -- %s\n", - entry->filename, entry->nodename, entry->label); - } - info_free_references (apropos_list); -} - -static char *apropos_list_nodename = "*Apropos*"; - -DECLARE_INFO_COMMAND (info_index_apropos, - "Grovel all known info file's indices for a string and build a menu") -{ - char *line; - - line = info_read_in_echo_area (window, "Index apropos: "); - - window = active_window; - - /* User aborted? */ - if (!line) - { - info_abort_key (window, 1, 1); - return; - } - - /* User typed something? */ - if (*line) - { - REFERENCE **apropos_list; - NODE *apropos_node; - - apropos_list = apropos_in_all_indices (line, 1); - - if (!apropos_list) - { - info_error (APROPOS_NONE, line); - } - else - { - register int i; - char *line_buffer; - - initialize_message_buffer (); - printf_to_message_buffer - ("\n* Menu: Nodes whoses indices contain \"%s\":\n", line); - line_buffer = (char *)xmalloc (500); - - for (i = 0; apropos_list[i]; i++) - { - int len; - sprintf (line_buffer, "* (%s)%s::", - apropos_list[i]->filename, apropos_list[i]->nodename); - len = pad_to (36, line_buffer); - sprintf (line_buffer + len, "%s", apropos_list[i]->label); - printf_to_message_buffer ("%s\n", line_buffer); - } - free (line_buffer); - } - - apropos_node = message_buffer_to_node (); - add_gcable_pointer (apropos_node); - name_internal_node (apropos_node, apropos_list_nodename); - - /* Even though this is an internal node, we don't want the window - system to treat it specially. So we turn off the internalness - of it here. */ - apropos_node->flags &= ~N_IsInternal; - - /* Find/Create a window to contain this node. */ - { - WINDOW *new; - NODE *node; - - set_remembered_pagetop_and_point (window); - - /* If a window is visible and showing an apropos list already, - re-use it. */ - for (new = windows; new; new = new->next) - { - node = new->node; - - if (internal_info_node_p (node) && - (strcmp (node->nodename, apropos_list_nodename) == 0)) - break; - } - - /* If we couldn't find an existing window, try to use the next window - in the chain. */ - if (!new && window->next) - new = window->next; - - /* If we still don't have a window, make a new one to contain - the list. */ - if (!new) - { - WINDOW *old_active; - - old_active = active_window; - active_window = window; - new = window_make_window ((NODE *)NULL); - active_window = old_active; - } - - /* If we couldn't make a new window, use this one. */ - if (!new) - new = window; - - /* Lines do not wrap in this window. */ - new->flags |= W_NoWrap; - - window_set_node_of_window (new, apropos_node); - remember_window_and_node (new, apropos_node); - active_window = new; - } - info_free_references (apropos_list); - } - free (line); - - if (!info_error_was_printed) - window_clear_echo_area (); -} - diff --git a/gnu/usr.bin/texinfo/info/indices.h b/gnu/usr.bin/texinfo/info/indices.h deleted file mode 100644 index b63a458..0000000 --- a/gnu/usr.bin/texinfo/info/indices.h +++ /dev/null @@ -1,39 +0,0 @@ -/* indices.h -- Functions defined in indices.c. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#ifndef _INDICES_H_ -#define _INDICES_H_ - -/* User-visible variable controls the output of info-index-next. */ -extern int show_index_match; - -extern REFERENCE **info_indices_of_window (), **info_indices_of_file_buffer (); -extern void info_apropos (); - -/* For every menu item in DIR, search the indices of that file for STRING. */ -REFERENCE **apropos_in_all_indices (); - -/* User visible functions declared in indices.c. */ -extern void info_index_search (), info_next_index_match (); - -#endif /* !_INDICES_H_ */ diff --git a/gnu/usr.bin/texinfo/info/info-utils.c b/gnu/usr.bin/texinfo/info/info-utils.c deleted file mode 100644 index 56edcd6..0000000 --- a/gnu/usr.bin/texinfo/info/info-utils.c +++ /dev/null @@ -1,653 +0,0 @@ -/* info-utils.c -- Useful functions for manipulating Info file quirks. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include <stdio.h> /* For "NULL". Yechhh! */ -#include <ctype.h> -#include <sys/types.h> -#include <sys/stat.h> -#include "info-utils.h" - -/* When non-zero, various display and input functions handle ISO Latin - character sets correctly. */ -int ISO_Latin_p = 0; - -/* Variable which holds the most recent filename parsed as a result of - calling info_parse_xxx (). */ -char *info_parsed_filename = (char *)NULL; - -/* Variable which holds the most recent nodename parsed as a result of - calling info_parse_xxx (). */ -char *info_parsed_nodename = (char *)NULL; - -/* Functions to remember a filename or nodename for later return. */ -static void save_filename (), saven_filename (); -static void save_nodename (), saven_nodename (); - -/* How to get a reference (either menu or cross). */ -static REFERENCE **info_references_internal (); - -/* Parse the filename and nodename out of STRING. If STRING doesn't - contain a filename (i.e., it is NOT (FILENAME)NODENAME) then set - INFO_PARSED_FILENAME to NULL. If second argument NEWLINES_OKAY is - non-zero, it says to allow the nodename specification to cross a - newline boundary (i.e., only `,', `.', or `TAB' can end the spec). */ -void -info_parse_node (string, newlines_okay) - char *string; - int newlines_okay; -{ - register int i = 0; - - /* Default the answer. */ - save_filename ((char *)NULL); - save_nodename ((char *)NULL); - - /* Special case of nothing passed. Return nothing. */ - if (!string || !*string) - return; - - string += skip_whitespace (string); - - /* Check for (FILENAME)NODENAME. */ - if (*string == '(') - { - i = 0; - /* Advance past the opening paren. */ - string++; - - /* Find the closing paren. */ - while (string[i] && string[i] != ')') - i++; - - /* Remember parsed filename. */ - saven_filename (string, i); - - /* Point directly at the nodename. */ - string += i; - - if (*string) - string++; - } - - /* Parse out nodename. */ - i = skip_node_characters (string, newlines_okay); - saven_nodename (string, i); - canonicalize_whitespace (info_parsed_nodename); - if (info_parsed_nodename && !*info_parsed_nodename) - { - free (info_parsed_nodename); - info_parsed_nodename = (char *)NULL; - } -} - -/* Return the node addressed by LABEL in NODE (usually one of "Prev:", - "Next:", "Up:", "File:", or "Node:". After a call to this function, - the global INFO_PARSED_NODENAME and INFO_PARSED_FILENAME contain - the information. */ -void -info_parse_label (label, node) - char *label; - NODE *node; -{ - register int i; - char *nodeline; - - /* Default answer to failure. */ - save_nodename ((char *)NULL); - save_filename ((char *)NULL); - - /* Find the label in the first line of this node. */ - nodeline = node->contents; - i = string_in_line (label, nodeline); - - if (i == -1) - return; - - nodeline += i; - nodeline += skip_whitespace (nodeline); - info_parse_node (nodeline, DONT_SKIP_NEWLINES); -} - -/* **************************************************************** */ -/* */ -/* Finding and Building Menus */ -/* */ -/* **************************************************************** */ - -/* Return a NULL terminated array of REFERENCE * which represents the menu - found in NODE. If there is no menu in NODE, just return a NULL pointer. */ -REFERENCE ** -info_menu_of_node (node) - NODE *node; -{ - long position; - SEARCH_BINDING search; - REFERENCE **menu = (REFERENCE **)NULL; - - search.buffer = node->contents; - search.start = 0; - search.end = node->nodelen; - search.flags = S_FoldCase; - - /* Find the start of the menu. */ - position = search_forward (INFO_MENU_LABEL, &search); - - if (position == -1) - return ((REFERENCE **) NULL); - - /* We have the start of the menu now. Glean menu items from the rest - of the node. */ - search.start = position + strlen (INFO_MENU_LABEL); - search.start += skip_line (search.buffer + search.start); - search.start--; - menu = info_menu_items (&search); - return (menu); -} - -/* Return a NULL terminated array of REFERENCE * which represents the cross - refrences found in NODE. If there are no cross references in NODE, just - return a NULL pointer. */ -REFERENCE ** -info_xrefs_of_node (node) - NODE *node; -{ - SEARCH_BINDING search; - - search.buffer = node->contents; - search.start = 0; - search.end = node->nodelen; - search.flags = S_FoldCase; - - return (info_xrefs (&search)); -} - -/* Glean menu entries from BINDING->buffer + BINDING->start until we - have looked at the entire contents of BINDING. Return an array - of REFERENCE * that represents each menu item in this range. */ -REFERENCE ** -info_menu_items (binding) - SEARCH_BINDING *binding; -{ - return (info_references_internal (INFO_MENU_ENTRY_LABEL, binding)); -} - -/* Glean cross references from BINDING->buffer + BINDING->start until - BINDING->end. Return an array of REFERENCE * that represents each - cross reference in this range. */ -REFERENCE ** -info_xrefs (binding) - SEARCH_BINDING *binding; -{ - return (info_references_internal (INFO_XREF_LABEL, binding)); -} - -/* Glean cross references or menu items from BINDING. Return an array - of REFERENCE * that represents the items found. */ -static REFERENCE ** -info_references_internal (label, binding) - char *label; - SEARCH_BINDING *binding; -{ - SEARCH_BINDING search; - REFERENCE **refs = (REFERENCE **)NULL; - int refs_index = 0, refs_slots = 0; - int searching_for_menu_items = 0; - long position; - - search.buffer = binding->buffer; - search.start = binding->start; - search.end = binding->end; - search.flags = S_FoldCase | S_SkipDest; - - searching_for_menu_items = (stricmp (label, INFO_MENU_ENTRY_LABEL) == 0); - - while ((position = search_forward (label, &search)) != -1) - { - int offset, start; - char *refdef; - REFERENCE *entry; - - search.start = position; - search.start += skip_whitespace (search.buffer + search.start); - start = search.start - binding->start; - refdef = search.buffer + search.start; - offset = string_in_line (":", refdef); - - /* When searching for menu items, if no colon, there is no - menu item on this line. */ - if (offset == -1) - { - if (searching_for_menu_items) - continue; - else - { - int temp; - - temp = skip_line (refdef); - offset = string_in_line (":", refdef + temp); - if (offset == -1) - continue; /* Give up? */ - else - offset += temp; - } - } - - entry = (REFERENCE *)xmalloc (sizeof (REFERENCE)); - entry->filename = (char *)NULL; - entry->nodename = (char *)NULL; - entry->label = (char *)xmalloc (offset); - strncpy (entry->label, refdef, offset - 1); - entry->label[offset - 1] = '\0'; - canonicalize_whitespace (entry->label); - - refdef += offset; - entry->start = start; - entry->end = refdef - binding->buffer; - - /* If this reference entry continues with another ':' then the - nodename is the same as the label. */ - if (*refdef == ':') - { - entry->nodename = savestring (entry->label); - } - else - { - /* This entry continues with a specific nodename. Parse the - nodename from the specification. */ - - refdef += skip_whitespace_and_newlines (refdef); - - if (searching_for_menu_items) - info_parse_node (refdef, DONT_SKIP_NEWLINES); - else - info_parse_node (refdef, SKIP_NEWLINES); - - if (info_parsed_filename) - entry->filename = savestring (info_parsed_filename); - - if (info_parsed_nodename) - entry->nodename = savestring (info_parsed_nodename); - } - - add_pointer_to_array - (entry, refs_index, refs, refs_slots, 50, REFERENCE *); - } - return (refs); -} - -/* Get the entry associated with LABEL in MENU. Return a pointer to the - REFERENCE if found, or NULL. */ -REFERENCE * -info_get_labeled_reference (label, references) - char *label; - REFERENCE **references; -{ - register int i; - REFERENCE *entry; - - for (i = 0; references && (entry = references[i]); i++) - { - if (strcmp (label, entry->label) == 0) - return (entry); - } - return ((REFERENCE *)NULL); -} - -/* A utility function for concatenating REFERENCE **. Returns a new - REFERENCE ** which is the concatenation of REF1 and REF2. The REF1 - and REF2 arrays are freed, but their contents are not. */ -REFERENCE ** -info_concatenate_references (ref1, ref2) - REFERENCE **ref1, **ref2; -{ - register int i, j; - REFERENCE **result; - int size; - - /* With one argument passed as NULL, simply return the other arg. */ - if (!ref1) - return (ref2); - else if (!ref2) - return (ref1); - - /* Get the total size of the slots that we will need. */ - for (i = 0; ref1[i]; i++); - size = i; - for (i = 0; ref2[i]; i++); - size += i; - - result = (REFERENCE **)xmalloc ((1 + size) * sizeof (REFERENCE *)); - - /* Copy the contents over. */ - for (i = 0; ref1[i]; i++) - result[i] = ref1[i]; - - j = i; - for (i = 0; ref2[i]; i++) - result[j++] = ref2[i]; - - result[j] = (REFERENCE *)NULL; - free (ref1); - free (ref2); - return (result); -} - -/* Free the data associated with REFERENCES. */ -void -info_free_references (references) - REFERENCE **references; -{ - register int i; - REFERENCE *entry; - - if (references) - { - for (i = 0; references && (entry = references[i]); i++) - { - maybe_free (entry->label); - maybe_free (entry->filename); - maybe_free (entry->nodename); - - free (entry); - } - - free (references); - } -} - -/* Search for sequences of whitespace or newlines in STRING, replacing - all such sequences with just a single space. Remove whitespace from - start and end of string. */ -void -canonicalize_whitespace (string) - char *string; -{ - register int i, j; - int len, whitespace_found, whitespace_loc; - char *temp; - - if (!string) - return; - - len = strlen (string); - temp = (char *)xmalloc (1 + len); - - /* Search for sequences of whitespace or newlines. Replace all such - sequences in the string with just a single space. */ - - whitespace_found = 0; - for (i = 0, j = 0; string[i]; i++) - { - if (whitespace_or_newline (string[i])) - { - whitespace_found++; - whitespace_loc = i; - continue; - } - else - { - if (whitespace_found && whitespace_loc) - { - whitespace_found = 0; - temp[j++] = ' '; - } - - temp[j++] = string[i]; - } - } - - /* Kill trailing whitespace. */ - if (j && whitespace (temp[j - 1])) - j--; - - temp[j] = '\0'; - strcpy (string, temp); - free (temp); -} - -/* String representation of a char returned by printed_representation (). */ -static char the_rep[10]; - -/* Return a pointer to a string which is the printed representation - of CHARACTER if it were printed at HPOS. */ -char * -printed_representation (character, hpos) - unsigned char character; - int hpos; -{ - register int i = 0; - int printable_limit; - - if (ISO_Latin_p) - printable_limit = 160; - else - printable_limit = 127; - - if (character == '\177') - { - the_rep[i++] = '^'; - the_rep[i++] = '?'; - } - else if (iscntrl (character)) - { - switch (character) - { - case '\r': - case '\n': - the_rep[i++] = character; - break; - - case '\t': - { - int tw; - - tw = ((hpos + 8) & 0xf8) - hpos; - while (i < tw) - the_rep[i++] = ' '; - } - break; - - default: - the_rep[i++] = '^'; - the_rep[i++] = (character | 0x40); - } - } - else if (character > printable_limit) - { - sprintf (the_rep + i, "\\%0o", character); - i = strlen (the_rep); - } - else - the_rep[i++] = character; - - the_rep[i] = '\0'; - - return (the_rep); -} - - -/* **************************************************************** */ -/* */ -/* Functions Static To This File */ -/* */ -/* **************************************************************** */ - -/* Amount of space allocated to INFO_PARSED_FILENAME via xmalloc (). */ -static int parsed_filename_size = 0; - -/* Amount of space allocated to INFO_PARSED_NODENAME via xmalloc (). */ -static int parsed_nodename_size = 0; - -static void save_string (), saven_string (); - -/* Remember FILENAME in PARSED_FILENAME. An empty FILENAME is translated - to a NULL pointer in PARSED_FILENAME. */ -static void -save_filename (filename) - char *filename; -{ - save_string (filename, &info_parsed_filename, &parsed_filename_size); -} - -/* Just like save_filename (), but you pass the length of the string. */ -static void -saven_filename (filename, len) - char *filename; - int len; -{ - saven_string (filename, len, - &info_parsed_filename, &parsed_filename_size); -} - -/* Remember NODENAME in PARSED_NODENAME. An empty NODENAME is translated - to a NULL pointer in PARSED_NODENAME. */ -static void -save_nodename (nodename) - char *nodename; -{ - save_string (nodename, &info_parsed_nodename, &parsed_nodename_size); -} - -/* Just like save_nodename (), but you pass the length of the string. */ -static void -saven_nodename (nodename, len) - char *nodename; - int len; -{ - saven_string (nodename, len, - &info_parsed_nodename, &parsed_nodename_size); -} - -/* Remember STRING in STRING_P. STRING_P should currently have STRING_SIZE_P - bytes allocated to it. An empty STRING is translated to a NULL pointer - in STRING_P. */ -static void -save_string (string, string_p, string_size_p) - char *string; - char **string_p; - int *string_size_p; -{ - if (!string || !*string) - { - if (*string_p) - free (*string_p); - - *string_p = (char *)NULL; - *string_size_p = 0; - } - else - { - if (strlen (string) >= *string_size_p) - *string_p = (char *)xrealloc - (*string_p, (*string_size_p = 1 + strlen (string))); - - strcpy (*string_p, string); - } -} - -/* Just like save_string (), but you also pass the length of STRING. */ -static void -saven_string (string, len, string_p, string_size_p) - char *string; - int len; - char **string_p; - int *string_size_p; -{ - if (!string) - { - if (*string_p) - free (*string_p); - - *string_p = (char *)NULL; - *string_size_p = 0; - } - else - { - if (len >= *string_size_p) - *string_p = (char *)xrealloc (*string_p, (*string_size_p = 1 + len)); - - strncpy (*string_p, string, len); - (*string_p)[len] = '\0'; - } -} - -/* Return a pointer to the part of PATHNAME that simply defines the file. */ -char * -filename_non_directory (pathname) - char *pathname; -{ - char *filename; - - filename = (char *)rindex (pathname, '/'); - - if (filename) - filename++; - else - filename = pathname; - - return (filename); -} - -/* Return non-zero if NODE is one especially created by Info. */ -int -internal_info_node_p (node) - NODE *node; -{ - if (node && - (node->filename && !*node->filename) && - !node->parent && node->nodename) - return (1); - else - return (0); -} - -/* Make NODE appear to be one especially created by Info. */ -void -name_internal_node (node, name) - NODE *node; - char *name; -{ - if (!node) - return; - - node->filename = ""; - node->parent = (char *)NULL; - node->nodename = name; - node->flags |= N_IsInternal; -} - -/* Return the window displaying NAME, the name of an internally created - Info window. */ -WINDOW * -get_internal_info_window (name) - char *name; -{ - WINDOW *win = (WINDOW *)NULL; - - for (win = windows; win; win = win->next) - if (internal_info_node_p (win->node) && - (strcmp (win->node->nodename, name) == 0)) - break; - - return (win); -} diff --git a/gnu/usr.bin/texinfo/info/info-utils.h b/gnu/usr.bin/texinfo/info/info-utils.h deleted file mode 100644 index 6c4ec30..0000000 --- a/gnu/usr.bin/texinfo/info/info-utils.h +++ /dev/null @@ -1,144 +0,0 @@ -/* info-utils.h -- Exported functions and variables from info-util.c. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#ifndef _INFO_UTILS_H_ -#define _INFO_UTILS_H_ - -#if !defined (HAVE_RINDEX) -#undef index -#undef rindex -#define index strchr -#define rindex strrchr -#endif - -#if !defined (HAVE_BCOPY) -#undef bcopy -#define bcopy(source, dest, count) memcpy(dest, source, count) -#endif - -#include "nodes.h" -#include "window.h" -#include "search.h" - -/* Structure which describes a node reference, such as a menu entry or - cross reference. Arrays of such references can be built by calling - info_menus_of_node () or info_xrefs_of_node (). */ -typedef struct { - char *label; /* User Label. */ - char *filename; /* File where this node can be found. */ - char *nodename; /* Name of the node. */ - int start, end; /* Offsets within the containing node of LABEL. */ -} REFERENCE; - -/* When non-zero, various display and input functions handle ISO Latin - character sets correctly. */ -extern int ISO_Latin_p; - -/* Variable which holds the most recent filename parsed as a result of - calling info_parse_xxx (). */ -extern char *info_parsed_filename; - -/* Variable which holds the most recent nodename parsed as a result of - calling info_parse_xxx (). */ -extern char *info_parsed_nodename; - -/* Parse the filename and nodename out of STRING. If STRING doesn't - contain a filename (i.e., it is NOT (FILENAME)NODENAME) then set - INFO_PARSED_FILENAME to NULL. If second argument NEWLINES_OKAY is - non-zero, it says to allow the nodename specification to cross a - newline boundary (i.e., only `,', `.', or `TAB' can end the spec). */ -void info_parse_node (); - -/* Return a NULL terminated array of REFERENCE * which represents the menu - found in NODE. If there is no menu in NODE, just return a NULL pointer. */ -extern REFERENCE **info_menu_of_node (); - -/* Return a NULL terminated array of REFERENCE * which represents the cross - refrences found in NODE. If there are no cross references in NODE, just - return a NULL pointer. */ -extern REFERENCE **info_xrefs_of_node (); - -/* Glean cross references from BINDING->buffer + BINDING->start until - BINDING->end. Return an array of REFERENCE * that represents each - cross reference in this range. */ -extern REFERENCE **info_xrefs (); - -/* Get the entry associated with LABEL in REFERENCES. Return a pointer to - the reference if found, or NULL. */ -extern REFERENCE *info_get_labeled_reference (); - -/* Glean menu entries from BINDING->buffer + BINDING->start until we - have looked at the entire contents of BINDING. Return an array - of REFERENCE * that represents each menu item in this range. */ -extern REFERENCE **info_menu_items (); - -/* A utility function for concatenating REFERENCE **. Returns a new - REFERENCE ** which is the concatenation of REF1 and REF2. The REF1 - and REF2 arrays are freed, but their contents are not. */ -REFERENCE **info_concatenate_references (); - -/* Free the data associated with REFERENCES. */ -extern void info_free_references (); - -/* Search for sequences of whitespace or newlines in STRING, replacing - all such sequences with just a single space. Remove whitespace from - start and end of string. */ -void canonicalize_whitespace (); - -/* Return a pointer to a string which is the printed representation - of CHARACTER if it were printed at HPOS. */ -extern char *printed_representation (); - -/* Return a pointer to the part of PATHNAME that simply defines the file. */ -extern char *filename_non_directory (); - -/* Return non-zero if NODE is one especially created by Info. */ -extern int internal_info_node_p (); - -/* Make NODE appear to be one especially created by Info, and give it NAME. */ -extern void name_internal_node (); - -/* Return the window displaying NAME, the name of an internally created - Info window. */ -extern WINDOW *get_internal_info_window (); - -/* Return the node addressed by LABEL in NODE (usually one of "Prev:", - "Next:", "Up:", "File:", or "Node:". After a call to this function, - the global INFO_PARSED_NODENAME and INFO_PARSED_FILENAME contain - the information. */ -extern void info_parse_label (/* label, node */); - -#define info_label_was_found \ - (info_parsed_nodename != NULL || info_parsed_filename != NULL) - -#define info_file_label_of_node(n) info_parse_label (INFO_FILE_LABEL, n) -#define info_next_label_of_node(n) info_parse_label (INFO_NEXT_LABEL, n) -#define info_up_label_of_node(n) info_parse_label (INFO_UP_LABEL, n) -#define info_prev_label_of_node(n) \ - do { \ - info_parse_label (INFO_PREV_LABEL, n); \ - if (!info_label_was_found) \ - info_parse_label (INFO_ALTPREV_LABEL, n); \ - } while (0) - -#endif /* !_INFO_UTILS_H_ */ diff --git a/gnu/usr.bin/texinfo/info/info.1 b/gnu/usr.bin/texinfo/info/info.1 deleted file mode 100644 index cd88463..0000000 --- a/gnu/usr.bin/texinfo/info/info.1 +++ /dev/null @@ -1,232 +0,0 @@ -.\" $Id$ -.\" -.TH info 1 "7th December 1990" -.SH NAME -info \- GNU's hypertext system -.SH SYNOPSIS -.B info -[ -.B \-\-option-name option-value -] -.B \menu-item... -.SH COPYRIGHT -.if n Copyright (C) 1989, 1993 Free Software Foundation, Inc. -.if t Copyright \(co 1989, 1993 Free Software Foundation, Inc. -.SH DESCRIPTION -.LP -The GNU project has a hypertext system called -.I Info -which allows the same source file to be either printed as a -paper manual, or viewed using -.B info. -It is possible to use the -.B info -program from inside Emacs, or to use the stand-alone version described here. -This manual page gives a brief summary of its capabilities. - -.SH OPTIONS -.TP -.B \-\-directory directory-path -Add -.B directory-path -to the list of directory paths searched when -.B info -needs to find a file. You may issue -.B \-\-directory -multiple times. -Alternatively, you may specify a value for the environment variable -.B INFOPATH; -if -.B \-\-directory -is not given, the value of -.B INFOPATH -is used. The value of -.B INFOPATH -is a colon separated list of directory names. If you do not supply either -.B INFOPATH -or -.B \-\-directory-path, -.B info -uses a default path. -.TP -.B \-f filename -Specify a particular -.B info -file to visit. By default, -.B info -visits -the file -.B dir; -if you use this option, -.B info -will start with -.B (FILENAME)Top -as the first file and node. -.TP -.B \-n nodename -Specify a particular node to visit in the initial file that -.B info -loads. This is especially useful in conjunction with -.B \-\-file. -You may specify -.B \-\-node -multiple times. -.TP -.B -o file -Direct output to -.B file -instead of starting an interactive -.B info -session. -.TP -.B \-h -Produce a relatively brief description of the available -.B info -options. -.TP -.B \-\-version -Print the version information of -.B info -and exit. -.TP -.B menu-item -.B info -treats its remaining arguments as the names of menu items. -The first argument is a menu item in the initial node visited, -while the second argument is a menu item in the first argument's -node. You can easily move to the node of your choice by -specifying the menu names which describe the path to that node. -For example, - -.B info emacs buffers - -first selects the menu item -.B emacs -in the node -.B (dir)Top, -and then selects the menu item -.B buffers -in the node -.B (emacs)Top. -.SH COMMANDS -When in -.B info -the following commands are available: -.TP -.B h -Invoke the Info tutorial. -.TP -.B ? -Get a short summary of -.B info -commands. -.TP -.B h -Select the -.B info -node from the main directory; this is much more complete than just -using -.B ?. -.TP -.B Ctrl-g -Abort whatever you are doing. -.TP -.B Ctrl-l -Redraw the screen. -.PP -Selecting other nodes: -.TP -.B n -Move to the "next" node of this node. -.TP -.B p -Move to the "previous" node of this node. -.TP -.B u -Move to this node's "up" node. -.TP -.B m -Pick a menu item specified by name. Picking a menu item causes another -node to be selected. You do not need to type a complete nodename; if -you type a few letters and then a space or tab -.B info -will try to fill in the rest of the nodename. If you ask for further -completion without typing any more characters you'll be given a list -of possibilities; you can also get the list with -.B ?. -If you type a few characters and then hit return -.B info -will try to do a completion, and if it is ambigous use the first possibility. -.TP -.B f -Follow a cross reference. You are asked for the name of the reference, -using command completion as for -.B m. -.TP -.B l -Move to the last node you were at. -.PP -Moving within a node: -.TP -.B Space -Scroll forward a page. -.TP -.B DEL -Scroll backward a page. -.TP -.B b -Go to the beginning of this node. -.PP -Advanced commands: -.TP -.B q -Quit -.B info. -.TP -.B 1 -Pick first item in node's menu. -.TP -.B 2 \-\- 5 -Pick second ... fifth item in node's menu. -.TP -.B g -Move to node specified by name. You may include a filename as well, -as -.B (FILENAME)NODENAME. -.TP -.B s -Search through this -.B info -file for a specified string, and select the node in which -the next occurrence is found. -.TP -.B M-x print-node -Pipe the contents of the current node through the command in the -environment variable -.B INFO_PRINT_COMMAND. -If the variable does not exist, the node is simply piped to -.B lpr. -.SH ENVIRONMENT -.TP -.B INFOPATHS -A colon-separated list of directories to search for -.B info -files. Used if -.B \-\-directory -is not given. -.TP -.B INFO_PRINT_COMMAND -The command used for printing. -.SH SEE ALSO -.BR man (1) -.\" .BR emacs (1) -.SH AUTHOR -.RS -Brian Fox, Free Software Foundation -.br -bfox@ai.mit.edu -.SH MANUAL AUTHOR -.RS -Robert Lupton; updated by Robert J. Chassell. -.br -rhl@astro.princeton.edu; bob@gnu.ai.mit.edu diff --git a/gnu/usr.bin/texinfo/info/info.c b/gnu/usr.bin/texinfo/info/info.c deleted file mode 100644 index dfbffcc..0000000 --- a/gnu/usr.bin/texinfo/info/info.c +++ /dev/null @@ -1,511 +0,0 @@ -/* info.c -- Display nodes of Info files in multiple windows. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include "info.h" -#include "dribble.h" -#include "getopt.h" - -/* The version numbers of this version of Info. */ -int info_major_version = 2; -int info_minor_version = 10; -int info_patch_level = 1; - -/* Non-zero means search all indices for APROPOS_SEARCH_STRING. */ -static int apropos_p = 0; - -/* Variable containing the string to search for when apropos_p is non-zero. */ -static char *apropos_search_string = (char *)NULL; - -/* Non-zero means print version info only. */ -static int print_version_p = 0; - -/* Non-zero means print a short description of the options. */ -static int print_help_p = 0; - -/* Array of the names of nodes that the user specified with "--node" on the - command line. */ -static char **user_nodenames = (char **)NULL; -static int user_nodenames_index = 0; -static int user_nodenames_slots = 0; - -/* String specifying the first file to load. This string can only be set - by the user specifying "--file" on the command line. */ -static char *user_filename = (char *)NULL; - -/* String specifying the name of the file to dump nodes to. This value is - filled if the user speficies "--output" on the command line. */ -static char *user_output_filename = (char *)NULL; - -/* Non-zero indicates that when "--output" is specified, all of the menu - items of the specified nodes (and their subnodes as well) should be - dumped in the order encountered. This basically can print a book. */ -int dump_subnodes = 0; - -/* Structure describing the options that Info accepts. We pass this structure - to getopt_long (). If you add or otherwise change this structure, you must - also change the string which follows it. */ -#define APROPOS_OPTION 1 -#define DRIBBLE_OPTION 2 -#define RESTORE_OPTION 3 -static struct option long_options[] = { - { "apropos", 1, 0, APROPOS_OPTION }, - { "directory", 1, 0, 'd' }, - { "node", 1, 0, 'n' }, - { "file", 1, 0, 'f' }, - { "subnodes", 0, &dump_subnodes, 1 }, - { "output", 1, 0, 'o' }, - { "help", 0, &print_help_p, 1 }, - { "version", 0, &print_version_p, 1 }, - { "dribble", 1, 0, DRIBBLE_OPTION }, - { "restore", 1, 0, RESTORE_OPTION }, - {NULL, 0, NULL, 0} -}; - -/* String describing the shorthand versions of the long options found above. */ -static char *short_options = "d:n:f:o:s"; - -/* When non-zero, the Info window system has been initialized. */ -int info_windows_initialized_p = 0; - -/* Some "forward" declarations. */ -static void usage (), info_short_help (), remember_info_program_name (); - - -/* **************************************************************** */ -/* */ -/* Main Entry Point to the Info Program */ -/* */ -/* **************************************************************** */ - -int -main (argc, argv) - int argc; - char **argv; -{ - int getopt_long_index; /* Index returned by getopt_long (). */ - NODE *initial_node; /* First node loaded by Info. */ - -#if defined (NeXT) && defined (NOTDEF) - malloc_debug (0x0ffffffff); -#endif /* NeXT && NOTDEF */ - - remember_info_program_name (argv[0]); - - while (1) - { - int option_character; - - option_character = getopt_long - (argc, argv, short_options, long_options, &getopt_long_index); - - /* getopt_long () returns EOF when there are no more long options. */ - if (option_character == EOF) - break; - - /* If this is a long option, then get the short version of it. */ - if (option_character == 0 && long_options[getopt_long_index].flag == 0) - option_character = long_options[getopt_long_index].val; - - /* Case on the option that we have received. */ - switch (option_character) - { - case 0: - break; - - /* User wants to add a directory. */ - case 'd': - info_add_path (optarg, INFOPATH_PREPEND); - break; - - /* User is specifying a particular node. */ - case 'n': - add_pointer_to_array (optarg, user_nodenames_index, user_nodenames, - user_nodenames_slots, 10, char *); - break; - - /* User is specifying a particular Info file. */ - case 'f': - if (user_filename) - free (user_filename); - - user_filename = savestring (optarg); - break; - - /* User is specifying the name of a file to output to. */ - case 'o': - if (user_output_filename) - free (user_output_filename); - user_output_filename = savestring (optarg); - break; - - /* User is specifying that she wishes to dump the subnodes of - the node that she is dumping. */ - case 's': - dump_subnodes = 1; - break; - - /* User has specified a string to search all indices for. */ - case APROPOS_OPTION: - apropos_p = 1; - maybe_free (apropos_search_string); - apropos_search_string = savestring (optarg); - break; - - /* User has specified a dribble file to receive keystrokes. */ - case DRIBBLE_OPTION: - close_dribble_file (); - open_dribble_file (optarg); - break; - - /* User has specified an alternate input stream. */ - case RESTORE_OPTION: - info_set_input_from_file (optarg); - break; - - default: - usage (); - } - } - - /* If the user specified --version, then show the version and exit. */ - if (print_version_p) - { - printf ("GNU Info, Version %s.\n", version_string ()); - exit (0); - } - - /* If the `--help' option was present, show the help and exit. */ - if (print_help_p) - { - info_short_help (); - exit (0); - } - - /* If the user hasn't specified a path for Info files, default that path - now. */ - if (!infopath) - { - char *path_from_env, *getenv (); - - path_from_env = getenv ("INFOPATH"); - - if (path_from_env) - info_add_path (path_from_env); - else - info_add_path (DEFAULT_INFOPATH); - } - - /* If the user specified a particular filename, add the path of that - file to the contents of INFOPATH. */ - if (user_filename) - { - char *directory_name, *temp; - - directory_name = savestring (user_filename); - temp = filename_non_directory (directory_name); - - if (temp != directory_name) - { - *temp = 0; - info_add_path (directory_name, INFOPATH_PREPEND); - } - - free (directory_name); - } - - /* If the user wants to search every known index for a given string, - do that now, and report the results. */ - if (apropos_p) - { - info_apropos (apropos_search_string); - exit (0); - } - - /* Get the initial Info node. It is either "(dir)Top", or what the user - specifed with values in user_filename and user_nodenames. */ - if (user_nodenames) - initial_node = info_get_node (user_filename, user_nodenames[0]); - else - initial_node = info_get_node (user_filename, (char *)NULL); - - /* If we couldn't get the initial node, this user is in trouble. */ - if (!initial_node) - { - if (info_recent_file_error) - info_error (info_recent_file_error); - else - info_error - (CANT_FIND_NODE, user_nodenames ? user_nodenames[0] : "Top"); - exit (1); - } - - /* Special cases for when the user specifies multiple nodes. If we are - dumping to an output file, dump all of the nodes specified. Otherwise, - attempt to create enough windows to handle the nodes that this user wants - displayed. */ - if (user_nodenames_index > 1) - { - free (initial_node); - - if (user_output_filename) - dump_nodes_to_file - (user_filename, user_nodenames, user_output_filename, dump_subnodes); - else - begin_multiple_window_info_session (user_filename, user_nodenames); - - exit (0); - } - - /* If there are arguments remaining, they are the names of menu items - in sequential info files starting from the first one loaded. That - file name is either "dir", or the contents of user_filename if one - was specified. */ - while (optind != argc) - { - REFERENCE **menu; - REFERENCE *entry; - NODE *node; - char *arg; - - /* Remember the name of the menu entry we want. */ - arg = argv[optind++]; - - /* Build and return a list of the menu items in this node. */ - menu = info_menu_of_node (initial_node); - - /* If there wasn't a menu item in this node, stop here, but let - the user continue to use Info. Perhaps they wanted this node - and didn't realize it. */ - if (!menu) - { - begin_info_session_with_error - (initial_node, "There is no menu in this node."); - exit (0); - } - - /* Find the specified menu item. */ - entry = info_get_labeled_reference (arg, menu); - - /* If the item wasn't found, search the list sloppily. Perhaps this - user typed "buffer" when they really meant "Buffers". */ - if (!entry) - { - register int i; - - for (i = 0; entry = menu[i]; i++) - if (strnicmp (entry->label, arg, strlen (arg)) == 0) - break; - } - - /* If we failed to find the reference, start Info with the current - node anyway. It is probably a misspelling. */ - if (!entry) - { - char *error_message = "There is no menu item \"%s\" in this node."; - - info_free_references (menu); - - /* If we were supposed to dump this node, complain. */ - if (user_output_filename) - info_error (error_message, arg); - else - begin_info_session_with_error (initial_node, error_message, arg); - - exit (0); - } - - /* We have found the reference that the user specified. Clean it - up a little bit. */ - if (!entry->filename) - { - if (initial_node->parent) - entry->filename = savestring (initial_node->parent); - else - entry->filename = savestring (initial_node->filename); - } - - /* Find this node. If we can find it, then turn the initial_node - into this one. If we cannot find it, try using the label of the - entry as a file (i.e., "(LABEL)Top"). Otherwise the Info file is - malformed in some way, and we will just use the current value of - initial node. */ - node = info_get_node (entry->filename, entry->nodename); - - if (!node && entry->nodename && - (strcmp (entry->label, entry->nodename) == 0)) - node = info_get_node (entry->label, "Top"); - - if (node) - { - free (initial_node); - initial_node = node; - info_free_references (menu); - } - else - { - char *temp = savestring (entry->label); - char *error_message; - - error_message = "Unable to find the node referenced by \"%s\"."; - - info_free_references (menu); - - /* If we were trying to dump the node, then give up. Otherwise, - start the session with an error message. */ - if (user_output_filename) - info_error (error_message, temp); - else - begin_info_session_with_error (initial_node, error_message, temp); - - exit (0); - } - } - - /* If the user specified that this node should be output, then do that - now. Otherwise, start the Info session with this node. */ - if (user_output_filename) - dump_node_to_file (initial_node, user_output_filename, dump_subnodes); - else - begin_info_session (initial_node); - - exit (0); -} - -/* Return a string describing the current version of Info. */ -char * -version_string () -{ - static char *vstring = (char *)NULL; - - if (!vstring) - { - vstring = (char *)xmalloc (50); - sprintf (vstring, "%d.%d", info_major_version, info_minor_version); - if (info_patch_level) - sprintf (vstring + strlen (vstring), "-p%d", info_patch_level); - } - return (vstring); -} - -/* **************************************************************** */ -/* */ -/* Error Handling for Info */ -/* */ -/* **************************************************************** */ - -static char *program_name = (char *)NULL; - -static void -remember_info_program_name (fullpath) - char *fullpath; -{ - char *filename; - - filename = filename_non_directory (fullpath); - program_name = savestring (filename); -} - -/* Non-zero if an error has been signalled. */ -int info_error_was_printed = 0; - -/* Non-zero means ring terminal bell on errors. */ -int info_error_rings_bell_p = 1; - -/* Print FORMAT with ARG1 and ARG2. If the window system was initialized, - then the message is printed in the echo area. Otherwise, a message is - output to stderr. */ -void -info_error (format, arg1, arg2) - char *format; - void *arg1, *arg2; -{ - info_error_was_printed = 1; - - if (!info_windows_initialized_p || display_inhibited) - { - fprintf (stderr, "%s: ", program_name); - fprintf (stderr, format, arg1, arg2); - fprintf (stderr, "\n"); - fflush (stderr); - } - else - { - if (!echo_area_is_active) - { - if (info_error_rings_bell_p) - terminal_ring_bell (); - window_message_in_echo_area (format, arg1, arg2); - } - else - { - NODE *temp; - - temp = build_message_node (format, arg1, arg2); - if (info_error_rings_bell_p) - terminal_ring_bell (); - inform_in_echo_area (temp->contents); - free (temp->contents); - free (temp); - } - } -} - -/* Produce a very brief descripton of the available options and exit with - an error. */ -static void -usage () -{ - fprintf (stderr,"%s\n%s\n%s\n%s\n%s\n", -"Usage: info [-d dir-path] [-f info-file] [-o output-file] [-n node-name]...", -" [--directory dir-path] [--file info-file] [--node node-name]...", -" [--help] [--output output-file] [--subnodes] [--version]", -" [--dribble dribble-file] [--restore from-file]", -" [menu-selection ...]"); - exit (1); -} - -/* Produce a scaled down description of the available options to Info. */ -static void -info_short_help () -{ - printf ("%s", "\ -Here is a quick description of Info's options. For a more complete\n\ -description of how to use Info, type `info info options'.\n\ -\n\ - --directory DIR Add DIR to INFOPATH.\n\ - --file FILENAME Specify Info file to visit.\n\ - --node NODENAME Specify nodes in first visited Info file.\n\ - --output FILENAME Output selected nodes to FILENAME.\n\ - --dribble FILENAME Remember user keystrokes in FILENAME.\n\ - --restore FILENAME Read initial keystrokes from FILENAME.\n\ - --subnodes Recursively output menu items.\n\ - --help Get this help message.\n\ - --version Display Info's version information.\n\ -\n\ -Remaining arguments to Info are treated as the names of menu\n\ -items in the initial node visited. You can easily move to the\n\ -node of your choice by specifying the menu names which describe\n\ -the path to that node. For example, `info emacs buffers'.\n"); - - exit (0); -} diff --git a/gnu/usr.bin/texinfo/info/info.h b/gnu/usr.bin/texinfo/info/info.h deleted file mode 100644 index 09e40c2..0000000 --- a/gnu/usr.bin/texinfo/info/info.h +++ /dev/null @@ -1,96 +0,0 @@ -/* info.h -- Header file which includes all of the other headers. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#ifndef _INFO_H_ -#define _INFO_H_ - -#include <stdio.h> -#include <ctype.h> -#include <sys/types.h> -#include <sys/stat.h> -#include "filesys.h" -#include "display.h" -#include "session.h" -#include "echo_area.h" -#include "doc.h" -#include "footnotes.h" -#include "gc.h" - -/* A structure associating the nodes visited in a particular window. */ -typedef struct { - WINDOW *window; /* The window that this list is attached to. */ - NODE **nodes; /* Array of nodes visited in this window. */ - int *pagetops; /* For each node in NODES, the pagetop. */ - long *points; /* For each node in NODES, the point. */ - int current; /* Index in NODES of the current node. */ - int nodes_index; /* Index where to add the next node. */ - int nodes_slots; /* Number of slots allocated to NODES. */ -} INFO_WINDOW; - -/* Array of structures describing for each window which nodes have been - visited in that window. */ -extern INFO_WINDOW **info_windows; - -/* For handling errors. If you initialize the window system, you should - also set info_windows_initialized_p to non-zero. It is used by the - info_error () function to determine how to format and output errors. */ -extern int info_windows_initialized_p; - -/* Non-zero if an error message has been printed. */ -extern int info_error_was_printed; - -/* Non-zero means ring terminal bell on errors. */ -extern int info_error_rings_bell_p; - -/* Print FORMAT with ARG1 and ARG2. If the window system was initialized, - then the message is printed in the echo area. Otherwise, a message is - output to stderr. */ -extern void info_error (); - -/* The version numbers of Info. */ -extern int info_major_version, info_minor_version, info_patch_level; - -/* How to get the version string for this version of Info. Returns - something similar to "2.9". */ -extern char *version_string (); - -/* Error message defines. */ -#define CANT_FIND_NODE "Cannot find the node \"%s\"." -#define CANT_FILE_NODE "Cannot find the node \"(%s)%s\"." -#define CANT_FIND_WIND "Cannot find a window!" -#define CANT_FIND_POINT "Point doesn't appear within this window's node!" -#define CANT_KILL_LAST "Cannot delete the last window." -#define NO_MENU_NODE "No menu in this node." -#define NO_FOOT_NODE "No footnotes in this node." -#define NO_XREF_NODE "No cross references in this node." -#define NO_POINTER "No \"%s\" pointer for this node." -#define UNKNOWN_COMMAND "Unknown Info command `%c'. `?' for help." -#define TERM_TOO_DUMB "Terminal type \"%s\" is not smart enough to run Info." -#define AT_NODE_BOTTOM "You are already at the last page of this node." -#define AT_NODE_TOP "You are already at the first page of this node." -#define ONE_WINDOW "Only one window." -#define WIN_TOO_SMALL "Resulting window would be too small." -#define CANT_MAKE_HELP \ -"There isn't enough room to make a help window. Please delete a window." - -#endif /* !_INFO_H_ */ diff --git a/gnu/usr.bin/texinfo/info/infodoc.c b/gnu/usr.bin/texinfo/info/infodoc.c deleted file mode 100644 index d92d40b..0000000 --- a/gnu/usr.bin/texinfo/info/infodoc.c +++ /dev/null @@ -1,689 +0,0 @@ -/* infohelp.c -- Functions which build documentation nodes. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include "info.h" - -/* **************************************************************** */ -/* */ -/* Info Help Windows */ -/* */ -/* **************************************************************** */ - -/* The name of the node used in the help window. */ -static char *info_help_nodename = "*Info Help*"; - -/* A node containing printed key bindings and their documentation. */ -static NODE *internal_info_help_node = (NODE *)NULL; - -/* The static text which appears in the internal info help node. */ -static char *info_internal_help_text[] = { - "Basic Commands in Info Windows", - "******************************", - "", - " h Invoke the Info tutorial.", - "", - "Selecting other nodes:", - "----------------------", - " n Move to the \"next\" node of this node.", - " p Move to the \"previous\" node of this node.", - " u Move \"up\" from this node.", - " m Pick menu item specified by name.", - " Picking a menu item causes another node to be selected.", - " f Follow a cross reference. Reads name of reference.", - " l Move to the last node seen in this window.", - " d Move to the `directory' node. Equivalent to `g(DIR)'.", - "", - "Moving within a node:", - "---------------------", - " SPC Scroll forward a page.", - " DEL Scroll backward a page.", - " b Go to the beginning of this node.", - " e Go to the end of this node.", - "", - "\"Advanced\" commands:", - "--------------------", - " q Quit Info.", - " 1 Pick first item in node's menu.", - " 2-9 Pick second ... ninth item in node's menu.", - " 0 Pick last item in node's menu.", - " g Move to node specified by name.", - " You may include a filename as well, as in (FILENAME)NODENAME.", - " s Search through this Info file for a specified string,", - " and select the node in which the next occurrence is found.", - (char *)NULL -}; - -void -dump_map_to_message_buffer (prefix, map) - char *prefix; - Keymap map; -{ - register int i; - - for (i = 0; i < 256; i++) - { - if (map[i].type == ISKMAP) - { - char *new_prefix, *keyname; - - keyname = pretty_keyname (i); - new_prefix = (char *) - xmalloc (3 + strlen (prefix) + strlen (keyname)); - sprintf (new_prefix, "%s%s%s ", prefix, *prefix ? " " : "", keyname); - - dump_map_to_message_buffer (new_prefix, (Keymap)map[i].function); - free (new_prefix); - } - else if (map[i].function) - { - register int last; - char *doc, *name; - - doc = function_documentation (map[i].function); - name = function_name (map[i].function); - - if (!*doc) - continue; - - /* Find out if there is a series of identical functions, as in - ea_insert (). */ - for (last = i + 1; last < 256; last++) - if ((map[last].type != ISFUNC) || - (map[last].function != map[i].function)) - break; - - if (last - 1 != i) - { - printf_to_message_buffer - ("%s%s .. ", prefix, pretty_keyname (i)); - printf_to_message_buffer - ("%s%s\t", prefix, pretty_keyname (last - 1)); - i = last - 1; - } - else - printf_to_message_buffer ("%s%s\t", prefix, pretty_keyname (i)); - -#if defined (NAMED_FUNCTIONS) - /* Print the name of the function, and some padding before the - documentation string is printed. */ - { - int length_so_far; - int desired_doc_start = 40; /* Must be multiple of 8. */ - - printf_to_message_buffer ("(%s)", name); - length_so_far = message_buffer_length_this_line (); - - if ((desired_doc_start + strlen (doc)) >= the_screen->width) - printf_to_message_buffer ("\n "); - else - { - while (length_so_far < desired_doc_start) - { - printf_to_message_buffer ("\t"); - length_so_far += character_width ('\t', length_so_far); - } - } - } -#endif /* NAMED_FUNCTIONS */ - printf_to_message_buffer ("%s\n", doc); - } - } -} - -/* How to create internal_info_help_node. */ -static void -create_internal_info_help_node () -{ - register int i; - - initialize_message_buffer (); - - for (i = 0; info_internal_help_text[i]; i++) - printf_to_message_buffer ("%s\n", info_internal_help_text[i]); - - printf_to_message_buffer ("---------------------\n\n"); - printf_to_message_buffer ("The current search path is:\n"); - printf_to_message_buffer (" \"%s\"\n", infopath); - printf_to_message_buffer ("---------------------\n\n"); - printf_to_message_buffer ("Commands available in Info windows:\n\n"); - dump_map_to_message_buffer ("", info_keymap); - printf_to_message_buffer ("---------------------\n\n"); - printf_to_message_buffer ("Commands available in the echo area:\n\n"); - dump_map_to_message_buffer ("", echo_area_keymap); - - { - char *message; - - message = replace_in_documentation - ("--- Use `\\[history-node]' or `\\[kill-node]' to exit ---\n"); - printf_to_message_buffer ("%s", message); - } - - internal_info_help_node = message_buffer_to_node (); - add_gcable_pointer (internal_info_help_node->contents); - name_internal_node (internal_info_help_node, info_help_nodename); - - /* Even though this is an internal node, we don't want the window - system to treat it specially. So we turn off the internalness - of it here. */ - internal_info_help_node->flags &= ~N_IsInternal; -} - -/* Return a window which is the window showing help in this Info. */ -static WINDOW * -info_find_or_create_help_window () -{ - WINDOW *help_window; - - help_window = get_internal_info_window (info_help_nodename); - - /* If we couldn't find the help window, then make it. */ - if (!help_window) - { - WINDOW *window, *eligible = (WINDOW *)NULL; - int max = 0; - - for (window = windows; window; window = window->next) - { - if (window->height > max) - { - max = window->height; - eligible = window; - } - } - - if (!eligible) - return ((WINDOW *)NULL); - else - { - /* Make a new node containing the help text. Split the largest - window into 2 windows, and show the help text in that window. */ - if (!internal_info_help_node) - create_internal_info_help_node (); - - if (eligible->height > 30) - { - active_window = eligible; - help_window = window_make_window (internal_info_help_node); - } - else - { - set_remembered_pagetop_and_point (active_window); - window_set_node_of_window - (active_window, internal_info_help_node); - help_window = active_window; - } - - remember_window_and_node (help_window, help_window->node); - } - } - return (help_window); -} - -/* Create or move to the help window. */ -DECLARE_INFO_COMMAND (info_get_help_window, "Display help message") -{ - WINDOW *help_window; - - help_window = info_find_or_create_help_window (); - if (help_window) - { - active_window = help_window; - active_window->flags |= W_UpdateWindow; - } - else - { - info_error (CANT_MAKE_HELP); - } -} - -/* Show the Info help node. This means that the "info" file is installed - where it can easily be found on your system. */ -DECLARE_INFO_COMMAND (info_get_info_help_node, "Visit Info node `(info)Help'") -{ - NODE *node; - char *nodename; - - /* If there is a window on the screen showing the node "(info)Help" or - the node "(info)Help-Small-Screen", simply select that window. */ - { - WINDOW *win; - - for (win = windows; win; win = win->next) - { - if (win->node && win->node->filename && - (stricmp - (filename_non_directory (win->node->filename), "info") == 0) && - ((strcmp (win->node->nodename, "Help") == 0) || - (strcmp (win->node->nodename, "Help-Small-Screen") == 0))) - { - active_window = win; - return; - } - } - } - - /* If the current window is small, show the small screen help. */ - if (active_window->height < 24) - nodename = "Help-Small-Screen"; - else - nodename = "Help"; - - /* Try to get the info file for Info. */ - node = info_get_node ("Info", nodename); - - if (!node) - { - if (info_recent_file_error) - info_error (info_recent_file_error); - else - info_error (CANT_FILE_NODE, "Info", nodename); - } - else - { - /* If the current window is very large (greater than 45 lines), - then split it and show the help node in another window. - Otherwise, use the current window. */ - - if (active_window->height > 45) - active_window = window_make_window (node); - else - { - set_remembered_pagetop_and_point (active_window); - window_set_node_of_window (active_window, node); - } - - remember_window_and_node (active_window, node); - } -} - -/* **************************************************************** */ -/* */ -/* Groveling Info Keymaps and Docs */ -/* */ -/* **************************************************************** */ - -/* Return the documentation associated with the Info command FUNCTION. */ -char * -function_documentation (function) - VFunction *function; -{ - register int i; - - for (i = 0; function_doc_array[i].func; i++) - if (function == function_doc_array[i].func) - break; - - return (replace_in_documentation (function_doc_array[i].doc)); -} - -#if defined (NAMED_FUNCTIONS) -/* Return the user-visible name of the function associated with the - Info command FUNCTION. */ -char * -function_name (function) - - VFunction *function; -{ - register int i; - - for (i = 0; function_doc_array[i].func; i++) - if (function == function_doc_array[i].func) - break; - - return (function_doc_array[i].func_name); -} - -/* Return a pointer to the function named NAME. */ -VFunction * -named_function (name) - char *name; -{ - register int i; - - for (i = 0; function_doc_array[i].func; i++) - if (strcmp (function_doc_array[i].func_name, name) == 0) - break; - - return (function_doc_array[i].func); -} -#endif /* NAMED_FUNCTIONS */ - -/* Return the documentation associated with KEY in MAP. */ -char * -key_documentation (key, map) - char key; - Keymap map; -{ - VFunction *function = map[key].function; - - if (function) - return (function_documentation (function)); - else - return ((char *)NULL); -} - -DECLARE_INFO_COMMAND (describe_key, "Print documentation for KEY") -{ - char keyname[50]; - int keyname_index = 0; - unsigned char keystroke; - char *rep; - Keymap map; - - keyname[0] = '\0'; - map = window->keymap; - - while (1) - { - message_in_echo_area ("Describe key: %s", keyname); - keystroke = info_get_input_char (); - unmessage_in_echo_area (); - - if (Meta_p (keystroke) && (!ISO_Latin_p || key < 160)) - { - if (map[ESC].type != ISKMAP) - { - window_message_in_echo_area - ("ESC %s is undefined.", pretty_keyname (UnMeta (keystroke))); - return; - } - - strcpy (keyname + keyname_index, "ESC "); - keyname_index = strlen (keyname); - keystroke = UnMeta (keystroke); - map = (Keymap)map[ESC].function; - } - - /* Add the printed representation of KEYSTROKE to our keyname. */ - rep = pretty_keyname (keystroke); - strcpy (keyname + keyname_index, rep); - keyname_index = strlen (keyname); - - if (map[keystroke].function == (VFunction *)NULL) - { - message_in_echo_area ("%s is undefined.", keyname); - return; - } - else if (map[keystroke].type == ISKMAP) - { - map = (Keymap)map[keystroke].function; - strcat (keyname, " "); - keyname_index = strlen (keyname); - continue; - } - else - { - char *message, *fundoc, *funname = ""; - -#if defined (NAMED_FUNCTIONS) - funname = function_name (map[keystroke].function); -#endif /* NAMED_FUNCTIONS */ - - fundoc = function_documentation (map[keystroke].function); - - message = (char *)xmalloc - (10 + strlen (keyname) + strlen (fundoc) + strlen (funname)); - -#if defined (NAMED_FUNCTIONS) - sprintf (message, "%s (%s): %s.", keyname, funname, fundoc); -#else - sprintf (message, "%s is defined to %s.", keyname, fundoc); -#endif /* !NAMED_FUNCTIONS */ - - window_message_in_echo_area ("%s", message); - free (message); - break; - } - } -} - -/* How to get the pretty printable name of a character. */ -static char rep_buffer[30]; - -char * -pretty_keyname (key) - unsigned char key; -{ - char *rep; - - if (Meta_p (key)) - { - char temp[20]; - - rep = pretty_keyname (UnMeta (key)); - - sprintf (temp, "ESC %s", rep); - strcpy (rep_buffer, temp); - rep = rep_buffer; - } - else if (Control_p (key)) - { - switch (key) - { - case '\n': rep = "LFD"; break; - case '\t': rep = "TAB"; break; - case '\r': rep = "RET"; break; - case ESC: rep = "ESC"; break; - - default: - sprintf (rep_buffer, "C-%c", UnControl (key)); - rep = rep_buffer; - } - } - else - { - switch (key) - { - case ' ': rep = "SPC"; break; - case DEL: rep = "DEL"; break; - default: - rep_buffer[0] = key; - rep_buffer[1] = '\0'; - rep = rep_buffer; - } - } - return (rep); -} - -/* Replace the names of functions with the key that invokes them. */ -static char *where_is (), *where_is_internal (); - -char * -replace_in_documentation (string) - char *string; -{ - register int i, start, next; - static char *result = (char *)NULL; - - maybe_free (result); - result = (char *)xmalloc (1 + strlen (string)); - - i = next = start = 0; - - /* Skip to the beginning of a replaceable function. */ - for (i = start; string[i]; i++) - { - /* Is this the start of a replaceable function name? */ - if (string[i] == '\\' && string[i + 1] == '[') - { - char *fun_name, *rep; - VFunction *function; - - /* Copy in the old text. */ - strncpy (result + next, string + start, i - start); - next += (i - start); - start = i + 2; - - /* Move to the end of the function name. */ - for (i = start; string[i] && (string[i] != ']'); i++); - - fun_name = (char *)xmalloc (1 + i - start); - strncpy (fun_name, string + start, i - start); - fun_name[i - start] = '\0'; - - /* Find a key which invokes this function in the info_keymap. */ - function = named_function (fun_name); - - /* If the internal documentation string fails, there is a - serious problem with the associated command's documentation. - We croak so that it can be fixed immediately. */ - if (!function) - abort (); - - rep = where_is (info_keymap, function); - strcpy (result + next, rep); - next = strlen (result); - - start = i; - if (string[i]) - start++; - } - } - strcpy (result + next, string + start); - return (result); -} - -/* Return a string of characters which could be typed from the keymap - MAP to invoke FUNCTION. */ -static char *where_is_rep = (char *)NULL; -static int where_is_rep_index = 0; -static int where_is_rep_size = 0; - -static char * -where_is (map, function) - Keymap map; - VFunction *function; -{ - char *rep; - - if (!where_is_rep_size) - where_is_rep = (char *)xmalloc (where_is_rep_size = 100); - where_is_rep_index = 0; - - rep = where_is_internal (map, function); - - /* If it couldn't be found, return "M-x Foo". */ - if (!rep) - { - char *name; - - name = function_name (function); - - if (name) - sprintf (where_is_rep, "M-x %s", name); - - rep = where_is_rep; - } - return (rep); -} - -/* Return the printed rep of FUNCTION as found in MAP, or NULL. */ -static char * -where_is_internal (map, function) - Keymap map; - VFunction *function; -{ - register int i; - - /* If the function is directly invokable in MAP, return the representation - of that keystroke. */ - for (i = 0; i < 256; i++) - if ((map[i].type == ISFUNC) && map[i].function == function) - { - sprintf (where_is_rep + where_is_rep_index, "%s", pretty_keyname (i)); - return (where_is_rep); - } - - /* Okay, search subsequent maps for this function. */ - for (i = 0; i < 256; i++) - { - if (map[i].type == ISKMAP) - { - int saved_index = where_is_rep_index; - char *rep; - - sprintf (where_is_rep + where_is_rep_index, "%s ", - pretty_keyname (i)); - - where_is_rep_index = strlen (where_is_rep); - rep = where_is_internal ((Keymap)map[i].function, function); - - if (rep) - return (where_is_rep); - - where_is_rep_index = saved_index; - } - } - - return ((char *)NULL); -} - -extern char *read_function_name (); - -DECLARE_INFO_COMMAND (info_where_is, - "Show what to type to execute a given command") -{ - char *command_name; - - command_name = read_function_name ("Where is command: ", window); - - if (!command_name) - { - info_abort_key (active_window, count, key); - return; - } - - if (*command_name) - { - VFunction *function; - - function = named_function (command_name); - - if (function) - { - char *location; - - location = where_is (active_window->keymap, function); - - if (!location) - { - info_error ("`%s' is not on any keys", command_name); - } - else - { - if (strncmp (location, "M-x ", 4) == 0) - window_message_in_echo_area - ("%s can only be invoked via %s.", command_name, location); - else - window_message_in_echo_area - ("%s can be invoked via %s.", command_name, location); - } - } - else - info_error ("There is no function named `%s'", command_name); - } - - free (command_name); -} - diff --git a/gnu/usr.bin/texinfo/info/infomap.c b/gnu/usr.bin/texinfo/info/infomap.c deleted file mode 100644 index 26906c5..0000000 --- a/gnu/usr.bin/texinfo/info/infomap.c +++ /dev/null @@ -1,328 +0,0 @@ -/* infomap.c -- Keymaps for Info. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include "stdio.h" -#include "ctype.h" -#include "infomap.h" -#include "funs.h" -#include "info.h" - -static void add_function_key(char *, VFunction *, Keymap); - -extern char *term_ku, *term_kd, *term_kr, *term_kl; -extern char *term_kP, *term_kN, *term_kh, *term_kH; - -/* Return a new keymap which has all the uppercase letters mapped to run - the function info_do_lowercase_version (). */ -Keymap -keymap_make_keymap () -{ - register int i; - Keymap keymap; - - keymap = (Keymap)xmalloc (256 * sizeof (KEYMAP_ENTRY)); - - for (i = 0; i < 256; i++) - { - keymap[i].type = ISFUNC; - keymap[i].function = (VFunction *)NULL; - } - - for (i = 'A'; i < ('Z' + 1); i++) - { - keymap[i].type = ISFUNC; - keymap[i].function = info_do_lowercase_version; - } - - return (keymap); -} - -/* Return a new keymap which is a copy of MAP. */ -Keymap -keymap_copy_keymap (map) - Keymap map; -{ - register int i; - Keymap keymap; - - keymap = keymap_make_keymap (); - - for (i = 0; i < 256; i++) - { - keymap[i].type = map[i].type; - keymap[i].function = map[i].function; - } - return (keymap); -} - -/* Free the keymap and it's descendents. */ -void -keymap_discard_keymap (map) - Keymap (map); -{ - register int i; - - if (!map) - return; - - for (i = 0; i < 256; i++) - { - switch (map[i].type) - { - case ISFUNC: - break; - - case ISKMAP: - keymap_discard_keymap ((Keymap)map[i].function); - break; - - } - } -} - -/* Initialize the standard info keymaps. */ - -Keymap info_keymap = (Keymap)NULL; -Keymap echo_area_keymap = (Keymap)NULL; - -void -initialize_info_keymaps () -{ - register int i; - Keymap map; - - if (!info_keymap) - { - info_keymap = keymap_make_keymap (); - info_keymap[ESC].type = ISKMAP; - info_keymap[ESC].function = (VFunction *)keymap_make_keymap (); - info_keymap[Control ('x')].type = ISKMAP; - info_keymap[Control ('x')].function = (VFunction *)keymap_make_keymap (); - echo_area_keymap = keymap_make_keymap (); - echo_area_keymap[ESC].type = ISKMAP; - echo_area_keymap[ESC].function = (VFunction *)keymap_make_keymap (); - echo_area_keymap[Control ('x')].type = ISKMAP; - echo_area_keymap[Control ('x')].function = - (VFunction *)keymap_make_keymap (); - } - - /* Bind numeric arg functions for both echo area and info window maps. */ - for (i = '0'; i < '9' + 1; i++) - { - ((Keymap) info_keymap[ESC].function)[i].function = - ((Keymap) echo_area_keymap[ESC].function)[i].function = - info_add_digit_to_numeric_arg; - } - ((Keymap) info_keymap[ESC].function)['-'].function = - ((Keymap) echo_area_keymap[ESC].function)['-'].function = - info_add_digit_to_numeric_arg; - - /* Bind the echo area routines. */ - map = echo_area_keymap; - - /* Bind the echo area insert routines. */ - for (i = 0; i < 160; i++) - if (isprint (i)) - map[i].function = ea_insert; - - map[Control ('a')].function = ea_beg_of_line; - map[Control ('b')].function = ea_backward; - map[Control ('d')].function = ea_delete; - map[Control ('e')].function = ea_end_of_line; - map[Control ('f')].function = ea_forward; - map[Control ('g')].function = ea_abort; - map[Control ('h')].function = ea_rubout; - map[Control ('k')].function = ea_kill_line; - map[Control ('l')].function = info_redraw_display; - map[Control ('q')].function = ea_quoted_insert; - map[Control ('t')].function = ea_transpose_chars; - map[Control ('u')].function = info_universal_argument; - map[Control ('y')].function = ea_yank; - - map[LFD].function = ea_newline; - map[RET].function = ea_newline; - map[SPC].function = ea_complete; - map[TAB].function = ea_complete; - map['?'].function = ea_possible_completions; - map[DEL].function = ea_rubout; - - /* Bind the echo area ESC keymap. */ - map = (Keymap)echo_area_keymap[ESC].function; - - map[Control ('g')].function = ea_abort; - map[Control ('v')].function = ea_scroll_completions_window; - map['b'].function = ea_backward_word; - map['d'].function = ea_kill_word; - map['f'].function = ea_forward_word; -#if defined (NAMED_FUNCTIONS) - /* map['x'].function = info_execute_command; */ -#endif /* NAMED_FUNCTIONS */ - map['y'].function = ea_yank_pop; - map['?'].function = ea_possible_completions; - map[TAB].function = ea_tab_insert; - map[DEL].function = ea_backward_kill_word; - - /* Bind the echo area Control-x keymap. */ - map = (Keymap)echo_area_keymap[Control ('x')].function; - - map['o'].function = info_next_window; - map[DEL].function = ea_backward_kill_line; - - /* Bind commands for Info window keymaps. */ - map = info_keymap; - map[TAB].function = info_move_to_next_xref; - map[LFD].function = info_select_reference_this_line; - map[RET].function = info_select_reference_this_line; - map[SPC].function = info_scroll_forward; - map[Control ('a')].function = info_beginning_of_line; - map[Control ('b')].function = info_backward_char; - map[Control ('e')].function = info_end_of_line; - map[Control ('f')].function = info_forward_char; - map[Control ('g')].function = info_abort_key; - map[Control ('h')].function = info_get_help_window; - map[Control ('l')].function = info_redraw_display; - map[Control ('n')].function = info_next_line; - map[Control ('p')].function = info_prev_line; - map[Control ('r')].function = isearch_backward; - map[Control ('s')].function = isearch_forward; - map[Control ('u')].function = info_universal_argument; - map[Control ('v')].function = info_scroll_forward; - map[','].function = info_next_index_match; - - for (i = '1'; i < '9' + 1; i++) - map[i].function = info_menu_digit; - map['0'].function = info_last_menu_item; - - map['<'].function = info_first_node; - map['>'].function = info_last_node; - map['?'].function = info_get_help_window; - map['['].function = info_global_prev_node; - map[']'].function = info_global_next_node; - - map['b'].function = info_beginning_of_node; - map['d'].function = info_dir_node; - map['e'].function = info_end_of_node; - map['f'].function = info_xref_item; - map['g'].function = info_goto_node; - map['h'].function = info_get_info_help_node; - map['i'].function = info_index_search; - map['l'].function = info_history_node; - map['m'].function = info_menu_item; - map['n'].function = info_next_node; - map['p'].function = info_prev_node; - map['q'].function = info_quit; - map['r'].function = info_xref_item; - map['s'].function = info_search; - map['t'].function = info_top_node; - map['u'].function = info_up_node; - map[DEL].function = info_scroll_backward; - - /* Bind members in the ESC map for Info windows. */ - map = (Keymap)info_keymap[ESC].function; - map[Control ('f')].function = info_show_footnotes; - map[Control ('g')].function = info_abort_key; - map[TAB].function = info_move_to_prev_xref; - map[Control ('v')].function = info_scroll_other_window; - map['<'].function = info_beginning_of_node; - map['>'].function = info_end_of_node; - map['b'].function = info_backward_word; - map['f'].function = info_forward_word; - map['r'].function = info_move_to_window_line; - map['v'].function = info_scroll_backward; -#if defined (NAMED_FUNCTIONS) - map['x'].function = info_execute_command; -#endif /* NAMED_FUNCTIONS */ - - /* Bind members in the Control-X map for Info windows. */ - map = (Keymap)info_keymap[Control ('x')].function; - - map[Control ('b')].function = list_visited_nodes; - map[Control ('c')].function = info_quit; - map[Control ('f')].function = info_view_file; - map[Control ('g')].function = info_abort_key; - map[Control ('v')].function = info_view_file; - map['0'].function = info_delete_window; - map['1'].function = info_keep_one_window; - map['2'].function = info_split_window; - map['^'].function = info_grow_window; - map['b'].function = select_visited_node; - map['k'].function = info_kill_node; - map['o'].function = info_next_window; - map['t'].function = info_tile_windows; - map['w'].function = info_toggle_wrap; - - /* Add functions for the arrow keys, PageUp, PageDown, Home, HomeDown */ - add_function_key(term_ku, info_prev_line, info_keymap); - add_function_key(term_kd, info_next_line, info_keymap); - add_function_key(term_kl, info_backward_char, info_keymap); - add_function_key(term_kr, info_forward_char, info_keymap); - add_function_key(term_kP, info_scroll_backward, info_keymap); - add_function_key(term_kN, info_scroll_forward, info_keymap); - add_function_key(term_kh, info_beginning_of_node, info_keymap); - add_function_key(term_kH, info_end_of_node, info_keymap); -} - -static void add_function_key(char *esc_seq, VFunction *func, Keymap map) -{ - char *end_str, *p; - - if (!esc_seq) - return; /* don't add keys which don't exist */ - - end_str = esc_seq + strlen(esc_seq); - - for (p = esc_seq; p < end_str; p++) - { - if (isupper(*p)) - *p = tolower(*p); - switch (map[*p].type) - { - case ISKMAP: /* Go one level down. Also has the effect - that we're not overwriting a previous - binding if we're at the end of p */ - map = (Keymap)map[*p].function; - break; - case ISFUNC: /* two possibilities here: - 1. map[*p].function == NULL means we have - a virgin keymap to fill; - 2. else this entry is already taken */ - if (map[*p].function == NULL) - { - if (p == end_str - 1) - { - map[*p].function = func; - return; - } - map[*p].type = ISKMAP; - map[*p].function = (VFunction *)keymap_make_keymap(); - map = (Keymap)map[*p].function; - } else - return; - break; - default: /* can't happen */ - info_error("unknown keymap type (%d).", map[*p].type); - break; - } - } - return; -} diff --git a/gnu/usr.bin/texinfo/info/infomap.h b/gnu/usr.bin/texinfo/info/infomap.h deleted file mode 100644 index 85e5d80..0000000 --- a/gnu/usr.bin/texinfo/info/infomap.h +++ /dev/null @@ -1,82 +0,0 @@ -/* infomap.h -- Description of a keymap in Info and related functions. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#ifndef _INFOMAP_H_ -#define _INFOMAP_H_ - -#include "general.h" - -#define ESC '\033' -#define DEL '\177' -#define TAB '\011' -#define RET '\r' -#define LFD '\n' -#define SPC ' ' - -#define meta_character_threshold (DEL + 1) -#define control_character_threshold (SPC) - -#define meta_character_bit 0x80 -#define control_character_bit 0x40 - -#define Meta_p(c) (((c) > meta_character_threshold)) -#define Control_p(c) ((c) < control_character_threshold) - -#define Meta(c) ((c) | (meta_character_bit)) -#define UnMeta(c) ((c) & (~meta_character_bit)) -#define Control(c) ((toupper (c)) & (~control_character_bit)) -#define UnControl(c) (tolower ((c) | control_character_bit)) - -/* A keymap contains one entry for each key in the ASCII set. - Each entry consists of a type and a pointer. - FUNCTION is the address of a function to run, or the - address of a keymap to indirect through. - TYPE says which kind of thing FUNCTION is. */ -typedef struct { - char type; - VFunction *function; -} KEYMAP_ENTRY; - -typedef KEYMAP_ENTRY *Keymap; - -/* The values that TYPE can have in a keymap entry. */ -#define ISFUNC 0 -#define ISKMAP 1 - -extern Keymap info_keymap; -extern Keymap echo_area_keymap; - -/* Return a new keymap which has all the uppercase letters mapped to run - the function info_do_lowercase_version (). */ -extern Keymap keymap_make_keymap (); - -/* Return a new keymap which is a copy of MAP. */ -extern Keymap keymap_copy_keymap (); - -/* Free MAP and it's descendents. */ -extern void keymap_discard_keymap (); - -/* Initialize the info keymaps. */ -extern void initialize_info_keymaps (); - -#endif /* _INFOMAP_H_ */ diff --git a/gnu/usr.bin/texinfo/info/m-x.c b/gnu/usr.bin/texinfo/info/m-x.c deleted file mode 100644 index 13a861f..0000000 --- a/gnu/usr.bin/texinfo/info/m-x.c +++ /dev/null @@ -1,195 +0,0 @@ -/* m-x.c -- Meta-X minibuffer reader. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include "info.h" - -/* **************************************************************** */ -/* */ -/* Reading Named Commands */ -/* */ -/* **************************************************************** */ - -/* Read the name of an Info function in the echo area and return the - name. A return value of NULL indicates that no function name could - be read. */ -char * -read_function_name (prompt, window) - char *prompt; - WINDOW *window; -{ - register int i; - char *line; - REFERENCE **array = (REFERENCE **)NULL; - int array_index = 0, array_slots = 0; - - /* Make an array of REFERENCE which actually contains the names of - the functions available in Info. */ - for (i = 0; function_doc_array[i].func; i++) - { - REFERENCE *entry; - - entry = (REFERENCE *)xmalloc (sizeof (REFERENCE)); - entry->label = savestring (function_doc_array[i].func_name); - entry->nodename = (char *)NULL; - entry->filename = (char *)NULL; - - add_pointer_to_array - (entry, array_index, array, array_slots, 200, REFERENCE *); - } - - line = info_read_completing_in_echo_area (window, prompt, array); - - info_free_references (array); - - if (!echo_area_is_active) - window_clear_echo_area (); - - return (line); -} - -DECLARE_INFO_COMMAND (describe_command, - "Read the name of an Info command and describe it") -{ - char *line; - - line = read_function_name ("Describe command: ", window); - - if (!line) - { - info_abort_key (active_window, count, key); - return; - } - - /* Describe the function named in "LINE". */ - if (*line) - { - char *fundoc; - VFunction *fun; - - fun = named_function (line); - - if (!fun) - return; - - window_message_in_echo_area ("%s: %s.", - line, function_documentation (fun)); - } - free (line); -} - -DECLARE_INFO_COMMAND (info_execute_command, - "Read a command name in the echo area and execute it") -{ - char *line; - - /* Ask the completer to read a reference for us. */ - if (info_explicit_arg || count != 1) - { - char *prompt; - - prompt = (char *)xmalloc (20); - sprintf (prompt, "%d M-x ", count); - line = read_function_name (prompt, window); - } - else - line = read_function_name ("M-x ", window); - - /* User aborted? */ - if (!line) - { - info_abort_key (active_window, count, key); - return; - } - - /* User accepted "default"? (There is none.) */ - if (!*line) - { - free (line); - return; - } - - /* User wants to execute a named command. Do it. */ - { - VFunction *function; - - if ((active_window != the_echo_area) && - (strncmp (line, "echo-area-", 10) == 0)) - { - free (line); - info_error ("Cannot execute an `echo-area' command here."); - return; - } - - function = named_function (line); - free (line); - - if (!function) - return; - - (*function) (active_window, count, 0); - } -} - -/* Okay, now that we have M-x, let the user set the screen height. */ -DECLARE_INFO_COMMAND (set_screen_height, - "Set the height of the displayed window") -{ - int new_height; - - if (info_explicit_arg || count != 1) - new_height = count; - else - { - char prompt[80]; - char *line; - - new_height = screenheight; - - sprintf (prompt, "Set screen height to (%d): ", new_height); - - line = info_read_in_echo_area (window, prompt); - - /* If the user aborted, do that now. */ - if (!line) - { - info_abort_key (active_window, count, 0); - return; - } - - /* Find out what the new height is supposed to be. */ - if (*line) - new_height = atoi (line); - - /* Clear the echo area if it isn't active. */ - if (!echo_area_is_active) - window_clear_echo_area (); - - free (line); - } - - terminal_clear_screen (); - display_clear_display (the_display); - screenheight = new_height; - display_initialize_display (screenwidth, screenheight); - window_new_screen_size (screenwidth, screenheight); -} diff --git a/gnu/usr.bin/texinfo/info/nodemenu.c b/gnu/usr.bin/texinfo/info/nodemenu.c deleted file mode 100644 index 674ea7c..0000000 --- a/gnu/usr.bin/texinfo/info/nodemenu.c +++ /dev/null @@ -1,321 +0,0 @@ -/* nodemenu.c -- Produce a menu of all visited nodes. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include "info.h" - -/* Return a line describing the format of a node information line. */ -static char * -nodemenu_format_info () -{ - return ("\n\ -* Menu:\n\ - (File)Node Lines Size Containing File\n\ - ---------- ----- ---- ---------------"); -} - -/* Produce a formatted line of information about NODE. Here is what we want - the output listing to look like: - -* Menu: - (File)Node Lines Size Containing File - ---------- ----- ---- --------------- -* (emacs)Buffers:: 48 2230 /usr/gnu/info/emacs/emacs-1 -* (autoconf)Writing configure.in:: 123 58789 /usr/gnu/info/autoconf/autoconf-1 -* (dir)Top:: 40 589 /usr/gnu/info/dir -*/ -static char * -format_node_info (node) - NODE *node; -{ - register int i, len; - char *parent, *containing_file; - static char *line_buffer = (char *)NULL; - - if (!line_buffer) - line_buffer = (char *)xmalloc (1000); - - if (node->parent) - { - parent = filename_non_directory (node->parent); - if (!parent) - parent = node->parent; - } - else - parent = (char *)NULL; - - containing_file = node->filename; - - if (!parent && !*containing_file) - sprintf (line_buffer, "* %s::", node->nodename); - else - { - char *file = (char *)NULL; - - if (parent) - file = parent; - else - file = filename_non_directory (containing_file); - - if (!file) - file = containing_file; - - if (!*file) - file = "dir"; - - sprintf (line_buffer, "* (%s)%s::", file, node->nodename); - } - - len = pad_to (36, line_buffer); - - { - int lines = 1; - - for (i = 0; i < node->nodelen; i++) - if (node->contents[i] == '\n') - lines++; - - sprintf (line_buffer + len, "%d", lines); - } - - len = pad_to (44, line_buffer); - sprintf (line_buffer + len, "%d", node->nodelen); - - if (node->filename && *(node->filename)) - { - len = pad_to (51, line_buffer); - sprintf (line_buffer + len, node->filename); - } - - return (savestring (line_buffer)); -} - -/* Little string comparison routine for qsort (). */ -static int -compare_strings (string1, string2) - char **string1, **string2; -{ - return (stricmp (*string1, *string2)); -} - -/* The name of the nodemenu node. */ -static char *nodemenu_nodename = "*Node Menu*"; - -/* Produce an informative listing of all the visited nodes, and return it - in a node. If FILTER_FUNC is non-null, it is a function which filters - which nodes will appear in the listing. FILTER_FUNC takes an argument - of NODE, and returns non-zero if the node should appear in the listing. */ -NODE * -get_visited_nodes (filter_func) - Function *filter_func; -{ - register int i, iw_index; - INFO_WINDOW *info_win; - NODE *node; - char **lines = (char **)NULL; - int lines_index = 0, lines_slots = 0; - - if (!info_windows) - return ((NODE *)NULL); - - for (iw_index = 0; info_win = info_windows[iw_index]; iw_index++) - { - for (i = 0; i < info_win->nodes_index; i++) - { - node = info_win->nodes[i]; - - /* We skip mentioning "*Node Menu*" nodes. */ - if (internal_info_node_p (node) && - (strcmp (node->nodename, nodemenu_nodename) == 0)) - continue; - - if (node && (!filter_func || (*filter_func) (node))) - { - char *line; - - line = format_node_info (node); - add_pointer_to_array - (line, lines_index, lines, lines_slots, 20, char *); - } - } - } - - /* Sort the array of information lines. */ - qsort (lines, lines_index, sizeof (char *), compare_strings); - - /* Delete duplicates. */ - { - register int j, newlen; - char **temp; - - for (i = 0, newlen = 1; i < lines_index - 1; i++) - { - if (strcmp (lines[i], lines[i + 1]) == 0) - { - free (lines[i]); - lines[i] = (char *)NULL; - } - else - newlen++; - } - - /* We have free ()'d and marked all of the duplicate slots. Copy the - live slots rather than pruning the dead slots. */ - temp = (char **)xmalloc ((1 + newlen) * sizeof (char *)); - for (i = 0, j = 0; i < lines_index; i++) - if (lines[i]) - temp[j++] = lines[i]; - - temp[j] = (char *)NULL; - free (lines); - lines = temp; - lines_index = newlen; - } - - initialize_message_buffer (); - printf_to_message_buffer - ("Here is a menu of nodes you could select with info-history-node:\n"); - printf_to_message_buffer ("%s\n", nodemenu_format_info ()); - for (i = 0; i < lines_index; i++) - { - printf_to_message_buffer ("%s\n", lines[i]); - free (lines[i]); - } - free (lines); - - node = message_buffer_to_node (); - add_gcable_pointer (node->contents); - return (node); -} - -DECLARE_INFO_COMMAND (list_visited_nodes, - "Make a window containing a menu of all of the currently visited nodes") -{ - WINDOW *new; - NODE *node; - - set_remembered_pagetop_and_point (window); - - /* If a window is visible and showing the buffer list already, re-use it. */ - for (new = windows; new; new = new->next) - { - node = new->node; - - if (internal_info_node_p (node) && - (strcmp (node->nodename, nodemenu_nodename) == 0)) - break; - } - - /* If we couldn't find an existing window, try to use the next window - in the chain. */ - if (!new && window->next) - new = window->next; - - /* If we still don't have a window, make a new one to contain the list. */ - if (!new) - { - WINDOW *old_active; - - old_active = active_window; - active_window = window; - new = window_make_window ((NODE *)NULL); - active_window = old_active; - } - - /* If we couldn't make a new window, use this one. */ - if (!new) - new = window; - - /* Lines do not wrap in this window. */ - new->flags |= W_NoWrap; - node = get_visited_nodes ((Function *)NULL); - name_internal_node (node, nodemenu_nodename); - - /* Even if this is an internal node, we don't want the window - system to treat it specially. So we turn off the internalness - of it here. */ - node->flags &= ~N_IsInternal; - - /* If this window is already showing a node menu, reuse the existing node - slot. */ - { - int remember_me = 1; - -#if defined (NOTDEF) - if (internal_info_node_p (new->node) && - (strcmp (new->node->nodename, nodemenu_nodename) == 0)) - remember_me = 0; -#endif /* NOTDEF */ - - window_set_node_of_window (new, node); - - if (remember_me) - remember_window_and_node (new, node); - } - - active_window = new; -} - -DECLARE_INFO_COMMAND (select_visited_node, - "Select a node which has been previously visited in a visible window") -{ - char *line; - NODE *node; - REFERENCE **menu; - - node = get_visited_nodes ((Function *)NULL); - - menu = info_menu_of_node (node); - free (node); - - line = - info_read_completing_in_echo_area (window, "Select visited node: ", menu); - - window = active_window; - - /* User aborts, just quit. */ - if (!line) - { - info_abort_key (window, 0, 0); - info_free_references (menu); - return; - } - - if (*line) - { - REFERENCE *entry; - - /* Find the selected label in the references. */ - entry = info_get_labeled_reference (line, menu); - - if (!entry) - info_error ("The reference disappeared! (%s).", line); - else - info_select_reference (window, entry); - } - - free (line); - info_free_references (menu); - - if (!info_error_was_printed) - window_clear_echo_area (); -} diff --git a/gnu/usr.bin/texinfo/info/nodes.c b/gnu/usr.bin/texinfo/info/nodes.c deleted file mode 100644 index 2036680..0000000 --- a/gnu/usr.bin/texinfo/info/nodes.c +++ /dev/null @@ -1,1167 +0,0 @@ -/* nodes.c -- How to get an Info file and node. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include <stdio.h> -#include <ctype.h> -#include <sys/types.h> -#include <sys/file.h> -#include <sys/errno.h> -#include <sys/stat.h> -#include "nodes.h" -#include "search.h" -#include "filesys.h" -#include "info-utils.h" - -#if !defined (O_RDONLY) -#if defined (HAVE_SYS_FCNTL_H) -#include <sys/fcntl.h> -#else /* !HAVE_SYS_FCNTL_H */ -#include <fcntl.h> -#endif /* !HAVE_SYS_FCNTL_H */ -#endif /* !O_RDONLY */ - -#if !defined (errno) -extern int errno; -#endif /* !errno */ - -/* **************************************************************** */ -/* */ -/* Functions Static to this File */ -/* */ -/* **************************************************************** */ - -static void forget_info_file (), remember_info_file (); -static void free_file_buffer_tags (), free_info_tag (); -static void get_nodes_of_tags_table (), get_nodes_of_info_file (); -static void get_tags_of_indirect_tags_table (); -static void info_reload_file_buffer_contents (); -static char *adjust_nodestart (); -static FILE_BUFFER *make_file_buffer (); -static FILE_BUFFER *info_load_file_internal (), *info_find_file_internal (); -static NODE *info_node_of_file_buffer_tags (); - -static long get_node_length (); - -/* Magic number that RMS used to decide how much a tags table pointer could - be off by. I feel that it should be much smaller, like on the order of - 4. */ -#define DEFAULT_INFO_FUDGE 1000 - -/* Passed to *_internal functions. INFO_GET_TAGS says to do what is - neccessary to fill in the nodes or tags arrays in FILE_BUFFER. */ -#define INFO_NO_TAGS 0 -#define INFO_GET_TAGS 1 - -/* **************************************************************** */ -/* */ -/* Global Variables */ -/* */ -/* **************************************************************** */ - -/* When non-zero, this is a string describing the recent file error. */ -char *info_recent_file_error = (char *)NULL; - -/* The list of already loaded nodes. */ -FILE_BUFFER **info_loaded_files = (FILE_BUFFER **)NULL; - -/* The number of slots currently allocated to LOADED_FILES. */ -int info_loaded_files_slots = 0; - -/* **************************************************************** */ -/* */ -/* Public Functions for Node Manipulation */ -/* */ -/* **************************************************************** */ - -/* Used to build "dir" menu from "localdir" files found in INFOPATH. */ -extern void maybe_build_dir_node (); - -/* Return a pointer to a NODE structure for the Info node (FILENAME)NODENAME. - FILENAME can be passed as NULL, in which case the filename of "dir" is used. - NODENAME can be passed as NULL, in which case the nodename of "Top" is used. - If the node cannot be found, return a NULL pointer. */ -NODE * -info_get_node (filename, nodename) - char *filename, *nodename; -{ - FILE_BUFFER *file_buffer; - NODE *node; - - file_buffer = (FILE_BUFFER *)NULL; - info_recent_file_error = (char *)NULL; - - info_parse_node (nodename, DONT_SKIP_NEWLINES); - nodename = (char *)NULL; - - if (info_parsed_filename) - filename = info_parsed_filename; - - if (info_parsed_nodename) - nodename = info_parsed_nodename; - - /* If FILENAME is not specified, it defaults to "dir". */ - if (!filename) - filename = "dir"; - - /* If the file to be looked up is "dir", build the contents from all of - the "localdir"'s found in INFOPATH. */ - if (stricmp (filename, "dir") == 0) - maybe_build_dir_node (filename, "localdir"); - - /* Find the correct info file. */ - file_buffer = info_find_file (filename); - - if (!file_buffer) - { - if (filesys_error_number) - info_recent_file_error = - filesys_error_string (filename, filesys_error_number); - return ((NODE *)NULL); - } - - node = info_get_node_of_file_buffer (nodename, file_buffer); - /* If the node looked for was "Top", try again looking for the node under - a slightly different name. */ - if (!node && (nodename == NULL || stricmp (nodename, "Top") == 0)) - { - node = info_get_node_of_file_buffer ("Top", file_buffer); - if (!node) - node = info_get_node_of_file_buffer ("top", file_buffer); - if (!node) - node = info_get_node_of_file_buffer ("TOP", file_buffer); - } - return (node); -} - -/* Return a pointer to a NODE structure for the Info node NODENAME in - FILE_BUFFER. NODENAME can be passed as NULL, in which case the - nodename of "Top" is used. If the node cannot be found, return a - NULL pointer. */ -NODE * -info_get_node_of_file_buffer (nodename, file_buffer) - char *nodename; - FILE_BUFFER *file_buffer; -{ - NODE *node = (NODE *)NULL; - - /* If we are unable to find the file, we have to give up. There isn't - anything else we can do. */ - if (!file_buffer) - return ((NODE *)NULL); - - /* If the file buffer was gc'ed, reload the contents now. */ - if (!file_buffer->contents) - info_reload_file_buffer_contents (file_buffer); - - /* If NODENAME is not specified, it defaults to "Top". */ - if (!nodename) - nodename = "Top"; - - /* If the name of the node that we wish to find is exactly "*", then the - node body is the contents of the entire file. Create and return such - a node. */ - if (strcmp (nodename, "*") == 0) - { - node = (NODE *)xmalloc (sizeof (NODE)); - node->filename = file_buffer->fullpath; - node->parent = (char *)NULL; - node->nodename = savestring ("*"); - node->contents = file_buffer->contents; - node->nodelen = file_buffer->filesize; - node->flags = 0; - } - - /* If this is the "main" info file, it might contain a tags table. Search - the tags table for an entry which matches the node that we want. If - there is a tags table, get the file which contains this node, but don't - bother building a node list for it. */ - else if (file_buffer->tags) - node = info_node_of_file_buffer_tags (file_buffer, nodename); - - /* Return the results of our node search. */ - return (node); -} - -/* Locate the file named by FILENAME, and return the information structure - describing this file. The file may appear in our list of loaded files - already, or it may not. If it does not already appear, find the file, - and add it to the list of loaded files. If the file cannot be found, - return a NULL FILE_BUFFER *. */ -FILE_BUFFER * -info_find_file (filename) - char *filename; -{ - return (info_find_file_internal (filename, INFO_GET_TAGS)); -} - -/* Load the info file FILENAME, remembering information about it in a - file buffer. */ -FILE_BUFFER * -info_load_file (filename) - char *filename; -{ - return (info_load_file_internal (filename, INFO_GET_TAGS)); -} - - -/* **************************************************************** */ -/* */ -/* Private Functions Implementation */ -/* */ -/* **************************************************************** */ - -/* The workhorse for info_find_file (). Non-zero 2nd argument says to - try to build a tags table (or otherwise glean the nodes) for this - file once found. By default, we build the tags table, but when this - function is called by info_get_node () when we already have a valid - tags table describing the nodes, it is unnecessary. */ -static FILE_BUFFER * -info_find_file_internal (filename, get_tags) - char *filename; - int get_tags; -{ - register int i; - register FILE_BUFFER *file_buffer; - - /* First try to find the file in our list of already loaded files. */ - if (info_loaded_files) - { - for (i = 0; file_buffer = info_loaded_files[i]; i++) - if ((strcmp (filename, file_buffer->filename) == 0) || - (strcmp (filename, file_buffer->fullpath) == 0) || - ((*filename != '/') && - strcmp (filename, - filename_non_directory (file_buffer->fullpath)) == 0)) - { - struct stat new_info, *old_info; - - /* This file is loaded. If the filename that we want is - specifically "dir", then simply return the file buffer. */ - if (stricmp (filename_non_directory (filename), "dir") == 0) - return (file_buffer); - - /* The file appears to be already loaded, and it is not "dir". - Check to see if it has changed since the last time it was - loaded. */ - if (stat (file_buffer->fullpath, &new_info) == -1) - { - filesys_error_number = errno; - return ((FILE_BUFFER *)NULL); - } - - old_info = &file_buffer->finfo; - - if ((new_info.st_size != old_info->st_size) || - (new_info.st_mtime != old_info->st_mtime)) - { - /* The file has changed. Forget that we ever had loaded it - in the first place. */ - forget_info_file (filename); - break; - } - else - { - /* The info file exists, and has not changed since the last - time it was loaded. If the caller requested a nodes list - for this file, and there isn't one here, build the nodes - for this file_buffer. In any case, return the file_buffer - object. */ - if (get_tags && !file_buffer->tags) - build_tags_and_nodes (file_buffer); - - return (file_buffer); - } - } - } - - /* The file wasn't loaded. Try to load it now. */ - file_buffer = info_load_file_internal (filename, get_tags); - - /* If the file was loaded, remember the name under which it was found. */ - if (file_buffer) - remember_info_file (file_buffer); - - return (file_buffer); -} - -/* The workhorse function for info_load_file (). Non-zero second argument - says to build a list of tags (or nodes) for this file. This is the - default behaviour when info_load_file () is called, but it is not - necessary when loading a subfile for which we already have tags. */ -static FILE_BUFFER * -info_load_file_internal (filename, get_tags) - char *filename; - int get_tags; -{ - char *fullpath, *contents; - long filesize; - struct stat finfo; - int retcode; - FILE_BUFFER *file_buffer = (FILE_BUFFER *)NULL; - - /* Get the full pathname of this file, as known by the info system. - That is to say, search along INFOPATH and expand tildes, etc. */ - fullpath = info_find_fullpath (filename); - - /* Did we actually find the file? */ - retcode = stat (fullpath, &finfo); - - /* If the file referenced by the name returned from info_find_fullpath () - doesn't exist, then try again with the last part of the filename - appearing in lowercase. */ - if (retcode < 0) - { - char *lowered_name; - char *basename; - - lowered_name = savestring (filename); - basename = (char *)rindex (lowered_name, '/'); - - if (basename) - basename++; - else - basename = lowered_name; - - while (*basename) - { - if (isupper (*basename)) - *basename = tolower (*basename); - - basename++; - } - - fullpath = info_find_fullpath (lowered_name); - free (lowered_name); - - retcode = stat (fullpath, &finfo); - } - - /* If the file wasn't found, give up, returning a NULL pointer. */ - if (retcode < 0) - { - filesys_error_number = errno; - return ((FILE_BUFFER *)NULL); - } - - /* Otherwise, try to load the file. */ - contents = filesys_read_info_file (fullpath, &filesize, &finfo); - - if (!contents) - return ((FILE_BUFFER *)NULL); - - /* The file was found, and can be read. Allocate FILE_BUFFER and fill - in the various members. */ - file_buffer = make_file_buffer (); - file_buffer->filename = savestring (filename); - file_buffer->fullpath = savestring (fullpath); - file_buffer->finfo = finfo; - file_buffer->filesize = filesize; - file_buffer->contents = contents; - if (file_buffer->filesize != file_buffer->finfo.st_size) - file_buffer->flags |= N_IsCompressed; - - /* If requested, build the tags and nodes for this file buffer. */ - if (get_tags) - build_tags_and_nodes (file_buffer); - - return (file_buffer); -} - -/* Grovel FILE_BUFFER->contents finding tags and nodes, and filling in the - various slots. This can also be used to rebuild a tag or node table. */ -void -build_tags_and_nodes (file_buffer) - FILE_BUFFER *file_buffer; -{ - SEARCH_BINDING binding; - long position; - - free_file_buffer_tags (file_buffer); - file_buffer->flags &= ~N_HasTagsTable; - - /* See if there is a tags table in this info file. */ - binding.buffer = file_buffer->contents; - binding.start = file_buffer->filesize; - binding.end = binding.start - 1000; - if (binding.end < 0) - binding.end = 0; - binding.flags = S_FoldCase; - - position = search_backward (TAGS_TABLE_END_LABEL, &binding); - - /* If there is a tag table, find the start of it, and grovel over it - extracting tag information. */ - if (position != -1) - while (1) - { - long tags_table_begin, tags_table_end; - - binding.end = position; - binding.start = binding.end - 5 - strlen (TAGS_TABLE_END_LABEL); - if (binding.start < 0) - binding.start = 0; - - position = find_node_separator (&binding); - - /* For this test, (and all others here) failure indicates a bogus - tags table. Grovel the file. */ - if (position == -1) - break; - - /* Remember the end of the tags table. */ - binding.start = position; - tags_table_end = binding.start; - binding.end = 0; - - /* Locate the start of the tags table. */ - position = search_backward (TAGS_TABLE_BEG_LABEL, &binding); - - if (position == -1) - break; - - binding.end = position; - binding.start = binding.end - 5 - strlen (TAGS_TABLE_BEG_LABEL); - position = find_node_separator (&binding); - - if (position == -1) - break; - - /* The file contains a valid tags table. Fill the FILE_BUFFER's - tags member. */ - file_buffer->flags |= N_HasTagsTable; - tags_table_begin = position; - - /* If this isn't an indirect tags table, just remember the nodes - described locally in this tags table. Note that binding.end - is pointing to just after the beginning label. */ - binding.start = binding.end; - binding.end = file_buffer->filesize; - - if (!looking_at (TAGS_TABLE_IS_INDIRECT_LABEL, &binding)) - { - binding.start = tags_table_begin; - binding.end = tags_table_end; - get_nodes_of_tags_table (file_buffer, &binding); - return; - } - else - { - /* This is an indirect tags table. Build TAGS member. */ - SEARCH_BINDING indirect; - - indirect.start = tags_table_begin; - indirect.end = 0; - indirect.buffer = binding.buffer; - indirect.flags = S_FoldCase; - - position = search_backward (INDIRECT_TAGS_TABLE_LABEL, &indirect); - - if (position == -1) - { - /* This file is malformed. Give up. */ - return; - } - - indirect.start = position; - indirect.end = tags_table_begin; - binding.start = tags_table_begin; - binding.end = tags_table_end; - get_tags_of_indirect_tags_table (file_buffer, &indirect, &binding); - return; - } - } - - /* This file doesn't contain any kind of tags table. Grovel the - file and build node entries for it. */ - get_nodes_of_info_file (file_buffer); -} - -/* Search through FILE_BUFFER->contents building an array of TAG *, - one entry per each node present in the file. Store the tags in - FILE_BUFFER->tags, and the number of allocated slots in - FILE_BUFFER->tags_slots. */ -static void -get_nodes_of_info_file (file_buffer) - FILE_BUFFER *file_buffer; -{ - long nodestart; - int tags_index = 0; - SEARCH_BINDING binding; - - binding.buffer = file_buffer->contents; - binding.start = 0; - binding.end = file_buffer->filesize; - binding.flags = S_FoldCase; - - while ((nodestart = find_node_separator (&binding)) != -1) - { - int start, end; - char *nodeline; - TAG *entry; - - /* Skip past the characters just found. */ - binding.start = nodestart; - binding.start += skip_node_separator (binding.buffer + binding.start); - - /* Move to the start of the line defining the node. */ - nodeline = binding.buffer + binding.start; - - /* Find "Node:" */ - start = string_in_line (INFO_NODE_LABEL, nodeline); - - /* If not there, this is not the start of a node. */ - if (start == -1) - continue; - - /* Find the start of the nodename. */ - start += skip_whitespace (nodeline + start); - - /* Find the end of the nodename. */ - end = start + - skip_node_characters (nodeline + start, DONT_SKIP_NEWLINES); - - /* Okay, we have isolated the node name, and we know where the - node starts. Remember this information in a NODE structure. */ - entry = (TAG *)xmalloc (sizeof (TAG)); - entry->nodename = (char *)xmalloc (1 + (end - start)); - strncpy (entry->nodename, nodeline + start, end - start); - entry->nodename[end - start] = '\0'; - entry->nodestart = nodestart; - { - SEARCH_BINDING node_body; - - node_body.buffer = binding.buffer + binding.start; - node_body.start = 0; - node_body.end = binding.end - binding.start; - node_body.flags = S_FoldCase; - entry->nodelen = get_node_length (&node_body); - } - - entry->filename = file_buffer->fullpath; - - /* Add this tag to the array of tag structures in this FILE_BUFFER. */ - add_pointer_to_array (entry, tags_index, file_buffer->tags, - file_buffer->tags_slots, 100, TAG *); - } -} - -/* Return the length of the node which starts at BINDING. */ -static long -get_node_length (binding) - SEARCH_BINDING *binding; -{ - register int i; - char *body; - - /* From the Info-RFC file: - [A node] ends with either a ^_, a ^L, or the end of file. */ - for (i = binding->start, body = binding->buffer; i < binding->end; i++) - { - if (body[i] == INFO_FF || body[i] == INFO_COOKIE) - break; - } - return ((long) i - binding->start); -} - -/* Build and save the array of nodes in FILE_BUFFER by searching through the - contents of BUFFER_BINDING for a tags table, and groveling the contents. */ -static void -get_nodes_of_tags_table (file_buffer, buffer_binding) - FILE_BUFFER *file_buffer; - SEARCH_BINDING *buffer_binding; -{ - int offset, tags_index = 0; - SEARCH_BINDING *search; - long position; - - search = copy_binding (buffer_binding); - - /* Find the start of the tags table. */ - position = find_tags_table (search); - - /* If none, we're all done. */ - if (position == -1) - return; - - /* Move to one character before the start of the actual table. */ - search->start = position; - search->start += skip_node_separator (search->buffer + search->start); - search->start += strlen (TAGS_TABLE_BEG_LABEL); - search->start--; - - /* The tag table consists of lines containing node names and positions. - Do each line until we find one that doesn't contain a node name. */ - while ((position = search_forward ("\n", search)) != -1) - { - TAG *entry; - char *nodedef; - - /* Prepare to skip this line. */ - search->start = position; - search->start++; - - /* Skip past informative "(Indirect)" tags table line. */ - if (!tags_index && looking_at (TAGS_TABLE_IS_INDIRECT_LABEL, search)) - continue; - - /* Find the label preceding the node name. */ - offset = - string_in_line (INFO_NODE_LABEL, search->buffer + search->start); - - /* If not there, not a defining line, so we must be out of the - tags table. */ - if (offset == -1) - break; - - /* Point to the beginning of the node definition. */ - search->start += offset; - nodedef = search->buffer + search->start; - nodedef += skip_whitespace (nodedef); - - /* Move past the node's name. */ - for (offset = 0; - (nodedef[offset]) && (nodedef[offset] != INFO_TAGSEP); - offset++); - - if (nodedef[offset] != INFO_TAGSEP) - continue; - - entry = (TAG *)xmalloc (sizeof (TAG)); - entry->nodename = (char *)xmalloc (1 + offset); - strncpy (entry->nodename, nodedef, offset); - entry->nodename[offset] = '\0'; - offset++; - entry->nodestart = (long) atol (nodedef + offset); - - /* We don't know the length of this node yet. */ - entry->nodelen = -1; - - /* The filename of this node is currently known as the same as the - name of this file. */ - entry->filename = file_buffer->fullpath; - - /* Add this node structure to the array of node structures in this - FILE_BUFFER. */ - add_pointer_to_array (entry, tags_index, file_buffer->tags, - file_buffer->tags_slots, 100, TAG *); - } - free (search); -} - -/* A structure used only in get_tags_of_indirect_tags_table () to hold onto - an intermediate value. */ -typedef struct { - char *filename; - long first_byte; -} SUBFILE; - -/* Remember in FILE_BUFFER the nodenames, subfilenames, and offsets within the - subfiles of every node which appears in TAGS_BINDING. The 2nd argument is - a binding surrounding the indirect files list. */ -static void -get_tags_of_indirect_tags_table (file_buffer, indirect_binding, tags_binding) - FILE_BUFFER *file_buffer; - SEARCH_BINDING *indirect_binding, *tags_binding; -{ - register int i; - SUBFILE **subfiles = (SUBFILE **)NULL; - int subfiles_index = 0, subfiles_slots = 0; - TAG *entry; - - /* First get the list of tags from the tags table. Then lookup the - associated file in the indirect list for each tag, and update it. */ - get_nodes_of_tags_table (file_buffer, tags_binding); - - /* We have the list of tags in file_buffer->tags. Get the list of - subfiles from the indirect table. */ - { - char *start, *end, *line; - SUBFILE *subfile; - - start = indirect_binding->buffer + indirect_binding->start; - end = indirect_binding->buffer + indirect_binding->end; - line = start; - - while (line < end) - { - int colon; - - colon = string_in_line (":", line); - - if (colon == -1) - break; - - subfile = (SUBFILE *)xmalloc (sizeof (SUBFILE)); - subfile->filename = (char *)xmalloc (colon); - strncpy (subfile->filename, line, colon - 1); - subfile->filename[colon - 1] = '\0'; - subfile->first_byte = (long) atol (line + colon); - - add_pointer_to_array - (subfile, subfiles_index, subfiles, subfiles_slots, 10, SUBFILE *); - - while (*line++ != '\n'); - } - } - - /* If we have successfully built the indirect files table, then - merge the information in the two tables. */ - if (!subfiles) - { - free_file_buffer_tags (file_buffer); - return; - } - else - { - register int tags_index; - long header_length; - SEARCH_BINDING binding; - - /* Find the length of the header of the file containing the indirect - tags table. This header appears at the start of every file. We - want the absolute position of each node within each subfile, so - we subtract the start of the containing subfile from the logical - position of the node, and then add the length of the header in. */ - binding.buffer = file_buffer->contents; - binding.start = 0; - binding.end = file_buffer->filesize; - binding.flags = S_FoldCase; - - header_length = find_node_separator (&binding); - if (header_length == -1) - header_length = 0; - - /* Build the file buffer's list of subfiles. */ - { - char *containing_dir, *temp; - int len_containing_dir; - - containing_dir = savestring (file_buffer->fullpath); - temp = (char *)rindex (containing_dir, '/'); - - if (temp) - *temp = '\0'; - - len_containing_dir = strlen (containing_dir); - - for (i = 0; subfiles[i]; i++); - - file_buffer->subfiles = (char **) xmalloc ((1 + i) * sizeof (char *)); - - for (i = 0; subfiles[i]; i++) - { - char *fullpath; - - fullpath = (char *) xmalloc - (2 + strlen (subfiles[i]->filename) + len_containing_dir); - - sprintf (fullpath, "%s/%s", - containing_dir, subfiles[i]->filename); - - file_buffer->subfiles[i] = fullpath; - } - file_buffer->subfiles[i] = (char *)NULL; - free (containing_dir); - } - - /* For each node in the file's tags table, remember the starting - position. */ - for (tags_index = 0; - entry = file_buffer->tags[tags_index]; - tags_index++) - { - for (i = 0; - subfiles[i] && entry->nodestart >= subfiles[i]->first_byte; - i++); - - /* If the Info file containing the indirect tags table is - malformed, then give up. */ - if (!i) - { - /* The Info file containing the indirect tags table is - malformed. Give up. */ - for (i = 0; subfiles[i]; i++) - { - free (subfiles[i]->filename); - free (subfiles[i]); - free (file_buffer->subfiles[i]); - } - file_buffer->subfiles = (char **)NULL; - free_file_buffer_tags (file_buffer); - return; - } - - /* SUBFILES[i] is the index of the first subfile whose logical - first byte is greater than the logical offset of this node's - starting position. This means that the subfile directly - preceding this one is the one containing the node. */ - - entry->filename = file_buffer->subfiles[i - 1]; - entry->nodestart -= subfiles[i -1]->first_byte; - entry->nodestart += header_length; - entry->nodelen = -1; - } - - /* We have successfully built the tags table. Remember that it - was indirect. */ - file_buffer->flags |= N_TagsIndirect; - } - - /* Free the structures assigned to SUBFILES. Free the names as well - as the structures themselves, then finally, the array. */ - for (i = 0; subfiles[i]; i++) - { - free (subfiles[i]->filename); - free (subfiles[i]); - } - free (subfiles); -} - -/* Return the node from FILE_BUFFER which matches NODENAME by searching - the tags table in FILE_BUFFER. If the node could not be found, return - a NULL pointer. */ -static NODE * -info_node_of_file_buffer_tags (file_buffer, nodename) - FILE_BUFFER *file_buffer; - char *nodename; -{ - register int i; - TAG *tag; - - for (i = 0; tag = file_buffer->tags[i]; i++) - if (strcmp (nodename, tag->nodename) == 0) - { - FILE_BUFFER *subfile; - - subfile = info_find_file_internal (tag->filename, INFO_NO_TAGS); - - if (!subfile) - return ((NODE *)NULL); - - if (!subfile->contents) - info_reload_file_buffer_contents (subfile); - - if (!subfile->contents) - return ((NODE *)NULL); - - /* If we were able to find this file and load it, then return - the node within it. */ - { - NODE *node; - - node = (NODE *)xmalloc (sizeof (NODE)); - node->filename = (subfile->fullpath); - node->nodename = tag->nodename; - node->contents = subfile->contents + tag->nodestart; - node->flags = 0; - node->parent = (char *)NULL; - - if (file_buffer->flags & N_HasTagsTable) - { - node->flags |= N_HasTagsTable; - - if (file_buffer->flags & N_TagsIndirect) - { - node->flags |= N_TagsIndirect; - node->parent = file_buffer->fullpath; - } - } - - if (subfile->flags & N_IsCompressed) - node->flags |= N_IsCompressed; - - /* If TAG->nodelen hasn't been calculated yet, then we aren't - in a position to trust the entry pointer. Adjust things so - that ENTRY->nodestart gets the exact address of the start of - the node separator which starts this node, and NODE->contents - gets the address of the line defining this node. If we cannot - do that, the node isn't really here. */ - if (tag->nodelen == -1) - { - int min, max; - char *node_sep; - SEARCH_BINDING node_body; - char *buff_end; - - min = max = DEFAULT_INFO_FUDGE; - - if (tag->nodestart < DEFAULT_INFO_FUDGE) - min = tag->nodestart; - - if (DEFAULT_INFO_FUDGE > - (subfile->filesize - tag->nodestart)) - max = subfile->filesize - tag->nodestart; - - /* NODE_SEP gets the address of the separator which defines - this node, or (char *)NULL if the node wasn't found. - NODE->contents is side-effected to point to right after - the separator. */ - node_sep = adjust_nodestart (node, min, max); - if (node_sep == (char *)NULL) - { - free (node); - return ((NODE *)NULL); - } - /* Readjust tag->nodestart. */ - tag->nodestart = node_sep - subfile->contents; - - /* Calculate the length of the current node. */ - buff_end = subfile->contents + subfile->filesize; - - node_body.buffer = node->contents; - node_body.start = 0; - node_body.end = buff_end - node_body.buffer; - node_body.flags = 0; - tag->nodelen = get_node_length (&node_body); - } - else - { - /* Since we know the length of this node, we have already - adjusted tag->nodestart to point to the exact start of - it. Simply skip the node separator. */ - node->contents += skip_node_separator (node->contents); - } - - node->nodelen = tag->nodelen; - return (node); - } - } - - /* There was a tag table for this file, and the node wasn't found. - Return NULL, since this file doesn't contain the desired node. */ - return ((NODE *)NULL); -} - -/* **************************************************************** */ -/* */ -/* Managing file_buffers, nodes, and tags. */ -/* */ -/* **************************************************************** */ - -static FILE_BUFFER * -make_file_buffer () -{ - FILE_BUFFER *file_buffer; - - file_buffer = (FILE_BUFFER *)xmalloc (sizeof (FILE_BUFFER)); - file_buffer->filename = file_buffer->fullpath = (char *)NULL; - file_buffer->contents = (char *)NULL; - file_buffer->tags = (TAG **)NULL; - file_buffer->subfiles = (char **)NULL; - file_buffer->tags_slots = 0; - file_buffer->flags = 0; - - return (file_buffer); -} - -/* Add FILE_BUFFER to our list of already loaded info files. */ -static void -remember_info_file (file_buffer) - FILE_BUFFER *file_buffer; -{ - int i; - - for (i = 0; info_loaded_files && info_loaded_files[i]; i++) - ; - - add_pointer_to_array (file_buffer, i, info_loaded_files, - info_loaded_files_slots, 10, FILE_BUFFER *); -} - -/* Forget the contents, tags table, nodes list, and names of FILENAME. */ -static void -forget_info_file (filename) - char *filename; -{ - register int i; - FILE_BUFFER *file_buffer; - - if (!info_loaded_files) - return; - - for (i = 0; file_buffer = info_loaded_files[i]; i++) - if ((strcmp (filename, file_buffer->filename) == 0) || - (strcmp (filename, file_buffer->fullpath) == 0)) - { - free (file_buffer->filename); - free (file_buffer->fullpath); - - if (file_buffer->contents) - free (file_buffer->contents); - - /* Note that free_file_buffer_tags () also kills the subfiles - list, since the subfiles list is only of use in conjunction - with tags. */ - free_file_buffer_tags (file_buffer); - - while (info_loaded_files[i] = info_loaded_files[++i]) - ; - - break; - } -} - -/* Free the tags (if any) associated with FILE_BUFFER. */ -static void -free_file_buffer_tags (file_buffer) - FILE_BUFFER *file_buffer; -{ - register int i; - - if (file_buffer->tags) - { - register TAG *tag; - - for (i = 0; tag = file_buffer->tags[i]; i++) - free_info_tag (tag); - - free (file_buffer->tags); - file_buffer->tags = (TAG **)NULL; - file_buffer->tags_slots = 0; - } - - if (file_buffer->subfiles) - { - for (i = 0; file_buffer->subfiles[i]; i++) - free (file_buffer->subfiles[i]); - - free (file_buffer->subfiles); - file_buffer->subfiles = (char **)NULL; - } -} - -/* Free the data associated with TAG, as well as TAG itself. */ -static void -free_info_tag (tag) - TAG *tag; -{ - free (tag->nodename); - - /* We don't free tag->filename, because that filename is part of the - subfiles list for the containing FILE_BUFFER. free_info_tags () - will free the subfiles when it is appropriate. */ - - free (tag); -} - -/* Load the contents of FILE_BUFFER->contents. This function is called - when a file buffer was loaded, and then in order to conserve memory, the - file buffer's contents were freed and the pointer was zero'ed. Note that - the file was already loaded at least once successfully, so the tags and/or - nodes members are still correctly filled. */ -static void -info_reload_file_buffer_contents (fb) - FILE_BUFFER *fb; -{ - fb->flags &= ~N_IsCompressed; - - /* Let the filesystem do all the work for us. */ - fb->contents = - filesys_read_info_file (fb->fullpath, &(fb->filesize), &(fb->finfo)); - if (fb->filesize != fb->finfo.st_size) - fb->flags |= N_IsCompressed; -} - -/* Return the actual starting memory location of NODE, side-effecting - NODE->contents. MIN and MAX are bounds for a search if one is necessary. - Because of the way that tags are implemented, the physical nodestart may - not actually be where the tag says it is. If that is the case, but the - node was found anyway, set N_UpdateTags in NODE->flags. If the node is - found, return non-zero. NODE->contents is returned positioned right after - the node separator that precedes this node, while the return value is - position directly on the separator that precedes this node. If the node - could not be found, return a NULL pointer. */ -static char * -adjust_nodestart (node, min, max) - NODE *node; - int min, max; -{ - long position; - SEARCH_BINDING node_body; - - /* Define the node body. */ - node_body.buffer = node->contents; - node_body.start = 0; - node_body.end = max; - node_body.flags = 0; - - /* Try the optimal case first. Who knows? This file may actually be - formatted (mostly) correctly. */ - if (node_body.buffer[0] != INFO_COOKIE && min > 2) - node_body.buffer -= 3; - - position = find_node_separator (&node_body); - - /* If we found a node start, then check it out. */ - if (position != -1) - { - int sep_len; - - sep_len = skip_node_separator (node->contents); - - /* If we managed to skip a node separator, then check for this node - being the right one. */ - if (sep_len != 0) - { - char *nodedef, *nodestart; - int offset; - - nodestart = node_body.buffer + position + sep_len; - nodedef = nodestart; - offset = string_in_line (INFO_NODE_LABEL, nodedef); - - if (offset != -1) - { - nodedef += offset; - nodedef += skip_whitespace (nodedef); - offset = skip_node_characters (nodedef, DONT_SKIP_NEWLINES); - if ((offset == strlen (node->nodename)) && - (strncmp (node->nodename, nodedef, offset) == 0)) - { - node->contents = nodestart; - return (node_body.buffer + position); - } - } - } - } - - /* Oh well, I guess we have to try to find it in a larger area. */ - node_body.buffer = node->contents - min; - node_body.start = 0; - node_body.end = min + max; - node_body.flags = 0; - - position = find_node_in_binding (node->nodename, &node_body); - - /* If the node couldn't be found, we lose big. */ - if (position == -1) - return ((char *)NULL); - - /* Otherwise, the node was found, but the tags table could need updating - (if we used a tag to get here, that is). Set the flag in NODE->flags. */ - node->contents = node_body.buffer + position; - node->contents += skip_node_separator (node->contents); - if (node->flags & N_HasTagsTable) - node->flags |= N_UpdateTags; - return (node_body.buffer + position); -} diff --git a/gnu/usr.bin/texinfo/info/nodes.h b/gnu/usr.bin/texinfo/info/nodes.h deleted file mode 100644 index 1b8cee3..0000000 --- a/gnu/usr.bin/texinfo/info/nodes.h +++ /dev/null @@ -1,164 +0,0 @@ -/* nodes.h -- How we represent nodes internally. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#ifndef _NODES_H_ -#define _NODES_H_ - -#include "general.h" - -/* **************************************************************** */ -/* */ -/* User Code Interface */ -/* */ -/* **************************************************************** */ - -/* Callers generally only want the node itself. This structure is used - to pass node information around. None of the information in this - structure should ever be directly freed. The structure itself can - be passed to free (). Note that NODE->parent is non-null if this - node's file is a subfile. In that case, NODE->parent is the logical - name of the file containing this node. Both names are given as full - paths, so you might have: node->filename = "/usr/gnu/info/emacs-1", - with node->parent = "/usr/gnu/info/emacs". */ -typedef struct { - char *filename; /* The physical file containing this node. */ - char *parent; /* Non-null is the logical file name. */ - char *nodename; /* The name of this node. */ - char *contents; /* Characters appearing in this node. */ - long nodelen; /* The length of the CONTENTS member. */ - int flags; /* See immediately below. */ -} NODE; - -/* Defines that can appear in NODE->flags. All informative. */ -#define N_HasTagsTable 0x01 /* This node was found through a tags table. */ -#define N_TagsIndirect 0x02 /* The tags table was an indirect one. */ -#define N_UpdateTags 0x04 /* The tags table is out of date. */ -#define N_IsCompressed 0x08 /* The file is compressed on disk. */ -#define N_IsInternal 0x10 /* This node was made by Info. */ -#define N_CannotGC 0x20 /* File buffer cannot be gc'ed. */ - -/* **************************************************************** */ -/* */ -/* Internal Data Structures */ -/* */ -/* **************************************************************** */ - -/* Some defines describing details about Info file contents. */ - -/* String Constants. */ -#define INFO_FILE_LABEL "File:" -#define INFO_NODE_LABEL "Node:" -#define INFO_PREV_LABEL "Prev:" -#define INFO_ALTPREV_LABEL "Previous:" -#define INFO_NEXT_LABEL "Next:" -#define INFO_UP_LABEL "Up:" -#define INFO_MENU_LABEL "\n* Menu:" -#define INFO_MENU_ENTRY_LABEL "\n* " -#define INFO_XREF_LABEL "*Note" -#define TAGS_TABLE_END_LABEL "\nEnd Tag Table" -#define TAGS_TABLE_BEG_LABEL "Tag Table:\n" -#define INDIRECT_TAGS_TABLE_LABEL "Indirect:\n" -#define TAGS_TABLE_IS_INDIRECT_LABEL "(Indirect)" - -/* Character Constants. */ -#define INFO_COOKIE '\037' -#define INFO_FF '\014' -#define INFO_TAGSEP '\177' - -/* For each logical file that we have loaded, we keep a list of the names - of the nodes that are found in that file. A pointer to a node in an - info file is called a "tag". For split files, the tag pointer is - "indirect"; that is, the pointer also contains the name of the split - file where the node can be found. For non-split files, the filename - member in the structure below simply contains the name of the current - file. The following structure describes a single node within a file. */ -typedef struct { - char *filename; /* The file where this node can be found. */ - char *nodename; /* The node pointed to by this tag. */ - long nodestart; /* The offset of the start of this node. */ - long nodelen; /* The length of this node. */ -} TAG; - -/* The following structure is used to remember information about the contents - of Info files that we have loaded at least once before. The FINFO member - is present so that we can reload the file if it has been modified since - last being loaded. All of the arrays appearing within this structure - are NULL terminated, and each array which can change size has a - corresponding SLOTS member which says how many slots have been allocated - (with malloc ()) for this array. */ -typedef struct { - char *filename; /* The filename used to find this file. */ - char *fullpath; /* The full pathname of this info file. */ - struct stat finfo; /* Information about this file. */ - char *contents; /* The contents of this particular file. */ - long filesize; /* The number of bytes this file expands to. */ - char **subfiles; /* If non-null, the list of subfiles. */ - TAG **tags; /* If non-null, the indirect tags table. */ - int tags_slots; /* Number of slots allocated for TAGS. */ - int flags; /* Various flags. Mimics of N_* flags. */ -} FILE_BUFFER; - -/* **************************************************************** */ -/* */ -/* Externally Visible Functions */ -/* */ -/* **************************************************************** */ - -/* Array of FILE_BUFFER * which represents the currently loaded info files. */ -extern FILE_BUFFER **info_loaded_files; - -/* The number of slots currently allocated to INFO_LOADED_FILES. */ -extern int info_loaded_files_slots; - -/* Locate the file named by FILENAME, and return the information structure - describing this file. The file may appear in our list of loaded files - already, or it may not. If it does not already appear, find the file, - and add it to the list of loaded files. If the file cannot be found, - return a NULL FILE_BUFFER *. */ -extern FILE_BUFFER *info_find_file (); - -/* Force load the file named FILENAME, and return the information structure - describing this file. Even if the file was already loaded, this loads - a new buffer, rebuilds tags and nodes, and returns a new FILE_BUFFER *. */ -extern FILE_BUFFER *info_load_file (); - -/* Return a pointer to a NODE structure for the Info node (FILENAME)NODENAME. - FILENAME can be passed as NULL, in which case the filename of "dir" is used. - NODENAME can be passed as NULL, in which case the nodename of "Top" is used. - If the node cannot be found, return a NULL pointer. */ -extern NODE *info_get_node (); - -/* Return a pointer to a NODE structure for the Info node NODENAME in - FILE_BUFFER. NODENAME can be passed as NULL, in which case the - nodename of "Top" is used. If the node cannot be found, return a - NULL pointer. */ -extern NODE *info_get_node_of_file_buffer (); - -/* Grovel FILE_BUFFER->contents finding tags and nodes, and filling in the - various slots. This can also be used to rebuild a tag or node table. */ -extern void build_tags_and_nodes (); - -/* When non-zero, this is a string describing the most recent file error. */ -extern char *info_recent_file_error; - -#endif /* !_NODES_H_ */ diff --git a/gnu/usr.bin/texinfo/info/search.c b/gnu/usr.bin/texinfo/info/search.c deleted file mode 100644 index d214f9d..0000000 --- a/gnu/usr.bin/texinfo/info/search.c +++ /dev/null @@ -1,566 +0,0 @@ -/* search.c -- How to search large bodies of text. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include <ctype.h> -#include <sys/types.h> -#include <sys/stat.h> -#include "general.h" -#include "search.h" -#include "nodes.h" - -#if !defined (NULL) -# define NULL 0x0 -#endif /* !NULL */ - -/* The search functions take two arguments: - - 1) a string to search for, and - - 2) a pointer to a SEARCH_BINDING which contains the buffer, start, - and end of the search. - - They return a long, which is the offset from the start of the buffer - at which the match was found. An offset of -1 indicates failure. */ - -/* A function which makes a binding with buffer and bounds. */ -SEARCH_BINDING * -make_binding (buffer, start, end) - char *buffer; - long start, end; -{ - SEARCH_BINDING *binding; - - binding = (SEARCH_BINDING *)xmalloc (sizeof (SEARCH_BINDING)); - binding->buffer = buffer; - binding->start = start; - binding->end = end; - binding->flags = 0; - - return (binding); -} - -/* Make a copy of BINDING without duplicating the data. */ -SEARCH_BINDING * -copy_binding (binding) - SEARCH_BINDING *binding; -{ - SEARCH_BINDING *copy; - - copy = make_binding (binding->buffer, binding->start, binding->end); - copy->flags = binding->flags; - return (copy); -} - - -/* **************************************************************** */ -/* */ -/* The Actual Searching Functions */ -/* */ -/* **************************************************************** */ - -/* Search forwards or backwards for the text delimited by BINDING. - The search is forwards if BINDING->start is greater than BINDING->end. */ -long -search (string, binding) - char *string; - SEARCH_BINDING *binding; -{ - long result; - - /* If the search is backwards, then search backwards, otherwise forwards. */ - if (binding->start > binding->end) - result = search_backward (string, binding); - else - result = search_forward (string, binding); - - return (result); -} - -/* Search forwards for STRING through the text delimited in BINDING. */ -long -search_forward (string, binding) - char *string; - SEARCH_BINDING *binding; -{ - register int c, i, len; - register char *buff, *end; - char *alternate = (char *)NULL; - - len = strlen (string); - - /* We match characters in the search buffer against STRING and ALTERNATE. - ALTERNATE is a case reversed version of STRING; this is cheaper than - case folding each character before comparison. Alternate is only - used if the case folding bit is turned on in the passed BINDING. */ - - if (binding->flags & S_FoldCase) - { - alternate = savestring (string); - - for (i = 0; i < len; i++) - { - if (islower (alternate[i])) - alternate[i] = toupper (alternate[i]); - else if (isupper (alternate[i])) - alternate[i] = tolower (alternate[i]); - } - } - - buff = binding->buffer + binding->start; - end = binding->buffer + binding->end + 1; - - while (buff < (end - len)) - { - for (i = 0; i < len; i++) - { - c = buff[i]; - - if ((c != string[i]) && (!alternate || c != alternate[i])) - break; - } - - if (!string[i]) - { - if (alternate) - free (alternate); - if (binding->flags & S_SkipDest) - buff += len; - return ((long) (buff - binding->buffer)); - } - - buff++; - } - - if (alternate) - free (alternate); - - return ((long) -1); -} - -/* Search for STRING backwards through the text delimited in BINDING. */ -long -search_backward (input_string, binding) - char *input_string; - SEARCH_BINDING *binding; -{ - register int c, i, len; - register char *buff, *end; - char *string; - char *alternate = (char *)NULL; - - len = strlen (input_string); - - /* Reverse the characters in the search string. */ - string = (char *)xmalloc (1 + len); - for (c = 0, i = len - 1; input_string[c]; c++, i--) - string[i] = input_string[c]; - - string[c] = '\0'; - - /* We match characters in the search buffer against STRING and ALTERNATE. - ALTERNATE is a case reversed version of STRING; this is cheaper than - case folding each character before comparison. ALTERNATE is only - used if the case folding bit is turned on in the passed BINDING. */ - - if (binding->flags & S_FoldCase) - { - alternate = savestring (string); - - for (i = 0; i < len; i++) - { - if (islower (alternate[i])) - alternate[i] = toupper (alternate[i]); - else if (isupper (alternate[i])) - alternate[i] = tolower (alternate[i]); - } - } - - buff = binding->buffer + binding->start; - end = binding->buffer + binding->end; - - while (buff > end + len) - { - for (i = 0; i < len; i++) - { - c = *(buff - i); - - if (c != string[i] && (alternate && c != alternate[i])) - break; - } - - if (!string[i]) - { - free (string); - if (alternate) - free (alternate); - - if (binding->flags & S_SkipDest) - buff -= len; - return ((long) (1 + (buff - binding->buffer))); - } - - buff--; - } - - free (string); - if (alternate) - free (alternate); - - return ((long) -1); -} - -/* Find STRING in LINE, returning the offset of the end of the string. - Return an offset of -1 if STRING does not appear in LINE. The search - is bound by the end of the line (i.e., either NEWLINE or 0). */ -int -string_in_line (string, line) - char *string, *line; -{ - register int end; - SEARCH_BINDING binding; - - /* Find the end of the line. */ - for (end = 0; line[end] && line[end] != '\n'; end++); - - /* Search for STRING within these confines. */ - binding.buffer = line; - binding.start = 0; - binding.end = end; - binding.flags = S_FoldCase | S_SkipDest; - - return (search_forward (string, &binding)); -} - -/* Return non-zero if STRING is the first text to appear at BINDING. */ -int -looking_at (string, binding) - char *string; - SEARCH_BINDING *binding; -{ - long search_end; - - search_end = search (string, binding); - - /* If the string was not found, SEARCH_END is -1. If the string was found, - but not right away, SEARCH_END is != binding->start. Otherwise, the - string was found at binding->start. */ - return (search_end == binding->start); -} - -/* **************************************************************** */ -/* */ -/* Small String Searches */ -/* */ -/* **************************************************************** */ - -/* Function names that start with "skip" are passed a string, and return - an offset from the start of that string. Function names that start - with "find" are passed a SEARCH_BINDING, and return an absolute position - marker of the item being searched for. "Find" functions return a value - of -1 if the item being looked for couldn't be found. */ - -/* Return the index of the first non-whitespace character in STRING. */ -int -skip_whitespace (string) - char *string; -{ - register int i; - - for (i = 0; string && whitespace (string[i]); i++); - return (i); -} - -/* Return the index of the first non-whitespace or newline character in - STRING. */ -int -skip_whitespace_and_newlines (string) - char *string; -{ - register int i; - - for (i = 0; string && (whitespace (string[i]) || string[i] == '\n'); i++); - return (i); -} - -/* Return the index of the first whitespace character in STRING. */ -int -skip_non_whitespace (string) - char *string; -{ - register int i; - - for (i = 0; string && !whitespace (string[i]); i++); - return (i); -} - -/* Return the index of the first non-node character in STRING. Note that - this function contains quite a bit of hair to ignore periods in some - special cases. This is because we here at GNU ship some info files which - contain nodenames that contain periods. No such nodename can start with - a period, or continue with whitespace, newline, or ')' immediately following - the period. If second argument NEWLINES_OKAY is non-zero, newlines should - be skipped while parsing out the nodename specification. */ -int -skip_node_characters (string, newlines_okay) - char *string; - int newlines_okay; -{ - register int c, i = 0; - int paren_seen = 0; - int paren = 0; - - /* Handle special case. This is when another function has parsed out the - filename component of the node name, and we just want to parse out the - nodename proper. In that case, a period at the start of the nodename - indicates an empty nodename. */ - if (string && *string == '.') - return (0); - - if (string && *string == '(') - { - paren++; - paren_seen++; - i++; - } - - for (; string && (c = string[i]); i++) - { - if (paren) - { - if (c == '(') - paren++; - else if (c == ')') - paren--; - - continue; - } - - /* If the character following the close paren is a space or period, - then this node name has no more characters associated with it. */ - if (c == '\t' || - c == ',' || - c == INFO_TAGSEP || - ((!newlines_okay) && (c == '\n')) || - ((paren_seen && string[i - 1] == ')') && - (c == ' ' || c == '.')) || - (c == '.' && - ((!string[i + 1]) || - (whitespace_or_newline (string[i + 1])) || - (string[i + 1] == ')')))) - break; - } - return (i); -} - -/* Unix doesn't have stricmp () functions. */ -int -stricmp (string1, string2) - char *string1, *string2; -{ - char ch1, ch2; - - for (;;) - { - ch1 = *string1++; - ch2 = *string2++; - - if (!(ch1 | ch2)) - return (0); - - ch1 = info_toupper (ch1); - ch2 = info_toupper (ch2); - - if (ch1 != ch2) - return (ch1 - ch2); - } -} - -/* Compare at most COUNT characters from string1 to string2. Case - doesn't matter. */ -int -strnicmp (string1, string2, count) - char *string1, *string2; - int count; -{ - register char ch1, ch2; - - while (count) - { - ch1 = *string1++; - ch2 = *string2++; - - ch1 = info_toupper (ch1); - ch2 = info_toupper (ch2); - - if (ch1 == ch2) - count--; - else - break; - } - return (count); -} - -/* **************************************************************** */ -/* */ -/* Searching FILE_BUFFER's */ -/* */ -/* **************************************************************** */ - -/* Return the absolute position of the first occurence of a node separator in - BINDING-buffer. The search starts at BINDING->start. Return -1 if no node - separator was found. */ -long -find_node_separator (binding) - SEARCH_BINDING *binding; -{ - register long i; - char *body; - - body = binding->buffer; - - /* A node is started by [^L]^_[^L]\n. That is to say, the C-l's are - optional, but the DELETE and NEWLINE are not. This separator holds - true for all separated elements in an Info file, including the tags - table (if present) and the indirect tags table (if present). */ - for (i = binding->start; i < binding->end - 1; i++) - if (((body[i] == INFO_FF && body[i + 1] == INFO_COOKIE) && - (body[i + 2] == '\n' || - (body[i + 2] == INFO_FF && body[i + 3] == '\n'))) || - ((body[i] == INFO_COOKIE) && - (body[i + 1] == '\n' || - (body[i + 1] == INFO_FF && body[i + 2] == '\n')))) - return (i); - return (-1); -} - -/* Return the length of the node separator characters that BODY is - currently pointing at. */ -int -skip_node_separator (body) - char *body; -{ - register int i; - - i = 0; - - if (body[i] == INFO_FF) - i++; - - if (body[i++] != INFO_COOKIE) - return (0); - - if (body[i] == INFO_FF) - i++; - - if (body[i++] != '\n') - return (0); - - return (i); -} - -/* Return the number of characters from STRING to the start of - the next line. */ -int -skip_line (string) - char *string; -{ - register int i; - - for (i = 0; string && string[i] && string[i] != '\n'; i++); - - if (string[i] == '\n') - i++; - - return (i); -} - -/* Return the absolute position of the beginning of a tags table in this - binding starting the search at binding->start. */ -long -find_tags_table (binding) - SEARCH_BINDING *binding; -{ - SEARCH_BINDING search; - long position; - - search.buffer = binding->buffer; - search.start = binding->start; - search.end = binding->end; - search.flags = S_FoldCase; - - while ((position = find_node_separator (&search)) != -1 ) - { - search.start = position; - search.start += skip_node_separator (search.buffer + search.start); - - if (looking_at (TAGS_TABLE_BEG_LABEL, &search)) - return (position); - } - return (-1); -} - -/* Return the absolute position of the node named NODENAME in BINDING. - This is a brute force search, and we wish to avoid it when possible. - This function is called when a tag (indirect or otherwise) doesn't - really point to the right node. It returns the absolute position of - the separator preceding the node. */ -long -find_node_in_binding (nodename, binding) - char *nodename; - SEARCH_BINDING *binding; -{ - register long position; - register int offset, namelen; - SEARCH_BINDING search; - - namelen = strlen (nodename); - - search.buffer = binding->buffer; - search.start = binding->start; - search.end = binding->end; - search.flags = 0; - - while ((position = find_node_separator (&search)) != -1) - { - search.start = position; - search.start += skip_node_separator (search.buffer + search.start); - - offset = string_in_line (INFO_NODE_LABEL, search.buffer + search.start); - - if (offset == -1) - continue; - - search.start += offset; - search.start += skip_whitespace (search.buffer + search.start); - offset = skip_node_characters - (search.buffer + search.start, DONT_SKIP_NEWLINES); - - /* Notice that this is an exact match. You cannot grovel through - the buffer with this function looking for random nodes. */ - if ((offset == namelen) && - (search.buffer[search.start] == nodename[0]) && - (strncmp (search.buffer + search.start, nodename, offset) == 0)) - return (position); - } - return (-1); -} diff --git a/gnu/usr.bin/texinfo/info/search.h b/gnu/usr.bin/texinfo/info/search.h deleted file mode 100644 index cc1cada..0000000 --- a/gnu/usr.bin/texinfo/info/search.h +++ /dev/null @@ -1,78 +0,0 @@ -/* search.h -- Structure used to search large bodies of text, with bounds. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -/* The search functions take two arguments: - - 1) a string to search for, and - - 2) a pointer to a SEARCH_BINDING which contains the buffer, start, - and end of the search. - - They return a long, which is the offset from the start of the buffer - at which the match was found. An offset of -1 indicates failure. */ - -#ifndef _SEARCH_H_ -#define _SEARCH_H_ - -typedef struct { - char *buffer; /* The buffer of text to search. */ - long start; /* Offset of the start of the search. */ - long end; /* Offset of the end of the searh. */ - int flags; /* Flags controlling the type of search. */ -} SEARCH_BINDING; - -#define S_FoldCase 0x01 /* Set means fold case in searches. */ -#define S_SkipDest 0x02 /* Set means return pointing after the dest. */ - -SEARCH_BINDING *make_binding (), *copy_binding (); -extern long search_forward (), search_backward (), search (); -extern int looking_at (); - -/* Note that STRING_IN_LINE () always returns the offset of the 1st character - after the string. */ -extern int string_in_line (); - -/* Unix doesn't have stricmp () functions. */ -/* strcmp (), but caseless. */ -extern int stricmp (); - -/* Compare at most COUNT characters from STRING1 to STRING2. Case - doesn't matter. */ -extern int strnicmp (); - -/* Function names that start with "skip" are passed a string, and return - an offset from the start of that string. Function names that start - with "find" are passed a SEARCH_BINDING, and return an absolute position - marker of the item being searched for. "Find" functions return a value - of -1 if the item being looked for couldn't be found. */ -extern int skip_whitespace (), skip_non_whitespace (); -extern int skip_whitespace_and_newlines (), skip_line (); -extern int skip_node_characters (), skip_node_separator (); -#define DONT_SKIP_NEWLINES 0 -#define SKIP_NEWLINES 1 - -extern long find_node_separator (), find_tags_table (); -extern long find_node_in_binding (); - -#endif /* !_SEARCH_H_ */ - diff --git a/gnu/usr.bin/texinfo/info/session.c b/gnu/usr.bin/texinfo/info/session.c deleted file mode 100644 index b1e4297..0000000 --- a/gnu/usr.bin/texinfo/info/session.c +++ /dev/null @@ -1,4168 +0,0 @@ -/* session.c -- The user windowing interface to Info. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include "info.h" -#include <sys/file.h> -#include <sys/ioctl.h> -#include <fcntl.h> -#include <stdlib.h> - -#if defined (HAVE_SYS_TIME_H) -# include <sys/time.h> -# define HAVE_STRUCT_TIMEVAL -#endif /* HAVE_SYS_TIME_H */ - -static void info_clear_pending_input (), info_set_pending_input (); -static void info_handle_pointer (); - -/* **************************************************************** */ -/* */ -/* Running an Info Session */ -/* */ -/* **************************************************************** */ - -/* The place that we are reading input from. */ -static FILE *info_input_stream = (FILE *)NULL; - -/* The last executed command. */ -VFunction *info_last_executed_command = (VFunction *)NULL; - -/* Becomes non-zero when 'q' is typed to an Info window. */ -int quit_info_immediately = 0; - -/* Array of structures describing for each window which nodes have been - visited in that window. */ -INFO_WINDOW **info_windows = (INFO_WINDOW **)NULL; - -/* Where to add the next window, if we need to add one. */ -static int info_windows_index = 0; - -/* Number of slots allocated to INFO_WINDOWS. */ -static int info_windows_slots = 0; - -void remember_window_and_node (), forget_window_and_nodes (); -void initialize_info_session (), info_session (); -void display_startup_message_and_start (); - -/* Begin an info session finding the nodes specified by FILENAME and NODENAMES. - For each loaded node, create a new window. Always split the largest of the - available windows. */ -void -begin_multiple_window_info_session (filename, nodenames) - char *filename; - char **nodenames; -{ - register int i; - WINDOW *window = (WINDOW *)NULL; - - for (i = 0; nodenames[i]; i++) - { - NODE *node; - - node = info_get_node (filename, nodenames[i]); - - if (!node) - break; - - /* If this is the first node, initialize the info session. */ - if (!window) - { - initialize_info_session (node); - window = active_window; - } - else - { - /* Find the largest window in WINDOWS, and make that be the active - one. Then split it and add our window and node to the list - of remembered windows and nodes. Then tile the windows. */ - register WINDOW *win, *largest = (WINDOW *)NULL; - int max_height = 0; - - for (win = windows; win; win = win->next) - if (win->height > max_height) - { - max_height = win->height; - largest = win; - } - - if (!largest) - { - display_update_display (windows); - info_error (CANT_FIND_WIND); - info_session (); - exit (0); - } - - active_window = largest; - window = window_make_window (node); - if (window) - { - window_tile_windows (TILE_INTERNALS); - remember_window_and_node (window, node); - } - else - { - display_update_display (windows); - info_error (WIN_TOO_SMALL); - info_session (); - exit (0); - } - } - } - display_startup_message_and_start (); -} - -/* Start an info session with INITIAL_NODE, and an error message in the echo - area made from FORMAT and ARG. */ -void -begin_info_session_with_error (initial_node, format, arg) - NODE *initial_node; - char *format; - void *arg; -{ - initialize_info_session (initial_node); - info_error (format, arg, (void *)NULL); - info_session (); -} - -/* Start an info session with INITIAL_NODE. */ -void -begin_info_session (initial_node) - NODE *initial_node; -{ - initialize_info_session (initial_node); - display_startup_message_and_start (); -} - -void -display_startup_message_and_start () -{ - char *format; - - format = replace_in_documentation - ("Welcome to Info version %s. Type \"\\[get-help-window]\" for help."); - - window_message_in_echo_area (format, version_string ()); - info_session (); -} - -/* Run an info session with an already initialized window and node. */ -void -info_session () -{ - terminal_prep_terminal (); - display_update_display (windows); - info_last_executed_command = (VFunction *)NULL; - info_read_and_dispatch (); - terminal_unprep_terminal (); - close_dribble_file (); -} - -/* Here is a window-location dependent event loop. Called from the - functions info_session (), and from read_xxx_in_echo_area (). */ -void -info_read_and_dispatch () -{ - unsigned char key; - int done; - done = 0; - - while (!done && !quit_info_immediately) - { - int lk; - - /* If we haven't just gone up or down a line, there is no - goal column for this window. */ - if ((info_last_executed_command != info_next_line) && - (info_last_executed_command != info_prev_line)) - active_window->goal_column = -1; - - if (echo_area_is_active) - { - lk = echo_area_last_command_was_kill; - echo_area_prep_read (); - } - - if (!info_any_buffered_input_p ()) - display_update_display (windows); - - display_cursor_at_point (active_window); - info_initialize_numeric_arg (); - - initialize_keyseq (); - key = info_get_input_char (); - - /* No errors yet. We just read a character, that's all. Only clear - the echo_area if it is not currently active. */ - if (!echo_area_is_active) - window_clear_echo_area (); - - info_error_was_printed = 0; - - /* Do the selected command. */ - info_dispatch_on_key (key, active_window->keymap); - - if (echo_area_is_active) - { - /* Echo area commands that do killing increment the value of - ECHO_AREA_LAST_COMMAND_WAS_KILL. Thus, if there is no - change in the value of this variable, the last command - executed was not a kill command. */ - if (lk == echo_area_last_command_was_kill) - echo_area_last_command_was_kill = 0; - - if (ea_last_executed_command == ea_newline || - info_aborted_echo_area) - { - ea_last_executed_command = (VFunction *)NULL; - done = 1; - } - - if (info_last_executed_command == info_quit) - quit_info_immediately = 1; - } - else if (info_last_executed_command == info_quit) - done = 1; - } -} - -/* Found in signals.c */ -extern void initialize_info_signal_handler (); - -/* Initialize the first info session by starting the terminal, window, - and display systems. */ -void -initialize_info_session (node) - NODE *node; -{ - char *getenv (), *term_name; - - term_name = getenv ("TERM"); - terminal_initialize_terminal (term_name); - - if (terminal_is_dumb_p) - { - if (!term_name) - term_name = "dumb"; - - info_error (TERM_TOO_DUMB, term_name); - exit (1); - } - terminal_clear_screen (); - initialize_info_keymaps (); - window_initialize_windows (screenwidth, screenheight); - initialize_info_signal_handler (); - display_initialize_display (screenwidth, screenheight); - info_set_node_of_window (active_window, node); - - /* Tell the window system how to notify us when a window needs to be - asynchronously deleted (e.g., user resizes window very small). */ - window_deletion_notifier = forget_window_and_nodes; - - /* If input has not been redirected yet, make it come from STDIN. */ - if (!info_input_stream) - info_input_stream = stdin; - - info_windows_initialized_p = 1; -} - -/* Tell Info that input is coming from the file FILENAME. */ -void -info_set_input_from_file (filename) - char *filename; -{ - FILE *stream; - - stream = fopen (filename, "r"); - - if (!stream) - return; - - if (info_input_stream != stdin) - fclose (info_input_stream); - - info_input_stream = stream; - - if (stream != stdin) - display_inhibited = 1; -} - -/* Return the INFO_WINDOW containing WINDOW, or NULL if there isn't one. */ -static INFO_WINDOW * -get_info_window_of_window (window) - WINDOW *window; -{ - register int i; - INFO_WINDOW *info_win = (INFO_WINDOW *)NULL; - - for (i = 0; info_windows && (info_win = info_windows[i]); i++) - if (info_win->window == window) - break; - - return (info_win); -} - -/* Reset the remembered pagetop and point of WINDOW to WINDOW's current - values if the window and node are the same as the current one being - displayed. */ -void -set_remembered_pagetop_and_point (window) - WINDOW *window; -{ - INFO_WINDOW *info_win; - - info_win = get_info_window_of_window (window); - - if (!info_win) - return; - - if (info_win->nodes_index && - (info_win->nodes[info_win->current] == window->node)) - { - info_win->pagetops[info_win->current] = window->pagetop; - info_win->points[info_win->current] = window->point; - } -} - -void -remember_window_and_node (window, node) - WINDOW *window; - NODE *node; -{ - INFO_WINDOW *info_win; - - /* See if we already have this window in our list. */ - info_win = get_info_window_of_window (window); - - /* If the window wasn't already on our list, then make a new entry. */ - if (!info_win) - { - info_win = (INFO_WINDOW *)xmalloc (sizeof (INFO_WINDOW)); - info_win->window = window; - info_win->nodes = (NODE **)NULL; - info_win->pagetops = (int *)NULL; - info_win->points = (long *)NULL; - info_win->current = 0; - info_win->nodes_index = 0; - info_win->nodes_slots = 0; - - add_pointer_to_array (info_win, info_windows_index, info_windows, - info_windows_slots, 10, INFO_WINDOW *); - } - - /* If this node, the current pagetop, and the current point are the - same as the last saved node and pagetop, don't really add this to - the list of history nodes. */ - { - int ni = info_win->nodes_index - 1; - - if ((ni != -1) && - (info_win->nodes[ni]->contents == node->contents) && - (info_win->pagetops[ni] == window->pagetop) && - (info_win->points[ni] == window->point)) - return; - } - - /* Remember this node, the currently displayed pagetop, and the current - location of point in this window. Because we are updating pagetops - and points as well as nodes, it is more efficient to avoid the - add_pointer_to_array macro here. */ - if (info_win->nodes_index + 2 >= info_win->nodes_slots) - { - info_win->nodes = (NODE **) - xrealloc (info_win->nodes, - (info_win->nodes_slots += 20) * sizeof (NODE *)); - - info_win->pagetops = (int *) - xrealloc (info_win->pagetops, info_win->nodes_slots * sizeof (int)); - - info_win->points = (long *) - xrealloc (info_win->points, info_win->nodes_slots * sizeof (long)); - } - - info_win->nodes[info_win->nodes_index] = node; - info_win->pagetops[info_win->nodes_index] = window->pagetop; - info_win->points[info_win->nodes_index] = window->point; - info_win->current = info_win->nodes_index++; - info_win->nodes[info_win->nodes_index] = (NODE *)NULL; - info_win->pagetops[info_win->nodes_index] = 0; - info_win->points[info_win->nodes_index] = 0; -} - -#define DEBUG_FORGET_WINDOW_AND_NODES -#if defined (DEBUG_FORGET_WINDOW_AND_NODES) -static void -consistency_check_info_windows () -{ - register int i; - INFO_WINDOW *info_win; - - for (i = 0; i < info_windows_index; i++) - { - WINDOW *win; - - for (win = windows; win; win = win->next) - if (win == info_windows[i]->window) - break; - - if (!win) - abort (); - } -} -#endif /* DEBUG_FORGET_WINDOW_AND_NODES */ - -/* Remove WINDOW and its associated list of nodes from INFO_WINDOWS. */ -void -forget_window_and_nodes (window) - WINDOW *window; -{ - register int i; - INFO_WINDOW *info_win = (INFO_WINDOW *)NULL; - - for (i = 0; info_windows && (info_win = info_windows[i]); i++) - if (info_win->window == window) - break; - - /* If we found the window to forget, then do so. */ - if (info_win) - { - while (i < info_windows_index) - info_windows[i] = info_windows[++i]; - - info_windows_index--; - info_windows[info_windows_index] = (INFO_WINDOW *)NULL; - - if (info_win->nodes) - { - for (i = 0; info_win->nodes[i]; i++) - if (internal_info_node_p (info_win->nodes[i])) - free (info_win->nodes[i]); - free (info_win->nodes); - - maybe_free (info_win->pagetops); - maybe_free (info_win->points); - } - - free (info_win); - } -#if defined (DEBUG_FORGET_WINDOW_AND_NODES) - consistency_check_info_windows (); -#endif /* DEBUG_FORGET_WINDOW_AND_NODES */ -} - -/* Set WINDOW to show NODE. Remember the new window in our list of Info - windows. If we are doing automatic footnote display, also try to display - the footnotes for this window. */ -void -info_set_node_of_window (window, node) - WINDOW *window; - NODE *node; -{ - /* Put this node into the window. */ - window_set_node_of_window (window, node); - - /* Remember this node and window in our list of info windows. */ - remember_window_and_node (window, node); - - /* If doing auto-footnote display/undisplay, show the footnotes belonging - to this window's node. */ - if (auto_footnotes_p) - info_get_or_remove_footnotes (window); -} - - -/* **************************************************************** */ -/* */ -/* Info Movement Commands */ -/* */ -/* **************************************************************** */ - -/* Change the pagetop of WINDOW to DESIRED_TOP, perhaps scrolling the screen - to do so. */ -void -set_window_pagetop (window, desired_top) - WINDOW *window; - int desired_top; -{ - int point_line, old_pagetop; - - if (desired_top < 0) - desired_top = 0; - else if (desired_top > window->line_count) - desired_top = window->line_count - 1; - - if (window->pagetop == desired_top) - return; - - old_pagetop = window->pagetop; - window->pagetop = desired_top; - - /* Make sure that point appears in this window. */ - point_line = window_line_of_point (window); - if ((point_line < window->pagetop) || - ((point_line - window->pagetop) > window->height - 1)) - window->point = - window->line_starts[window->pagetop] - window->node->contents; - - window->flags |= W_UpdateWindow; - - /* Find out which direction to scroll, and scroll the window in that - direction. Do this only if there would be a savings in redisplay - time. This is true if the amount to scroll is less than the height - of the window, and if the number of lines scrolled would be greater - than 10 % of the window's height. */ - if (old_pagetop < desired_top) - { - int start, end, amount; - - amount = desired_top - old_pagetop; - - if ((amount >= window->height) || - (((window->height - amount) * 10) < window->height)) - return; - - start = amount + window->first_row; - end = window->height + window->first_row; - - display_scroll_display (start, end, -amount); - } - else - { - int start, end, amount; - - amount = old_pagetop - desired_top; - - if ((amount >= window->height) || - (((window->height - amount) * 10) < window->height)) - return; - - start = window->first_row; - end = (window->first_row + window->height) - amount; - display_scroll_display (start, end, amount); - } -} - -/* Immediately make WINDOW->point visible on the screen, and move the - terminal cursor there. */ -static void -info_show_point (window) - WINDOW *window; -{ - int old_pagetop; - - old_pagetop = window->pagetop; - window_adjust_pagetop (window); - if (old_pagetop != window->pagetop) - { - int new_pagetop; - - new_pagetop = window->pagetop; - window->pagetop = old_pagetop; - set_window_pagetop (window, new_pagetop); - } - - if (window->flags & W_UpdateWindow) - display_update_one_window (window); - - display_cursor_at_point (window); -} - -/* Move WINDOW->point from OLD line index to NEW line index. */ -static void -move_to_new_line (old, new, window) - int old, new; - WINDOW *window; -{ - if (old == -1) - { - info_error (CANT_FIND_POINT); - } - else - { - int goal; - - if (new >= window->line_count || new < 0) - return; - - goal = window_get_goal_column (window); - window->goal_column = goal; - - window->point = window->line_starts[new] - window->node->contents; - window->point += window_chars_to_goal (window->line_starts[new], goal); - info_show_point (window); - } -} - -/* Move WINDOW's point down to the next line if possible. */ -DECLARE_INFO_COMMAND (info_next_line, "Move down to the next line") -{ - int old_line, new_line; - - if (count < 0) - info_prev_line (window, -count, key); - else - { - old_line = window_line_of_point (window); - new_line = old_line + count; - move_to_new_line (old_line, new_line, window); - } -} - -/* Move WINDOW's point up to the previous line if possible. */ -DECLARE_INFO_COMMAND (info_prev_line, "Move up to the previous line") -{ - int old_line, new_line; - - if (count < 0) - info_next_line (window, -count, key); - else - { - old_line = window_line_of_point (window); - new_line = old_line - count; - move_to_new_line (old_line, new_line, window); - } -} - -/* Move WINDOW's point to the end of the true line. */ -DECLARE_INFO_COMMAND (info_end_of_line, "Move to the end of the line") -{ - register int point, len; - register char *buffer; - - buffer = window->node->contents; - len = window->node->nodelen; - - for (point = window->point; - (point < len) && (buffer[point] != '\n'); - point++); - - if (point != window->point) - { - window->point = point; - info_show_point (window); - } -} - -/* Move WINDOW's point to the beginning of the true line. */ -DECLARE_INFO_COMMAND (info_beginning_of_line, "Move to the start of the line") -{ - register int point; - register char *buffer; - - buffer = window->node->contents; - point = window->point; - - for (; (point) && (buffer[point - 1] != '\n'); point--); - - /* If at a line start alreay, do nothing. */ - if (point != window->point) - { - window->point = point; - info_show_point (window); - } -} - -/* Move point forward in the node. */ -DECLARE_INFO_COMMAND (info_forward_char, "Move forward a character") -{ - if (count < 0) - info_backward_char (window, -count, key); - else - { - window->point += count; - - if (window->point >= window->node->nodelen) - window->point = window->node->nodelen - 1; - - info_show_point (window); - } -} - -/* Move point backward in the node. */ -DECLARE_INFO_COMMAND (info_backward_char, "Move backward a character") -{ - if (count < 0) - info_forward_char (window, -count, key); - else - { - window->point -= count; - - if (window->point < 0) - window->point = 0; - - info_show_point (window); - } -} - -#define alphabetic(c) (islower (c) || isupper (c) || isdigit (c)) - -/* Move forward a word in this node. */ -DECLARE_INFO_COMMAND (info_forward_word, "Move forward a word") -{ - long point; - char *buffer; - int end, c; - - if (count < 0) - { - info_backward_word (window, -count, key); - return; - } - - point = window->point; - buffer = window->node->contents; - end = window->node->nodelen; - - while (count) - { - if (point + 1 >= end) - return; - - /* If we are not in a word, move forward until we are in one. - Then, move forward until we hit a non-alphabetic character. */ - c = buffer[point]; - - if (!alphabetic (c)) - { - while (++point < end) - { - c = buffer[point]; - if (alphabetic (c)) - break; - } - } - - if (point >= end) return; - - while (++point < end) - { - c = buffer[point]; - if (!alphabetic (c)) - break; - } - --count; - } - window->point = point; - info_show_point (window); -} - -DECLARE_INFO_COMMAND (info_backward_word, "Move backward a word") -{ - long point; - char *buffer; - int c; - - if (count < 0) - { - info_forward_word (window, -count, key); - return; - } - - buffer = window->node->contents; - point = window->point; - - while (count) - { - if (point == 0) - break; - - /* Like info_forward_word (), except that we look at the - characters just before point. */ - - c = buffer[point - 1]; - - if (!alphabetic (c)) - { - while (--point) - { - c = buffer[point - 1]; - if (alphabetic (c)) - break; - } - } - - while (point) - { - c = buffer[point - 1]; - if (!alphabetic (c)) - break; - else - --point; - } - --count; - } - window->point = point; - info_show_point (window); -} - -/* Here is a list of time counter names which correspond to ordinal numbers. - It is used to print "once" instead of "1". */ -static char *counter_names[] = { - "not at all", "once", "twice", "three", "four", "five", "six", - (char *)NULL -}; - -/* Buffer used to return values from times_description (). */ -static char td_buffer[50]; - -/* Function returns a static string fully describing the number of times - present in COUNT. */ -static char * -times_description (count) - int count; -{ - register int i; - - td_buffer[0] = '\0'; - - for (i = 0; counter_names[i]; i++) - if (count == i) - break; - - if (counter_names[i]) - sprintf (td_buffer, "%s%s", counter_names[i], count > 2 ? " times" : ""); - else - sprintf (td_buffer, "%d times", count); - - return (td_buffer); -} - -/* Variable controlling the behaviour of default scrolling when you are - already at the bottom of a node. Possible values are defined in session.h. - The meanings are: - - IS_Continuous Try to get first menu item, or failing that, the - "Next:" pointer, or failing that, the "Up:" and - "Next:" of the up. - IS_NextOnly Try to get "Next:" menu item. - IS_PageOnly Simply give up at the bottom of a node. */ - -int info_scroll_behaviour = IS_Continuous; - -/* Choices used by the completer when reading a value for the user-visible - variable "scroll-behaviour". */ -char *info_scroll_choices[] = { - "Continuous", "Next Only", "Page Only", (char *)NULL -}; - -/* Move to 1st menu item, Next, Up/Next, or error in this window. */ -static void -forward_move_node_structure (window, behaviour) - WINDOW *window; - int behaviour; -{ - switch (behaviour) - { - case IS_PageOnly: - info_error (AT_NODE_BOTTOM); - break; - - case IS_NextOnly: - info_next_label_of_node (window->node); - if (!info_parsed_nodename && !info_parsed_filename) - info_error ("No \"Next\" pointer for this node."); - else - { - window_message_in_echo_area ("Following \"Next\" node..."); - info_handle_pointer ("Next", window); - } - break; - - case IS_Continuous: - { - /* First things first. If this node contains a menu, move down - into the menu. */ - { - REFERENCE **menu; - - menu = info_menu_of_node (window->node); - - if (menu) - { - info_free_references (menu); - window_message_in_echo_area ("Selecting first menu item..."); - info_menu_digit (window, 1, '1'); - return; - } - } - - /* Okay, this node does not contain a menu. If it contains a - "Next:" pointer, use that. */ - info_next_label_of_node (window->node); - if (info_label_was_found) - { - window_message_in_echo_area ("Selecting \"Next\" node..."); - info_handle_pointer ("Next", window); - return; - } - - /* Okay, there wasn't a "Next:" for this node. Move "Up:" until we - can move "Next:". If that isn't possible, complain that there - are no more nodes. */ - { - int up_counter, old_current; - INFO_WINDOW *info_win; - - /* Remember the current node and location. */ - info_win = get_info_window_of_window (window); - old_current = info_win->current; - - /* Back up through the "Up:" pointers until we have found a "Next:" - that isn't the same as the first menu item found in that node. */ - up_counter = 0; - while (!info_error_was_printed) - { - info_up_label_of_node (window->node); - if (info_label_was_found) - { - info_handle_pointer ("Up", window); - if (info_error_was_printed) - continue; - - up_counter++; - - info_next_label_of_node (window->node); - - /* If no "Next" pointer, keep backing up. */ - if (!info_label_was_found) - continue; - - /* If this node's first menu item is the same as this node's - Next pointer, keep backing up. */ - if (!info_parsed_filename) - { - REFERENCE **menu; - char *next_nodename; - - /* Remember the name of the Next node, since reading - the menu can overwrite the contents of the - info_parsed_xxx strings. */ - next_nodename = savestring (info_parsed_nodename); - - menu = info_menu_of_node (window->node); - if (menu && - (strcmp - (menu[0]->nodename, next_nodename) == 0)) - { - info_free_references (menu); - free (next_nodename); - continue; - } - else - { - /* Restore the world to where it was before - reading the menu contents. */ - info_free_references (menu); - free (next_nodename); - info_next_label_of_node (window->node); - } - } - - /* This node has a "Next" pointer, and it is not the - same as the first menu item found in this node. */ - window_message_in_echo_area - ("Moving \"Up\" %s, then \"Next\".", - times_description (up_counter)); - - info_handle_pointer ("Next", window); - return; - } - else - { - /* No more "Up" pointers. Print an error, and call it - quits. */ - register int i; - - for (i = 0; i < up_counter; i++) - { - info_win->nodes_index--; - free (info_win->nodes[info_win->nodes_index]); - info_win->nodes[info_win->nodes_index] = (NODE *)NULL; - } - info_win->current = old_current; - window->node = info_win->nodes[old_current]; - window->pagetop = info_win->pagetops[old_current]; - window->point = info_win->points[old_current]; - recalculate_line_starts (window); - window->flags |= W_UpdateWindow; - info_error ("No more nodes."); - } - } - } - break; - } - } -} - -/* Move Prev, Up or error in WINDOW depending on BEHAVIOUR. */ -static void -backward_move_node_structure (window, behaviour) - WINDOW *window; - int behaviour; -{ - switch (behaviour) - { - case IS_PageOnly: - info_error (AT_NODE_TOP); - break; - - case IS_NextOnly: - info_prev_label_of_node (window->node); - if (!info_parsed_nodename && !info_parsed_filename) - info_error ("No \"Prev\" for this node."); - else - { - window_message_in_echo_area ("Moving \"Prev\" in this window."); - info_handle_pointer ("Prev", window); - } - break; - - case IS_Continuous: - info_prev_label_of_node (window->node); - - if (!info_parsed_nodename && !info_parsed_filename) - { - info_up_label_of_node (window->node); - if (!info_parsed_nodename && !info_parsed_filename) - info_error ("No \"Prev\" or \"Up\" for this node."); - else - { - window_message_in_echo_area ("Moving \"Up\" in this window."); - info_handle_pointer ("Up", window); - } - } - else - { - REFERENCE **menu; - int inhibit_menu_traversing = 0; - - /* Watch out! If this node's Prev is the same as the Up, then - move Up. Otherwise, we could move Prev, and then to the last - menu item in the Prev. This would cause the user to loop - through a subsection of the info file. */ - if (!info_parsed_filename && info_parsed_nodename) - { - char *pnode; - - pnode = savestring (info_parsed_nodename); - info_up_label_of_node (window->node); - - if (!info_parsed_filename && info_parsed_nodename && - strcmp (info_parsed_nodename, pnode) == 0) - { - /* The nodes are the same. Inhibit moving to the last - menu item. */ - free (pnode); - inhibit_menu_traversing = 1; - } - else - { - free (pnode); - info_prev_label_of_node (window->node); - } - } - - /* Move to the previous node. If this node now contains a menu, - and we have not inhibited movement to it, move to the node - corresponding to the last menu item. */ - window_message_in_echo_area ("Moving \"Prev\" in this window."); - info_handle_pointer ("Prev", window); - - if (!inhibit_menu_traversing) - { - while (!info_error_was_printed && - (menu = info_menu_of_node (window->node))) - { - info_free_references (menu); - window_message_in_echo_area - ("Moving to \"Prev\"'s last menu item."); - info_menu_digit (window, 1, '0'); - } - } - } - break; - } -} - -/* Move continuously forward through the node structure of this info file. */ -DECLARE_INFO_COMMAND (info_global_next_node, - "Move forwards or down through node structure") -{ - if (count < 0) - info_global_prev_node (window, -count, key); - else - { - while (count && !info_error_was_printed) - { - forward_move_node_structure (window, IS_Continuous); - count--; - } - } -} - -/* Move continuously backward through the node structure of this info file. */ -DECLARE_INFO_COMMAND (info_global_prev_node, - "Move backwards or up through node structure") -{ - if (count < 0) - info_global_next_node (window, -count, key); - else - { - while (count && !info_error_was_printed) - { - backward_move_node_structure (window, IS_Continuous); - count--; - } - } -} - -/* Show the next screen of WINDOW's node. */ -DECLARE_INFO_COMMAND (info_scroll_forward, "Scroll forward in this window") -{ - if (count < 0) - info_scroll_backward (window, -count, key); - else - { - int desired_top; - - /* Without an explicit numeric argument, scroll the bottom two - lines to the top of this window, Or, if at bottom of window, - and the user wishes to scroll through nodes get the "Next" node - for this window. */ - if (!info_explicit_arg && count == 1) - { - desired_top = window->pagetop + (window->height - 2); - - /* If there are no more lines to scroll here, error, or get - another node, depending on INFO_SCROLL_BEHAVIOUR. */ - if (desired_top > window->line_count) - { - int behaviour = info_scroll_behaviour; - - /* Here is a hack. If the key being used is not SPC, do the - PageOnly behaviour. */ - if (key != SPC && key != DEL) - behaviour = IS_PageOnly; - - forward_move_node_structure (window, behaviour); - return; - } - } - else - desired_top = window->pagetop + count; - - if (desired_top >= window->line_count) - desired_top = window->line_count - 2; - - if (window->pagetop > desired_top) - return; - else - set_window_pagetop (window, desired_top); - } -} - -/* Show the previous screen of WINDOW's node. */ -DECLARE_INFO_COMMAND (info_scroll_backward, "Scroll backward in this window") -{ - if (count < 0) - info_scroll_forward (window, -count, key); - else - { - int desired_top; - - /* Without an explicit numeric argument, scroll the top two lines - to the bottom of this window, or move to the previous, or Up'th - node. */ - if (!info_explicit_arg && count == 1) - { - desired_top = window->pagetop - (window->height - 2); - - if ((desired_top < 0) && (window->pagetop == 0)) - { - int behaviour = info_scroll_behaviour; - - /* Same kind of hack as in info_scroll_forward. If the key - used to invoke this command is not DEL, do only the PageOnly - behaviour. */ - if (key != DEL && key != SPC) - behaviour = IS_PageOnly; - - backward_move_node_structure (window, behaviour); - return; - } - } - else - desired_top = window->pagetop - count; - - if (desired_top < 0) - desired_top = 0; - - set_window_pagetop (window, desired_top); - } -} - -/* Move to the beginning of the node. */ -DECLARE_INFO_COMMAND (info_beginning_of_node, "Move to the start of this node") -{ - window->pagetop = window->point = 0; - window->flags |= W_UpdateWindow; -} - -/* Move to the end of the node. */ -DECLARE_INFO_COMMAND (info_end_of_node, "Move to the end of this node") -{ - window->point = window->node->nodelen - 1; - info_show_point (window); -} - -/* **************************************************************** */ -/* */ -/* Commands for Manipulating Windows */ -/* */ -/* **************************************************************** */ - -/* Make the next window in the chain be the active window. */ -DECLARE_INFO_COMMAND (info_next_window, "Select the next window") -{ - if (count < 0) - { - info_prev_window (window, -count, key); - return; - } - - /* If no other window, error now. */ - if (!windows->next && !echo_area_is_active) - { - info_error (ONE_WINDOW); - return; - } - - while (count--) - { - if (window->next) - window = window->next; - else - { - if (window == the_echo_area || !echo_area_is_active) - window = windows; - else - window = the_echo_area; - } - } - - if (active_window != window) - { - if (auto_footnotes_p) - info_get_or_remove_footnotes (window); - - window->flags |= W_UpdateWindow; - active_window = window; - } -} - -/* Make the previous window in the chain be the active window. */ -DECLARE_INFO_COMMAND (info_prev_window, "Select the previous window") -{ - if (count < 0) - { - info_next_window (window, -count, key); - return; - } - - /* Only one window? */ - - if (!windows->next && !echo_area_is_active) - { - info_error (ONE_WINDOW); - return; - } - - while (count--) - { - /* If we are in the echo area, or if the echo area isn't active and we - are in the first window, find the last window in the chain. */ - if (window == the_echo_area || - (window == windows && !echo_area_is_active)) - { - register WINDOW *win, *last; - - for (win = windows; win; win = win->next) - last = win; - - window = last; - } - else - { - if (window == windows) - window = the_echo_area; - else - window = window->prev; - } - } - - if (active_window != window) - { - if (auto_footnotes_p) - info_get_or_remove_footnotes (window); - - window->flags |= W_UpdateWindow; - active_window = window; - } -} - -/* Split WINDOW into two windows, both showing the same node. If we - are automatically tiling windows, re-tile after the split. */ -DECLARE_INFO_COMMAND (info_split_window, "Split the current window") -{ - WINDOW *split, *old_active; - int pagetop; - - /* Remember the current pagetop of the window being split. If it doesn't - change, we can scroll its contents around after the split. */ - pagetop = window->pagetop; - - /* Make the new window. */ - old_active = active_window; - active_window = window; - split = window_make_window (window->node); - active_window = old_active; - - if (!split) - { - info_error (WIN_TOO_SMALL); - } - else - { -#if defined (SPLIT_BEFORE_ACTIVE) - /* Try to scroll the old window into its new postion. */ - if (pagetop == window->pagetop) - { - int start, end, amount; - - start = split->first_row; - end = start + window->height; - amount = split->height + 1; - display_scroll_display (start, end, amount); - } -#else /* !SPLIT_BEFORE_ACTIVE */ - /* Make sure point still appears in the active window. */ - info_show_point (window); -#endif /* !SPLIT_BEFORE_ACTIVE */ - - /* If the window just split was one internal to Info, try to display - something else in it. */ - if (internal_info_node_p (split->node)) - { - register int i, j; - INFO_WINDOW *iw; - NODE *node = (NODE *)NULL; - char *filename; - - for (i = 0; iw = info_windows[i]; i++) - { - for (j = 0; j < iw->nodes_index; j++) - if (!internal_info_node_p (iw->nodes[j])) - { - if (iw->nodes[j]->parent) - filename = iw->nodes[j]->parent; - else - filename = iw->nodes[j]->filename; - - node = info_get_node (filename, iw->nodes[j]->nodename); - if (node) - { - window_set_node_of_window (split, node); - i = info_windows_index - 1; - break; - } - } - } - } - split->pagetop = window->pagetop; - - if (auto_tiling_p) - window_tile_windows (DONT_TILE_INTERNALS); - else - window_adjust_pagetop (split); - - remember_window_and_node (split, split->node); - } -} - -/* Delete WINDOW, forgetting the list of last visited nodes. If we are - automatically displaying footnotes, show or remove the footnotes - window. If we are automatically tiling windows, re-tile after the - deletion. */ -DECLARE_INFO_COMMAND (info_delete_window, "Delete the current window") -{ - if (!windows->next) - { - info_error (CANT_KILL_LAST); - } - else if (window->flags & W_WindowIsPerm) - { - info_error ("Cannot delete a permanent window"); - } - else - { - info_delete_window_internal (window); - - if (auto_footnotes_p) - info_get_or_remove_footnotes (active_window); - - if (auto_tiling_p) - window_tile_windows (DONT_TILE_INTERNALS); - } -} - -/* Do the physical deletion of WINDOW, and forget this window and - associated nodes. */ -void -info_delete_window_internal (window) - WINDOW *window; -{ - if (windows->next && ((window->flags & W_WindowIsPerm) == 0)) - { - /* We not only delete the window from the display, we forget it from - our list of remembered windows. */ - forget_window_and_nodes (window); - window_delete_window (window); - - if (echo_area_is_active) - echo_area_inform_of_deleted_window (window); - } -} - -/* Just keep WINDOW, deleting all others. */ -DECLARE_INFO_COMMAND (info_keep_one_window, "Delete all other windows") -{ - int num_deleted; /* The number of windows we deleted. */ - int pagetop, start, end; - - /* Remember a few things about this window. We may be able to speed up - redisplay later by scrolling its contents. */ - pagetop = window->pagetop; - start = window->first_row; - end = start + window->height; - - num_deleted = 0; - - while (1) - { - WINDOW *win; - - /* Find an eligible window and delete it. If no eligible windows - are found, we are done. A window is eligible for deletion if - is it not permanent, and it is not WINDOW. */ - for (win = windows; win; win = win->next) - if (win != window && ((win->flags & W_WindowIsPerm) == 0)) - break; - - if (!win) - break; - - info_delete_window_internal (win); - num_deleted++; - } - - /* Scroll the contents of this window into the right place so that the - user doesn't have to wait any longer than necessary for redisplay. */ - if (num_deleted) - { - int amount; - - amount = (window->first_row - start); - amount -= (window->pagetop - pagetop); - display_scroll_display (start, end, amount); - } - - window->flags |= W_UpdateWindow; -} - -/* Scroll the "other" window of WINDOW. */ -DECLARE_INFO_COMMAND (info_scroll_other_window, "Scroll the other window") -{ - WINDOW *other; - - /* If only one window, give up. */ - if (!windows->next) - { - info_error (ONE_WINDOW); - return; - } - - other = window->next; - - if (!other) - other = window->prev; - - info_scroll_forward (other, count, key); -} - -/* Change the size of WINDOW by AMOUNT. */ -DECLARE_INFO_COMMAND (info_grow_window, "Grow (or shrink) this window") -{ - window_change_window_height (window, count); -} - -/* When non-zero, tiling takes place automatically when info_split_window - is called. */ -int auto_tiling_p = 0; - -/* Tile all of the visible windows. */ -DECLARE_INFO_COMMAND (info_tile_windows, - "Divide the available screen space among the visible windows") -{ - window_tile_windows (TILE_INTERNALS); -} - -/* Toggle the state of this window's wrapping of lines. */ -DECLARE_INFO_COMMAND (info_toggle_wrap, - "Toggle the state of line wrapping in the current window") -{ - window_toggle_wrap (window); -} - -/* **************************************************************** */ -/* */ -/* Info Node Commands */ -/* */ -/* **************************************************************** */ - -/* Using WINDOW for various defaults, select the node referenced by ENTRY - in it. If the node is selected, the window and node are remembered. */ -void -info_select_reference (window, entry) - WINDOW *window; - REFERENCE *entry; -{ - NODE *node; - char *filename, *nodename, *file_system_error; - - file_system_error = (char *)NULL; - - filename = entry->filename; - if (!filename) - filename = window->node->parent; - if (!filename) - filename = window->node->filename; - - if (filename) - filename = savestring (filename); - - if (entry->nodename) - nodename = savestring (entry->nodename); - else - nodename = savestring ("Top"); - - node = info_get_node (filename, nodename); - - /* Try something a little weird. If the node couldn't be found, and the - reference was of the form "foo::", see if the entry->label can be found - as a file, with a node of "Top". */ - if (!node) - { - if (info_recent_file_error) - file_system_error = savestring (info_recent_file_error); - - if (entry->nodename && (strcmp (entry->nodename, entry->label) == 0)) - { - node = info_get_node (entry->label, "Top"); - if (!node && info_recent_file_error) - { - maybe_free (file_system_error); - file_system_error = savestring (info_recent_file_error); - } - } - } - - if (!node) - { - if (file_system_error) - info_error (file_system_error); - else - info_error (CANT_FIND_NODE, nodename); - } - - maybe_free (file_system_error); - maybe_free (filename); - maybe_free (nodename); - - if (node) - { - set_remembered_pagetop_and_point (window); - info_set_node_of_window (window, node); - } -} - -/* Parse the node specification in LINE using WINDOW to default the filename. - Select the parsed node in WINDOW and remember it, or error if the node - couldn't be found. */ -static void -info_parse_and_select (line, window) - char *line; - WINDOW *window; -{ - REFERENCE entry; - - info_parse_node (line, DONT_SKIP_NEWLINES); - - entry.nodename = info_parsed_nodename; - entry.filename = info_parsed_filename; - entry.label = "*info-parse-and-select*"; - - info_select_reference (window, &entry); -} - -/* Given that the values of INFO_PARSED_FILENAME and INFO_PARSED_NODENAME - are previously filled, try to get the node represented by them into - WINDOW. The node should have been pointed to by the LABEL pointer of - WINDOW->node. */ -static void -info_handle_pointer (label, window) - char *label; - WINDOW *window; -{ - if (info_parsed_filename || info_parsed_nodename) - { - char *filename, *nodename; - NODE *node; - - filename = nodename = (char *)NULL; - - if (info_parsed_filename) - filename = savestring (info_parsed_filename); - else - { - if (window->node->parent) - filename = savestring (window->node->parent); - else if (window->node->filename) - filename = savestring (window->node->filename); - } - - if (info_parsed_nodename) - nodename = savestring (info_parsed_nodename); - else - nodename = savestring ("Top"); - - node = info_get_node (filename, nodename); - - if (node) - { - INFO_WINDOW *info_win; - - info_win = get_info_window_of_window (window); - if (info_win) - { - info_win->pagetops[info_win->current] = window->pagetop; - info_win->points[info_win->current] = window->point; - } - set_remembered_pagetop_and_point (window); - info_set_node_of_window (window, node); - } - else - { - if (info_recent_file_error) - info_error (info_recent_file_error); - else - info_error (CANT_FILE_NODE, filename, nodename); - } - - free (filename); - free (nodename); - } - else - { - info_error (NO_POINTER, label); - } -} - -/* Make WINDOW display the "Next:" node of the node currently being - displayed. */ -DECLARE_INFO_COMMAND (info_next_node, "Select the `Next' node") -{ - info_next_label_of_node (window->node); - info_handle_pointer ("Next", window); -} - -/* Make WINDOW display the "Prev:" node of the node currently being - displayed. */ -DECLARE_INFO_COMMAND (info_prev_node, "Select the `Prev' node") -{ - info_prev_label_of_node (window->node); - info_handle_pointer ("Prev", window); -} - -/* Make WINDOW display the "Up:" node of the node currently being - displayed. */ -DECLARE_INFO_COMMAND (info_up_node, "Select the `Up' node") -{ - info_up_label_of_node (window->node); - info_handle_pointer ("Up", window); -} - -/* Make WINDOW display the last node of this info file. */ -DECLARE_INFO_COMMAND (info_last_node, "Select the last node in this file") -{ - register int i; - FILE_BUFFER *fb = file_buffer_of_window (window); - NODE *node = (NODE *)NULL; - - if (fb && fb->tags) - { - for (i = 0; fb->tags[i]; i++); - node = info_get_node (fb->filename, fb->tags[i - 1]->nodename); - } - - if (!node) - info_error ("This window has no additional nodes"); - else - { - set_remembered_pagetop_and_point (window); - info_set_node_of_window (window, node); - } -} - -/* Make WINDOW display the first node of this info file. */ -DECLARE_INFO_COMMAND (info_first_node, "Select the first node in this file") -{ - FILE_BUFFER *fb = file_buffer_of_window (window); - NODE *node = (NODE *)NULL; - - if (fb && fb->tags) - node = info_get_node (fb->filename, fb->tags[0]->nodename); - - if (!node) - info_error ("This window has no additional nodes"); - else - { - set_remembered_pagetop_and_point (window); - info_set_node_of_window (window, node); - } -} - -/* Make WINDOW display the previous node displayed in this window. */ -DECLARE_INFO_COMMAND (info_history_node, - "Select the most recently selected node") -{ - INFO_WINDOW *info_win; - - /* Find the INFO_WINDOW which contains WINDOW. */ - info_win = get_info_window_of_window (window); - - if (!info_win) - { - info_error ("Requested window is not present!"); - return; - } - - set_remembered_pagetop_and_point (window); - if (!info_win->current) - { - if (info_win->nodes_index > 1) - { - window_message_in_echo_area - ("Now wrapped around to beginning of history."); - info_win->current = info_win->nodes_index; - } - else - { - info_error ("No earlier nodes in this window."); - return; - } - } - - info_win->current--; - window_set_node_of_window (window, info_win->nodes[info_win->current]); - window->pagetop = info_win->pagetops[info_win->current]; - window->point = info_win->points[info_win->current]; - window->flags |= W_UpdateWindow; - if (auto_footnotes_p) - info_get_or_remove_footnotes (window); -} - -/* Select the last menu item in WINDOW->node. */ -DECLARE_INFO_COMMAND (info_last_menu_item, - "Select the last item in this node's menu") -{ - info_menu_digit (window, 1, '0'); -} - -/* Use KEY (a digit) to select the Nth menu item in WINDOW->node. */ -DECLARE_INFO_COMMAND (info_menu_digit, "Select this menu item") -{ - register int i, item; - register REFERENCE *entry, **menu; - - menu = info_menu_of_node (window->node); - - if (!menu) - { - info_error (NO_MENU_NODE); - return; - } - - /* We have the menu. See if there are this many items in it. */ - item = key - '0'; - - /* Special case. Item "0" is the last item in this menu. */ - if (item == 0) - for (i = 0; menu[i + 1]; i++); - else - { - for (i = 0; entry = menu[i]; i++) - if (i == item - 1) - break; - } - - if (menu[i]) - info_select_reference (window, menu[i]); - else - info_error ("There aren't %d items in this menu.", item); - - info_free_references (menu); - return; -} - -/* Read a menu or followed reference from the user defaulting to the - reference found on the current line, and select that node. The - reading is done with completion. BUILDER is the function used - to build the list of references. ASK_P is non-zero if the user - should be prompted, or zero to select the default item. */ -static void -info_menu_or_ref_item (window, count, key, builder, ask_p) - WINDOW *window; - int count; - unsigned char key; - REFERENCE **(*builder) (); - int ask_p; -{ - REFERENCE **menu, *entry, *defentry = (REFERENCE *)NULL; - char *line; - - menu = (*builder) (window->node); - - if (!menu) - { - if (builder == info_menu_of_node) - info_error (NO_MENU_NODE); - else - info_error (NO_XREF_NODE); - return; - } - - /* Default the selected reference to the one which is on the line that - point is in. */ - { - REFERENCE **refs = (REFERENCE **)NULL; - int point_line; - - point_line = window_line_of_point (window); - - if (point_line != -1) - { - SEARCH_BINDING binding; - - binding.start = 0; - binding.buffer = window->line_starts[point_line]; - if (window->line_starts[point_line + 1]) - binding.end = window->line_starts[point_line + 1] - binding.buffer; - else - binding.end = - (window->node->contents + window->node->nodelen) - binding.buffer; - binding.flags = 0; - - if (builder == info_menu_of_node) - { - if (point_line) - { - binding.buffer--; - binding.end++; - - refs = info_menu_items (&binding); - } - } - else - refs = info_xrefs (&binding); - - if (refs) - { - if ((strcmp (refs[0]->label, "Menu") != 0) || - (builder == info_xrefs_of_node)) - { - defentry = (REFERENCE *)xmalloc (sizeof (REFERENCE)); - defentry->label = savestring (refs[0]->label); - defentry->filename = refs[0]->filename; - defentry->nodename = refs[0]->nodename; - - if (defentry->filename) - defentry->filename = savestring (defentry->filename); - if (defentry->nodename) - defentry->nodename = savestring (defentry->nodename); - } - info_free_references (refs); - } - } - } - - /* If we are going to ask the user a question, do it now. */ - if (ask_p) - { - char *prompt; - - /* Build the prompt string. */ - if (defentry) - prompt = (char *)xmalloc (20 + strlen (defentry->label)); - else - prompt = (char *)xmalloc (20); - - if (builder == info_menu_of_node) - { - if (defentry) - sprintf (prompt, "Menu item (%s): ", defentry->label); - else - sprintf (prompt, "Menu item: "); - } - else - { - if (defentry) - sprintf (prompt, "Follow xref (%s): ", defentry->label); - else - sprintf (prompt, "Follow xref: "); - } - - line = info_read_completing_in_echo_area (window, prompt, menu); - free (prompt); - - window = active_window; - - /* User aborts, just quit. */ - if (!line) - { - maybe_free (defentry); - info_free_references (menu); - info_abort_key (window, 0, 0); - return; - } - - /* If we had a default and the user accepted it, use that. */ - if (!*line) - { - free (line); - if (defentry) - line = savestring (defentry->label); - else - line = (char *)NULL; - } - } - else - { - /* Not going to ask any questions. If we have a default entry, use - that, otherwise return. */ - if (!defentry) - return; - else - line = savestring (defentry->label); - } - - if (line) - { - /* Find the selected label in the references. */ - entry = info_get_labeled_reference (line, menu); - - if (!entry && defentry) - info_error ("The reference disappeared! (%s).", line); - else - { - NODE *orig; - - orig = window->node; - info_select_reference (window, entry); - if ((builder == info_xrefs_of_node) && (window->node != orig)) - { - long offset; - long start; - - if (window->line_count > 0) - start = window->line_starts[1] - window->node->contents; - else - start = 0; - - offset = - info_target_search_node (window->node, entry->label, start); - - if (offset != -1) - { - window->point = offset; - window_adjust_pagetop (window); - } - } - } - - free (line); - if (defentry) - { - free (defentry->label); - maybe_free (defentry->filename); - maybe_free (defentry->nodename); - free (defentry); - } - } - - info_free_references (menu); - - if (!info_error_was_printed) - window_clear_echo_area (); -} - -/* Read a line (with completion) which is the name of a menu item, - and select that item. */ -DECLARE_INFO_COMMAND (info_menu_item, "Read a menu item and select its node") -{ - info_menu_or_ref_item (window, count, key, info_menu_of_node, 1); -} - -/* Read a line (with completion) which is the name of a reference to - follow, and select the node. */ -DECLARE_INFO_COMMAND - (info_xref_item, "Read a footnote or cross reference and select its node") -{ - info_menu_or_ref_item (window, count, key, info_xrefs_of_node, 1); -} - -/* Position the cursor at the start of this node's menu. */ -DECLARE_INFO_COMMAND (info_find_menu, "Move to the start of this node's menu") -{ - SEARCH_BINDING binding; - long position; - - binding.buffer = window->node->contents; - binding.start = 0; - binding.end = window->node->nodelen; - binding.flags = S_FoldCase | S_SkipDest; - - position = search (INFO_MENU_LABEL, &binding); - - if (position == -1) - info_error (NO_MENU_NODE); - else - { - window->point = position; - window_adjust_pagetop (window); - window->flags |= W_UpdateWindow; - } -} - -/* Visit as many menu items as is possible, each in a separate window. */ -DECLARE_INFO_COMMAND (info_visit_menu, - "Visit as many menu items at once as possible") -{ - register int i; - REFERENCE *entry, **menu; - - menu = info_menu_of_node (window->node); - - if (!menu) - info_error (NO_MENU_NODE); - - for (i = 0; (!info_error_was_printed) && (entry = menu[i]); i++) - { - WINDOW *new; - - new = window_make_window (window->node); - window_tile_windows (TILE_INTERNALS); - - if (!new) - info_error (WIN_TOO_SMALL); - else - { - active_window = new; - info_select_reference (new, entry); - } - } -} - -/* Read a line of input which is a node name, and go to that node. */ -DECLARE_INFO_COMMAND (info_goto_node, "Read a node name and select it") -{ - char *line; - NODE *node; - -#define GOTO_COMPLETES -#if defined (GOTO_COMPLETES) - /* Build a completion list of all of the known nodes. */ - { - register int fbi, i; - FILE_BUFFER *current; - REFERENCE **items = (REFERENCE **)NULL; - int items_index = 0; - int items_slots = 0; - - current = file_buffer_of_window (window); - - for (fbi = 0; info_loaded_files && info_loaded_files[fbi]; fbi++) - { - FILE_BUFFER *fb; - REFERENCE *entry; - int this_is_the_current_fb; - - fb = info_loaded_files[fbi]; - this_is_the_current_fb = (current == fb); - - entry = (REFERENCE *)xmalloc (sizeof (REFERENCE)); - entry->filename = entry->nodename = (char *)NULL; - entry->label = (char *)xmalloc (4 + strlen (fb->filename)); - sprintf (entry->label, "(%s)*", fb->filename); - - add_pointer_to_array - (entry, items_index, items, items_slots, 10, REFERENCE *); - - if (fb->tags) - { - for (i = 0; fb->tags[i]; i++) - { - entry = (REFERENCE *)xmalloc (sizeof (REFERENCE)); - entry->filename = entry->nodename = (char *)NULL; - entry->label = (char *) xmalloc - (4 + strlen (fb->filename) + strlen (fb->tags[i]->nodename)); - sprintf (entry->label, "(%s)%s", - fb->filename, fb->tags[i]->nodename); - - add_pointer_to_array - (entry, items_index, items, items_slots, 100, REFERENCE *); - } - - if (this_is_the_current_fb) - { - for (i = 0; fb->tags[i]; i++) - { - entry = (REFERENCE *)xmalloc (sizeof (REFERENCE)); - entry->filename = entry->nodename = (char *)NULL; - entry->label = savestring (fb->tags[i]->nodename); - add_pointer_to_array (entry, items_index, items, - items_slots, 100, REFERENCE *); - } - } - } - } - line = info_read_maybe_completing (window, "Goto Node: ", items); - info_free_references (items); - } -#else /* !GOTO_COMPLETES */ - line = info_read_in_echo_area (window, "Goto Node: "); -#endif /* !GOTO_COMPLETES */ - - /* If the user aborted, quit now. */ - if (!line) - { - info_abort_key (window, 0, 0); - return; - } - - canonicalize_whitespace (line); - - if (*line) - info_parse_and_select (line, window); - - free (line); - if (!info_error_was_printed) - window_clear_echo_area (); -} - -/* Move to the "Top" node in this file. */ -DECLARE_INFO_COMMAND (info_top_node, "Select the node `Top' in this file") -{ - info_parse_and_select ("Top", window); -} - -/* Move to the node "(dir)Top". */ -DECLARE_INFO_COMMAND (info_dir_node, "Select the node `(dir)'") -{ - info_parse_and_select ("(dir)Top", window); -} - -/* Try to delete the current node appearing in this window, showing the most - recently selected node in this window. */ -DECLARE_INFO_COMMAND (info_kill_node, "Kill this node") -{ - register int iw, i; - register INFO_WINDOW *info_win; - char *nodename = (char *)NULL; - NODE *temp = (NODE *)NULL; - - /* Read the name of a node to kill. The list of available nodes comes - from the nodes appearing in the current window configuration. */ - { - REFERENCE **menu = (REFERENCE **)NULL; - int menu_index = 0, menu_slots = 0; - char *default_nodename, *prompt; - - for (iw = 0; info_win = info_windows[iw]; iw++) - { - REFERENCE *entry; - - entry = (REFERENCE *)xmalloc (sizeof (REFERENCE)); - entry->label = savestring (info_win->window->node->nodename); - entry->filename = entry->nodename = (char *)NULL; - - add_pointer_to_array - (entry, menu_index, menu, menu_slots, 10, REFERENCE *); - } - - default_nodename = savestring (active_window->node->nodename); - prompt = (char *)xmalloc (40 + strlen (default_nodename)); - sprintf (prompt, "Kill node (%s): ", default_nodename); - - nodename = info_read_completing_in_echo_area (window, prompt, menu); - free (prompt); - info_free_references (menu); - if (nodename && !*nodename) - { - free (nodename); - nodename = default_nodename; - } - else - free (default_nodename); - } - - /* If there is no nodename to kill, quit now. */ - if (!nodename) - { - info_abort_key (window, 0, 0); - return; - } - - /* If there is a nodename, find it in our window list. */ - for (iw = 0; info_win = info_windows[iw]; iw++) - if (strcmp (nodename, info_win->nodes[info_win->current]->nodename) == 0) - break; - - if (!info_win) - { - if (*nodename) - info_error ("Cannot kill the node `%s'", nodename); - else - window_clear_echo_area (); - - return; - } - - /* If there are no more nodes left anywhere to view, complain and exit. */ - if (info_windows_index == 1 && info_windows[0]->nodes_index == 1) - { - info_error ("Cannot kill the last node"); - return; - } - - /* INFO_WIN contains the node that the user wants to stop viewing. - Delete this node from the list of nodes previously shown in this - window. */ - for (i = info_win->current; i < info_win->nodes_index; i++) - info_win->nodes[i] = info_win->nodes[i++]; - - /* There is one less node in this window's history list. */ - info_win->nodes_index--; - - /* Make this window show the most recent history node. */ - info_win->current = info_win->nodes_index - 1; - - /* If there aren't any nodes left in this window, steal one from the - next window. */ - if (info_win->current < 0) - { - INFO_WINDOW *stealer; - int which, pagetop; - long point; - - if (info_windows[iw + 1]) - stealer = info_windows[iw + 1]; - else - stealer = info_windows[0]; - - /* If the node being displayed in the next window is not the most - recently loaded one, get the most recently loaded one. */ - if ((stealer->nodes_index - 1) != stealer->current) - which = stealer->nodes_index - 1; - - /* Else, if there is another node behind the stealers current node, - use that one. */ - else if (stealer->current > 0) - which = stealer->current - 1; - - /* Else, just use the node appearing in STEALER's window. */ - else - which = stealer->current; - - /* Copy this node. */ - { - NODE *copy; - - temp = stealer->nodes[which]; - point = stealer->points[which]; - pagetop = stealer->pagetops[which]; - - copy = (NODE *)xmalloc (sizeof (NODE)); - copy->filename = temp->filename; - copy->parent = temp->parent; - copy->nodename = temp->nodename; - copy->contents = temp->contents; - copy->nodelen = temp->nodelen; - copy->flags = temp->flags; - - temp = copy; - } - - window_set_node_of_window (info_win->window, temp); - window->point = point; - window->pagetop = pagetop; - remember_window_and_node (info_win->window, temp); - } - else - { - temp = info_win->nodes[info_win->current]; - window_set_node_of_window (info_win->window, temp); - } - if (!info_error_was_printed) - window_clear_echo_area (); -} - -/* Read the name of a file and select the entire file. */ -DECLARE_INFO_COMMAND (info_view_file, "Read the name of a file and select it") -{ - char *line; - - line = info_read_in_echo_area (window, "Find file: "); - if (!line) - { - info_abort_key (active_window, 1, 0); - return; - } - - if (*line) - { - NODE *node; - - node = info_get_node (line, "*"); - if (!node) - { - if (info_recent_file_error) - info_error (info_recent_file_error); - else - info_error ("Cannot find \"%s\".", line); - } - else - { - set_remembered_pagetop_and_point (active_window); - info_set_node_of_window (window, node); - } - free (line); - } - - if (!info_error_was_printed) - window_clear_echo_area (); -} - -/* **************************************************************** */ -/* */ -/* Dumping and Printing Nodes */ -/* */ -/* **************************************************************** */ - -#define VERBOSE_NODE_DUMPING -static void write_node_to_stream (); -static void dump_node_to_stream (); -static void initialize_dumping (); - -/* Dump the nodes specified by FILENAME and NODENAMES to the file named - in OUTPUT_FILENAME. If DUMP_SUBNODES is non-zero, recursively dump - the nodes which appear in the menu of each node dumped. */ -void -dump_nodes_to_file (filename, nodenames, output_filename, dump_subnodes) - char *filename; - char **nodenames; - char *output_filename; - int dump_subnodes; -{ - register int i; - FILE *output_stream; - - /* Get the stream to print the nodes to. Special case of an output - filename of "-" means to dump the nodes to stdout. */ - if (strcmp (output_filename, "-") == 0) - output_stream = stdout; - else - output_stream = fopen (output_filename, "w"); - - if (!output_stream) - { - info_error ("Could not create output file \"%s\".", output_filename); - return; - } - - /* Print each node to stream. */ - initialize_dumping (); - for (i = 0; nodenames[i]; i++) - dump_node_to_stream (filename, nodenames[i], output_stream, dump_subnodes); - - if (output_stream != stdout) - fclose (output_stream); - -#if defined (VERBOSE_NODE_DUMPING) - info_error ("Done."); -#endif /* VERBOSE_NODE_DUMPING */ -} - -/* A place to remember already dumped nodes. */ -static char **dumped_already = (char **)NULL; -static int dumped_already_index = 0; -static int dumped_already_slots = 0; - -static void -initialize_dumping () -{ - dumped_already_index = 0; -} - -/* Get and print the node specified by FILENAME and NODENAME to STREAM. - If DUMP_SUBNODES is non-zero, recursively dump the nodes which appear - in the menu of each node dumped. */ -static void -dump_node_to_stream (filename, nodename, stream, dump_subnodes) - char *filename, *nodename; - FILE *stream; - int dump_subnodes; -{ - register int i; - NODE *node; - - node = info_get_node (filename, nodename); - - if (!node) - { - if (info_recent_file_error) - info_error (info_recent_file_error); - else - { - if (filename && *nodename != '(') - info_error - (CANT_FILE_NODE, filename_non_directory (filename), nodename); - else - info_error (CANT_FIND_NODE, nodename); - } - return; - } - - /* If we have already dumped this node, don't dump it again. */ - for (i = 0; i < dumped_already_index; i++) - if (strcmp (node->nodename, dumped_already[i]) == 0) - { - free (node); - return; - } - add_pointer_to_array (node->nodename, dumped_already_index, dumped_already, - dumped_already_slots, 50, char *); - -#if defined (VERBOSE_NODE_DUMPING) - /* Maybe we should print some information about the node being output. */ - if (node->filename) - info_error ("Writing node \"(%s)%s\"...", - filename_non_directory (node->filename), node->nodename); - else - info_error ("Writing node \"%s\"...", node->nodename); -#endif /* VERBOSE_NODE_DUMPING */ - - write_node_to_stream (node, stream); - - /* If we are dumping subnodes, get the list of menu items in this node, - and dump each one recursively. */ - if (dump_subnodes) - { - REFERENCE **menu = (REFERENCE **)NULL; - - /* If this node is an Index, do not dump the menu references. */ - if (string_in_line ("Index", node->nodename) == -1) - menu = info_menu_of_node (node); - - if (menu) - { - for (i = 0; menu[i]; i++) - { - /* We don't dump Info files which are different than the - current one. */ - if (!menu[i]->filename) - dump_node_to_stream - (filename, menu[i]->nodename, stream, dump_subnodes); - } - info_free_references (menu); - } - } - - free (node); -} - -/* Dump NODE to FILENAME. If DUMP_SUBNODES is non-zero, recursively dump - the nodes which appear in the menu of each node dumped. */ -void -dump_node_to_file (node, filename, dump_subnodes) - NODE *node; - char *filename; - int dump_subnodes; -{ - FILE *output_stream; - char *nodes_filename; - - /* Get the stream to print this node to. Special case of an output - filename of "-" means to dump the nodes to stdout. */ - if (strcmp (filename, "-") == 0) - output_stream = stdout; - else - output_stream = fopen (filename, "w"); - - if (!output_stream) - { - info_error ("Could not create output file \"%s\".", filename); - return; - } - - if (node->parent) - nodes_filename = node->parent; - else - nodes_filename = node->filename; - - initialize_dumping (); - dump_node_to_stream - (nodes_filename, node->nodename, output_stream, dump_subnodes); - - if (output_stream != stdout) - fclose (output_stream); - -#if defined (VERBOSE_NODE_DUMPING) - info_error ("Done."); -#endif /* VERBOSE_NODE_DUMPING */ -} - -#if !defined (DEFAULT_INFO_PRINT_COMMAND) -# define DEFAULT_INFO_PRINT_COMMAND "lpr" -#endif /* !DEFAULT_INFO_PRINT_COMMAND */ - -DECLARE_INFO_COMMAND (info_print_node, - "Pipe the contents of this node through INFO_PRINT_COMMAND") -{ - print_node (window->node); -} - -/* Print NODE on a printer piping it into INFO_PRINT_COMMAND. */ -void -print_node (node) - NODE *node; -{ - char *print_command, *getenv (); - FILE *printer_pipe; - - print_command = getenv ("INFO_PRINT_COMMAND"); - - if (!print_command || !*print_command) - print_command = DEFAULT_INFO_PRINT_COMMAND; - - printer_pipe = popen (print_command, "w"); - - if (!printer_pipe) - { - info_error ("Cannot open pipe to \"%s\".", print_command); - return; - } - -#if defined (VERBOSE_NODE_DUMPING) - /* Maybe we should print some information about the node being output. */ - if (node->filename) - info_error ("Printing node \"(%s)%s\"...", - filename_non_directory (node->filename), node->nodename); - else - info_error ("Printing node \"%s\"...", node->nodename); -#endif /* VERBOSE_NODE_DUMPING */ - - write_node_to_stream (node, printer_pipe); - pclose (printer_pipe); - -#if defined (VERBOSE_NODE_DUMPING) - info_error ("Done."); -#endif /* VERBOSE_NODE_DUMPING */ -} - -static void -write_node_to_stream (node, stream) - NODE *node; - FILE *stream; -{ - fwrite (node->contents, 1, node->nodelen, stream); -} - -/* **************************************************************** */ -/* */ -/* Info Searching Commands */ -/* */ -/* **************************************************************** */ - -/* Variable controlling the garbage collection of files briefly visited - during searches. Such files are normally gc'ed, unless they were - compressed to begin with. If this variable is non-zero, it says - to gc even those file buffer contents which had to be uncompressed. */ -int gc_compressed_files = 0; - -static void info_gc_file_buffers (); - -static char *search_string = (char *)NULL; -static int search_string_index = 0; -static int search_string_size = 0; -static int isearch_is_active = 0; - -/* Return the file buffer which belongs to WINDOW's node. */ -FILE_BUFFER * -file_buffer_of_window (window) - WINDOW *window; -{ - /* If this window has no node, then it has no file buffer. */ - if (!window->node) - return ((FILE_BUFFER *)NULL); - - if (window->node->parent) - return (info_find_file (window->node->parent)); - - if (window->node->filename) - return (info_find_file (window->node->filename)); - - return ((FILE_BUFFER *)NULL); -} - -/* Search for STRING in NODE starting at START. Return -1 if the string - was not found, or the location of the string if it was. If WINDOW is - passed as non-null, set the window's node to be NODE, its point to be - the found string, and readjust the window's pagetop. Final argument - DIR says which direction to search in. If it is positive, search - forward, else backwards. */ -long -info_search_in_node (string, node, start, window, dir) - char *string; - NODE *node; - long start; - WINDOW *window; - int dir; -{ - SEARCH_BINDING binding; - long offset; - - binding.buffer = node->contents; - binding.start = start; - binding.end = node->nodelen; - binding.flags = S_FoldCase; - - if (dir < 0) - { - binding.end = 0; - binding.flags |= S_SkipDest; - } - - if (binding.start < 0) - return (-1); - - /* For incremental searches, we always wish to skip past the string. */ - if (isearch_is_active) - binding.flags |= S_SkipDest; - - offset = search (string, &binding); - - if (offset != -1 && window) - { - set_remembered_pagetop_and_point (window); - if (window->node != node) - window_set_node_of_window (window, node); - window->point = offset; - window_adjust_pagetop (window); - } - return (offset); -} - -/* Search NODE, looking for the largest possible match of STRING. Start the - search at START. Return the absolute position of the match, or -1, if - no part of the string could be found. */ -long -info_target_search_node (node, string, start) - NODE *node; - char *string; - long start; -{ - register int i; - long offset; - char *target; - - target = savestring (string); - i = strlen (target); - - /* Try repeatedly searching for this string while removing words from - the end of it. */ - while (i) - { - target[i] = '\0'; - offset = info_search_in_node (target, node, start, (WINDOW *)NULL, 1); - - if (offset != -1) - break; - - /* Delete the last word from TARGET. */ - for (; i && (!whitespace (target[i]) && (target[i] != ',')); i--); - } - free (target); - return (offset); -} - -/* Search for STRING starting in WINDOW at point. If the string is found - in this node, set point to that position. Otherwise, get the file buffer - associated with WINDOW's node, and search through each node in that file. - If the search fails, return non-zero, else zero. Side-effect window - leaving the node and point where the string was found current. */ -static char *last_searched_for_string = (char *)NULL; -static int -info_search_internal (string, window, dir) - char *string; - WINDOW *window; - int dir; -{ - register int i; - FILE_BUFFER *file_buffer; - char *initial_nodename; - long ret, start = 0; - - file_buffer = file_buffer_of_window (window); - initial_nodename = window->node->nodename; - - if ((info_last_executed_command == info_search) && - (last_searched_for_string) && - (strcmp (last_searched_for_string, string) == 0)) - { - ret = info_search_in_node - (string, window->node, window->point + dir, window, dir); - } - else - { - ret = info_search_in_node - (string, window->node, window->point, window, dir); - } - - maybe_free (last_searched_for_string); - last_searched_for_string = savestring (string); - - if (ret != -1) - { - /* We won! */ - if (!echo_area_is_active && !isearch_is_active) - window_clear_echo_area (); - return (0); - } - - /* The string wasn't found in the current node. Search through the - window's file buffer, iff the current node is not "*". */ - if (!file_buffer || (strcmp (initial_nodename, "*") == 0)) - return (-1); - - /* If this file has tags, search through every subfile, starting at - this node's subfile and node. Otherwise, search through the - file's node list. */ - if (file_buffer->tags) - { - register int current_tag, number_of_tags; - char *last_subfile; - TAG *tag; - - /* Find number of tags and current tag. */ - last_subfile = (char *)NULL; - for (i = 0; file_buffer->tags[i]; i++) - if (strcmp (initial_nodename, file_buffer->tags[i]->nodename) == 0) - { - current_tag = i; - last_subfile = file_buffer->tags[i]->filename; - } - - number_of_tags = i; - - /* If there is no last_subfile, our tag wasn't found. */ - if (!last_subfile) - return (-1); - - /* Search through subsequent nodes, wrapping around to the top - of the info file until we find the string or return to this - window's node and point. */ - while (1) - { - NODE *node; - - /* Allow C-g to quit the search, failing it if pressed. */ - return_if_control_g (-1); - - current_tag += dir; - - if (current_tag < 0) - current_tag = number_of_tags - 1; - else if (current_tag == number_of_tags) - current_tag = 0; - - tag = file_buffer->tags[current_tag]; - - if (!echo_area_is_active && (last_subfile != tag->filename)) - { - window_message_in_echo_area - ("Searching subfile \"%s\"...", - filename_non_directory (tag->filename)); - - last_subfile = tag->filename; - } - - node = info_get_node (file_buffer->filename, tag->nodename); - - if (!node) - { - /* If not doing i-search... */ - if (!echo_area_is_active) - { - if (info_recent_file_error) - info_error (info_recent_file_error); - else - info_error (CANT_FILE_NODE, - filename_non_directory (file_buffer->filename), - tag->nodename); - } - return (-1); - } - - if (dir < 0) - start = tag->nodelen; - - ret = - info_search_in_node (string, node, start, window, dir); - - /* Did we find the string in this node? */ - if (ret != -1) - { - /* Yes! We win. */ - remember_window_and_node (window, node); - if (!echo_area_is_active) - window_clear_echo_area (); - return (0); - } - - /* No. Free this node, and make sure that we haven't passed - our starting point. */ - free (node); - - if (strcmp (initial_nodename, tag->nodename) == 0) - return (-1); - } - } - return (-1); -} - -DECLARE_INFO_COMMAND (info_search, "Read a string and search for it") -{ - char *line, *prompt; - int result, old_pagetop; - int direction; - - if (count < 0) - direction = -1; - else - direction = 1; - - /* Read a string from the user, defaulting the search to SEARCH_STRING. */ - if (!search_string) - { - search_string = (char *)xmalloc (search_string_size = 100); - search_string[0] = '\0'; - } - - prompt = (char *)xmalloc (50 + strlen (search_string)); - - sprintf (prompt, "%s for string [%s]: ", - direction < 0 ? "Search backward" : "Search", - search_string); - - line = info_read_in_echo_area (window, prompt); - free (prompt); - - if (!line) - { - info_abort_key (); - return; - } - - if (*line) - { - if (strlen (line) + 1 > search_string_size) - search_string = (char *) - xrealloc (search_string, (search_string_size += 50 + strlen (line))); - - strcpy (search_string, line); - search_string_index = strlen (line); - free (line); - } - - old_pagetop = active_window->pagetop; - result = info_search_internal (search_string, active_window, direction); - - if (result != 0 && !info_error_was_printed) - info_error ("Search failed."); - else if (old_pagetop != active_window->pagetop) - { - int new_pagetop; - - new_pagetop = active_window->pagetop; - active_window->pagetop = old_pagetop; - set_window_pagetop (active_window, new_pagetop); - if (auto_footnotes_p) - info_get_or_remove_footnotes (active_window); - } - - /* Perhaps free the unreferenced file buffers that were searched, but - not retained. */ - info_gc_file_buffers (); -} - -/* **************************************************************** */ -/* */ -/* Incremental Searching */ -/* */ -/* **************************************************************** */ - -static void incremental_search (); - -DECLARE_INFO_COMMAND (isearch_forward, - "Search interactively for a string as you type it") -{ - incremental_search (window, count, key); -} - -DECLARE_INFO_COMMAND (isearch_backward, - "Search interactively for a string as you type it") -{ - incremental_search (window, -count, key); -} - -/* Incrementally search for a string as it is typed. */ -/* The last accepted incremental search string. */ -static char *last_isearch_accepted = (char *)NULL; - -/* The current incremental search string. */ -static char *isearch_string = (char *)NULL; -static int isearch_string_index = 0; -static int isearch_string_size = 0; -static unsigned char isearch_terminate_search_key = ESC; - -/* Structure defining the current state of an incremental search. */ -typedef struct { - WINDOW_STATE_DECL; /* The node, pagetop and point. */ - int search_index; /* Offset of the last char in the search string. */ - int direction; /* The direction that this search is heading in. */ - int failing; /* Whether or not this search failed. */ -} SEARCH_STATE; - -/* Array of search states. */ -static SEARCH_STATE **isearch_states = (SEARCH_STATE **)NULL; -static int isearch_states_index = 0; -static int isearch_states_slots = 0; - -/* Push the state of this search. */ -static void -push_isearch (window, search_index, direction, failing) - WINDOW *window; - int search_index, direction, failing; -{ - SEARCH_STATE *state; - - state = (SEARCH_STATE *)xmalloc (sizeof (SEARCH_STATE)); - window_get_state (window, state); - state->search_index = search_index; - state->direction = direction; - state->failing = failing; - - add_pointer_to_array (state, isearch_states_index, isearch_states, - isearch_states_slots, 20, SEARCH_STATE *); -} - -/* Pop the state of this search to WINDOW, SEARCH_INDEX, and DIRECTION. */ -static void -pop_isearch (window, search_index, direction, failing) - WINDOW *window; - int *search_index, *direction, *failing; -{ - SEARCH_STATE *state; - - if (isearch_states_index) - { - isearch_states_index--; - state = isearch_states[isearch_states_index]; - window_set_state (window, state); - *search_index = state->search_index; - *direction = state->direction; - *failing = state->failing; - - free (state); - isearch_states[isearch_states_index] = (SEARCH_STATE *)NULL; - } -} - -/* Free the memory used by isearch_states. */ -static void -free_isearch_states () -{ - register int i; - - for (i = 0; i < isearch_states_index; i++) - { - free (isearch_states[i]); - isearch_states[i] = (SEARCH_STATE *)NULL; - } - isearch_states_index = 0; -} - -/* Display the current search in the echo area. */ -static void -show_isearch_prompt (dir, string, failing_p) - int dir; - unsigned char *string; - int failing_p; -{ - register int i; - char *prefix, *prompt, *p_rep; - int prompt_len, p_rep_index, p_rep_size; - - if (dir < 0) - prefix = "I-search backward: "; - else - prefix = "I-search: "; - - p_rep_index = p_rep_size = 0; - p_rep = (char *)NULL; - for (i = 0; string[i]; i++) - { - char *rep; - - switch (string[i]) - { - case ' ': rep = " "; break; - case LFD: rep = "\\n"; break; - case TAB: rep = "\\t"; break; - default: - rep = pretty_keyname (string[i]); - } - if ((p_rep_index + strlen (rep) + 1) >= p_rep_size) - p_rep = (char *)xrealloc (p_rep, p_rep_size += 100); - - strcpy (p_rep + p_rep_index, rep); - p_rep_index += strlen (rep); - } - - prompt_len = strlen (prefix) + p_rep_index + 20; - prompt = (char *)xmalloc (prompt_len); - sprintf (prompt, "%s%s%s", failing_p ? "Failing " : "", prefix, - p_rep ? p_rep : ""); - - window_message_in_echo_area ("%s", prompt); - maybe_free (p_rep); - free (prompt); - display_cursor_at_point (active_window); -} - -static void -incremental_search (window, count, ignore) - WINDOW *window; - int count; - unsigned char ignore; -{ - unsigned char key; - int last_search_result, search_result, dir; - SEARCH_STATE mystate, orig_state; - - if (count < 0) - dir = -1; - else - dir = 1; - - last_search_result = search_result = 0; - - window_get_state (window, &orig_state); - - isearch_string_index = 0; - if (!isearch_string_size) - isearch_string = (char *)xmalloc (isearch_string_size = 50); - - /* Show the search string in the echo area. */ - isearch_string[isearch_string_index] = '\0'; - show_isearch_prompt (dir, isearch_string, search_result); - - isearch_is_active = 1; - - while (isearch_is_active) - { - VFunction *func = (VFunction *)NULL; - int quoted = 0; - - /* If a recent display was interrupted, then do the redisplay now if - it is convenient. */ - if (!info_any_buffered_input_p () && display_was_interrupted_p) - { - display_update_one_window (window); - display_cursor_at_point (active_window); - } - - /* Read a character and dispatch on it. */ - key = info_get_input_char (); - window_get_state (window, &mystate); - - if (key == DEL) - { - /* User wants to delete one level of search? */ - if (!isearch_states_index) - { - terminal_ring_bell (); - continue; - } - else - { - pop_isearch - (window, &isearch_string_index, &dir, &search_result); - isearch_string[isearch_string_index] = '\0'; - show_isearch_prompt (dir, isearch_string, search_result); - goto after_search; - } - } - else if (key == Control ('q')) - { - key = info_get_input_char (); - quoted = 1; - } - - /* We are about to search again, or quit. Save the current search. */ - push_isearch (window, isearch_string_index, dir, search_result); - - if (quoted) - goto insert_and_search; - - if (!Meta_p (key) || (ISO_Latin_p && key < 160)) - { - func = window->keymap[key].function; - - /* If this key invokes an incremental search, then this means that - we will either search again in the same direction, search - again in the reverse direction, or insert the last search - string that was accepted through incremental searching. */ - if (func == isearch_forward || func == isearch_backward) - { - if ((func == isearch_forward && dir > 0) || - (func == isearch_backward && dir < 0)) - { - /* If the user has typed no characters, then insert the - last successful search into the current search string. */ - if (isearch_string_index == 0) - { - /* Of course, there must be something to insert. */ - if (last_isearch_accepted) - { - if (strlen (last_isearch_accepted) + 1 >= - isearch_string_size) - isearch_string = (char *) - xrealloc (isearch_string, - isearch_string_size += 10 + - strlen (last_isearch_accepted)); - strcpy (isearch_string, last_isearch_accepted); - isearch_string_index = strlen (isearch_string); - goto search_now; - } - else - continue; - } - else - { - /* Search again in the same direction. This means start - from a new place if the last search was successful. */ - if (search_result == 0) - window->point += dir; - } - } - else - { - /* Reverse the direction of the search. */ - dir = -dir; - } - } - else if (isprint (key) || func == (VFunction *)NULL) - { - insert_and_search: - - if (isearch_string_index + 2 >= isearch_string_size) - isearch_string = (char *)xrealloc - (isearch_string, isearch_string_size += 100); - - isearch_string[isearch_string_index++] = key; - isearch_string[isearch_string_index] = '\0'; - goto search_now; - } - else if (func == info_abort_key) - { - /* If C-g pressed, and the search is failing, pop the search - stack back to the last unfailed search. */ - if (isearch_states_index && (search_result != 0)) - { - terminal_ring_bell (); - while (isearch_states_index && (search_result != 0)) - pop_isearch - (window, &isearch_string_index, &dir, &search_result); - isearch_string[isearch_string_index] = '\0'; - show_isearch_prompt (dir, isearch_string, search_result); - continue; - } - else - goto exit_search; - } - else - goto exit_search; - } - else - { - exit_search: - /* The character is not printable, or it has a function which is - non-null. Exit the search, remembering the search string. If - the key is not the same as the isearch_terminate_search_key, - then push it into pending input. */ - if (isearch_string_index && func != info_abort_key) - { - maybe_free (last_isearch_accepted); - last_isearch_accepted = savestring (isearch_string); - } - - if (key != isearch_terminate_search_key) - info_set_pending_input (key); - - if (func == info_abort_key) - { - if (isearch_states_index) - window_set_state (window, &orig_state); - } - - if (!echo_area_is_active) - window_clear_echo_area (); - - if (auto_footnotes_p) - info_get_or_remove_footnotes (active_window); - - isearch_is_active = 0; - continue; - } - - /* Search for the contents of isearch_string. */ - search_now: - show_isearch_prompt (dir, isearch_string, search_result); - - if (search_result == 0) - { - /* Check to see if the current search string is right here. If - we are looking at it, then don't bother calling the search - function. */ - if (((dir < 0) && - (strnicmp (window->node->contents + window->point, - isearch_string, isearch_string_index) == 0)) || - ((dir > 0) && - ((window->point - isearch_string_index) >= 0) && - (strnicmp (window->node->contents + - (window->point - (isearch_string_index - 1)), - isearch_string, isearch_string_index) == 0))) - { - if (dir > 0) - window->point++; - } - else - search_result = info_search_internal (isearch_string, window, dir); - } - - /* If this search failed, and we didn't already have a failed search, - then ring the terminal bell. */ - if (search_result != 0 && last_search_result == 0) - terminal_ring_bell (); - - after_search: - show_isearch_prompt (dir, isearch_string, search_result); - - if (search_result == 0) - { - if ((mystate.node == window->node) && - (mystate.pagetop != window->pagetop)) - { - int newtop = window->pagetop; - window->pagetop = mystate.pagetop; - set_window_pagetop (window, newtop); - } - display_update_one_window (window); - display_cursor_at_point (window); - } - - last_search_result = search_result; - } - - /* Free the memory used to remember each search state. */ - free_isearch_states (); - - /* Perhaps GC some file buffers. */ - info_gc_file_buffers (); - - /* After searching, leave the window in the correct state. */ - if (!echo_area_is_active) - window_clear_echo_area (); -} - -/* GC some file buffers. A file buffer can be gc-ed if there we have - no nodes in INFO_WINDOWS that reference this file buffer's contents. - Garbage collecting a file buffer means to free the file buffers - contents. */ -static void -info_gc_file_buffers () -{ - register int fb_index, iw_index, i; - register FILE_BUFFER *fb; - register INFO_WINDOW *iw; - - if (!info_loaded_files) - return; - - for (fb_index = 0; fb = info_loaded_files[fb_index]; fb_index++) - { - int fb_referenced_p = 0; - - /* If already gc-ed, do nothing. */ - if (!fb->contents) - continue; - - /* If this file had to be uncompressed, check to see if we should - gc it. This means that the user-variable "gc-compressed-files" - is non-zero. */ - if ((fb->flags & N_IsCompressed) && !gc_compressed_files) - continue; - - /* If this file's contents are not gc-able, move on. */ - if (fb->flags & N_CannotGC) - continue; - - /* Check each INFO_WINDOW to see if it has any nodes which reference - this file. */ - for (iw_index = 0; iw = info_windows[iw_index]; iw_index++) - { - for (i = 0; iw->nodes && iw->nodes[i]; i++) - { - if ((strcmp (fb->fullpath, iw->nodes[i]->filename) == 0) || - (strcmp (fb->filename, iw->nodes[i]->filename) == 0)) - { - fb_referenced_p = 1; - break; - } - } - } - - /* If this file buffer wasn't referenced, free its contents. */ - if (!fb_referenced_p) - { - free (fb->contents); - fb->contents = (char *)NULL; - } - } -} - -/* **************************************************************** */ -/* */ -/* Traversing and Selecting References */ -/* */ -/* **************************************************************** */ - -/* Move to the next or previous cross reference in this node. */ -static void -info_move_to_xref (window, count, key, dir) - WINDOW *window; - int count; - unsigned char key; - int dir; -{ - long firstmenu, firstxref; - long nextmenu, nextxref; - long placement = -1; - long start = 0; - NODE *node = window->node; - - if (dir < 0) - start = node->nodelen; - - /* This search is only allowed to fail if there is no menu or cross - reference in the current node. Otherwise, the first menu or xref - found is moved to. */ - - firstmenu = info_search_in_node - (INFO_MENU_ENTRY_LABEL, node, start, (WINDOW *)NULL, dir); - - /* FIRSTMENU may point directly to the line defining the menu. Skip that - and go directly to the first item. */ - - if (firstmenu != -1) - { - char *text = node->contents + firstmenu; - - if (strncmp (text, INFO_MENU_LABEL, strlen (INFO_MENU_LABEL)) == 0) - firstmenu = info_search_in_node - (INFO_MENU_ENTRY_LABEL, node, firstmenu + dir, (WINDOW *)NULL, dir); - } - - firstxref = - info_search_in_node (INFO_XREF_LABEL, node, start, (WINDOW *)NULL, dir); - - if (firstmenu == -1 && firstxref == -1) - { - info_error ("No cross references in this node."); - return; - } - - /* There is at least one cross reference or menu entry in this node. - Try hard to find the next available one. */ - - nextmenu = info_search_in_node - (INFO_MENU_ENTRY_LABEL, node, window->point + dir, (WINDOW *)NULL, dir); - - nextxref = info_search_in_node - (INFO_XREF_LABEL, node, window->point + dir, (WINDOW *)NULL, dir); - - /* Ignore "Menu:" as a menu item. */ - if (nextmenu != -1) - { - char *text = node->contents + nextmenu; - - if (strncmp (text, INFO_MENU_LABEL, strlen (INFO_MENU_LABEL)) == 0) - nextmenu = info_search_in_node - (INFO_MENU_ENTRY_LABEL, node, nextmenu + dir, (WINDOW *)NULL, dir); - } - - /* If there is both a next menu entry, and a next xref entry, choose the - one which occurs first. Otherwise, select the one which actually - appears in this node following point. */ - if (nextmenu != -1 && nextxref != -1) - { - if (((dir == 1) && (nextmenu < nextxref)) || - ((dir == -1) && (nextmenu > nextxref))) - placement = nextmenu + 1; - else - placement = nextxref; - } - else if (nextmenu != -1) - placement = nextmenu + 1; - else if (nextxref != -1) - placement = nextxref; - - /* If there was neither a menu or xref entry appearing in this node after - point, choose the first menu or xref entry appearing in this node. */ - if (placement == -1) - { - if (firstmenu != -1 && firstxref != -1) - { - if (((dir == 1) && (firstmenu < firstxref)) || - ((dir == -1) && (firstmenu > firstxref))) - placement = firstmenu + 1; - else - placement = firstxref; - } - else if (firstmenu != -1) - placement = firstmenu + 1; - else - placement = firstxref; - } - window->point = placement; - window_adjust_pagetop (window); - window->flags |= W_UpdateWindow; -} - -DECLARE_INFO_COMMAND (info_move_to_prev_xref, - "Move to the previous cross reference") -{ - if (count < 0) - info_move_to_prev_xref (window, -count, key); - else - info_move_to_xref (window, count, key, -1); -} - -DECLARE_INFO_COMMAND (info_move_to_next_xref, - "Move to the next cross reference") -{ - if (count < 0) - info_move_to_next_xref (window, -count, key); - else - info_move_to_xref (window, count, key, 1); -} - -/* Select the menu item or reference that appears on this line. */ -DECLARE_INFO_COMMAND (info_select_reference_this_line, - "Select reference or menu item appearing on this line") -{ - char *line; - NODE *orig; - - line = window->line_starts[window_line_of_point (window)]; - orig = window->node; - - /* If this line contains a menu item, select that one. */ - if (strncmp ("* ", line, 2) == 0) - info_menu_or_ref_item (window, count, key, info_menu_of_node, 0); - else - info_menu_or_ref_item (window, count, key, info_xrefs_of_node, 0); -} - -/* **************************************************************** */ -/* */ -/* Miscellaneous Info Commands */ -/* */ -/* **************************************************************** */ - -/* What to do when C-g is pressed in a window. */ -DECLARE_INFO_COMMAND (info_abort_key, "Cancel current operation") -{ - /* If error printing doesn't oridinarily ring the bell, do it now, - since C-g always rings the bell. Otherwise, let the error printer - do it. */ - if (!info_error_rings_bell_p) - terminal_ring_bell (); - info_error ("Quit"); - - info_initialize_numeric_arg (); - info_clear_pending_input (); - info_last_executed_command = (VFunction *)NULL; -} - -/* Move the cursor to the desired line of the window. */ -DECLARE_INFO_COMMAND (info_move_to_window_line, - "Move to the cursor to a specific line of the window") -{ - int line; - - /* With no numeric argument of any kind, default to the center line. */ - if (!info_explicit_arg && count == 1) - line = (window->height / 2) + window->pagetop; - else - { - if (count < 0) - line = (window->height + count) + window->pagetop; - else - line = window->pagetop + count; - } - - /* If the line doesn't appear in this window, make it do so. */ - if ((line - window->pagetop) >= window->height) - line = window->pagetop + (window->height - 1); - - /* If the line is too small, make it fit. */ - if (line < window->pagetop) - line = window->pagetop; - - /* If the selected line is past the bottom of the node, force it back. */ - if (line >= window->line_count) - line = window->line_count - 1; - - window->point = (window->line_starts[line] - window->node->contents); -} - -/* Clear the screen and redraw its contents. Given a numeric argument, - move the line the cursor is on to the COUNT'th line of the window. */ -DECLARE_INFO_COMMAND (info_redraw_display, "Redraw the display") -{ - if ((!info_explicit_arg && count == 1) || echo_area_is_active) - { - terminal_clear_screen (); - display_clear_display (the_display); - window_mark_chain (windows, W_UpdateWindow); - display_update_display (windows); - } - else - { - int desired_line, point_line; - int new_pagetop; - - point_line = window_line_of_point (window) - window->pagetop; - - if (count < 0) - desired_line = window->height + count; - else - desired_line = count; - - if (desired_line < 0) - desired_line = 0; - - if (desired_line >= window->height) - desired_line = window->height - 1; - - if (desired_line == point_line) - return; - - new_pagetop = window->pagetop + (point_line - desired_line); - - set_window_pagetop (window, new_pagetop); - } -} -/* This command does nothing. It is the fact that a key is bound to it - that has meaning. See the code at the top of info_session (). */ -DECLARE_INFO_COMMAND (info_quit, "Quit using Info") -{} - - -/* **************************************************************** */ -/* */ -/* Reading Keys and Dispatching on Them */ -/* */ -/* **************************************************************** */ - -/* Declaration only. Special cased in info_dispatch_on_key (). */ -DECLARE_INFO_COMMAND (info_do_lowercase_version, "") -{} - -static void -dispatch_error (keyseq) - char *keyseq; -{ - char *rep; - - rep = pretty_keyseq (keyseq); - - if (!echo_area_is_active) - info_error ("Unknown command (%s).", rep); - else - { - char *temp; - - temp = (char *)xmalloc (1 + strlen (rep) + strlen ("\"\" is invalid")); - - sprintf (temp, "\"%s\" is invalid", rep); - terminal_ring_bell (); - inform_in_echo_area (temp); - free (temp); - } -} - -/* Keeping track of key sequences. */ -static char *info_keyseq = (char *)NULL; -static char keyseq_rep[100]; -static int info_keyseq_index = 0; -static int info_keyseq_size = 0; -static int info_keyseq_displayed_p = 0; - -/* Initialize the length of the current key sequence. */ -void -initialize_keyseq () -{ - info_keyseq_index = 0; - info_keyseq_displayed_p = 0; -} - -/* Add CHARACTER to the current key sequence. */ -void -add_char_to_keyseq (character) - char character; -{ - if (info_keyseq_index + 2 >= info_keyseq_size) - info_keyseq = (char *)xrealloc (info_keyseq, info_keyseq_size += 10); - - info_keyseq[info_keyseq_index++] = character; - info_keyseq[info_keyseq_index] = '\0'; -} - -/* Return the pretty printable string which represents KEYSEQ. */ -char * -pretty_keyseq (keyseq) - char *keyseq; -{ - register int i; - - keyseq_rep[0] = '\0'; - - for (i = 0; keyseq[i]; i++) - { - sprintf (keyseq_rep + strlen (keyseq_rep), "%s%s", - strlen (keyseq_rep) ? " " : "", - pretty_keyname (keyseq[i])); - } - - return (keyseq_rep); -} - -/* Display the current value of info_keyseq. If argument EXPECTING is - non-zero, input is expected to be read after the key sequence is - displayed, so add an additional prompting character to the sequence. */ -void -display_info_keyseq (expecting_future_input) - int expecting_future_input; -{ - char *rep; - - rep = pretty_keyseq (info_keyseq); - if (expecting_future_input) - strcat (rep, "-"); - - if (echo_area_is_active) - inform_in_echo_area (rep); - else - { - window_message_in_echo_area (rep); - display_cursor_at_point (active_window); - } - info_keyseq_displayed_p = 1; -} - -/* Called by interactive commands to read a keystroke. */ -unsigned char -info_get_another_input_char () -{ - int ready = 0; - - /* If there isn't any input currently available, then wait a - moment looking for input. If we don't get it fast enough, - prompt a little bit with the current key sequence. */ - if (!info_keyseq_displayed_p && - !info_any_buffered_input_p () && - !info_input_pending_p ()) - { -#if defined (FD_SET) - struct timeval timer; - fd_set readfds; - - FD_ZERO (&readfds); - FD_SET (fileno (info_input_stream), &readfds); - timer.tv_sec = 0; - timer.tv_usec = 0; - ready = select (1, &readfds, (fd_set *)NULL, (fd_set *)NULL, &timer); -#endif /* FD_SET */ - } - - if (!ready) - display_info_keyseq (1); - - return (info_get_input_char ()); -} - -/* Do the command associated with KEY in MAP. If the associated command is - really a keymap, then read another key, and dispatch into that map. */ -void -info_dispatch_on_key (key, map) - unsigned char key; - Keymap map; -{ - if (Meta_p (key) && (!ISO_Latin_p || map[key].function != ea_insert)) - { - if (map[ESC].type == ISKMAP) - { - map = (Keymap)map[ESC].function; - add_char_to_keyseq (ESC); - key = UnMeta (key); - info_dispatch_on_key (key, map); - } - else - { - dispatch_error (info_keyseq); - } - return; - } - - switch (map[key].type) - { - case ISFUNC: - { - VFunction *func; - - func = map[key].function; - if (func != (VFunction *)NULL) - { - /* Special case info_do_lowercase_version (). */ - if (func == info_do_lowercase_version) - { - info_dispatch_on_key (tolower (key), map); - return; - } - - add_char_to_keyseq (key); - - if (info_keyseq_displayed_p) - display_info_keyseq (0); - - { - WINDOW *where; - - where = active_window; - (*map[key].function) - (active_window, info_numeric_arg * info_numeric_arg_sign, key); - - /* If we have input pending, then the last command was a prefix - command. Don't change the value of the last function vars. - Otherwise, remember the last command executed in the var - appropriate to the window in which it was executed. */ - if (!info_input_pending_p ()) - { - if (where == the_echo_area) - ea_last_executed_command = map[key].function; - else - info_last_executed_command = map[key].function; - } - } - } - else - { - add_char_to_keyseq (key); - dispatch_error (info_keyseq); - return; - } - } - break; - - case ISKMAP: - add_char_to_keyseq (key); - if (map[key].function != (VFunction *)NULL) - { - unsigned char newkey; - - newkey = info_get_another_input_char (); - info_dispatch_on_key (newkey, (Keymap)map[key].function); - } - else - { - dispatch_error (info_keyseq); - return; - } - break; - } -} - -/* **************************************************************** */ -/* */ -/* Numeric Arguments */ -/* */ -/* **************************************************************** */ - -/* Handle C-u style numeric args, as well as M--, and M-digits. */ - -/* Non-zero means that an explicit argument has been passed to this - command, as in C-u C-v. */ -int info_explicit_arg = 0; - -/* The sign of the numeric argument. */ -int info_numeric_arg_sign = 1; - -/* The value of the argument itself. */ -int info_numeric_arg = 1; - -/* Add the current digit to the argument in progress. */ -DECLARE_INFO_COMMAND (info_add_digit_to_numeric_arg, - "Add this digit to the current numeric argument") -{ - info_numeric_arg_digit_loop (window, 0, key); -} - -/* C-u, universal argument. Multiply the current argument by 4. - Read a key. If the key has nothing to do with arguments, then - dispatch on it. If the key is the abort character then abort. */ -DECLARE_INFO_COMMAND (info_universal_argument, - "Start (or multiply by 4) the current numeric argument") -{ - info_numeric_arg *= 4; - info_numeric_arg_digit_loop (window, 0, 0); -} - -/* Create a default argument. */ -void -info_initialize_numeric_arg () -{ - info_numeric_arg = info_numeric_arg_sign = 1; - info_explicit_arg = 0; -} - -DECLARE_INFO_COMMAND (info_numeric_arg_digit_loop, "") -{ - unsigned char pure_key; - Keymap keymap = window->keymap; - - while (1) - { - if (key) - pure_key = key; - else - { - if (display_was_interrupted_p && !info_any_buffered_input_p ()) - display_update_display (windows); - - if (active_window != the_echo_area) - display_cursor_at_point (active_window); - - pure_key = key = info_get_another_input_char (); - - if (Meta_p (key)) - add_char_to_keyseq (ESC); - - add_char_to_keyseq (UnMeta (key)); - } - - if (Meta_p (key)) - key = UnMeta (key); - - if (keymap[key].type == ISFUNC && - keymap[key].function == info_universal_argument) - { - info_numeric_arg *= 4; - key = 0; - continue; - } - - if (isdigit (key)) - { - if (info_explicit_arg) - info_numeric_arg = (info_numeric_arg * 10) + (key - '0'); - else - info_numeric_arg = (key - '0'); - info_explicit_arg = 1; - } - else - { - if (key == '-' && !info_explicit_arg) - { - info_numeric_arg_sign = -1; - info_numeric_arg = 1; - } - else - { - info_keyseq_index--; - info_dispatch_on_key (pure_key, keymap); - return; - } - } - key = 0; - } -} - -/* **************************************************************** */ -/* */ -/* Input Character Buffering */ -/* */ -/* **************************************************************** */ - -/* Character waiting to be read next. */ -static int pending_input_character = 0; - -/* How to make there be no pending input. */ -static void -info_clear_pending_input () -{ - pending_input_character = 0; -} - -/* How to set the pending input character. */ -static void -info_set_pending_input (key) - unsigned char key; -{ - pending_input_character = key; -} - -/* How to see if there is any pending input. */ -unsigned char -info_input_pending_p () -{ - return (pending_input_character); -} - -/* Largest number of characters that we can read in advance. */ -#define MAX_INFO_INPUT_BUFFERING 512 - -static int pop_index = 0, push_index = 0; -static unsigned char info_input_buffer[MAX_INFO_INPUT_BUFFERING]; - -/* Add KEY to the buffer of characters to be read. */ -static void -info_push_typeahead (key) - unsigned char key; -{ - /* Flush all pending input in the case of C-g pressed. */ - if (key == Control ('g')) - { - push_index = pop_index; - info_set_pending_input (Control ('g')); - } - else - { - info_input_buffer[push_index++] = key; - if (push_index >= sizeof (info_input_buffer)) - push_index = 0; - } -} - -/* Return the amount of space available in INFO_INPUT_BUFFER for new chars. */ -static int -info_input_buffer_space_available () -{ - if (pop_index > push_index) - return (pop_index - push_index); - else - return (sizeof (info_input_buffer - (push_index - pop_index))); -} - -/* Get a key from the buffer of characters to be read. - Return the key in KEY. - Result is non-zero if there was a key, or 0 if there wasn't. */ -static int -info_get_key_from_typeahead (key) - unsigned char *key; -{ - if (push_index == pop_index) - return (0); - - *key = info_input_buffer[pop_index++]; - - if (pop_index >= sizeof (info_input_buffer)) - pop_index = 0; - - return (1); -} - -int -info_any_buffered_input_p () -{ - info_gather_typeahead (); - return (push_index != pop_index); -} - -/* Push KEY into the *front* of the input buffer. Returns non-zero if - successful, zero if there is no space left in the buffer. */ -static int -info_replace_key_to_typeahead (key) - unsigned char key; -{ - if (info_input_buffer_space_available ()) - { - pop_index--; - if (pop_index < 0) - pop_index = sizeof (info_input_buffer) - 1; - info_input_buffer[pop_index] = key; - return (1); - } - return (0); -} - -/* If characters are available to be read, then read them and stuff them into - info_input_buffer. Otherwise, do nothing. */ -void -info_gather_typeahead () -{ - int tty, space_avail; - long chars_avail; - unsigned char input[MAX_INFO_INPUT_BUFFERING]; - - tty = fileno (info_input_stream); - chars_avail = 0; - - space_avail = info_input_buffer_space_available (); - - /* If we can just find out how many characters there are to read, do so. */ -#if defined (FIONREAD) - { - ioctl (tty, FIONREAD, &chars_avail); - - if (chars_avail > space_avail) - chars_avail = space_avail; - - if (chars_avail) - read (tty, &input[0], chars_avail); - } -#else /* !FIONREAD */ -# if defined (O_NDELAY) - { - int flags; - - flags = fcntl (tty, F_GETFL, 0); - - fcntl (tty, F_SETFL, (flags | O_NDELAY)); - chars_avail = read (tty, &input[0], space_avail); - fcntl (tty, F_SETFL, flags); - - if (chars_avail == -1) - chars_avail = 0; - } -# endif /* O_NDELAY */ -#endif /* !FIONREAD */ - - /* Store the input characters just read into our input buffer. */ - { - register int i; - - for (i = 0; i < chars_avail; i++) - info_push_typeahead (input[i]); - } -} - -/* How to read a single character. */ -unsigned char -info_get_input_char () -{ - unsigned char keystroke; - - info_gather_typeahead (); - - if (pending_input_character) - { - keystroke = pending_input_character; - pending_input_character = 0; - } - else if (info_get_key_from_typeahead (&keystroke) == 0) - { - int rawkey; - - rawkey = getc (info_input_stream); - keystroke = rawkey; - - if (rawkey == EOF) - { - if (info_input_stream != stdin) - { - fclose (info_input_stream); - info_input_stream = stdin; - display_inhibited = 0; - display_update_display (windows); - display_cursor_at_point (active_window); - rawkey = getc (info_input_stream); - keystroke = rawkey; - } - - if (rawkey == EOF) - { - terminal_unprep_terminal (); - close_dribble_file (); - exit (0); - } - } - } - - if (info_dribble_file) - dribble (keystroke); - - return (keystroke); -} diff --git a/gnu/usr.bin/texinfo/info/session.h b/gnu/usr.bin/texinfo/info/session.h deleted file mode 100644 index 08042dd..0000000 --- a/gnu/usr.bin/texinfo/info/session.h +++ /dev/null @@ -1,146 +0,0 @@ -/* session.h -- Functions found in session.c. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#ifndef _SESSION_H_ -#define _SESSION_H_ - -#include "general.h" -#include "dribble.h" - -/* All commands that can be invoked from within info_session () receive - arguments in the same way. This simple define declares the header - of a function named NAME, with associated documentation DOC. The - documentation string is groveled out of the source files by the - utility program `builddoc', which is also responsible for making - the documentation/function-pointer maps. */ -#define DECLARE_INFO_COMMAND(name, doc) \ -void name (window, count, key) WINDOW *window; int count; unsigned char key; - -/* Variables found in session.h. */ -extern VFunction *info_last_executed_command; - -/* Variable controlling the garbage collection of files briefly visited - during searches. Such files are normally gc'ed, unless they were - compressed to begin with. If this variable is non-zero, it says - to gc even those file buffer contents which had to be uncompressed. */ -extern int gc_compressed_files; - -/* When non-zero, tiling takes place automatically when info_split_window - is called. */ -extern int auto_tiling_p; - -/* Variable controlling the behaviour of default scrolling when you are - already at the bottom of a node. */ -extern int info_scroll_behaviour; -extern char *info_scroll_choices[]; - -/* Values for info_scroll_behaviour. */ -#define IS_Continuous 0 /* Try to get first menu item, or failing that, the - "Next:" pointer, or failing that, the "Up:" and - "Next:" of the up. */ -#define IS_NextOnly 1 /* Try to get "Next:" menu item. */ -#define IS_PageOnly 2 /* Simply give up at the bottom of a node. */ - -/* Utility functions found in session.c */ -extern void info_dispatch_on_key (); -extern unsigned char info_get_input_char (), info_get_another_input_char (); -extern unsigned char info_input_pending_p (); -extern void remember_window_and_node (), set_remembered_pagetop_and_point (); -extern void set_window_pagetop (), info_set_node_of_window (); -extern char *pretty_keyseq (); -extern void initialize_keyseq (), add_char_to_keyseq (); -extern void info_gather_typeahead (); -extern FILE_BUFFER *file_buffer_of_window (); -extern long info_search_in_node (), info_target_search_node (); -extern void info_select_reference (); -extern int info_any_buffered_input_p (); -extern void print_node (); -extern void dump_node_to_file (), dump_nodes_to_file (); - -/* Do the physical deletion of WINDOW, and forget this window and - associated nodes. */ -extern void info_delete_window_internal (); - -/* Tell Info that input is coming from the file FILENAME. */ -extern void info_set_input_from_file (); - -#define return_if_control_g(val) \ - do { \ - info_gather_typeahead (); \ - if (info_input_pending_p () == Control ('g')) \ - return (val); \ - } while (0) - -/* The names of the functions that run an info session. */ - -/* Starting an info session. */ -extern void begin_multiple_window_info_session (), begin_info_session (); -extern void begin_info_session_with_error (), info_session (); -extern void info_read_and_dispatch (); - -/* Moving the point within a node. */ -extern void info_next_line (), info_prev_line (); -extern void info_end_of_line (), info_beginning_of_line (); -extern void info_forward_char (), info_backward_char (); -extern void info_forward_word (), info_backward_word (); -extern void info_beginning_of_node (), info_end_of_node (); -extern void info_move_to_prev_xref (), info_move_to_next_xref (); - -/* Scrolling text within a window. */ -extern void info_scroll_forward (), info_scroll_backward (); -extern void info_redraw_display (), info_toggle_wrap (); -extern void info_move_to_window_line (); - -/* Manipulating multiple windows. */ -extern void info_split_window (), info_delete_window (); -extern void info_keep_one_window (), info_grow_window (); -extern void info_scroll_other_window (), info_tile_windows (); -extern void info_next_window (), info_prev_window (); - -/* Selecting nodes. */ -extern void info_next_node (), info_prev_node (), info_up_node (); -extern void info_last_node (), info_first_node (), info_history_node (); -extern void info_goto_node (), info_top_node (), info_dir_node (); -extern void info_global_next_node (), info_global_prev_node (); -extern void info_kill_node (), info_view_file (); - -/* Selecting cross references. */ -extern void info_menu_digit (), info_menu_item (), info_xref_item (); -extern void info_find_menu (), info_select_reference_this_line (); - -/* Hacking numeric arguments. */ -extern int info_explicit_arg, info_numeric_arg, info_numeric_arg_sign; - -extern void info_add_digit_to_numeric_arg (), info_universal_argument (); -extern void info_initialize_numeric_arg (), info_numeric_arg_digit_loop (); - -/* Searching commands. */ -extern void info_search (), isearch_forward (), isearch_backward (); - -/* Dumping and printing nodes. */ -extern void info_print_node (); - -/* Miscellaneous commands. */ -extern void info_abort_key (), info_quit (), info_do_lowercase_version (); - -#endif /* _SESSION_H_ */ diff --git a/gnu/usr.bin/texinfo/info/signals.c b/gnu/usr.bin/texinfo/info/signals.c deleted file mode 100644 index 7184f6a..0000000 --- a/gnu/usr.bin/texinfo/info/signals.c +++ /dev/null @@ -1,189 +0,0 @@ -/* signals.c -- Install and maintain Info signal handlers. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include "info.h" -#include "signals.h" - -/* **************************************************************** */ -/* */ -/* Pretending That We Have POSIX Signals */ -/* */ -/* **************************************************************** */ - -#if !defined (_POSIX_VERSION) -/* Perform OPERATION on NEWSET, perhaps leaving information in OLDSET. */ -static void -sigprocmask (operation, newset, oldset) - int operation, *newset, *oldset; -{ - switch (operation) - { - case SIG_UNBLOCK: -#if defined (HAVE_SIGSETMASK) - sigsetmask (sigblock (0) & ~(*newset)); -#endif /* HAVE_SIGSETMASK */ - break; - - case SIG_BLOCK: - *oldset = sigblock (*newset); - break; - - case SIG_SETMASK: -#if defined (HAVE_SIGSETMASK) - sigsetmask (*newset); -#endif /* HAVE_SIGSETMASK */ - break; - - default: - abort (); - } -} -#endif /* !_POSIX_VERSION */ - -/* **************************************************************** */ -/* */ -/* Signal Handling for Info */ -/* */ -/* **************************************************************** */ - -typedef void SigHandlerType; -typedef SigHandlerType SigHandler (); - -static SigHandlerType info_signal_handler (); -static SigHandler *old_TSTP, *old_TTOU, *old_TTIN; -static SigHandler *old_WINCH, *old_INT, *old_CONT; - -void -initialize_info_signal_handler () -{ -#if defined (SIGTSTP) - old_TSTP = (SigHandler *) signal (SIGTSTP, info_signal_handler); - old_TTOU = (SigHandler *) signal (SIGTTOU, info_signal_handler); - old_TTIN = (SigHandler *) signal (SIGTTIN, info_signal_handler); -#endif /* SIGTSTP */ - -#if defined (SIGWINCH) - old_WINCH = (SigHandler *) signal (SIGWINCH, info_signal_handler); -#if defined (SIGCONT) - old_CONT = (SigHandler *) signal (SIGCONT, info_signal_handler); -#endif /* SIGCONT */ -#endif /* SIGWINCH */ - -#if defined (SIGINT) - old_INT = (SigHandler *) signal (SIGINT, info_signal_handler); -#endif -} - -static void -redisplay_after_signal () -{ - terminal_clear_screen (); - display_clear_display (the_display); - window_mark_chain (windows, W_UpdateWindow); - display_update_display (windows); - display_cursor_at_point (active_window); - fflush (stdout); -} - -static SigHandlerType -info_signal_handler (sig) - int sig; -{ - SigHandler **old_signal_handler; - - switch (sig) - { -#if defined (SIGTSTP) - case SIGTSTP: - case SIGTTOU: - case SIGTTIN: -#endif -#if defined (SIGINT) - case SIGINT: -#endif - { -#if defined (SIGTSTP) - if (sig == SIGTSTP) - old_signal_handler = &old_TSTP; - if (sig == SIGTTOU) - old_signal_handler = &old_TTOU; - if (sig == SIGTTIN) - old_signal_handler = &old_TTIN; -#endif /* SIGTSTP */ - if (sig == SIGINT) - old_signal_handler = &old_INT; - - /* For stop signals, restore the terminal IO, leave the cursor - at the bottom of the window, and stop us. */ - terminal_goto_xy (0, screenheight - 1); - terminal_clear_to_eol (); - fflush (stdout); - terminal_unprep_terminal (); - signal (sig, *old_signal_handler); - UNBLOCK_SIGNAL (sig); - kill (getpid (), sig); - - /* The program is returning now. Restore our signal handler, - turn on terminal handling, redraw the screen, and place the - cursor where it belongs. */ - terminal_prep_terminal (); - *old_signal_handler = (SigHandler *) signal (sig, info_signal_handler); - redisplay_after_signal (); - fflush (stdout); - } - break; - -#if defined (SIGWINCH) && defined(SIGCONT) - case SIGCONT: - if(old_CONT) - (void)(old_CONT)(sig); - /* pretend a SIGWINCH in case the terminal window size has changed - while we've been asleep */ - /* FALLTROUGH */ -#endif /* defined (SIGWINCH) && defined(SIGCONT) */ - -#if defined (SIGWINCH) - case SIGWINCH: - { - /* Turn off terminal IO, tell our parent that the window has changed, - then reinitialize the terminal and rebuild our windows. */ - old_signal_handler = &old_WINCH; - terminal_goto_xy (0, 0); - fflush (stdout); - terminal_unprep_terminal (); - signal (sig, *old_signal_handler); - UNBLOCK_SIGNAL (sig); - kill (getpid (), sig); - - /* After our old signal handler returns... */ - terminal_get_screen_size (); - terminal_prep_terminal (); - display_initialize_display (screenwidth, screenheight); - window_new_screen_size (screenwidth, screenheight, (VFunction *)NULL); - *old_signal_handler = (SigHandler *) signal (sig, info_signal_handler); - redisplay_after_signal (); - } - break; -#endif /* SIGWINCH */ - } -} diff --git a/gnu/usr.bin/texinfo/info/signals.h b/gnu/usr.bin/texinfo/info/signals.h deleted file mode 100644 index 8fb77f8..0000000 --- a/gnu/usr.bin/texinfo/info/signals.h +++ /dev/null @@ -1,85 +0,0 @@ -/* signals.h -- Header to include system dependent signal definitions. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#ifndef _SIGNALS_H_ -#define _SIGNALS_H_ - -#include <signal.h> - -#define HAVE_SIGSETMASK - -#if !defined (_POSIX_VERSION) && !defined (sigmask) -# define sigmask(x) (1 << ((x)-1)) -#endif /* !POSIX && !sigmask */ - -#if !defined (_POSIX_VERSION) -# if !defined (SIG_BLOCK) -# define SIG_UNBLOCK 1 -# define SIG_BLOCK 2 -# define SIG_SETMASK 3 -# endif /* SIG_BLOCK */ - -/* Type of a signal set. */ -# define sigset_t int - -/* Make SET have no signals in it. */ -# define sigemptyset(set) (*(set) = (sigset_t)0x0) - -/* Make SET have the full range of signal specifications possible. */ -# define sigfillset(set) (*(set) = (sigset_t)0xffffffffff) - -/* Add SIG to the contents of SET. */ -# define sigaddset(set, sig) *(set) |= sigmask (sig) - -/* Delete SIG from the contents of SET. */ -# define sigdelset(set, sig) *(set) &= ~(sigmask (sig)) - -/* Tell if SET contains SIG. */ -# define sigismember(set, sig) (*(set) & (sigmask (sig))) - -/* Suspend the process until the reception of one of the signals - not present in SET. */ -# define sigsuspend(set) sigpause (*(set)) -#endif /* !_POSIX_VERSION */ - -/* These definitions are used both in POSIX and non-POSIX implementations. */ - -#define BLOCK_SIGNAL(sig) \ - do { \ - sigset_t nvar, ovar; \ - sigemptyset (&nvar); \ - sigemptyset (&ovar); \ - sigaddset (&nvar, sig); \ - sigprocmask (SIG_BLOCK, &nvar, &ovar); \ - } while (0) - -#define UNBLOCK_SIGNAL(sig) \ - do { \ - sigset_t nvar, ovar; \ - sigemptyset (&ovar); \ - sigemptyset (&nvar); \ - sigaddset (&nvar, sig); \ - sigprocmask (SIG_UNBLOCK, &nvar, &ovar); \ - } while (0) - -#endif /* !_SIGNALS_H_ */ diff --git a/gnu/usr.bin/texinfo/info/termdep.h b/gnu/usr.bin/texinfo/info/termdep.h deleted file mode 100644 index f4b6634..0000000 --- a/gnu/usr.bin/texinfo/info/termdep.h +++ /dev/null @@ -1,64 +0,0 @@ -/* termdep.h -- System things that terminal.c depends on. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#if defined (HAVE_SYS_FCNTL_H) -#include <sys/fcntl.h> -#else -#include <fcntl.h> -#endif /* !HAVE_SYS_FCNTL_H */ - -#if defined (HAVE_TERMIO_H) -#include <termio.h> -#include <string.h> -#if defined (HAVE_SYS_PTEM_H) -#if !defined (M_XENIX) -#include <sys/stream.h> -#include <sys/ptem.h> -#undef TIOCGETC -#else /* M_XENIX */ -#define tchars tc -#endif /* M_XENIX */ -#endif /* HAVE_SYS_PTEM_H */ -#else /* !HAVE_TERMIO_H */ -#include <sys/file.h> -#include <sgtty.h> -#include <strings.h> -#endif /* !HAVE_TERMIO_H */ - -#if defined (HAVE_SYS_TTOLD_H) -#include <sys/ttold.h> -#endif /* HAVE_SYS_TTOLD_H */ - -#if !defined (HAVE_RINDEX) -#undef index -#undef rindex -#define index strchr -#define rindex strrchr -#endif - -#if !defined (HAVE_BCOPY) -#undef bcopy -#define bcopy(source, dest, count) memcpy(dest, source, count) -#endif - -/* eof */ diff --git a/gnu/usr.bin/texinfo/info/terminal.c b/gnu/usr.bin/texinfo/info/terminal.c deleted file mode 100644 index 3c92337..0000000 --- a/gnu/usr.bin/texinfo/info/terminal.c +++ /dev/null @@ -1,768 +0,0 @@ -/* terminal.c -- How to handle the physical terminal for Info. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - This file has appeared in prior works by the Free Software Foundation; - thus it carries copyright dates from 1988 through 1993. - - Copyright (C) 1988, 1989, 1990, 1991, 1992, 1993 Free Software - Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include <stdio.h> -#include <stdlib.h> -#include <sys/types.h> -#include "terminal.h" -#include "termdep.h" - -extern void *xmalloc (), *xrealloc (); - -/* The Unix termcap interface code. */ - -extern int tgetnum (), tgetflag (), tgetent (); -extern char *tgetstr (), *tgoto (); -extern char *getenv (); -extern void tputs (); - -/* Function "hooks". If you make one of these point to a function, that - function is called when appropriate instead of its namesake. Your - function is called with exactly the same arguments that were passed - to the namesake function. */ -VFunction *terminal_begin_inverse_hook = (VFunction *)NULL; -VFunction *terminal_end_inverse_hook = (VFunction *)NULL; -VFunction *terminal_prep_terminal_hook = (VFunction *)NULL; -VFunction *terminal_unprep_terminal_hook = (VFunction *)NULL; -VFunction *terminal_up_line_hook = (VFunction *)NULL; -VFunction *terminal_down_line_hook = (VFunction *)NULL; -VFunction *terminal_clear_screen_hook = (VFunction *)NULL; -VFunction *terminal_clear_to_eol_hook = (VFunction *)NULL; -VFunction *terminal_get_screen_size_hook = (VFunction *)NULL; -VFunction *terminal_goto_xy_hook = (VFunction *)NULL; -VFunction *terminal_initialize_terminal_hook = (VFunction *)NULL; -VFunction *terminal_new_terminal_hook = (VFunction *)NULL; -VFunction *terminal_put_text_hook = (VFunction *)NULL; -VFunction *terminal_ring_bell_hook = (VFunction *)NULL; -VFunction *terminal_write_chars_hook = (VFunction *)NULL; -VFunction *terminal_scroll_terminal_hook = (VFunction *)NULL; - -/* **************************************************************** */ -/* */ -/* Terminal and Termcap */ -/* */ -/* **************************************************************** */ - -/* On Solaris2, sys/types.h #includes sys/reg.h, which #defines PC. - Unfortunately, PC is a global variable used by the termcap library. */ -#undef PC - -/* TERMCAP requires these variables, whether we access them or not. */ -char PC; -char *BC, *UP; -short ospeed; - -/* A buffer which holds onto the current terminal description, and a pointer - used to float within it. */ -static char *term_buffer = (char *)NULL; -static char *term_string_buffer = (char *)NULL; - -/* Some strings to control terminal actions. These are output by tputs (). */ -static char *term_goto, *term_clreol, *term_cr, *term_clrpag; -static char *term_begin_use, *term_end_use; -static char *term_AL, *term_DL, *term_al, *term_dl; - -/* How to go up a line. */ -static char *term_up; - -/* How to go down a line. */ -static char *term_dn; - -/* An audible bell, if the terminal can be made to make noise. */ -static char *audible_bell; - -/* A visible bell, if the terminal can be made to flash the screen. */ -static char *visible_bell; - -/* The string to write to turn on the meta key, if this term has one. */ -static char *term_mm; - -/* The string to write to turn off the meta key, if this term has one. */ -static char *term_mo; - -/* The string to turn on inverse mode, if this term has one. */ -static char *term_invbeg; - -/* The string to turn off inverse mode, if this term has one. */ -static char *term_invend; - -/* The string to turn on keypad transmit mode, if this term has one. */ -static char *term_ks; - -/* The string to turn off keypad transmit mode, if this term has one. */ -static char *term_ke; - -static void -output_character_function (c) - int c; -{ - putc (c, stdout); -} - -/* Macro to send STRING to the terminal. */ -#define send_to_terminal(string) \ - do { \ - if (string) \ - tputs (string, 1, output_character_function); \ - } while (0) - -/* Tell the terminal that we will be doing cursor addressable motion. */ -static void -terminal_begin_using_terminal () -{ - send_to_terminal (term_begin_use); - if (term_ks) - send_to_terminal(term_ks); -} - -/* Tell the terminal that we will not be doing any more cursor addressable - motion. */ -static void -terminal_end_using_terminal () -{ - if (term_ke) - send_to_terminal(term_ke); - send_to_terminal (term_end_use); -} - -/* **************************************************************** */ -/* */ -/* Necessary Terminal Functions */ -/* */ -/* **************************************************************** */ - -/* The functions and variables on this page implement the user visible - portion of the terminal interface. */ - -/* The width and height of the terminal. */ -int screenwidth, screenheight; - -/* Non-zero means this terminal can't really do anything. */ -int terminal_is_dumb_p = 0; - -/* Non-zero means that this terminal has a meta key. */ -int terminal_has_meta_p = 0; - -/* Non-zero means that this terminal can produce a visible bell. */ -int terminal_has_visible_bell_p = 0; - -/* Non-zero means to use that visible bell if at all possible. */ -int terminal_use_visible_bell_p = 0; - -/* Non-zero means that the terminal can do scrolling. */ -int terminal_can_scroll = 0; - -/* The key sequences output by the arrow keys, if this terminal has any. */ -/* Also use PageUp, PageDown, Home, End, if available. */ -char *term_ku, *term_kd, *term_kr, *term_kl; -char *term_kP, *term_kN, *term_kh, *term_kH; - -/* Move the cursor to the terminal location of X and Y. */ -void -terminal_goto_xy (x, y) - int x, y; -{ - if (terminal_goto_xy_hook) - (*terminal_goto_xy_hook) (x, y); - else - { - if (term_goto) - tputs (tgoto (term_goto, x, y), 1, output_character_function); - } -} - -/* Print STRING to the terminal at the current position. */ -void -terminal_put_text (string) - char *string; -{ - if (terminal_put_text_hook) - (*terminal_put_text_hook) (string); - else - { - printf ("%s", string); - } -} - -/* Print NCHARS from STRING to the terminal at the current position. */ -void -terminal_write_chars (string, nchars) - char *string; - int nchars; -{ - if (terminal_write_chars_hook) - (*terminal_write_chars_hook) (string, nchars); - else - { - if (nchars) - fwrite (string, 1, nchars, stdout); - } -} - -/* Clear from the current position of the cursor to the end of the line. */ -void -terminal_clear_to_eol () -{ - if (terminal_clear_to_eol_hook) - (*terminal_clear_to_eol_hook) (); - else - { - send_to_terminal (term_clreol); - } -} - -/* Clear the entire terminal screen. */ -void -terminal_clear_screen () -{ - if (terminal_clear_screen_hook) - (*terminal_clear_screen_hook) (); - else - { - send_to_terminal (term_clrpag); - } -} - -/* Move the cursor up one line. */ -void -terminal_up_line () -{ - if (terminal_up_line_hook) - (*terminal_up_line_hook) (); - else - { - send_to_terminal (term_up); - } -} - -/* Move the cursor down one line. */ -void -terminal_down_line () -{ - if (terminal_down_line_hook) - (*terminal_down_line_hook) (); - else - { - send_to_terminal (term_dn); - } -} - -/* Turn on reverse video if possible. */ -void -terminal_begin_inverse () -{ - if (terminal_begin_inverse_hook) - (*terminal_begin_inverse_hook) (); - else - { - send_to_terminal (term_invbeg); - } -} - -/* Turn off reverse video if possible. */ -void -terminal_end_inverse () -{ - if (terminal_end_inverse_hook) - (*terminal_end_inverse_hook) (); - else - { - send_to_terminal (term_invend); - } -} - -/* Ring the terminal bell. The bell is run visibly if it both has one and - terminal_use_visible_bell_p is non-zero. */ -void -terminal_ring_bell () -{ - if (terminal_ring_bell_hook) - (*terminal_ring_bell_hook) (); - else - { - if (terminal_has_visible_bell_p && terminal_use_visible_bell_p) - send_to_terminal (visible_bell); - else - send_to_terminal (audible_bell); - } -} - -/* At the line START, delete COUNT lines from the terminal display. */ -static void -terminal_delete_lines (start, count) - int start, count; -{ - int lines; - - /* Normalize arguments. */ - if (start < 0) - start = 0; - - lines = screenheight - start; - terminal_goto_xy (0, start); - if (term_DL) - tputs (tgoto (term_DL, 0, count), lines, output_character_function); - else - { - while (count--) - tputs (term_dl, lines, output_character_function); - } - - fflush (stdout); -} - -/* At the line START, insert COUNT lines in the terminal display. */ -static void -terminal_insert_lines (start, count) - int start, count; -{ - int lines; - - /* Normalize arguments. */ - if (start < 0) - start = 0; - - lines = screenheight - start; - terminal_goto_xy (0, start); - - if (term_AL) - tputs (tgoto (term_AL, 0, count), lines, output_character_function); - else - { - while (count--) - tputs (term_al, lines, output_character_function); - } - - fflush (stdout); -} - -/* Scroll an area of the terminal, starting with the region from START - to END, AMOUNT lines. If AMOUNT is negative, the lines are scrolled - towards the top of the screen, else they are scrolled towards the - bottom of the screen. */ -void -terminal_scroll_terminal (start, end, amount) - int start, end, amount; -{ - if (!terminal_can_scroll) - return; - - /* Any scrolling at all? */ - if (amount == 0) - return; - - if (terminal_scroll_terminal_hook) - (*terminal_scroll_terminal_hook) (start, end, amount); - else - { - /* If we are scrolling down, delete AMOUNT lines at END. Then insert - AMOUNT lines at START. */ - if (amount > 0) - { - terminal_delete_lines (end, amount); - terminal_insert_lines (start, amount); - } - - /* If we are scrolling up, delete AMOUNT lines before START. This - actually does the upwards scroll. Then, insert AMOUNT lines - after the already scrolled region (i.e., END - AMOUNT). */ - if (amount < 0) - { - int abs_amount = -amount; - terminal_delete_lines (start - abs_amount, abs_amount); - terminal_insert_lines (end - abs_amount, abs_amount); - } - } -} - -/* Re-initialize the terminal considering that the TERM/TERMCAP variable - has changed. */ -void -terminal_new_terminal (terminal_name) - char *terminal_name; -{ - if (terminal_new_terminal_hook) - (*terminal_new_terminal_hook) (terminal_name); - else - { - terminal_initialize_terminal (terminal_name); - } -} - -/* Set the global variables SCREENWIDTH and SCREENHEIGHT. */ -void -terminal_get_screen_size () -{ - if (terminal_get_screen_size_hook) - (*terminal_get_screen_size_hook) (); - else - { - screenwidth = screenheight = 0; - -#if defined (TIOCGWINSZ) - { - struct winsize window_size; - - if (ioctl (fileno (stdout), TIOCGWINSZ, &window_size) == 0) - { - screenwidth = (int) window_size.ws_col; - screenheight = (int) window_size.ws_row; - } - } -#endif /* TIOCGWINSZ */ - - /* Environment variable COLUMNS overrides setting of "co". */ - if (screenwidth <= 0) - { - char *sw = getenv ("COLUMNS"); - - if (sw) - screenwidth = atoi (sw); - - if (screenwidth <= 0) - screenwidth = tgetnum ("co"); - } - - /* Environment variable LINES overrides setting of "li". */ - if (screenheight <= 0) - { - char *sh = getenv ("LINES"); - - if (sh) - screenheight = atoi (sh); - - if (screenheight <= 0) - screenheight = tgetnum ("li"); - } - - /* If all else fails, default to 80x24 terminal. */ - if (screenwidth <= 0) - screenwidth = 80; - - if (screenheight <= 0) - screenheight = 24; - } -} - -/* Initialize the terminal which is known as TERMINAL_NAME. If this terminal - doesn't have cursor addressability, TERMINAL_IS_DUMB_P becomes non-zero. - The variables SCREENHEIGHT and SCREENWIDTH are set to the dimensions that - this terminal actually has. The variable TERMINAL_HAS_META_P becomes non- - zero if this terminal supports a Meta key. Finally, the terminal screen is - cleared. */ -void -terminal_initialize_terminal (terminal_name) - char *terminal_name; -{ - char *term, *buffer; - - terminal_is_dumb_p = 0; - - if (terminal_initialize_terminal_hook) - { - (*terminal_initialize_terminal_hook) (terminal_name); - return; - } - - term = terminal_name ? terminal_name : getenv ("TERM"); - - if (!term_string_buffer) - term_string_buffer = (char *)xmalloc (2048); - - if (!term_buffer) - term_buffer = (char *)xmalloc (2048); - - buffer = term_string_buffer; - - term_clrpag = term_cr = term_clreol = (char *)NULL; - - if (!term) - term = "dumb"; - - if (tgetent (term_buffer, term) <= 0) - { - terminal_is_dumb_p = 1; - screenwidth = 80; - screenheight = 24; - term_cr = "\r"; - term_up = term_dn = audible_bell = visible_bell = (char *)NULL; - term_ku = term_kd = term_kl = term_kr = (char *)NULL; - term_kP = term_kN = term_kh = term_kH = (char *)NULL; - return; - } - - BC = tgetstr ("pc", &buffer); - PC = BC ? *BC : 0; - -#if defined (TIOCGETP) - { - struct sgttyb sg; - - if (ioctl (fileno (stdout), TIOCGETP, &sg) != -1) - ospeed = sg.sg_ospeed; - else - ospeed = B9600; - } -#else - ospeed = B9600; -#endif /* !TIOCGETP */ - - term_cr = tgetstr ("cr", &buffer); - term_clreol = tgetstr ("ce", &buffer); - term_clrpag = tgetstr ("cl", &buffer); - term_goto = tgetstr ("cm", &buffer); - - /* Find out about this terminals scrolling capability. */ - term_AL = tgetstr ("AL", &buffer); - term_DL = tgetstr ("DL", &buffer); - term_al = tgetstr ("al", &buffer); - term_dl = tgetstr ("dl", &buffer); - - terminal_can_scroll = ((term_AL || term_al) && (term_DL || term_dl)); - - term_invbeg = tgetstr ("mr", &buffer); - if (term_invbeg) - term_invend = tgetstr ("me", &buffer); - else - term_invend = (char *)NULL; - - if (!term_cr) - term_cr = "\r"; - - terminal_get_screen_size (); - - term_up = tgetstr ("up", &buffer); - term_dn = tgetstr ("dn", &buffer); - visible_bell = tgetstr ("vb", &buffer); - terminal_has_visible_bell_p = (visible_bell != (char *)NULL); - audible_bell = tgetstr ("bl", &buffer); - if (!audible_bell) - audible_bell = "\007"; - term_begin_use = tgetstr ("ti", &buffer); - term_end_use = tgetstr ("te", &buffer); - - /* Check to see if this terminal has a meta key. */ - terminal_has_meta_p = (tgetflag ("km") || tgetflag ("MT")); - if (terminal_has_meta_p) - { - term_mm = tgetstr ("mm", &buffer); - term_mo = tgetstr ("mo", &buffer); - } - else - { - term_mm = (char *)NULL; - term_mo = (char *)NULL; - } - - /* Attempt to find the arrow keys. */ - term_ku = tgetstr ("ku", &buffer); - term_kd = tgetstr ("kd", &buffer); - term_kr = tgetstr ("kr", &buffer); - term_kl = tgetstr ("kl", &buffer); - term_kP = tgetstr ("kP", &buffer); - term_kN = tgetstr ("kN", &buffer); - term_kh = tgetstr ("kh", &buffer); - term_kH = tgetstr ("kH", &buffer); - - /* Enable keypad and cursor keys if ks defined */ - term_ks = tgetstr ("ks", &buffer); - term_ke = tgetstr ("ke", &buffer); - - /* If this terminal is not cursor addressable, then it is really dumb. */ - if (!term_goto) - terminal_is_dumb_p = 1; - - terminal_begin_using_terminal (); -} - -/* **************************************************************** */ -/* */ -/* How to Read Characters From the Terminal */ -/* */ -/* **************************************************************** */ - -#if defined (TIOCGETC) -/* A buffer containing the terminal interrupt characters upon entry - to Info. */ -struct tchars original_tchars; -#endif - -#if defined (TIOCGLTC) -/* A buffer containing the local terminal mode characters upon entry - to Info. */ -struct ltchars original_ltchars; -#endif - -#if defined (HAVE_TERMIO_H) -/* A buffer containing the terminal mode flags upon entry to info. */ -struct termio original_termio, ttybuff; -#else /* !HAVE_TERMIO_H */ -/* Buffers containing the terminal mode flags upon entry to info. */ -int original_tty_flags = 0; -int original_lmode; -struct sgttyb ttybuff; -#endif /* !HAVE_TERMIO_H */ - -/* Prepare to start using the terminal to read characters singly. */ -void -terminal_prep_terminal () -{ - int tty; - - if (terminal_prep_terminal_hook) - { - (*terminal_prep_terminal_hook) (); - return; - } - - tty = fileno (stdin); - -#if defined (HAVE_TERMIO_H) - ioctl (tty, TCGETA, &original_termio); - ioctl (tty, TCGETA, &ttybuff); - ttybuff.c_iflag &= (~ISTRIP & ~INLCR & ~IGNCR & ~ICRNL & ~IXON); - ttybuff.c_oflag &= (~ONLCR & ~OCRNL); - ttybuff.c_lflag &= (~ICANON & ~ECHO); - - ttybuff.c_cc[VMIN] = 1; - ttybuff.c_cc[VTIME] = 0; - - if (ttybuff.c_cc[VINTR] = '\177') - ttybuff.c_cc[VINTR] = -1; - - if (ttybuff.c_cc[VQUIT] = '\177') - ttybuff.c_cc[VQUIT] = -1; - - ioctl (tty, TCSETA, &ttybuff); - -#else /* !HAVE_TERMIO_H */ - - ioctl (tty, TIOCGETP, &ttybuff); - - if (!original_tty_flags) - original_tty_flags = ttybuff.sg_flags; - - /* Make this terminal pass 8 bits around while we are using it. */ -#if defined (PASS8) - ttybuff.sg_flags |= PASS8; -#endif /* PASS8 */ - -#if defined (TIOCLGET) && defined (LPASS8) - { - int flags; - ioctl (tty, TIOCLGET, &flags); - original_lmode = flags; - flags |= LPASS8; - ioctl (tty, TIOCLSET, &flags); - } -#endif /* TIOCLGET && LPASS8 */ - -#if defined (TIOCGETC) - { - struct tchars temp; - - ioctl (tty, TIOCGETC, &original_tchars); - temp = original_tchars; - - /* C-s and C-q. */ - temp.t_startc = temp.t_stopc = -1; - - /* Often set to C-d. */ - temp.t_eofc = -1; - - /* If the a quit or interrupt character conflicts with one of our - commands, then make it go away. */ - if (temp.t_intrc == '\177') - temp.t_intrc = -1; - - if (temp.t_quitc == '\177') - temp.t_quitc = -1; - - ioctl (tty, TIOCSETC, &temp); - } -#endif /* TIOCGETC */ - -#if defined (TIOCGLTC) - { - struct ltchars temp; - - ioctl (tty, TIOCGLTC, &original_ltchars); - temp = original_ltchars; - - /* Make the interrupt keys go away. Just enough to make people happy. */ - temp.t_lnextc = -1; /* C-v. */ - temp.t_dsuspc = -1; /* C-y. */ - temp.t_flushc = -1; /* C-o. */ - ioctl (tty, TIOCSLTC, &temp); - } -#endif /* TIOCGLTC */ - - ttybuff.sg_flags &= ~ECHO; - ttybuff.sg_flags |= CBREAK; - ioctl (tty, TIOCSETN, &ttybuff); -#endif /* !HAVE_TERMIO_H */ - terminal_begin_using_terminal(); -} - -/* Restore the tty settings back to what they were before we started using - this terminal. */ -void -terminal_unprep_terminal () -{ - int tty; - - if (terminal_unprep_terminal_hook) - { - (*terminal_unprep_terminal_hook) (); - return; - } - - tty = fileno (stdin); - -#if defined (HAVE_TERMIO_H) - ioctl (tty, TCSETA, &original_termio); -#else /* !HAVE_TERMIO_H */ - ioctl (tty, TIOCGETP, &ttybuff); - ttybuff.sg_flags = original_tty_flags; - ioctl (tty, TIOCSETN, &ttybuff); - -#if defined (TIOCGETC) - ioctl (tty, TIOCSETC, &original_tchars); -#endif /* TIOCGETC */ - -#if defined (TIOCGLTC) - ioctl (tty, TIOCSLTC, &original_ltchars); -#endif /* TIOCGLTC */ - -#if defined (TIOCLGET) && defined (LPASS8) - ioctl (tty, TIOCLSET, &original_lmode); -#endif /* TIOCLGET && LPASS8 */ - -#endif /* !HAVE_TERMIO_H */ - terminal_end_using_terminal (); -} - diff --git a/gnu/usr.bin/texinfo/info/terminal.h b/gnu/usr.bin/texinfo/info/terminal.h deleted file mode 100644 index a86a23c..0000000 --- a/gnu/usr.bin/texinfo/info/terminal.h +++ /dev/null @@ -1,126 +0,0 @@ -/* terminal.h -- The external interface to terminal I/O. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#ifndef _TERMINAL_H_ -#define _TERMINAL_H_ - -/* We use the following data type to talk about pointers to functions. */ -#if !defined (__FUNCTION_DEF) -# define __FUNCTION_DEF -typedef int Function (); -typedef void VFunction (); -#endif /* _FUNCTION_DEF */ - -/* For almost every function externally visible from terminal.c, there is - a corresponding "hook" function which can be bound in order to replace - the functionality of the one found in terminal.c. This is how we go - about implemented X window display. */ - -/* The width and height of the terminal. */ -extern int screenwidth, screenheight; - -/* Non-zero means this terminal can't really do anything. */ -extern int terminal_is_dumb_p; - -/* Non-zero means that this terminal has a meta key. */ -extern int terminal_has_meta_p; - -/* Non-zero means that this terminal can produce a visible bell. */ -extern int terminal_has_visible_bell_p; - -/* Non-zero means to use that visible bell if at all possible. */ -extern int terminal_use_visible_bell_p; - -/* Non-zero means that this terminal can scroll lines up and down. */ -extern int terminal_can_scroll; - -/* Initialize the terminal which is known as TERMINAL_NAME. If this terminal - doesn't have cursor addressability, TERMINAL_IS_DUMB_P becomes non-zero. - The variables SCREENHEIGHT and SCREENWIDTH are set to the dimensions that - this terminal actually has. The variable TERMINAL_HAS_META_P becomes non- - zero if this terminal supports a Meta key. */ -extern void terminal_initialize_terminal (); -extern VFunction *terminal_initialize_terminal_hook; - -/* Return the current screen width and height in the variables - SCREENWIDTH and SCREENHEIGHT. */ -extern void terminal_get_screen_size (); -extern VFunction *terminal_get_screen_size_hook; - -/* Save and restore tty settings. */ -extern void terminal_prep_terminal (), terminal_unprep_terminal (); -extern VFunction *terminal_prep_terminal_hook, *terminal_unprep_terminal_hook; - -/* Re-initialize the terminal to TERMINAL_NAME. */ -extern void terminal_new_terminal (); -extern VFunction *terminal_new_terminal_hook; - -/* Move the cursor to the terminal location of X and Y. */ -extern void terminal_goto_xy (); -extern VFunction *terminal_goto_xy_hook; - -/* Print STRING to the terminal at the current position. */ -extern void terminal_put_text (); -extern VFunction *terminal_put_text_hook; - -/* Print NCHARS from STRING to the terminal at the current position. */ -extern void terminal_write_chars (); -extern VFunction *terminal_write_chars_hook; - -/* Clear from the current position of the cursor to the end of the line. */ -extern void terminal_clear_to_eol (); -extern VFunction *terminal_clear_to_eol_hook; - -/* Clear the entire terminal screen. */ -extern void terminal_clear_screen (); -extern VFunction *terminal_clear_screen_hook; - -/* Move the cursor up one line. */ -extern void terminal_up_line (); -extern VFunction *terminal_up_line_hook; - -/* Move the cursor down one line. */ -extern void terminal_down_line (); -extern VFunction *terminal_down_line_hook; - -/* Turn on reverse video if possible. */ -extern void terminal_begin_inverse (); -extern VFunction *terminal_begin_inverse_hook; - -/* Turn off reverse video if possible. */ -extern void terminal_end_inverse (); -extern VFunction *terminal_end_inverse_hook; - -/* Scroll an area of the terminal, starting with the region from START - to END, AMOUNT lines. If AMOUNT is negative, the lines are scrolled - towards the top of the screen, else they are scrolled towards the - bottom of the screen. */ -extern void terminal_scroll_terminal (); -extern VFunction *terminal_scroll_terminal_hook; - -/* Ring the terminal bell. The bell is run visibly if it both has one and - terminal_use_visible_bell_p is non-zero. */ -extern void terminal_ring_bell (); -extern VFunction *terminal_ring_bell_hook; - -#endif /* !_TERMINAL_H_ */ diff --git a/gnu/usr.bin/texinfo/info/tilde.c b/gnu/usr.bin/texinfo/info/tilde.c deleted file mode 100644 index c01951b..0000000 --- a/gnu/usr.bin/texinfo/info/tilde.c +++ /dev/null @@ -1,379 +0,0 @@ -/* tilde.c -- Tilde expansion code (~/foo := $HOME/foo). */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - This file has appeared in prior works by the Free Software Foundation; - thus it carries copyright dates from 1988 through 1993. - - Copyright (C) 1988, 1989, 1990, 1991, 1992, 1993 Free Software - Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#if defined (__GNUC__) -# define alloca __builtin_alloca -#else /* !__GNUC__ */ -# if defined (_AIX) - #pragma alloca -# else /* !_AIX */ -# if defined (HAVE_ALLOCA_H) -# include <alloca.h> -# endif /* HAVE_ALLOCA_H */ -# endif /* !AIX */ -#endif /* !__GNUC__ */ - -#include "tilde.h" -#include <pwd.h> - -#if !defined (savestring) -#define savestring(x) (char *)strcpy (xmalloc (1 + strlen (x)), (x)) -#endif /* !savestring */ - -#if !defined (NULL) -# define NULL 0x0 -#endif - -#if defined (TEST) || defined (STATIC_MALLOC) -static char *xmalloc (), *xrealloc (); -#else -extern char *xmalloc (), *xrealloc (); -#endif /* TEST || STATIC_MALLOC */ - -/* The default value of tilde_additional_prefixes. This is set to - whitespace preceding a tilde so that simple programs which do not - perform any word separation get desired behaviour. */ -static char *default_prefixes[] = - { " ~", "\t~", (char *)NULL }; - -/* The default value of tilde_additional_suffixes. This is set to - whitespace or newline so that simple programs which do not - perform any word separation get desired behaviour. */ -static char *default_suffixes[] = - { " ", "\n", (char *)NULL }; - -/* If non-null, this contains the address of a function to call if the - standard meaning for expanding a tilde fails. The function is called - with the text (sans tilde, as in "foo"), and returns a malloc()'ed string - which is the expansion, or a NULL pointer if there is no expansion. */ -Function *tilde_expansion_failure_hook = (Function *)NULL; - -/* When non-null, this is a NULL terminated array of strings which - are duplicates for a tilde prefix. Bash uses this to expand - `=~' and `:~'. */ -char **tilde_additional_prefixes = default_prefixes; - -/* When non-null, this is a NULL terminated array of strings which match - the end of a username, instead of just "/". Bash sets this to - `:' and `=~'. */ -char **tilde_additional_suffixes = default_suffixes; - -/* Find the start of a tilde expansion in STRING, and return the index of - the tilde which starts the expansion. Place the length of the text - which identified this tilde starter in LEN, excluding the tilde itself. */ -static int -tilde_find_prefix (string, len) - char *string; - int *len; -{ - register int i, j, string_len; - register char **prefixes = tilde_additional_prefixes; - - string_len = strlen (string); - *len = 0; - - if (!*string || *string == '~') - return (0); - - if (prefixes) - { - for (i = 0; i < string_len; i++) - { - for (j = 0; prefixes[j]; j++) - { - if (strncmp (string + i, prefixes[j], strlen (prefixes[j])) == 0) - { - *len = strlen (prefixes[j]) - 1; - return (i + *len); - } - } - } - } - return (string_len); -} - -/* Find the end of a tilde expansion in STRING, and return the index of - the character which ends the tilde definition. */ -static int -tilde_find_suffix (string) - char *string; -{ - register int i, j, string_len; - register char **suffixes = tilde_additional_suffixes; - - string_len = strlen (string); - - for (i = 0; i < string_len; i++) - { - if (string[i] == '/' || !string[i]) - break; - - for (j = 0; suffixes && suffixes[j]; j++) - { - if (strncmp (string + i, suffixes[j], strlen (suffixes[j])) == 0) - return (i); - } - } - return (i); -} - -/* Return a new string which is the result of tilde expanding STRING. */ -char * -tilde_expand (string) - char *string; -{ - char *result, *tilde_expand_word (); - int result_size, result_index; - - result_size = result_index = 0; - result = (char *)NULL; - - /* Scan through STRING expanding tildes as we come to them. */ - while (1) - { - register int start, end; - char *tilde_word, *expansion; - int len; - - /* Make START point to the tilde which starts the expansion. */ - start = tilde_find_prefix (string, &len); - - /* Copy the skipped text into the result. */ - if ((result_index + start + 1) > result_size) - result = (char *)xrealloc (result, 1 + (result_size += (start + 20))); - - strncpy (result + result_index, string, start); - result_index += start; - - /* Advance STRING to the starting tilde. */ - string += start; - - /* Make END be the index of one after the last character of the - username. */ - end = tilde_find_suffix (string); - - /* If both START and END are zero, we are all done. */ - if (!start && !end) - break; - - /* Expand the entire tilde word, and copy it into RESULT. */ - tilde_word = (char *)xmalloc (1 + end); - strncpy (tilde_word, string, end); - tilde_word[end] = '\0'; - string += end; - - expansion = tilde_expand_word (tilde_word); - free (tilde_word); - - len = strlen (expansion); - if ((result_index + len + 1) > result_size) - result = (char *)xrealloc (result, 1 + (result_size += (len + 20))); - - strcpy (result + result_index, expansion); - result_index += len; - free (expansion); - } - - result[result_index] = '\0'; - - return (result); -} - -/* Do the work of tilde expansion on FILENAME. FILENAME starts with a - tilde. If there is no expansion, call tilde_expansion_failure_hook. */ -char * -tilde_expand_word (filename) - char *filename; -{ - char *dirname; - - dirname = filename ? savestring (filename) : (char *)NULL; - - if (dirname && *dirname == '~') - { - char *temp_name; - if (!dirname[1] || dirname[1] == '/') - { - /* Prepend $HOME to the rest of the string. */ - char *temp_home = (char *)getenv ("HOME"); - - /* If there is no HOME variable, look up the directory in - the password database. */ - if (!temp_home) - { -/* extern struct passwd *getpwuid (); */ - struct passwd *entry; - - entry = getpwuid (getuid ()); - if (entry) - temp_home = entry->pw_dir; - } - - temp_name = (char *)alloca (1 + strlen (&dirname[1]) - + (temp_home ? strlen (temp_home) : 0)); - temp_name[0] = '\0'; - if (temp_home) - strcpy (temp_name, temp_home); - strcat (temp_name, &dirname[1]); - free (dirname); - dirname = savestring (temp_name); - } - else - { - struct passwd *getpwnam (), *user_entry; - char *username = (char *)alloca (257); - int i, c; - - for (i = 1; c = dirname[i]; i++) - { - if (c == '/') - break; - else - username[i - 1] = c; - } - username[i - 1] = '\0'; - - if (!(user_entry = getpwnam (username))) - { - /* If the calling program has a special syntax for - expanding tildes, and we couldn't find a standard - expansion, then let them try. */ - if (tilde_expansion_failure_hook) - { - char *expansion; - - expansion = - (char *)(*tilde_expansion_failure_hook) (username); - - if (expansion) - { - temp_name = (char *)alloca (1 + strlen (expansion) - + strlen (&dirname[i])); - strcpy (temp_name, expansion); - strcat (temp_name, &dirname[i]); - free (expansion); - goto return_name; - } - } - /* We shouldn't report errors. */ - } - else - { - temp_name = (char *)alloca (1 + strlen (user_entry->pw_dir) - + strlen (&dirname[i])); - strcpy (temp_name, user_entry->pw_dir); - strcat (temp_name, &dirname[i]); - return_name: - free (dirname); - dirname = savestring (temp_name); - } - endpwent (); - } - } - return (dirname); -} - - -#if defined (TEST) -#undef NULL -#include <stdio.h> - -main (argc, argv) - int argc; - char **argv; -{ - char *result, line[512]; - int done = 0; - - while (!done) - { - printf ("~expand: "); - fflush (stdout); - - if (!gets (line)) - strcpy (line, "done"); - - if ((strcmp (line, "done") == 0) || - (strcmp (line, "quit") == 0) || - (strcmp (line, "exit") == 0)) - { - done = 1; - break; - } - - result = tilde_expand (line); - printf (" --> %s\n", result); - free (result); - } - exit (0); -} - -static void memory_error_and_abort (); - -static char * -xmalloc (bytes) - int bytes; -{ - char *temp = (char *)malloc (bytes); - - if (!temp) - memory_error_and_abort (); - return (temp); -} - -static char * -xrealloc (pointer, bytes) - char *pointer; - int bytes; -{ - char *temp; - - if (!pointer) - temp = (char *)malloc (bytes); - else - temp = (char *)realloc (pointer, bytes); - - if (!temp) - memory_error_and_abort (); - - return (temp); -} - -static void -memory_error_and_abort () -{ - fprintf (stderr, "readline: Out of virtual memory!\n"); - abort (); -} - -/* - * Local variables: - * compile-command: "gcc -g -DTEST -o tilde tilde.c" - * end: - */ -#endif /* TEST */ - diff --git a/gnu/usr.bin/texinfo/info/tilde.h b/gnu/usr.bin/texinfo/info/tilde.h deleted file mode 100644 index b48fc19..0000000 --- a/gnu/usr.bin/texinfo/info/tilde.h +++ /dev/null @@ -1,62 +0,0 @@ -/* tilde.h: Externally available variables and function in libtilde.a. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - This file has appeared in prior works by the Free Software Foundation; - thus it carries copyright dates from 1988 through 1993. - - Copyright (C) 1988, 1989, 1990, 1991, 1992, 1993 Free Software - Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#ifndef _TILDE_H_ -#define _TILDE_H_ - -/* Function pointers can be declared as (Function *)foo. */ -#if !defined (__FUNCTION_DEF) -# define __FUNCTION_DEF -typedef int Function (); -typedef void VFunction (); -#endif /* _FUNCTION_DEF */ - -/* If non-null, this contains the address of a function to call if the - standard meaning for expanding a tilde fails. The function is called - with the text (sans tilde, as in "foo"), and returns a malloc()'ed string - which is the expansion, or a NULL pointer if there is no expansion. */ -extern Function *tilde_expansion_failure_hook; - -/* When non-null, this is a NULL terminated array of strings which - are duplicates for a tilde prefix. Bash uses this to expand - `=~' and `:~'. */ -extern char **tilde_additional_prefixes; - -/* When non-null, this is a NULL terminated array of strings which match - the end of a username, instead of just "/". Bash sets this to - `:' and `=~'. */ -extern char **tilde_additional_suffixes; - -/* Return a new string which is the result of tilde expanding STRING. */ -extern char *tilde_expand (); - -/* Do the work of tilde expansion on FILENAME. FILENAME starts with a - tilde. If there is no expansion, call tilde_expansion_failure_hook. */ -extern char *tilde_expand_word (); - -#endif - diff --git a/gnu/usr.bin/texinfo/info/variables.c b/gnu/usr.bin/texinfo/info/variables.c deleted file mode 100644 index b70af83..0000000 --- a/gnu/usr.bin/texinfo/info/variables.c +++ /dev/null @@ -1,272 +0,0 @@ -/* variables.c -- How to manipulate user visible variables in Info. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include "info.h" -#include "variables.h" - -/* **************************************************************** */ -/* */ -/* User Visible Variables in Info */ -/* */ -/* **************************************************************** */ - -/* Choices used by the completer when reading a zero/non-zero value for - a variable. */ -static char *on_off_choices[] = { "Off", "On", (char *)NULL }; - -VARIABLE_ALIST info_variables[] = { - { "automatic-footnotes", - "When \"On\", footnotes appear and disappear automatically", - &auto_footnotes_p, (char **)on_off_choices }, - - { "automatic-tiling", - "When \"On\", creating or deleting a window resizes other windows", - &auto_tiling_p, (char **)on_off_choices }, - - { "visible-bell", - "When \"On\", flash the screen instead of ringing the bell", - &terminal_use_visible_bell_p, (char **)on_off_choices }, - - { "errors-ring-bell", - "When \"On\", errors cause the bell to ring", - &info_error_rings_bell_p, (char **)on_off_choices }, - - { "gc-compressed-files", - "When \"On\", Info garbage collects files which had to be uncompressed", - &gc_compressed_files, (char **)on_off_choices }, - { "show-index-match", - "When \"On\", the portion of the matched search string is highlighted", - &show_index_match, (char **)on_off_choices }, - - { "scroll-behaviour", - "Controls what happens when scrolling is requested at the end of a node", - &info_scroll_behaviour, (char **)info_scroll_choices }, - - { "scroll-step", - "The number lines to scroll when the cursor moves out of the window", - &window_scroll_step, (char **)NULL }, - - { "ISO-Latin", - "When \"On\", Info accepts and displays ISO Latin characters", - &ISO_Latin_p, (char **)on_off_choices }, - - { (char *)NULL, (char *)NULL, (int *)NULL, (char **)NULL } -}; - -DECLARE_INFO_COMMAND (describe_variable, "Explain the use of a variable") -{ - VARIABLE_ALIST *var; - char *description; - - /* Get the variable's name. */ - var = read_variable_name ("Describe variable: ", window); - - if (!var) - return; - - description = (char *)xmalloc (20 + strlen (var->name) + strlen (var->doc)); - - if (var->choices) - sprintf (description, "%s (%s): %s.", - var->name, var->choices[*(var->value)], var->doc); - else - sprintf (description, "%s (%d): %s.", var->name, *(var->value), var->doc); - - window_message_in_echo_area ("%s", description); - free (description); -} - -DECLARE_INFO_COMMAND (set_variable, "Set the value of an Info variable") -{ - VARIABLE_ALIST *var; - char *line; - - /* Get the variable's name and value. */ - var = read_variable_name ("Set variable: ", window); - - if (!var) - return; - - /* Read a new value for this variable. */ - { - char prompt[100]; - - if (!var->choices) - { - int potential_value; - - if (info_explicit_arg || count != 1) - potential_value = count; - else - potential_value = *(var->value); - - sprintf (prompt, "Set %s to value (%d): ", - var->name, potential_value); - line = info_read_in_echo_area (active_window, prompt); - - /* If no error was printed, clear the echo area. */ - if (!info_error_was_printed) - window_clear_echo_area (); - - /* User aborted? */ - if (!line) - return; - - /* If the user specified a value, get that, otherwise, we are done. */ - canonicalize_whitespace (line); - if (*line) - *(var->value) = atoi (line); - else - *(var->value) = potential_value; - - free (line); - } - else - { - register int i; - REFERENCE **array = (REFERENCE **)NULL; - int array_index = 0; - int array_slots = 0; - - for (i = 0; var->choices[i]; i++) - { - REFERENCE *entry; - - entry = (REFERENCE *)xmalloc (sizeof (REFERENCE)); - entry->label = savestring (var->choices[i]); - entry->nodename = (char *)NULL; - entry->filename = (char *)NULL; - - add_pointer_to_array - (entry, array_index, array, array_slots, 10, REFERENCE *); - } - - sprintf (prompt, "Set %s to value (%s): ", - var->name, var->choices[*(var->value)]); - - /* Ask the completer to read a variable value for us. */ - line = info_read_completing_in_echo_area (window, prompt, array); - - info_free_references (array); - - if (!echo_area_is_active) - window_clear_echo_area (); - - /* User aborted? */ - if (!line) - { - info_abort_key (active_window, 0, 0); - return; - } - - /* User accepted default choice? If so, no change. */ - if (!*line) - { - free (line); - return; - } - - /* Find the choice in our list of choices. */ - for (i = 0; var->choices[i]; i++) - if (strcmp (var->choices[i], line) == 0) - break; - - if (var->choices[i]) - *(var->value) = i; - } - } -} - -/* Read the name of an Info variable in the echo area and return the - address of a VARIABLE_ALIST member. A return value of NULL indicates - that no variable could be read. */ -VARIABLE_ALIST * -read_variable_name (prompt, window) - char *prompt; - WINDOW *window; -{ - register int i; - char *line; - REFERENCE **variables; - - /* Get the completion array of variable names. */ - variables = make_variable_completions_array (); - - /* Ask the completer to read a variable for us. */ - line = - info_read_completing_in_echo_area (window, prompt, variables); - - info_free_references (variables); - - if (!echo_area_is_active) - window_clear_echo_area (); - - /* User aborted? */ - if (!line) - { - info_abort_key (active_window, 0, 0); - return ((VARIABLE_ALIST *)NULL); - } - - /* User accepted "default"? (There is none.) */ - if (!*line) - { - free (line); - return ((VARIABLE_ALIST *)NULL); - } - - /* Find the variable in our list of variables. */ - for (i = 0; info_variables[i].name; i++) - if (strcmp (info_variables[i].name, line) == 0) - break; - - if (!info_variables[i].name) - return ((VARIABLE_ALIST *)NULL); - else - return (&(info_variables[i])); -} - -/* Make an array of REFERENCE which actually contains the names of the - variables available in Info. */ -REFERENCE ** -make_variable_completions_array () -{ - register int i; - REFERENCE **array = (REFERENCE **)NULL; - int array_index = 0, array_slots = 0; - - for (i = 0; info_variables[i].name; i++) - { - REFERENCE *entry; - - entry = (REFERENCE *)xmalloc (sizeof (REFERENCE)); - entry->label = savestring (info_variables[i].name); - entry->nodename = (char *)NULL; - entry->filename = (char *)NULL; - - add_pointer_to_array - (entry, array_index, array, array_slots, 200, REFERENCE *); - } - - return (array); -} diff --git a/gnu/usr.bin/texinfo/info/variables.h b/gnu/usr.bin/texinfo/info/variables.h deleted file mode 100644 index ce40fa5..0000000 --- a/gnu/usr.bin/texinfo/info/variables.h +++ /dev/null @@ -1,64 +0,0 @@ -/* variables.h -- Description of user visible variables in Info. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#ifndef _VARIABLES_H_ -#define _VARIABLES_H_ - -/* A variable (in the Info sense) is an integer value with a user-visible - name. You may supply an array of strings to complete over when the - variable is set; in that case, the variable is set to the index of the - string that the user chose. If you supply a null list, the user can - set the variable to a numeric value. */ - -/* Structure describing a user visible variable. */ -typedef struct { - char *name; /* Polite name. */ - char *doc; /* Documentation string. */ - int *value; /* Address of value. */ - char **choices; /* Array of strings or NULL if numeric only. */ -} VARIABLE_ALIST; - -/* Read the name of an Info variable in the echo area and return the - address of a VARIABLE_ALIST member. A return value of NULL indicates - that no variable could be read. */ -extern VARIABLE_ALIST *read_variable_name (); - -/* Make an array of REFERENCE which actually contains the names of the - variables available in Info. */ -extern REFERENCE **make_variable_completions_array (); - -/* Set the value of an info variable. */ -extern void set_variable (); - -/* The list of user-visible variables. */ -extern int auto_footnotes_p; -extern int auto_tiling_p; -extern int terminal_use_visible_bell_p; -extern int info_error_rings_bell_p; -extern int gc_compressed_files; -extern int show_index_match; -extern int info_scroll_behaviour; -extern int window_scroll_step; -extern int ISO_Latin_p; - -#endif /* _VARIABLES_H_ */ diff --git a/gnu/usr.bin/texinfo/info/window.c b/gnu/usr.bin/texinfo/info/window.c deleted file mode 100644 index b114986..0000000 --- a/gnu/usr.bin/texinfo/info/window.c +++ /dev/null @@ -1,1478 +0,0 @@ -/* window.c -- Windows in Info. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#include <stdio.h> -#include <ctype.h> -#include <sys/types.h> -#include <sys/stat.h> -#include "nodes.h" -#include "window.h" -#include "display.h" -#include "info-utils.h" -#include "infomap.h" - -/* The window which describes the screen. */ -WINDOW *the_screen = (WINDOW *)NULL; - -/* The window which describes the echo area. */ -WINDOW *the_echo_area = (WINDOW *)NULL; - -/* The list of windows in Info. */ -WINDOW *windows = (WINDOW *)NULL; - -/* Pointer to the active window in WINDOW_LIST. */ -WINDOW *active_window = (WINDOW *)NULL; - -/* The size of the echo area in Info. It never changes, irregardless of the - size of the screen. */ -#define ECHO_AREA_HEIGHT 1 - -/* Macro returns the amount of space that the echo area truly requires relative - to the entire screen. */ -#define echo_area_required (1 + the_echo_area->height) - -/* Initalize the window system by creating THE_SCREEN and THE_ECHO_AREA. - Create the first window ever. - You pass the dimensions of the total screen size. */ -void -window_initialize_windows (width, height) - int width, height; -{ - the_screen = (WINDOW *)xmalloc (sizeof (WINDOW)); - the_echo_area = (WINDOW *)xmalloc (sizeof (WINDOW)); - windows = (WINDOW *)xmalloc (sizeof (WINDOW)); - active_window = windows; - - zero_mem (the_screen, sizeof (WINDOW)); - zero_mem (the_echo_area, sizeof (WINDOW)); - zero_mem (active_window, sizeof (WINDOW)); - - /* None of these windows has a goal column yet. */ - the_echo_area->goal_column = -1; - active_window->goal_column = -1; - the_screen->goal_column = -1; - - /* The active and echo_area windows are visible. - The echo_area is permanent. - The screen is permanent. */ - active_window->flags = W_WindowVisible; - the_echo_area->flags = W_WindowIsPerm | W_InhibitMode | W_WindowVisible; - the_screen->flags = W_WindowIsPerm; - - /* The height of the echo area never changes. It is statically set right - here, and it must be at least 1 line for display. The size of the - initial window cannot be the same size as the screen, since the screen - includes the echo area. So, we make the height of the initial window - equal to the screen's displayable region minus the height of the echo - area. */ - the_echo_area->height = ECHO_AREA_HEIGHT; - active_window->height = the_screen->height - 1 - the_echo_area->height; - window_new_screen_size (width, height, (VFunction *)NULL); - - /* The echo area uses a different keymap than normal info windows. */ - the_echo_area->keymap = echo_area_keymap; - active_window->keymap = info_keymap; -} - -/* Given that the size of the screen has changed to WIDTH and HEIGHT - from whatever it was before (found in the_screen->height, ->width), - change the size (and possibly location) of each window in the screen. - If a window would become too small, call the function DELETER on it, - after deleting the window from our chain of windows. If DELETER is NULL, - nothing extra is done. The last window can never be deleted, but it can - become invisible. */ - -/* If non-null, a function to call with WINDOW as argument when the function - window_new_screen_size () has deleted WINDOW. */ -VFunction *window_deletion_notifier = (VFunction *)NULL; - -void -window_new_screen_size (width, height) - int width, height; -{ - register WINDOW *win; - int delta_height, delta_each, delta_leftover; - int numwins; - - /* If no change, do nothing. */ - if (width == the_screen->width && height == the_screen->height) - return; - - /* If the new window height is too small, make it be zero. */ - if (height < (WINDOW_MIN_SIZE + the_echo_area->height)) - height = 0; - if (width < 0) - width = 0; - - /* Find out how many windows will change. */ - for (numwins = 0, win = windows; win; win = win->next, numwins++); - - /* See if some windows will need to be deleted. This is the case if - the screen is getting smaller, and the available space divided by - the number of windows is less than WINDOW_MIN_SIZE. In that case, - delete some windows and try again until there is either enough - space to divy up among the windows, or until there is only one - window left. */ - while ((height - echo_area_required) / numwins <= WINDOW_MIN_SIZE) - { - /* If only one window, make the size of it be zero, and return - immediately. */ - if (!windows->next) - { - windows->height = 0; - maybe_free (windows->line_starts); - windows->line_starts = (char **)NULL; - windows->line_count = 0; - break; - } - - /* If we have some temporary windows, delete one of them. */ - for (win = windows; win; win = win->next) - if (win->flags & W_TempWindow) - break; - - /* Otherwise, delete the first window, and try again. */ - if (!win) - win = windows; - - if (window_deletion_notifier) - (*window_deletion_notifier) (win); - - window_delete_window (win); - numwins--; - } - - /* The screen has changed height and width. */ - delta_height = height - the_screen->height; /* This is how much. */ - the_screen->height = height; /* This is the new height. */ - the_screen->width = width; /* This is the new width. */ - - /* Set the start of the echo area. */ - the_echo_area->first_row = height - the_echo_area->height; - the_echo_area->width = width; - - /* Check to see if the screen can really be changed this way. */ - if ((!windows->next) && ((windows->height == 0) && (delta_height < 0))) - return; - - /* Divide the change in height among the available windows. */ - delta_each = delta_height / numwins; - delta_leftover = delta_height - (delta_each * numwins); - - /* Change the height of each window in the chain by delta_each. Change - the height of the last window in the chain by delta_each and by the - leftover amount of change. Change the width of each window to be - WIDTH. */ - for (win = windows; win; win = win->next) - { - if ((win->width != width) && ((win->flags & W_InhibitMode) == 0)) - { - win->width = width; - maybe_free (win->modeline); - win->modeline = (char *)xmalloc (1 + width); - } - - win->height += delta_each; - - /* If the previous height of this window was zero, it was the only - window, and it was not visible. Thus we need to compensate for - the echo_area. */ - if (win->height == delta_each) - win->height -= (1 + the_echo_area->height); - - /* If this is not the first window in the chain, then change the - first row of it. We cannot just add delta_each to the first row, - since this window's first row is the sum of the collective increases - that have gone before it. So we just add one to the location of the - previous window's modeline. */ - if (win->prev) - win->first_row = (win->prev->first_row + win->prev->height) + 1; - - /* The last window in the chain gets the extra space (or shrinkage). */ - if (!win->next) - win->height += delta_leftover; - - if (win->node) - recalculate_line_starts (win); - - win->flags |= W_UpdateWindow; - } - - /* If the screen got smaller, check over the windows just shrunk to - keep them within bounds. Some of the windows may have gotten smaller - than WINDOW_MIN_HEIGHT in which case some of the other windows are - larger than the available display space in the screen. Because of our - intial test above, we know that there is enough space for all of the - windows. */ - if ((delta_each < 0) && ((windows->height != 0) && windows->next)) - { - int avail; - - avail = the_screen->height - (numwins + the_echo_area->height); - win = windows; - - while (win) - { - if ((win->height < WINDOW_MIN_HEIGHT) || - (win->height > avail)) - { - WINDOW *lastwin; - - /* Split the space among the available windows. */ - delta_each = avail / numwins; - delta_leftover = avail - (delta_each * numwins); - - for (win = windows; win; win = win->next) - { - lastwin = win; - if (win->prev) - win->first_row = - (win->prev->first_row + win->prev->height) + 1; - win->height = delta_each; - } - - /* Give the leftover space (if any) to the last window. */ - lastwin->height += delta_leftover; - break; - } - else - win= win->next; - } - } -} - -/* Make a new window showing NODE, and return that window structure. - If NODE is passed as NULL, then show the node showing in the active - window. If the window could not be made return a NULL pointer. The - active window is not changed.*/ -WINDOW * -window_make_window (node) - NODE *node; -{ - WINDOW *window; - - if (!node) - node = active_window->node; - - /* If there isn't enough room to make another window, return now. */ - if ((active_window->height / 2) < WINDOW_MIN_SIZE) - return ((WINDOW *)NULL); - - /* Make and initialize the new window. - The fudging about with -1 and +1 is because the following window in the - chain cannot start at window->height, since that is where the modeline - for the previous window is displayed. The inverse adjustment is made - in window_delete_window (). */ - window = (WINDOW *)xmalloc (sizeof (WINDOW)); - window->width = the_screen->width; - window->height = (active_window->height / 2) - 1; -#if defined (SPLIT_BEFORE_ACTIVE) - window->first_row = active_window->first_row; -#else - window->first_row = active_window->first_row + - (active_window->height - window->height); -#endif - window->keymap = info_keymap; - window->goal_column = -1; - window->modeline = (char *)xmalloc (1 + window->width); - window->line_starts = (char **)NULL; - window->flags = W_UpdateWindow | W_WindowVisible; - window_set_node_of_window (window, node); - - /* Adjust the height of the old active window. */ - active_window->height -= (window->height + 1); -#if defined (SPLIT_BEFORE_ACTIVE) - active_window->first_row += (window->height + 1); -#endif - active_window->flags |= W_UpdateWindow; - - /* Readjust the new and old windows so that their modelines and contents - will be displayed correctly. */ -#if defined (NOTDEF) - /* We don't have to do this for WINDOW since window_set_node_of_window () - already did. */ - window_adjust_pagetop (window); - window_make_modeline (window); -#endif /* NOTDEF */ - - /* We do have to readjust the existing active window. */ - window_adjust_pagetop (active_window); - window_make_modeline (active_window); - -#if defined (SPLIT_BEFORE_ACTIVE) - /* This window is just before the active one. The active window gets - bumped down one. The active window is not changed. */ - window->next = active_window; - - window->prev = active_window->prev; - active_window->prev = window; - - if (window->prev) - window->prev->next = window; - else - windows = window; -#else - /* This window is just after the active one. Which window is active is - not changed. */ - window->prev = active_window; - window->next = active_window->next; - active_window->next = window; - if (window->next) - window->next->prev = window; -#endif /* !SPLIT_BEFORE_ACTIVE */ - return (window); -} - -/* These useful macros make it possible to read the code in - window_change_window_height (). */ -#define grow_me_shrinking_next(me, next, diff) \ - do { \ - me->height += diff; \ - next->height -= diff; \ - next->first_row += diff; \ - window_adjust_pagetop (next); \ - } while (0) - -#define grow_me_shrinking_prev(me, prev, diff) \ - do { \ - me->height += diff; \ - prev->height -= diff; \ - me->first_row -=diff; \ - window_adjust_pagetop (prev); \ - } while (0) - -#define shrink_me_growing_next(me, next, diff) \ - do { \ - me->height -= diff; \ - next->height += diff; \ - next->first_row -= diff; \ - window_adjust_pagetop (next); \ - } while (0) - -#define shrink_me_growing_prev(me, prev, diff) \ - do { \ - me->height -= diff; \ - prev->height += diff; \ - me->first_row += diff; \ - window_adjust_pagetop (prev); \ - } while (0) - -/* Change the height of WINDOW by AMOUNT. This also automagically adjusts - the previous and next windows in the chain. If there is only one user - window, then no change takes place. */ -void -window_change_window_height (window, amount) - WINDOW *window; - int amount; -{ - register WINDOW *win, *prev, *next; - - /* If there is only one window, or if the amount of change is zero, - return immediately. */ - if (!windows->next || amount == 0) - return; - - /* Find this window in our chain. */ - for (win = windows; win; win = win->next) - if (win == window) - break; - - /* If the window is isolated (i.e., doesn't appear in our window list, - then quit now. */ - if (!win) - return; - - /* Change the height of this window by AMOUNT, if that is possible. - It can be impossible if there isn't enough available room on the - screen, or if the resultant window would be too small. */ - - prev = window->prev; - next = window->next; - - /* WINDOW decreasing in size? */ - if (amount < 0) - { - int abs_amount = -amount; /* It is easier to deal with this way. */ - - /* If the resultant window would be too small, stop here. */ - if ((window->height - abs_amount) < WINDOW_MIN_HEIGHT) - return; - - /* If we have two neighboring windows, choose the smaller one to get - larger. */ - if (next && prev) - { - if (prev->height < next->height) - shrink_me_growing_prev (window, prev, abs_amount); - else - shrink_me_growing_next (window, next, abs_amount); - } - else if (next) - shrink_me_growing_next (window, next, abs_amount); - else - shrink_me_growing_prev (window, prev, abs_amount); - } - - /* WINDOW increasing in size? */ - if (amount > 0) - { - int total_avail, next_avail = 0, prev_avail = 0; - - if (next) - next_avail = next->height - WINDOW_MIN_SIZE; - - if (prev) - prev_avail = prev->height - WINDOW_MIN_SIZE; - - total_avail = next_avail + prev_avail; - - /* If there isn't enough space available to grow this window, give up. */ - if (amount > total_avail) - return; - - /* If there aren't two neighboring windows, or if one of the neighbors - is larger than the other one by at least AMOUNT, grow that one. */ - if ((next && !prev) || ((next_avail - amount) >= prev_avail)) - grow_me_shrinking_next (window, next, amount); - else if ((prev && !next) || ((prev_avail - amount) >= next_avail)) - grow_me_shrinking_prev (window, prev, amount); - else - { - int change; - - /* This window has two neighbors. They both must be shrunk in to - make enough space for WINDOW to grow. Make them both the same - size. */ - if (prev_avail > next_avail) - { - change = prev_avail - next_avail; - grow_me_shrinking_prev (window, prev, change); - amount -= change; - } - else - { - change = next_avail - prev_avail; - grow_me_shrinking_next (window, next, change); - amount -= change; - } - - /* Both neighbors are the same size. Split the difference in - AMOUNT between them. */ - while (amount) - { - window->height++; - amount--; - - /* Odd numbers grow next, even grow prev. */ - if (amount & 1) - { - prev->height--; - window->first_row--; - } - else - { - next->height--; - next->first_row++; - } - } - window_adjust_pagetop (prev); - window_adjust_pagetop (next); - } - } - if (prev) - prev->flags |= W_UpdateWindow; - - if (next) - next->flags |= W_UpdateWindow; - - window->flags |= W_UpdateWindow; - window_adjust_pagetop (window); -} - -/* Tile all of the windows currently displayed in the global variable - WINDOWS. If argument STYLE is TILE_INTERNALS, tile windows displaying - internal nodes as well, otherwise do not change the height of such - windows. */ -void -window_tile_windows (style) - int style; -{ - WINDOW *win, *last_adjusted; - int numwins, avail, per_win_height, leftover; - int do_internals; - - numwins = avail = 0; - do_internals = (style == TILE_INTERNALS); - - for (win = windows; win; win = win->next) - if (do_internals || !win->node || - (win->node->flags & N_IsInternal) == 0) - { - avail += win->height; - numwins++; - } - - if (numwins <= 1 || !the_screen->height) - return; - - /* Find the size for each window. Divide the size of the usable portion - of the screen by the number of windows. */ - per_win_height = avail / numwins; - leftover = avail - (per_win_height * numwins); - - last_adjusted = (WINDOW *)NULL; - for (win = windows; win; win = win->next) - { - if (do_internals || !win->node || - (win->node->flags & N_IsInternal) == 0) - { - last_adjusted = win; - win->height = per_win_height; - } - } - - if (last_adjusted) - last_adjusted->height += leftover; - - /* Readjust the first_row of every window in the chain. */ - for (win = windows; win; win = win->next) - { - if (win->prev) - win->first_row = win->prev->first_row + win->prev->height + 1; - - window_adjust_pagetop (win); - win->flags |= W_UpdateWindow; - } -} - -/* Toggle the state of line wrapping in WINDOW. This can do a bit of fancy - redisplay. */ -void -window_toggle_wrap (window) - WINDOW *window; -{ - if (window->flags & W_NoWrap) - window->flags &= ~W_NoWrap; - else - window->flags |= W_NoWrap; - - if (window != the_echo_area) - { - char **old_starts; - int old_lines, old_pagetop; - - old_starts = window->line_starts; - old_lines = window->line_count; - old_pagetop = window->pagetop; - - calculate_line_starts (window); - - /* Make sure that point appears within this window. */ - window_adjust_pagetop (window); - - /* If the pagetop hasn't changed maybe we can do some scrolling now - to speed up the display. Many of the line starts will be the same, - so scrolling here is a very good optimization.*/ - if (old_pagetop == window->pagetop) - display_scroll_line_starts - (window, old_pagetop, old_starts, old_lines); - maybe_free (old_starts); - } - window->flags |= W_UpdateWindow; -} - -/* Set WINDOW to display NODE. */ -void -window_set_node_of_window (window, node) - WINDOW *window; - NODE *node; -{ - window->node = node; - window->pagetop = 0; - window->point = 0; - recalculate_line_starts (window); - window->flags |= W_UpdateWindow; - window_adjust_pagetop (window); - window_make_modeline (window); -} - -/* Delete WINDOW from the list of known windows. If this window was the - active window, make the next window in the chain be the active window. - If the active window is the next or previous window, choose that window - as the recipient of the extra space. Otherwise, prefer the next window. */ -void -window_delete_window (window) - WINDOW *window; -{ - WINDOW *next, *prev, *window_to_fix; - - next = window->next; - prev = window->prev; - - /* You cannot delete the only window or a permanent window. */ - if ((!next && !prev) || (window->flags & W_WindowIsPerm)) - return; - - if (next) - next->prev = prev; - - if (!prev) - windows = next; - else - prev->next = next; - - if (window->line_starts) - free (window->line_starts); - - if (window->modeline) - free (window->modeline); - - if (window == active_window) - { - /* If there isn't a next window, then there must be a previous one, - since we cannot delete the last window. If there is a next window, - prefer to use that as the active window. */ - if (next) - active_window = next; - else - active_window = prev; - } - - if (next && active_window == next) - window_to_fix = next; - else if (prev && active_window == prev) - window_to_fix = prev; - else if (next) - window_to_fix = next; - else if (prev) - window_to_fix = prev; - else - window_to_fix = windows; - - if (window_to_fix->first_row > window->first_row) - { - int diff; - - /* Try to adjust the visible part of the node so that as little - text as possible has to move. */ - diff = window_to_fix->first_row - window->first_row; - window_to_fix->first_row = window->first_row; - - window_to_fix->pagetop -= diff; - if (window_to_fix->pagetop < 0) - window_to_fix->pagetop = 0; - } - - /* The `+ 1' is to offset the difference between the first_row locations. - See the code in window_make_window (). */ - window_to_fix->height += window->height + 1; - window_to_fix->flags |= W_UpdateWindow; - - free (window); -} - -/* For every window in CHAIN, set the flags member to have FLAG set. */ -void -window_mark_chain (chain, flag) - WINDOW *chain; - int flag; -{ - register WINDOW *win; - - for (win = chain; win; win = win->next) - win->flags |= flag; -} - -/* For every window in CHAIN, clear the flags member of FLAG. */ -void -window_unmark_chain (chain, flag) - WINDOW *chain; - int flag; -{ - register WINDOW *win; - - for (win = chain; win; win = win->next) - win->flags &= ~flag; -} - -/* Return the number of characters it takes to display CHARACTER on the - screen at HPOS. */ -int -character_width (character, hpos) - int character, hpos; -{ - int printable_limit = 127; - int width = 1; - - if (ISO_Latin_p) - printable_limit = 160; - - if (character > printable_limit) - width = 3; - else if (iscntrl (character)) - { - switch (character) - { - case '\r': - case '\n': - width = the_screen->width - hpos; - break; - case '\t': - width = ((hpos + 8) & 0xf8) - hpos; - break; - default: - width = 2; - } - } - else if (character == DEL) - width = 2; - - return (width); -} - -/* Return the number of characters it takes to display STRING on the screen - at HPOS. */ -int -string_width (string, hpos) - char *string; - int hpos; -{ - register int i, width, this_char_width; - - for (width = 0, i = 0; string[i]; i++) - { - this_char_width = character_width (string[i], hpos); - width += this_char_width; - hpos += this_char_width; - } - return (width); -} - -/* Quickly guess the approximate number of lines to that NODE would - take to display. This really only counts carriage returns. */ -int -window_physical_lines (node) - NODE *node; -{ - register int i, lines; - char *contents; - - if (!node) - return (0); - - contents = node->contents; - for (i = 0, lines = 1; i < node->nodelen; i++) - if (contents[i] == '\n') - lines++; - - return (lines); -} - -/* Calculate a list of line starts for the node belonging to WINDOW. The line - starts are pointers to the actual text within WINDOW->NODE. */ -void -calculate_line_starts (window) - WINDOW *window; -{ - register int i, hpos; - char **line_starts = (char **)NULL; - int line_starts_index = 0, line_starts_slots = 0; - int bump_index; - NODE *node; - - window->line_starts = (char **)NULL; - window->line_count = 0; - node = window->node; - - if (!node) - return; - - /* Grovel the node starting at the top, and for each line calculate the - width of the characters appearing in that line. Add each line start - to our array. */ - i = 0; - hpos = 0; - bump_index = 0; - - while (i < node->nodelen) - { - char *line = node->contents + i; - unsigned int cwidth, c; - - add_pointer_to_array (line, line_starts_index, line_starts, - line_starts_slots, 100, char *); - if (bump_index) - { - i++; - bump_index = 0; - } - - while (1) - { - c = node->contents[i]; - cwidth = character_width (c, hpos); - - /* If this character fits within this line, just do the next one. */ - if ((hpos + cwidth) < window->width) - { - i++; - hpos += cwidth; - continue; - } - else - { - /* If this character would position the cursor at the start of - the next printed screen line, then do the next line. */ - if (c == '\n' || c == '\r' || c == '\t') - { - i++; - hpos = 0; - break; - } - else - { - /* This character passes the window width border. Postion - the cursor after the printed character, but remember this - line start as where this character is. A bit tricky. */ - - /* If this window doesn't wrap lines, proceed to the next - physical line here. */ - if (window->flags & W_NoWrap) - { - hpos = 0; - while (i < node->nodelen && node->contents[i] != '\n') - i++; - - if (node->contents[i] == '\n') - i++; - } - else - { - hpos = the_screen->width - hpos; - bump_index++; - } - break; - } - } - } - } - window->line_starts = line_starts; - window->line_count = line_starts_index; -} - -/* Given WINDOW, recalculate the line starts for the node it displays. */ -void -recalculate_line_starts (window) - WINDOW *window; -{ - maybe_free (window->line_starts); - calculate_line_starts (window); -} - -/* Global variable control redisplay of scrolled windows. If non-zero, it - is the desired number of lines to scroll the window in order to make - point visible. A user might set this to 1 for smooth scrolling. If - set to zero, the line containing point is centered within the window. */ -int window_scroll_step = 0; - -/* Adjust the pagetop of WINDOW such that the cursor point will be visible. */ -void -window_adjust_pagetop (window) - WINDOW *window; -{ - register int line = 0; - char *contents; - - if (!window->node) - return; - - contents = window->node->contents; - - /* Find the first printed line start which is after WINDOW->point. */ - for (line = 0; line < window->line_count; line++) - { - char *line_start; - - line_start = window->line_starts[line]; - - if ((line_start - contents) > window->point) - break; - } - - /* The line index preceding the line start which is past point is the - one containing point. */ - line--; - - /* If this line appears in the current displayable page, do nothing. - Otherwise, adjust the top of the page to make this line visible. */ - if ((line < window->pagetop) || - (line - window->pagetop > (window->height - 1))) - { - /* The user-settable variable "scroll-step" is used to attempt - to make point visible, iff it is non-zero. If that variable - is zero, then the line containing point is centered within - the window. */ - if (window_scroll_step < window->height) - { - if ((line < window->pagetop) && - ((window->pagetop - window_scroll_step) <= line)) - window->pagetop -= window_scroll_step; - else if ((line - window->pagetop > (window->height - 1)) && - ((line - (window->pagetop + window_scroll_step) - < window->height))) - window->pagetop += window_scroll_step; - else - window->pagetop = line - ((window->height - 1) / 2); - } - else - window->pagetop = line - ((window->height - 1) / 2); - - if (window->pagetop < 0) - window->pagetop = 0; - window->flags |= W_UpdateWindow; - } -} - -/* Return the index of the line containing point. */ -int -window_line_of_point (window) - WINDOW *window; -{ - register int i, start = 0; - - /* Try to optimize. Check to see if point is past the pagetop for - this window, and if so, start searching forward from there. */ - if ((window->pagetop > -1 && window->pagetop < window->line_count) && - (window->line_starts[window->pagetop] - window->node->contents) - <= window->point) - start = window->pagetop; - - for (i = start; i < window->line_count; i++) - { - if ((window->line_starts[i] - window->node->contents) > window->point) - break; - } - - return (i - 1); -} - -/* Get and return the goal column for this window. */ -int -window_get_goal_column (window) - WINDOW *window; -{ - if (!window->node) - return (-1); - - if (window->goal_column != -1) - return (window->goal_column); - - /* Okay, do the work. Find the printed offset of the cursor - in this window. */ - return (window_get_cursor_column (window)); -} - -/* Get and return the printed column offset of the cursor in this window. */ -int -window_get_cursor_column (window) - WINDOW *window; -{ - int i, hpos, end; - char *line; - - i = window_line_of_point (window); - - if (i < 0) - return (-1); - - line = window->line_starts[i]; - end = window->point - (line - window->node->contents); - - for (hpos = 0, i = 0; i < end; i++) - hpos += character_width (line[i], hpos); - - return (hpos); -} - -/* Count the number of characters in LINE that precede the printed column - offset of GOAL. */ -int -window_chars_to_goal (line, goal) - char *line; - int goal; -{ - register int i, check, hpos; - - for (hpos = 0, i = 0; line[i] != '\n'; i++) - { - - check = hpos + character_width (line[i], hpos); - - if (check > goal) - break; - - hpos = check; - } - return (i); -} - -/* Create a modeline for WINDOW, and store it in window->modeline. */ -void -window_make_modeline (window) - WINDOW *window; -{ - register int i; - char *modeline; - char location_indicator[4]; - int lines_remaining; - - /* Only make modelines for those windows which have one. */ - if (window->flags & W_InhibitMode) - return; - - /* Find the number of lines actually displayed in this window. */ - lines_remaining = window->line_count - window->pagetop; - - if (window->pagetop == 0) - { - if (lines_remaining <= window->height) - strcpy (location_indicator, "All"); - else - strcpy (location_indicator, "Top"); - } - else - { - if (lines_remaining <= window->height) - strcpy (location_indicator, "Bot"); - else - { - float pt, lc; - int percentage; - - pt = (float)window->pagetop; - lc = (float)window->line_count; - - percentage = 100 * (pt / lc); - - sprintf (location_indicator, "%2d%%", percentage); - } - } - - /* Calculate the maximum size of the information to stick in MODELINE. */ - { - int modeline_len = 0; - char *parent = (char *)NULL, *filename = "*no file*"; - char *nodename = "*no node*"; - char *update_message = (char *)NULL; - NODE *node = window->node; - - if (node) - { - if (node->nodename) - nodename = node->nodename; - - if (node->parent) - { - parent = filename_non_directory (node->parent); - modeline_len += strlen ("Subfile: ") + strlen (node->filename); - } - - if (node->filename) - filename = filename_non_directory (node->filename); - - if (node->flags & N_UpdateTags) - update_message = "--*** Tags out of Date ***"; - } - - if (update_message) - modeline_len += strlen (update_message); - modeline_len += strlen (filename); - modeline_len += strlen (nodename); - modeline_len += 4; /* strlen (location_indicator). */ - - /* 10 for the decimal representation of the number of lines in this - node, and the remainder of the text that can appear in the line. */ - modeline_len += 10 + strlen ("-----Info: (), lines ----, "); - modeline_len += window->width; - - modeline = (char *)xmalloc (1 + modeline_len); - - /* Special internal windows have no filename. */ - if (!parent && !*filename) - sprintf (modeline, "-%s---Info: %s, %d lines --%s--", - (window->flags & W_NoWrap) ? "$" : "-", - nodename, window->line_count, location_indicator); - else - sprintf (modeline, "-%s%s-Info: (%s)%s, %d lines --%s--", - (window->flags & W_NoWrap) ? "$" : "-", - (node && (node->flags & N_IsCompressed)) ? "zz" : "--", - parent ? parent : filename, - nodename, window->line_count, location_indicator); - - if (parent) - sprintf (modeline + strlen (modeline), " Subfile: %s", filename); - - if (update_message) - sprintf (modeline + strlen (modeline), "%s", update_message); - - i = strlen (modeline); - - if (i >= window->width) - modeline[window->width] = '\0'; - else - { - while (i < window->width) - modeline[i++] = '-'; - modeline[i] = '\0'; - } - - strcpy (window->modeline, modeline); - free (modeline); - } -} - -/* Make WINDOW start displaying at PERCENT percentage of its node. */ -void -window_goto_percentage (window, percent) - WINDOW *window; - int percent; -{ - int desired_line; - - if (!percent) - desired_line = 0; - else - desired_line = - (int) ((float)window->line_count * ((float)percent / 100.0)); - - window->pagetop = desired_line; - window->point = - window->line_starts[window->pagetop] - window->node->contents; - window->flags |= W_UpdateWindow; - window_make_modeline (window); -} - -/* Get the state of WINDOW, and save it in STATE. */ -void -window_get_state (window, state) - WINDOW *window; - WINDOW_STATE *state; -{ - state->node = window->node; - state->pagetop = window->pagetop; - state->point = window->point; -} - -/* Set the node, pagetop, and point of WINDOW. */ -void -window_set_state (window, state) - WINDOW *window; - WINDOW_STATE *state; -{ - if (window->node != state->node) - window_set_node_of_window (window, state->node); - window->pagetop = state->pagetop; - window->point = state->point; -} - - -/* **************************************************************** */ -/* */ -/* Manipulating Home-Made Nodes */ -/* */ -/* **************************************************************** */ - -/* A place to buffer echo area messages. */ -static NODE *echo_area_node = (NODE *)NULL; - -/* Make the node of the_echo_area be an empty one. */ -static void -free_echo_area () -{ - if (echo_area_node) - { - maybe_free (echo_area_node->contents); - free (echo_area_node); - } - - echo_area_node = (NODE *)NULL; - window_set_node_of_window (the_echo_area, echo_area_node); -} - -/* Clear the echo area, removing any message that is already present. - The echo area is cleared immediately. */ -void -window_clear_echo_area () -{ - free_echo_area (); - display_update_one_window (the_echo_area); -} - -/* Make a message appear in the echo area, built from FORMAT, ARG1 and ARG2. - The arguments are treated similar to printf () arguments, but not all of - printf () hair is present. The message appears immediately. If there was - already a message appearing in the echo area, it is removed. */ -void -window_message_in_echo_area (format, arg1, arg2) - char *format; - void *arg1, *arg2; -{ - free_echo_area (); - echo_area_node = build_message_node (format, arg1, arg2); - window_set_node_of_window (the_echo_area, echo_area_node); - display_update_one_window (the_echo_area); -} - -/* Place a temporary message in the echo area built from FORMAT, ARG1 - and ARG2. The message appears immediately, but does not destroy - any existing message. A future call to unmessage_in_echo_area () - restores the old contents. */ -static NODE **old_echo_area_nodes = (NODE **)NULL; -static int old_echo_area_nodes_index = 0; -static int old_echo_area_nodes_slots = 0; - -void -message_in_echo_area (format, arg1, arg2) - char *format; - void *arg1, *arg2; -{ - if (echo_area_node) - { - add_pointer_to_array (echo_area_node, old_echo_area_nodes_index, - old_echo_area_nodes, old_echo_area_nodes_slots, - 4, NODE *); - } - echo_area_node = (NODE *)NULL; - window_message_in_echo_area (format, arg1, arg2); -} - -void -unmessage_in_echo_area () -{ - free_echo_area (); - - if (old_echo_area_nodes_index) - echo_area_node = old_echo_area_nodes[--old_echo_area_nodes_index]; - - window_set_node_of_window (the_echo_area, echo_area_node); - display_update_one_window (the_echo_area); -} - -/* A place to build a message. */ -static char *message_buffer = (char *)NULL; -static int message_buffer_index = 0; -static int message_buffer_size = 0; - -/* Ensure that there is enough space to stuff LENGTH characters into - MESSAGE_BUFFER. */ -static void -message_buffer_resize (length) - int length; -{ - if (!message_buffer) - { - message_buffer_size = length + 1; - message_buffer = (char *)xmalloc (message_buffer_size); - message_buffer_index = 0; - } - - while (message_buffer_size <= message_buffer_index + length) - message_buffer = (char *) - xrealloc (message_buffer, - message_buffer_size += 100 + (2 * length)); -} - -/* Format MESSAGE_BUFFER with the results of printing FORMAT with ARG1 and - ARG2. */ -static void -build_message_buffer (format, arg1, arg2) - char *format; - void *arg1, *arg2; -{ - register int i, len; - void *args[2]; - int arg_index = 0; - - args[0] = arg1; - args[1] = arg2; - - len = strlen (format); - - message_buffer_resize (len); - - for (i = 0; format[i]; i++) - { - if (format[i] != '%') - { - message_buffer[message_buffer_index++] = format[i]; - len--; - } - else - { - char c; - - c = format[++i]; - - switch (c) - { - case '%': /* Insert a percent sign. */ - message_buffer_resize (len + 1); - message_buffer[message_buffer_index++] = '%'; - break; - - case 's': /* Insert the current arg as a string. */ - { - char *string; - int string_len; - - string = (char *)args[arg_index++]; - string_len = strlen (string); - - message_buffer_resize (len + string_len); - sprintf - (message_buffer + message_buffer_index, "%s", string); - message_buffer_index += string_len; - } - break; - - case 'd': /* Insert the current arg as an integer. */ - { - int integer; - - integer = (int)args[arg_index++]; - - message_buffer_resize (len + 32); - sprintf - (message_buffer + message_buffer_index, "%d", integer); - message_buffer_index = strlen (message_buffer); - } - break; - - case 'c': /* Insert the current arg as a character. */ - { - int character; - - character = (int)args[arg_index++]; - - message_buffer_resize (len + 1); - message_buffer[message_buffer_index++] = character; - } - break; - - default: - abort (); - } - } - } - message_buffer[message_buffer_index] = '\0'; -} - -/* Build a new node which has FORMAT printed with ARG1 and ARG2 as the - contents. */ -NODE * -build_message_node (format, arg1, arg2) - char *format; - void *arg1, *arg2; -{ - NODE *node; - - message_buffer_index = 0; - build_message_buffer (format, arg1, arg2); - - node = message_buffer_to_node (); - return (node); -} - -/* Convert the contents of the message buffer to a node. */ -NODE * -message_buffer_to_node () -{ - NODE *node; - - node = (NODE *)xmalloc (sizeof (NODE)); - node->filename = (char *)NULL; - node->parent = (char *)NULL; - node->nodename = (char *)NULL; - node->flags = 0; - - /* Make sure that this buffer ends with a newline. */ - node->nodelen = 1 + strlen (message_buffer); - node->contents = (char *)xmalloc (1 + node->nodelen); - strcpy (node->contents, message_buffer); - node->contents[node->nodelen - 1] = '\n'; - node->contents[node->nodelen] = '\0'; - return (node); -} - -/* Useful functions can be called from outside of window.c. */ -void -initialize_message_buffer () -{ - message_buffer_index = 0; -} - -/* Print FORMAT with ARG1,2 to the end of the current message buffer. */ -void -printf_to_message_buffer (format, arg1, arg2) - char *format; - void *arg1, *arg2; -{ - build_message_buffer (format, arg1, arg2); -} - -/* Return the current horizontal position of the "cursor" on the most - recently output message buffer line. */ -int -message_buffer_length_this_line () -{ - register int i; - - if (!message_buffer_index) - return (0); - - for (i = message_buffer_index; i && message_buffer[i - 1] != '\n'; i--); - - return (string_width (message_buffer + i, 0)); -} - -/* Pad STRING to COUNT characters by inserting blanks. */ -int -pad_to (count, string) - int count; - char *string; -{ - register int i; - - i = strlen (string); - - if (i >= count) - string[i++] = ' '; - else - { - while (i < count) - string[i++] = ' '; - } - string[i] = '\0'; - - return (i); -} diff --git a/gnu/usr.bin/texinfo/info/window.h b/gnu/usr.bin/texinfo/info/window.h deleted file mode 100644 index 3e82570..0000000 --- a/gnu/usr.bin/texinfo/info/window.h +++ /dev/null @@ -1,229 +0,0 @@ -/* window.h -- Structure and flags used in manipulating Info windows. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#ifndef _WINDOW_H_ -#define _WINDOW_H_ - -#include "nodes.h" -#include "infomap.h" - -/* Smallest number of visible lines in a window. The actual height is - always one more than this number because each window has a modeline. */ -#define WINDOW_MIN_HEIGHT 2 - -/* Smallest number of screen lines that can be used to fully present a - window. This number includes the modeline of the window. */ -#define WINDOW_MIN_SIZE (WINDOW_MIN_HEIGHT + 1) - -/* The exact same elements are used within the WINDOW_STATE structure and a - subsection of the WINDOW structure. We could define a structure which - contains this elements, and include that structure in each of WINDOW_STATE - and WINDOW. But that would lead references in the code such as - window->state->node which we would like to avoid. Instead, we #define the - elements here, and simply include the define in both data structures. Thus, - if you need to change window state information, here is where you would - do it. NB> The last element does NOT end with a semi-colon. */ -#define WINDOW_STATE_DECL \ - NODE *node; /* The node displayed in this window. */ \ - int pagetop; /* LINE_STARTS[PAGETOP] is first line in WINDOW. */ \ - long point /* Offset within NODE of the cursor position. */ - -/* Structure which defines a window. Windows are doubly linked, next - and prev. The list of windows is kept on WINDOWS. The structure member - window->height is the total height of the window. The position location - (0, window->height + window->first_row) is the first character of this - windows modeline. The number of lines that can be displayed in a window - is equal to window->height - 1. */ -typedef struct __window__ { - struct __window__ *next; /* Next window in this chain. */ - struct __window__ *prev; /* Previous window in this chain. */ - int width; /* Width of this window. */ - int height; /* Height of this window. */ - int first_row; /* Offset of the first line in the_screen. */ - int goal_column; /* The column we would like the cursor to appear in. */ - Keymap keymap; /* Keymap used to read commands in this window. */ - WINDOW_STATE_DECL; /* Node, pagetop and point. */ - char *modeline; /* Calculated text of the modeline for this window. */ - char **line_starts; /* Array of printed line starts for this node. */ - int line_count; /* Number of lines appearing in LINE_STARTS. */ - int flags; /* See below for details. */ -} WINDOW; - -typedef struct { - WINDOW_STATE_DECL; /* What gets saved. */ -} WINDOW_STATE; - -#define W_UpdateWindow 0x01 /* WINDOW needs updating. */ -#define W_WindowIsPerm 0x02 /* This WINDOW is a permanent object. */ -#define W_WindowVisible 0x04 /* This WINDOW is currently visible. */ -#define W_InhibitMode 0x08 /* This WINDOW has no modeline. */ -#define W_NoWrap 0x10 /* Lines do not wrap in this window. */ -#define W_InputWindow 0x20 /* Window accepts input. */ -#define W_TempWindow 0x40 /* Window is less important. */ - -extern WINDOW *windows; /* List of visible Info windows. */ -extern WINDOW *active_window; /* The currently active window. */ -extern WINDOW *the_screen; /* The Info screen is just another window. */ -extern WINDOW *the_echo_area; /* THE_ECHO_AREA is a window in THE_SCREEN. */ - -/* Global variable control redisplay of scrolled windows. If non-zero, it - is the desired number of lines to scroll the window in order to make - point visible. A user might set this to 1 for smooth scrolling. If - set to zero, the line containing point is centered within the window. */ -extern int window_scroll_step; - - /* Make the modeline member for WINDOW. */ -extern void window_make_modeline (); - -/* Initalize the window system by creating THE_SCREEN and THE_ECHO_AREA. - Create the first window ever, and make it permanent. - You pass WIDTH and HEIGHT; the dimensions of the total screen size. */ -extern void window_initialize_windows (); - -/* Make a new window showing NODE, and return that window structure. - The new window is made to be the active window. If NODE is passed - as NULL, then show the node showing in the active window. If the - window could not be made return a NULL pointer. The active window - is not changed.*/ -extern WINDOW *window_make_window (); - -/* Delete WINDOW from the list of known windows. If this window was the - active window, make the next window in the chain be the active window, - or the previous window in the chain if there is no next window. */ -extern void window_delete_window (); - -/* A function to call when the screen changes size, and some windows have - to get deleted. The function is called with the window to be deleted - as an argument, and it can't do anything about the window getting deleted; - it can only clean up dangling references to that window. */ -extern VFunction *window_deletion_notifier; - -/* Set WINDOW to display NODE. */ -extern void window_set_node_of_window (); - -/* Tell the window system that the size of the screen has changed. This - causes lots of interesting things to happen. The permanent windows - are resized, as well as every visible window. You pass WIDTH and HEIGHT; - the dimensions of the total screen size. */ -extern void window_new_screen_size (); - -/* Change the height of WINDOW by AMOUNT. This also automagically adjusts - the previous and next windows in the chain. If there is only one user - window, then no change takes place. */ -extern void window_change_window_height (); - -/* Adjust the pagetop of WINDOW such that the cursor point will be visible. */ -extern void window_adjust_pagetop (); - -/* Tile all of the windows currently displayed in the global variable - WINDOWS. If argument DO_INTERNALS is non-zero, tile windows displaying - internal nodes as well. */ -#define DONT_TILE_INTERNALS 0 -#define TILE_INTERNALS 1 -extern void window_tile_windows (); - -/* Toggle the state of line wrapping in WINDOW. This can do a bit of fancy - redisplay. */ -extern void window_toggle_wrap (); - -/* For every window in CHAIN, set the flags member to have FLAG set. */ -extern void window_mark_chain (); - -/* For every window in CHAIN, clear the flags member of FLAG. */ -extern void window_unmark_chain (); - -/* Make WINDOW start displaying at PERCENT percentage of its node. */ -extern void window_goto_percentage (); - -/* Build a new node which has FORMAT printed with ARG1 and ARG2 as the - contents. */ -extern NODE *build_message_node (); - -/* Useful functions can be called from outside of window.c. */ -extern void initialize_message_buffer (); - -/* Print FORMAT with ARG1,2 to the end of the current message buffer. */ -extern void printf_to_message_buffer (); - -/* Convert the contents of the message buffer to a node. */ -extern NODE *message_buffer_to_node (); - -/* Return the length of the most recently printed line in message buffer. */ -extern int message_buffer_length_this_line (); - -/* Pad STRING to COUNT characters by inserting blanks. */ -extern int pad_to (); - -/* Make a message appear in the echo area, built from FORMAT, ARG1 and ARG2. - The arguments are treated similar to printf () arguments, but not all of - printf () hair is present. The message appears immediately. If there was - already a message appearing in the echo area, it is removed. */ -extern void window_message_in_echo_area (); - -/* Place a temporary message in the echo area built from FORMAT, ARG1 - and ARG2. The message appears immediately, but does not destroy - any existing message. A future call to unmessage_in_echo_area () - restores the old contents. */ -extern void message_in_echo_area (); -extern void unmessage_in_echo_area (); - -/* Clear the echo area, removing any message that is already present. - The echo area is cleared immediately. */ -extern void window_clear_echo_area (); - -/* Quickly guess the approximate number of lines to that NODE would - take to display. This really only counts carriage returns. */ -extern int window_physical_lines (); - -/* Calculate a list of line starts for the node belonging to WINDOW. The line - starts are pointers to the actual text within WINDOW->NODE. */ -extern void calculate_line_starts (); - -/* Given WINDOW, recalculate the line starts for the node it displays. */ -extern void recalculate_line_starts (); - -/* Return the number of characters it takes to display CHARACTER on the - screen at HPOS. */ -extern int character_width (); - -/* Return the number of characters it takes to display STRING on the - screen at HPOS. */ -extern int string_width (); - -/* Return the index of the line containing point. */ -extern int window_line_of_point (); - -/* Get and return the goal column for this window. */ -extern int window_get_goal_column (); - -/* Get and return the printed column offset of the cursor in this window. */ -extern int window_get_cursor_column (); - -/* Get and Set the node, pagetop, and point of WINDOW. */ -extern void window_get_state (), window_set_state (); - -/* Count the number of characters in LINE that precede the printed column - offset of GOAL. */ -extern int window_chars_to_goal (); - -#endif /* !_WINDOW_H_ */ diff --git a/gnu/usr.bin/texinfo/info/xmalloc.c b/gnu/usr.bin/texinfo/info/xmalloc.c deleted file mode 100644 index 6ebb84c..0000000 --- a/gnu/usr.bin/texinfo/info/xmalloc.c +++ /dev/null @@ -1,78 +0,0 @@ -/* xmalloc.c -- safe versions of malloc and realloc */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - This file has appeared in prior works by the Free Software Foundation; - thus it carries copyright dates from 1988 through 1993. - - Copyright (C) 1988, 1989, 1990, 1991, 1992, 1993 Free Software - Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#if !defined (ALREADY_HAVE_XMALLOC) -#include <stdio.h> - -static void memory_error_and_abort (); - -/* **************************************************************** */ -/* */ -/* Memory Allocation and Deallocation. */ -/* */ -/* **************************************************************** */ - -/* Return a pointer to free()able block of memory large enough - to hold BYTES number of bytes. If the memory cannot be allocated, - print an error message and abort. */ -void * -xmalloc (bytes) - int bytes; -{ - void *temp = (void *)malloc (bytes); - - if (!temp) - memory_error_and_abort ("xmalloc"); - return (temp); -} - -void * -xrealloc (pointer, bytes) - void *pointer; - int bytes; -{ - void *temp; - - if (!pointer) - temp = (void *)malloc (bytes); - else - temp = (void *)realloc (pointer, bytes); - - if (!temp) - memory_error_and_abort ("xrealloc"); - - return (temp); -} - -static void -memory_error_and_abort (fname) - char *fname; -{ - fprintf (stderr, "%s: Out of virtual memory!\n", fname); - abort (); -} -#endif /* !ALREADY_HAVE_XMALLOC */ diff --git a/gnu/usr.bin/texinfo/install-info/Makefile b/gnu/usr.bin/texinfo/install-info/Makefile new file mode 100644 index 0000000..1f3e47b --- /dev/null +++ b/gnu/usr.bin/texinfo/install-info/Makefile @@ -0,0 +1,26 @@ +# +# $Id$ +# + +INSTALLINFODIR= ${.CURDIR}/../../../../contrib/texinfo/util +TXIDIR= ${.CURDIR}/../../../../contrib/texinfo/libtxi +LIBTXI= ${.CURDIR}/../libtxi/libtxi.a +BINDIR= /usr/bin + +PROG= install-info +NOMAN=yes +SRCS+= install-info.c + +CFLAGS+= -g +CFLAGS+= -DSTDC_HEADERS=1 -DHAVE_UNISTD_H=1 -DHAVE_TERMIOS_H=1 -DHAVE_STRINGS_H=1 -DHAVE_STRING_H=1 +CFLAGS+= -DHAVE_VARARGS_H=1 -DHAVE_SYS_TIME_H=1 -DHAVE_SYS_FCNTL_H=1 -DHAVE_SYS_FILE_H=1 -DHAVE_ALLOCA=1 +CFLAGS+= -DHAVE_SETVBUF=1 -DHAVE_GETCWD=1 -DHAVE_MEMSET=1 -DHAVE_BZERO=1 -DHAVE_STRCHR=1 +CFLAGS+= -DHAVE_STRCASECMP=1 -DHAVE_VFPRINTF=1 -DHAVE_VSPRINTF=1 -DHAVE_STRERROR=1 -DHAVE_SIGPROCMASK=1 +CFLAGS+= -DHAVE_SIGSETMASK=1 -I../libtxi -I$(TXIDIR) + +LDADD+= -L../libtxi -ltxi +DPADD+= ${LIBTXI} + +.PATH: $(INSTALLINFODIR) + +.include <bsd.prog.mk> diff --git a/gnu/usr.bin/texinfo/libtxi/Makefile b/gnu/usr.bin/texinfo/libtxi/Makefile new file mode 100644 index 0000000..3f5e8ac --- /dev/null +++ b/gnu/usr.bin/texinfo/libtxi/Makefile @@ -0,0 +1,20 @@ +# +# $Id$ +# + +TXIDIR= ${.CURDIR}/../../../../contrib/texinfo/libtxi + +.PATH: $(TXIDIR) + +LIB= txi + +SRCS+= getopt.c getopt1.c + +NOPROFILE= NO +NOPIC= NO +NOSHARED= NO + +install: + @true + +.include <bsd.lib.mk> diff --git a/gnu/usr.bin/texinfo/makedoc/Makefile b/gnu/usr.bin/texinfo/makedoc/Makefile deleted file mode 100644 index d97ec09..0000000 --- a/gnu/usr.bin/texinfo/makedoc/Makefile +++ /dev/null @@ -1,20 +0,0 @@ -# -# Bmakefile for GNU info -# -# $Id: Makefile,v 1.2 1994/09/15 13:10:41 jkh Exp $ -# - -PROG= makedoc -NOMAN=yes -SRCS+= makedoc.c xmalloc.c - -CFLAGS+= -I${.CURDIR}/../info -I${.CURDIR} -CFLAGS+= -DNAMED_FUNCTIONS=1 -DSTDC_HEADERS=1 -CFLAGS+= -DHAVE_UNISTD_H=1 -DHAVE_STRING_H=1 -DHAVE_VARARGS_H=1 -CFLAGS+= -DHAVE_SYS_FCNTL_H=1 -DHAVE_SETVBUF=1 -DHAVE_GETCWD=1 -DHAVE_BZERO=1 -CFLAGS+= -DHAVE_RINDEX=1 -DHAVE_VFPRINTF=1 -DHAVE_VSPRINTF=1 -CFLAGS+= -DHAVE_SYS_TIME_H=1 -DDEFAULT_INFOPATH='"${INFODIR}"' - -.include "../../Makefile.inc" -.include <bsd.prog.mk> - diff --git a/gnu/usr.bin/texinfo/makedoc/makedoc.c b/gnu/usr.bin/texinfo/makedoc/makedoc.c deleted file mode 100644 index ddf19b7..0000000 --- a/gnu/usr.bin/texinfo/makedoc/makedoc.c +++ /dev/null @@ -1,477 +0,0 @@ -/* makedoc.c -- Make DOC.C and FUNS.H from input files. */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - Copyright (C) 1993 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -/* This program grovels the contents of the source files passed as arguments - and writes out a file of function pointers and documentation strings, and - a header file which describes the contents. This only does the functions - declared with DECLARE_INFO_COMMAND. */ - -#include <stdio.h> -#include <ctype.h> -#include <sys/types.h> -#include <sys/file.h> -#include <sys/stat.h> -#include "general.h" - -#if !defined (O_RDONLY) -#if defined (HAVE_SYS_FCNTL_H) -#include <sys/fcntl.h> -#else /* !HAVE_SYS_FCNTL_H */ -#include <fcntl.h> -#endif /* !HAVE_SYS_FCNTL_H */ -#endif /* !O_RDONLY */ - -extern void *xmalloc (), *xrealloc (); -static void fatal_file_error (); - -/* Name of the header file which receives the declarations of functions. */ -static char *funs_filename = "funs.h"; - -/* Name of the documentation to function pointer file. */ -static char *doc_filename = "doc.c"; - -static char *doc_header[] = { - "/* doc.c -- Generated structure containing function names and doc strings.", - "", - " This file was automatically made from various source files with the", - " command \"%s\". DO NOT EDIT THIS FILE, only \"%s.c\".", - (char *)NULL -}; - -static char *doc_header_1[] = { - " An entry in the array FUNCTION_DOC_ARRAY is made for each command", - " found in the above files; each entry consists of a function pointer,", -#if defined (NAMED_FUNCTIONS) - " a string which is the user-visible name of the function,", -#endif /* NAMED_FUNCTIONS */ - " and a string which documents its purpose. */", - "", - "#include \"doc.h\"", - "#include \"funs.h\"", - "", - "FUNCTION_DOC function_doc_array[] = {", - "", - (char *)NULL -}; - -/* How to remember the locations of the functions found so that Emacs - can use the information in a tag table. */ -typedef struct { - char *name; /* Name of the tag. */ - int line; /* Line number at which it appears. */ - long char_offset; /* Character offset at which it appears. */ -} EMACS_TAG; - -typedef struct { - char *filename; /* Name of the file containing entries. */ - long entrylen; /* Total number of characters in tag block. */ - EMACS_TAG **entries; /* Entries found in FILENAME. */ - int entries_index; - int entries_slots; -} EMACS_TAG_BLOCK; - -EMACS_TAG_BLOCK **emacs_tags = (EMACS_TAG_BLOCK **)NULL; -int emacs_tags_index = 0; -int emacs_tags_slots = 0; - -#define DECLARATION_STRING "\nDECLARE_INFO_COMMAND" - -static void process_one_file (); -static void maybe_dump_tags (); -static FILE *must_fopen (); - -int -main (argc, argv) - int argc; - char **argv; -{ - register int i; - int tags_only = 0; - FILE *funs_stream, *doc_stream; - - for (i = 1; i < argc; i++) - if (strcmp (argv[i], "-tags") == 0) - { - tags_only++; - break; - } - - if (tags_only) - { - funs_filename = "/dev/null"; - doc_filename = "/dev/null"; - } - - funs_stream = must_fopen (funs_filename, "w"); - doc_stream = must_fopen (doc_filename, "w"); - - fprintf (funs_stream, - "/* %s -- Generated declarations for Info commands. */\n", - funs_filename); - - for (i = 0; doc_header[i]; i++) - { - fprintf (doc_stream, doc_header[i], argv[0], argv[0]); - fprintf (doc_stream, "\n"); - } - - fprintf (doc_stream, - " Source files groveled to make this file include:\n\n"); - - for (i = 1; i < argc; i++) - fprintf (doc_stream, "\t%s\n", argv[i]); - - fprintf (doc_stream, "\n"); - - for (i = 0; doc_header_1[i]; i++) - fprintf (doc_stream, "%s\n", doc_header_1[i]); - - - for (i = 1; i < argc; i++) - { - char *curfile; - curfile = argv[i]; - - if (*curfile == '-') - continue; - - fprintf (doc_stream, "/* Commands found in \"%s\". */\n", curfile); - fprintf (funs_stream, "\n/* Functions declared in \"%s\". */\n", - curfile); - - process_one_file (curfile, doc_stream, funs_stream); - } - - fprintf (doc_stream, - " { (VFunction *)NULL, (char *)NULL, (char *)NULL }\n};\n"); - - fclose (funs_stream); - fclose (doc_stream); - - if (tags_only) - maybe_dump_tags (stdout); - exit (0); -} - -/* Dumping out the contents of an Emacs tags table. */ -static void -maybe_dump_tags (stream) - FILE *stream; -{ - register int i; - - /* Print out the information for each block. */ - for (i = 0; i < emacs_tags_index; i++) - { - register int j; - register EMACS_TAG_BLOCK *block; - register EMACS_TAG *etag; - long block_len; - - block_len = 0; - block = emacs_tags[i]; - - /* Calculate the length of the dumped block first. */ - for (j = 0; j < block->entries_index; j++) - { - char digits[30]; - etag = block->entries[j]; - block_len += 3 + strlen (etag->name); - sprintf (digits, "%d,%d", etag->line, etag->char_offset); - block_len += strlen (digits); - } - - /* Print out the defining line. */ - fprintf (stream, "\f\n%s,%d\n", block->filename, block_len); - - /* Print out the individual tags. */ - for (j = 0; j < block->entries_index; j++) - { - etag = block->entries[j]; - - fprintf (stream, "%s,\177%d,%d\n", - etag->name, etag->line, etag->char_offset); - } - } -} - -/* Keeping track of names, line numbers and character offsets of functions - found in source files. */ -static EMACS_TAG_BLOCK * -make_emacs_tag_block (filename) - char *filename; -{ - EMACS_TAG_BLOCK *block; - - block = (EMACS_TAG_BLOCK *)xmalloc (sizeof (EMACS_TAG_BLOCK)); - block->filename = savestring (filename); - block->entrylen = 0; - block->entries = (EMACS_TAG **)NULL; - block->entries_index = 0; - block->entries_slots = 0; - return (block); -} - -static void -add_tag_to_block (block, name, line, char_offset) - EMACS_TAG_BLOCK *block; - char *name; - int line; - long char_offset; -{ - EMACS_TAG *tag; - - tag = (EMACS_TAG *)xmalloc (sizeof (EMACS_TAG)); - tag->name = name; - tag->line = line; - tag->char_offset = char_offset; - add_pointer_to_array (tag, block->entries_index, block->entries, - block->entries_slots, 50, EMACS_TAG *); -} - -/* Read the file represented by FILENAME into core, and search it for Info - function declarations. Output the declarations in various forms to the - DOC_STREAM and FUNS_STREAM. */ -static void -process_one_file (filename, doc_stream, funs_stream) - char *filename; - FILE *doc_stream, *funs_stream; -{ - int descriptor, decl_len; - char *buffer, *decl_str; - struct stat finfo; - long offset; - EMACS_TAG_BLOCK *block; - - if (stat (filename, &finfo) == -1) - fatal_file_error (filename); - - descriptor = open (filename, O_RDONLY, 0666); - - if (descriptor == -1) - fatal_file_error (filename); - - buffer = (char *)xmalloc (1 + finfo.st_size); - read (descriptor, buffer, finfo.st_size); - close (descriptor); - - offset = 0; - decl_str = DECLARATION_STRING; - decl_len = strlen (decl_str); - - block = make_emacs_tag_block (filename); - - while (1) - { - long point = 0; - long line_start = 0; - int line_number = 0; - - char *func, *doc; -#if defined (NAMED_FUNCTIONS) - char *func_name; -#endif /* NAMED_FUNCTIONS */ - - for (; offset < (finfo.st_size - decl_len); offset++) - { - if (buffer[offset] == '\n') - { - line_number++; - line_start = offset + 1; - } - - if (strncmp (buffer + offset, decl_str, decl_len) == 0) - { - offset += decl_len; - point = offset; - break; - } - } - - if (!point) - break; - - /* Skip forward until we find the open paren. */ - while (point < finfo.st_size) - { - if (buffer[point] == '\n') - { - line_number++; - line_start = point + 1; - } - else if (buffer[point] == '(') - break; - - point++; - } - - while (point++ < finfo.st_size) - { - if (!whitespace_or_newline (buffer[point])) - break; - else if (buffer[point] == '\n') - { - line_number++; - line_start = point + 1; - } - } - - if (point >= finfo.st_size) - break; - - /* Now looking at name of function. Get it. */ - for (offset = point; buffer[offset] != ','; offset++); - func = (char *)xmalloc (1 + (offset - point)); - strncpy (func, buffer + point, offset - point); - func[offset - point] = '\0'; - - /* Remember this tag in the current block. */ - { - char *tag_name; - - tag_name = (char *)xmalloc (1 + (offset - line_start)); - strncpy (tag_name, buffer + line_start, offset - line_start); - tag_name[offset - line_start] = '\0'; - add_tag_to_block (block, tag_name, line_number, point); - } - -#if defined (NAMED_FUNCTIONS) - /* Generate the user-visible function name from the function's name. */ - { - register int i; - char *name_start; - - name_start = func; - - if (strncmp (name_start, "info_", 5) == 0) - name_start += 5; - - func_name = savestring (name_start); - - /* Fix up "ea" commands. */ - if (strncmp (func_name, "ea_", 3) == 0) - { - char *temp_func_name; - - temp_func_name = (char *)xmalloc (10 + strlen (func_name)); - strcpy (temp_func_name, "echo_area_"); - strcat (temp_func_name, func_name + 3); - free (func_name); - func_name = temp_func_name; - } - - for (i = 0; func_name[i]; i++) - if (func_name[i] == '_') - func_name[i] = '-'; - } -#endif /* NAMED_FUNCTIONS */ - - /* Find doc string. */ - point = offset + 1; - - while (point < finfo.st_size) - { - if (buffer[point] == '\n') - { - line_number++; - line_start = point + 1; - } - - if (buffer[point] == '"') - break; - else - point++; - } - - offset = point + 1; - - while (offset < finfo.st_size) - { - if (buffer[offset] == '\n') - { - line_number++; - line_start = offset + 1; - } - - if (buffer[offset] == '\\') - offset += 2; - else if (buffer[offset] == '"') - break; - else - offset++; - } - - offset++; - if (offset >= finfo.st_size) - break; - - doc = (char *)xmalloc (1 + (offset - point)); - strncpy (doc, buffer + point, offset - point); - doc[offset - point] = '\0'; - -#if defined (NAMED_FUNCTIONS) - fprintf (doc_stream, " { %s, \"%s\", %s },\n", func, func_name, doc); - free (func_name); -#else /* !NAMED_FUNCTIONS */ - fprintf (doc_stream, " { %s, %s },\n", func, doc); -#endif /* !NAMED_FUNCTIONS */ - - fprintf (funs_stream, "extern void %s ();\n", func); - free (func); - free (doc); - } - free (buffer); - - /* If we created any tags, remember this file on our global list. Otherwise, - free the memory already allocated to it. */ - if (block->entries) - add_pointer_to_array (block, emacs_tags_index, emacs_tags, - emacs_tags_slots, 10, EMACS_TAG_BLOCK *); - else - { - free (block->filename); - free (block); - } -} - -static void -fatal_file_error (filename) - char *filename; -{ - fprintf (stderr, "Couldn't manipulate the file %s.\n", filename); - exit (2); -} - -static FILE * -must_fopen (filename, mode) - char *filename, *mode; -{ - FILE *stream; - - stream = fopen (filename, mode); - if (!stream) - fatal_file_error (filename); - - return (stream); -} - diff --git a/gnu/usr.bin/texinfo/makedoc/xmalloc.c b/gnu/usr.bin/texinfo/makedoc/xmalloc.c deleted file mode 100644 index 6ebb84c..0000000 --- a/gnu/usr.bin/texinfo/makedoc/xmalloc.c +++ /dev/null @@ -1,78 +0,0 @@ -/* xmalloc.c -- safe versions of malloc and realloc */ - -/* This file is part of GNU Info, a program for reading online documentation - stored in Info format. - - This file has appeared in prior works by the Free Software Foundation; - thus it carries copyright dates from 1988 through 1993. - - Copyright (C) 1988, 1989, 1990, 1991, 1992, 1993 Free Software - Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Written by Brian Fox (bfox@ai.mit.edu). */ - -#if !defined (ALREADY_HAVE_XMALLOC) -#include <stdio.h> - -static void memory_error_and_abort (); - -/* **************************************************************** */ -/* */ -/* Memory Allocation and Deallocation. */ -/* */ -/* **************************************************************** */ - -/* Return a pointer to free()able block of memory large enough - to hold BYTES number of bytes. If the memory cannot be allocated, - print an error message and abort. */ -void * -xmalloc (bytes) - int bytes; -{ - void *temp = (void *)malloc (bytes); - - if (!temp) - memory_error_and_abort ("xmalloc"); - return (temp); -} - -void * -xrealloc (pointer, bytes) - void *pointer; - int bytes; -{ - void *temp; - - if (!pointer) - temp = (void *)malloc (bytes); - else - temp = (void *)realloc (pointer, bytes); - - if (!temp) - memory_error_and_abort ("xrealloc"); - - return (temp); -} - -static void -memory_error_and_abort (fname) - char *fname; -{ - fprintf (stderr, "%s: Out of virtual memory!\n", fname); - abort (); -} -#endif /* !ALREADY_HAVE_XMALLOC */ diff --git a/gnu/usr.bin/texinfo/makeinfo/Makefile b/gnu/usr.bin/texinfo/makeinfo/Makefile index e102200..cdd8a88 100644 --- a/gnu/usr.bin/texinfo/makeinfo/Makefile +++ b/gnu/usr.bin/texinfo/makeinfo/Makefile @@ -1,22 +1,25 @@ # -# Bmakefile for GNU info -# -# $Id: Makefile,v 1.2 1994/09/15 13:11:36 jkh Exp $ +# $Id$ # +MAKEINFODIR= ${.CURDIR}/../../../../contrib/texinfo/makeinfo +TXIDIR= ${.CURDIR}/../../../../contrib/texinfo/libtxi +LIBTXI= ${.CURDIR}/../libtxi/libtxi.a +BINDIR= /usr/bin + PROG= makeinfo NOMAN=yes -SRCS+= makeinfo.c getopt1.c getopt.c +SRCS+= makeinfo.c multi.c -.PATH: ${.CURDIR}/../info +CFLAGS+= -DSTDC_HEADERS=1 -DHAVE_UNISTD_H=1 -DHAVE_TERMIOS_H=1 -DHAVE_STRINGS_H=1 -DHAVE_STRING_H=1 +CFLAGS+= -DHAVE_VARARGS_H=1 -DHAVE_SYS_TIME_H=1 -DHAVE_SYS_FCNTL_H=1 -DHAVE_SYS_FILE_H=1 -DHAVE_ALLOCA=1 +CFLAGS+= -DHAVE_SETVBUF=1 -DHAVE_GETCWD=1 -DHAVE_MEMSET=1 -DHAVE_BZERO=1 -DHAVE_STRCHR=1 +CFLAGS+= -DHAVE_STRCASECMP=1 -DHAVE_VFPRINTF=1 -DHAVE_VSPRINTF=1 -DHAVE_STRERROR=1 -DHAVE_SIGPROCMASK=1 +CFLAGS+= -DHAVE_SIGSETMASK=1 -I../libtxi -I$(TXIDIR) -CFLAGS+= -I${.CURDIR}/../info -I${.CURDIR} -CFLAGS+= -DNAMED_FUNCTIONS=1 -DSTDC_HEADERS=1 -CFLAGS+= -DHAVE_UNISTD_H=1 -DHAVE_STRING_H=1 -DHAVE_VARARGS_H=1 -CFLAGS+= -DHAVE_SYS_FCNTL_H=1 -DHAVE_SETVBUF=1 -DHAVE_GETCWD=1 -DHAVE_BZERO=1 -CFLAGS+= -DHAVE_RINDEX=1 -DHAVE_VFPRINTF=1 -DHAVE_VSPRINTF=1 -CFLAGS+= -DHAVE_SYS_TIME_H=1 -DDEFAULT_INFOPATH='"${INFODIR}"' +LDADD+= -L../libtxi -ltxi +DPADD+= ${LIBTXI} -.include "../../Makefile.inc" -.include <bsd.prog.mk> +.PATH: $(MAKEINFODIR) +.include <bsd.prog.mk> diff --git a/gnu/usr.bin/texinfo/makeinfo/makeinfo.c b/gnu/usr.bin/texinfo/makeinfo/makeinfo.c deleted file mode 100644 index 1e292922..0000000 --- a/gnu/usr.bin/texinfo/makeinfo/makeinfo.c +++ /dev/null @@ -1,7549 +0,0 @@ -/* Makeinfo -- convert texinfo format files into info files. - - Copyright (C) 1987, 1992, 1993 Free Software Foundation, Inc. - - This file is part of GNU Info. - - Makeinfo is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY. No author or distributor accepts - responsibility to anyone for the consequences of using it or for - whether it serves any particular purpose or works at all, unless he - says so in writing. Refer to the GNU Emacs General Public License - for full details. - - Everyone is granted permission to copy, modify and redistribute - Makeinfo, but only under the conditions described in the GNU Emacs - General Public License. A copy of this license is supposed to - have been given to you along with GNU Emacs so you can know your - rights and responsibilities. It should be in a file named COPYING. - Among other things, the copyright notice and this notice must be - preserved on all copies. */ - -/* This is Makeinfo version 1.55. If you change the version number of - Makeinfo, please change it here and at the lines reading: - - int major_version = 1; - int minor_version = 55; - - in the code below. - - Makeinfo is authored by Brian Fox (bfox@ai.mit.edu). */ - -/* You can change some of the behaviour of Makeinfo by changing the - following defines: */ - -/* Define INDENT_PARAGRAPHS_IN_TABLE if you want the paragraphs which - appear within an @table, @ftable, or @itemize environment to have - standard paragraph indentation. Without this, such paragraphs have - no starting indentation. */ -/* #define INDENT_PARAGRAPHS_IN_TABLE */ - -/* Define DEFAULT_INDENTATION_INCREMENT as an integer which is the amount - that @example should increase indentation by. This incremement is used - for all insertions which indent the enclosed text. */ -#define DEFAULT_INDENTATION_INCREMENT 5 - -/* Define PARAGRAPH_START_INDENT to be the amount of indentation that - the first lines of paragraphs receive by default, where no other - value has been specified. Users can change this value on the command - line, with the +paragraph-indent option, or within the texinfo file, - with the @paragraphindent command. */ -#define PARAGRAPH_START_INDENT 3 - -/* Define DEFAULT_PARAGRAPH_SPACING as the number of blank lines that you - wish to appear between paragraphs. A value of 1 creates a single blank - line between paragraphs. Paragraphs are defined by 2 or more consecutive - newlines in the input file (i.e., one or more blank lines). */ -#define DEFAULT_PARAGRAPH_SPACING 1 - -/* **************************************************************** */ -/* */ -/* Include File Declarations */ -/* */ -/* **************************************************************** */ - -/* Indent #pragma so that older Cpp's don't try to parse it. */ -#if defined (_AIX) - # pragma alloca -#endif /* _AIX */ - -#include <stdio.h> -#include <sys/types.h> -#include <ctype.h> -#include <sys/stat.h> -#include <ctype.h> -#include <pwd.h> -#include <errno.h> -#if defined (HAVE_VARARGS_H) -#include <varargs.h> -#endif /* HAVE_VARARGS_H */ -#include "getopt.h" - -#if defined (VMS) -#include <perror.h> -#endif - -#if defined (HAVE_STRING_H) -#include <string.h> -#else -#include <strings.h> -#endif /* !HAVE_STRING_H */ - -#if defined (TM_IN_SYS_TIME) -#include <sys/time.h> -#else -#include <time.h> -#endif /* !TM_IN_SYS_TIME */ - -#if defined (HAVE_SYS_FCNTL_H) -#include <sys/fcntl.h> -#else -#include <fcntl.h> -#endif /* !HAVE_SYS_FCNTL_H */ - -#include <sys/file.h> - -#if defined (__GNUC__) -#define alloca __builtin_alloca -#else -#if defined(HAVE_ALLOCA_H) -#include <alloca.h> -#else /* !HAVE_ALLOCA_H */ -#if !defined (_AIX) -extern char *alloca (); -#endif /* !_AIX */ -#endif /* !HAVE_ALLOCA_H */ -#endif /* !__GNUC__ */ - -void *xmalloc (), *xrealloc (); -static void isolate_nodename (); - -/* Non-zero means that we are currently hacking the insides of an - insertion which would use a fixed width font. */ -static int in_fixed_width_font = 0; - -/* Non-zero means that start_paragraph () MUST be called before we pay - any attention to close_paragraph () calls. */ -int must_start_paragraph = 0; - -/* Some systems don't declare this function in pwd.h. */ -struct passwd *getpwnam (); - - -/* **************************************************************** */ -/* */ -/* Global Defines */ -/* */ -/* **************************************************************** */ - -/* Error levels */ -#define NO_ERROR 0 -#define SYNTAX 2 -#define FATAL 4 - -/* How to allocate permanent storage for STRING. */ -#define savestring(x) \ - ((char *)strcpy ((char *)xmalloc (1 + ((x) ? strlen (x) : 0)), \ - (x) ? (x) : "")) - -/* C's standard macros don't check to make sure that the characters being - changed are within range. So I have to check explicitly. */ - -/* GNU Library doesn't have toupper(). Until GNU gets this fixed, I will - have to do it. */ -#ifndef toupper -#define toupper(c) ((c) - 32) -#endif - -#define coerce_to_upper(c) ((islower(c) ? toupper(c) : (c))) -#define coerce_to_lower(c) ((isupper(c) ? tolower(c) : (c))) - -#define control_character_bit 0x40 /* %01000000, must be off. */ -#define meta_character_bit 0x080/* %10000000, must be on. */ -#define CTL(c) ((c) & (~control_character_bit)) -#define UNCTL(c) coerce_to_upper(((c)|control_character_bit)) -#define META(c) ((c) | (meta_character_bit)) -#define UNMETA(c) ((c) & (~meta_character_bit)) - -#define whitespace(c) (((c) == '\t') || ((c) == ' ')) -#define sentence_ender(c) ((c) == '.' || (c) == '?' || (c) == '!') -#define cr_or_whitespace(c) (((c) == '\t') || ((c) == ' ') || ((c) == '\n')) - -#ifndef isletter -#define isletter(c) (((c) >= 'A' && (c) <= 'Z') || ((c) >= 'a' && (c) <= 'z')) -#endif - -#ifndef isupper -#define isupper(c) ((c) >= 'A' && (c) <= 'Z') -#endif - -#ifndef isdigit -#define isdigit(c) ((c) >= '0' && (c) <= '9') -#endif - -#ifndef digit_value -#define digit_value(c) ((c) - '0') -#endif - -#define member(c, s) (strchr (s, c) != NULL) - -#define COMMAND_PREFIX '@' - -/* Stuff for splitting large files. */ -#define SPLIT_SIZE_THRESHOLD 70000 /* What's good enough for Stallman... */ -#define DEFAULT_SPLIT_SIZE 50000 /* Is probably good enough for me. */ -int splitting = 1; /* Always true for now. */ - -typedef int FUNCTION (); /* So I can say FUNCTION *foo; */ - - -/* **************************************************************** */ -/* */ -/* Global Variables */ -/* */ -/* **************************************************************** */ - -/* Global pointer to argv[0]. */ -char *progname; - -/* The current input file state. */ -char *input_filename; -char *input_text; -int size_of_input_text; -int input_text_offset; -int line_number; - -#define curchar() input_text[input_text_offset] - -#define command_char(c) ((!whitespace(c)) && \ - ((c) != '\n') && \ - ((c) != '{') && \ - ((c) != '}') && \ - ((c) != '=')) - -#define skip_whitespace() while (input_text_offset != size_of_input_text \ - && whitespace(curchar()))\ - input_text_offset++ - -/* Return non-zero if STRING is the text at input_text + input_text_offset, - else zero. */ -#define looking_at(string) \ - (strncmp (input_text + input_text_offset, string, strlen (string)) == 0) - -/* And writing to the output. */ - -/* The output file name. */ -char *output_filename = (char *)NULL; -char *pretty_output_filename; - -/* Name of the output file that the user elected to pass on the command line. - Such a name overrides any name found with the @setfilename command. */ -char *command_output_filename = (char *)NULL; - -/* A colon separated list of directories to search for files included - with @include. This can be controlled with the `-I' option to makeinfo. */ -char *include_files_path = (char *)NULL; - -/* Current output stream. */ -FILE *output_stream; - -/* Position in the output file. */ -int output_position; - -/* Output paragraph buffer. */ -unsigned char *output_paragraph; - -/* Offset into OUTPUT_PARAGRAPH. */ -int output_paragraph_offset; - -/* The output paragraph "cursor" horizontal position. */ -int output_column = 0; - -/* Non-zero means output_paragraph contains text. */ -int paragraph_is_open = 0; - -#define INITIAL_PARAGRAPH_SPACE 5000 -int paragraph_buffer_len = INITIAL_PARAGRAPH_SPACE; - -/* Filling.. */ -/* Non-zero indicates that filling will take place on long lines. */ -int filling_enabled = 1; - -/* Non-zero means that words are not to be split, even in long lines. This - gets changed for cm_w (). */ -int non_splitting_words = 0; - -/* Non-zero indicates that filling a line also indents the new line. */ -int indented_fill = 0; - -/* The column at which long lines are broken. */ -int fill_column = 72; - -/* The amount of indentation to apply at the start of each line. */ -int current_indent = 0; - -/* The amount of indentation to add at the starts of paragraphs. - 0 means don't change existing indentation at paragraph starts. - > 0 is amount to indent new paragraphs by. - < 0 means indent to column zero by removing indentation if necessary. - - This is normally zero, but some people prefer paragraph starts to be - somewhat more indented than paragraph bodies. A pretty value for - this is 3. */ -int paragraph_start_indent = PARAGRAPH_START_INDENT; - -/* Non-zero means that the use of paragraph_start_indent is inhibited. - @example uses this to line up the left columns of the example text. - A negative value for this variable is incremented each time it is used. - @noindent uses this to inhibit indentation for a single paragraph. */ -int inhibit_paragraph_indentation = 0; - -/* Indentation that is pending insertion. We have this for hacking lines - which look blank, but contain whitespace. We want to treat those as - blank lines. */ -int pending_indent = 0; - -/* The amount that indentation increases/decreases by. */ -int default_indentation_increment = DEFAULT_INDENTATION_INCREMENT; - -/* Non-zero indicates that indentation is temporarily turned off. */ -int no_indent = 1; - -/* Non-zero means forcing output text to be flushright. */ -int force_flush_right = 0; - -/* Non-zero means that the footnote style for this document was set on - the command line, which overrides any other settings. */ -int footnote_style_preset = 0; - -/* Non-zero means that we automatically number footnotes that have no - specified marker. */ -int number_footnotes = 1; - -/* The current footnote number in this node. Each time a new node is - started this is reset to 1. */ -int current_footnote_number = 1; - -/* Command name in the process of being hacked. */ -char *command; - -/* The index in our internal command table of the currently - executing command. */ -int command_index; - -/* A stack of file information records. If a new file is read in with - "@input", we remember the old input file state on this stack. */ -typedef struct fstack -{ - struct fstack *next; - char *filename; - char *text; - int size; - int offset; - int line_number; -} FSTACK; - -FSTACK *filestack = (FSTACK *) NULL; - -/* Stuff for nodes. */ -/* The current nodes node name. */ -char *current_node = (char *)NULL; - -/* The current nodes section level. */ -int current_section = 0; - -/* The filename of the current input file. This is never freed. */ -char *node_filename = (char *)NULL; - -/* What we remember for each node. */ -typedef struct tentry -{ - struct tentry *next_ent; - char *node; /* name of this node. */ - char *prev; /* name of "Prev:" for this node. */ - char *next; /* name of "Next:" for this node. */ - char *up; /* name of "Up:" for this node. */ - int position; /* output file position of this node. */ - int line_no; /* defining line in source file. */ - char *filename; /* The file that this node was found in. */ - int touched; /* non-zero means this node has been referenced. */ - int flags; /* Room for growth. Right now, contains 1 bit. */ -} TAG_ENTRY; - -/* If node-a has a "Next" for node-b, but node-b has no "Prev" for node-a, - we turn on this flag bit in node-b's tag entry. This means that when - it is time to validate node-b, we don't report an additional error - if there was no "Prev" field. */ -#define PREV_ERROR 0x1 -#define NEXT_ERROR 0x2 -#define UP_ERROR 0x4 -#define NO_WARN 0x8 -#define IS_TOP 0x10 - -TAG_ENTRY *tag_table = (TAG_ENTRY *) NULL; - -#define HAVE_MACROS -#if defined (HAVE_MACROS) -/* Macro definitions for user-defined commands. */ -typedef struct { - char *name; /* Name of the macro. */ - char *definition; /* Definition text. */ - char *filename; /* File where this macro is defined. */ - int lineno; /* Line number within FILENAME. */ -} MACRO_DEF; - -void add_macro (), execute_macro (); -MACRO_DEF *find_macro (), *delete_macro (); -#endif /* HAVE_MACROS */ - -/* Menu reference, *note reference, and validation hacking. */ - -/* The various references that we know about. */ -enum reftype -{ - menu_reference, followed_reference -}; - -/* A structure to remember references with. A reference to a node is - either an entry in a menu, or a cross-reference made with [px]ref. */ -typedef struct node_ref -{ - struct node_ref *next; - char *node; /* Name of node referred to. */ - char *containing_node; /* Name of node containing this reference. */ - int line_no; /* Line number where the reference occurs. */ - int section; /* Section level where the reference occurs. */ - char *filename; /* Name of file where the reference occurs. */ - enum reftype type; /* Type of reference, either menu or note. */ -} NODE_REF; - -/* The linked list of such structures. */ -NODE_REF *node_references = (NODE_REF *) NULL; - -/* Flag which tells us whether to examine menu lines or not. */ -int in_menu = 0; - -/* Flags controlling the operation of the program. */ - -/* Default is to notify users of bad choices. */ -int print_warnings = 1; - -/* Default is to check node references. */ -int validating = 1; - -/* Non-zero means do not output "Node: Foo" for node separations. */ -int no_headers = 0; - -/* Number of errors that we tolerate on a given fileset. */ -int max_error_level = 100; - -/* Maximum number of references to a single node before complaining. */ -int reference_warning_limit = 1000; - -/* Non-zero means print out information about what is going on when it - is going on. */ -int verbose_mode = 0; - -/* The list of commands that we hack in texinfo. Each one - has an associated function. When the command is encountered in the - text, the associated function is called with START as the argument. - If the function expects arguments in braces, it remembers itself on - the stack. When the corresponding close brace is encountered, the - function is called with END as the argument. */ - -#define START 0 -#define END 1 - -typedef struct brace_element -{ - struct brace_element *next; - FUNCTION *proc; - int pos, line; -} BRACE_ELEMENT; - -BRACE_ELEMENT *brace_stack = (BRACE_ELEMENT *) NULL; - -/* Forward declarations. */ - -int insert_self (), cm_ignore_line (); - -int - cm_tex (), cm_asterisk (), cm_dots (), cm_bullet (), cm_TeX (), - cm_copyright (), cm_code (), cm_samp (), cm_file (), cm_kbd (), - cm_key (), cm_ctrl (), cm_var (), cm_dfn (), cm_emph (), cm_strong (), - cm_cite (), cm_italic (), cm_bold (), cm_roman (), cm_title (), cm_w (), - cm_refill (), cm_titlefont (); - -int - cm_chapter (), cm_unnumbered (), cm_appendix (), cm_top (), - cm_section (), cm_unnumberedsec (), cm_appendixsec (), - cm_subsection (), cm_unnumberedsubsec (), cm_appendixsubsec (), - cm_subsubsection (), cm_unnumberedsubsubsec (), cm_appendixsubsubsec (), - cm_heading (), cm_chapheading (), cm_subheading (), cm_subsubheading (), - cm_majorheading (), cm_raisesections (), cm_lowersections (); - -/* All @defxxx commands map to cm_defun (). */ -int cm_defun (); - -int - cm_node (), cm_menu (), cm_xref (), cm_ftable (), cm_vtable (), cm_pxref (), - cm_inforef (), cm_quotation (), cm_display (), cm_itemize (), - cm_enumerate (), cm_table (), cm_itemx (), cm_noindent (), cm_setfilename (), - cm_br (), cm_sp (), cm_page (), cm_group (), cm_center (), cm_include (), - cm_bye (), cm_item (), cm_end (), cm_infoinclude (), cm_ifinfo (), - cm_kindex (), cm_cindex (), cm_findex (), cm_pindex (), cm_vindex (), - cm_tindex (), cm_asis (), cm_synindex (), cm_printindex (), cm_minus (), - cm_footnote (), cm_force_abbreviated_whitespace (), cm_example (), - cm_smallexample (), cm_lisp (), cm_format (), cm_exdent (), cm_defindex (), - cm_defcodeindex (), cm_sc (), cm_result (), cm_expansion (), cm_equiv (), - cm_print (), cm_error (), cm_point (), cm_today (), cm_flushleft (), - cm_flushright (), cm_smalllisp (), cm_finalout (), cm_math (), - cm_cartouche (), cm_ignore_sentence_ender (); - -/* Conditionals. */ -int cm_set (), cm_clear (), cm_ifset (), cm_ifclear (), cm_value (); - -#if defined (HAVE_MACROS) -/* Define a user-defined command which is simple substitution. */ -int cm_macro (), cm_unmacro (); -#endif /* HAVE_MACROS */ - -/* Options. */ -int cm_paragraphindent (), cm_footnotestyle (); - -/* Internals. */ -int do_nothing (), command_name_condition (); -int misplaced_brace (), cm_obsolete (); - -typedef struct -{ - char *name; - FUNCTION *proc; - int argument_in_braces; -} COMMAND; - -/* Stuff for defining commands on the fly. */ -COMMAND **user_command_array = (COMMAND **) NULL; -int user_command_array_len = 0; - -#define NO_BRACE_ARGS 0 -#define BRACE_ARGS 1 - -static COMMAND CommandTable[] = { - { "!", cm_ignore_sentence_ender, NO_BRACE_ARGS }, - { "'", insert_self, NO_BRACE_ARGS }, - { "*", cm_asterisk, NO_BRACE_ARGS }, - { ".", cm_ignore_sentence_ender, NO_BRACE_ARGS }, - { ":", cm_force_abbreviated_whitespace, NO_BRACE_ARGS }, - { "?", cm_ignore_sentence_ender, NO_BRACE_ARGS }, - { "|", do_nothing, NO_BRACE_ARGS }, - { "@", insert_self, NO_BRACE_ARGS }, - { " ", insert_self, NO_BRACE_ARGS }, - { "\n", insert_self, NO_BRACE_ARGS }, - { "TeX", cm_TeX, BRACE_ARGS }, - { "`", insert_self, NO_BRACE_ARGS }, - { "appendix", cm_appendix, NO_BRACE_ARGS }, - { "appendixsection", cm_appendixsec, NO_BRACE_ARGS }, - { "appendixsec", cm_appendixsec, NO_BRACE_ARGS }, - { "appendixsubsec", cm_appendixsubsec, NO_BRACE_ARGS }, - { "appendixsubsubsec", cm_appendixsubsubsec, NO_BRACE_ARGS }, - { "asis", cm_asis, BRACE_ARGS }, - { "b", cm_bold, BRACE_ARGS }, - { "br", cm_br, NO_BRACE_ARGS }, - { "bullet", cm_bullet, BRACE_ARGS }, - { "bye", cm_bye, NO_BRACE_ARGS }, - { "c", cm_ignore_line, NO_BRACE_ARGS }, - { "cartouche", cm_cartouche, NO_BRACE_ARGS }, - { "center", cm_center, NO_BRACE_ARGS }, - { "chapheading", cm_chapheading, NO_BRACE_ARGS }, - { "chapter", cm_chapter, NO_BRACE_ARGS }, - { "cindex", cm_cindex, NO_BRACE_ARGS }, - { "cite", cm_cite, BRACE_ARGS }, - { "clear", cm_clear, NO_BRACE_ARGS }, - { "code", cm_code, BRACE_ARGS }, - { "comment", cm_ignore_line, NO_BRACE_ARGS }, - { "contents", do_nothing, NO_BRACE_ARGS }, - { "copyright", cm_copyright, BRACE_ARGS }, - { "ctrl", cm_ctrl, BRACE_ARGS }, - { "defcodeindex", cm_defcodeindex, NO_BRACE_ARGS }, - { "defindex", cm_defindex, NO_BRACE_ARGS }, - { "dfn", cm_dfn, BRACE_ARGS }, - -/* The `def' commands. */ - { "deffn", cm_defun, NO_BRACE_ARGS }, - { "deffnx", cm_defun, NO_BRACE_ARGS }, - { "defun", cm_defun, NO_BRACE_ARGS }, - { "defunx", cm_defun, NO_BRACE_ARGS }, - { "defmac", cm_defun, NO_BRACE_ARGS }, - { "defmacx", cm_defun, NO_BRACE_ARGS }, - { "defspec", cm_defun, NO_BRACE_ARGS }, - { "defspecx", cm_defun, NO_BRACE_ARGS }, - { "defvr", cm_defun, NO_BRACE_ARGS }, - { "defvrx", cm_defun, NO_BRACE_ARGS }, - { "defvar", cm_defun, NO_BRACE_ARGS }, - { "defvarx", cm_defun, NO_BRACE_ARGS }, - { "defopt", cm_defun, NO_BRACE_ARGS }, - { "defoptx", cm_defun, NO_BRACE_ARGS }, - { "deftypefn", cm_defun, NO_BRACE_ARGS }, - { "deftypefnx", cm_defun, NO_BRACE_ARGS }, - { "deftypefun", cm_defun, NO_BRACE_ARGS }, - { "deftypefunx", cm_defun, NO_BRACE_ARGS }, - { "deftypevr", cm_defun, NO_BRACE_ARGS }, - { "deftypevrx", cm_defun, NO_BRACE_ARGS }, - { "deftypevar", cm_defun, NO_BRACE_ARGS }, - { "deftypevarx", cm_defun, NO_BRACE_ARGS }, - { "defcv", cm_defun, NO_BRACE_ARGS }, - { "defcvx", cm_defun, NO_BRACE_ARGS }, - { "defivar", cm_defun, NO_BRACE_ARGS }, - { "defivarx", cm_defun, NO_BRACE_ARGS }, - { "defop", cm_defun, NO_BRACE_ARGS }, - { "defopx", cm_defun, NO_BRACE_ARGS }, - { "defmethod", cm_defun, NO_BRACE_ARGS }, - { "defmethodx", cm_defun, NO_BRACE_ARGS }, - { "deftypemethod", cm_defun, NO_BRACE_ARGS }, - { "deftypemethodx", cm_defun, NO_BRACE_ARGS }, - { "deftp", cm_defun, NO_BRACE_ARGS }, - { "deftpx", cm_defun, NO_BRACE_ARGS }, -/* The end of the `def' commands. */ - - { "display", cm_display, NO_BRACE_ARGS }, - { "dots", cm_dots, BRACE_ARGS }, - { "dmn", do_nothing, BRACE_ARGS }, - { "emph", cm_emph, BRACE_ARGS }, - { "end", cm_end, NO_BRACE_ARGS }, - { "enumerate", cm_enumerate, NO_BRACE_ARGS }, - { "equiv", cm_equiv, BRACE_ARGS }, - { "error", cm_error, BRACE_ARGS }, - { "example", cm_example, NO_BRACE_ARGS }, - { "exdent", cm_exdent, NO_BRACE_ARGS }, - { "expansion", cm_expansion, BRACE_ARGS }, - { "file", cm_file, BRACE_ARGS }, - { "findex", cm_findex, NO_BRACE_ARGS }, - { "finalout", do_nothing, NO_BRACE_ARGS }, - { "flushleft", cm_flushleft, NO_BRACE_ARGS }, - { "flushright", cm_flushright, NO_BRACE_ARGS }, - { "format", cm_format, NO_BRACE_ARGS }, - { "ftable", cm_ftable, NO_BRACE_ARGS }, - { "group", cm_group, NO_BRACE_ARGS }, - { "heading", cm_heading, NO_BRACE_ARGS }, - { "headings", cm_ignore_line, NO_BRACE_ARGS }, - { "i", cm_italic, BRACE_ARGS }, - { "iappendix", cm_appendix, NO_BRACE_ARGS }, - { "iappendixsection", cm_appendixsec, NO_BRACE_ARGS }, - { "iappendixsec", cm_appendixsec, NO_BRACE_ARGS }, - { "iappendixsubsec", cm_appendixsubsec, NO_BRACE_ARGS }, - { "iappendixsubsubsec", cm_appendixsubsubsec, NO_BRACE_ARGS }, - { "ichapter", cm_chapter, NO_BRACE_ARGS }, - { "ifclear", cm_ifclear, NO_BRACE_ARGS }, - { "ifinfo", cm_ifinfo, NO_BRACE_ARGS }, - { "ifset", cm_ifset, NO_BRACE_ARGS }, - { "iftex", command_name_condition, NO_BRACE_ARGS }, - { "ignore", command_name_condition, NO_BRACE_ARGS }, - { "include", cm_include, NO_BRACE_ARGS }, - { "inforef", cm_inforef, BRACE_ARGS }, - { "input", cm_include, NO_BRACE_ARGS }, - { "isection", cm_section, NO_BRACE_ARGS }, - { "isubsection", cm_subsection, NO_BRACE_ARGS }, - { "isubsubsection", cm_subsubsection, NO_BRACE_ARGS }, - { "item", cm_item, NO_BRACE_ARGS }, - { "itemize", cm_itemize, NO_BRACE_ARGS }, - { "itemx", cm_itemx, NO_BRACE_ARGS }, - { "iunnumbered", cm_unnumbered, NO_BRACE_ARGS }, - { "iunnumberedsec", cm_unnumberedsec, NO_BRACE_ARGS }, - { "iunnumberedsubsec", cm_unnumberedsubsec, NO_BRACE_ARGS }, - { "iunnumberedsubsubsec", cm_unnumberedsubsubsec, NO_BRACE_ARGS }, - { "kbd", cm_kbd, BRACE_ARGS }, - { "key", cm_key, BRACE_ARGS }, - { "kindex", cm_kindex, NO_BRACE_ARGS }, - { "lowersections", cm_lowersections, NO_BRACE_ARGS }, - { "lisp", cm_lisp, NO_BRACE_ARGS }, - { "macro", cm_macro, NO_BRACE_ARGS }, - { "majorheading", cm_majorheading, NO_BRACE_ARGS }, - { "math", cm_math, BRACE_ARGS }, - { "menu", cm_menu, NO_BRACE_ARGS }, - { "minus", cm_minus, BRACE_ARGS }, - { "need", cm_ignore_line, NO_BRACE_ARGS }, - { "node", cm_node, NO_BRACE_ARGS }, - { "noindent", cm_noindent, NO_BRACE_ARGS }, - { "nwnode", cm_node, NO_BRACE_ARGS }, - { "overfullrule", cm_ignore_line, NO_BRACE_ARGS }, - { "page", do_nothing, NO_BRACE_ARGS }, - { "pindex", cm_pindex, NO_BRACE_ARGS }, - { "point", cm_point, BRACE_ARGS }, - { "print", cm_print, BRACE_ARGS }, - { "printindex", cm_printindex, NO_BRACE_ARGS }, - { "pxref", cm_pxref, BRACE_ARGS }, - { "quotation", cm_quotation, NO_BRACE_ARGS }, - { "r", cm_roman, BRACE_ARGS }, - { "raisesections", cm_raisesections, NO_BRACE_ARGS }, - { "ref", cm_xref, BRACE_ARGS }, - { "refill", cm_refill, NO_BRACE_ARGS }, - { "result", cm_result, BRACE_ARGS }, - { "samp", cm_samp, BRACE_ARGS }, - { "sc", cm_sc, BRACE_ARGS }, - { "section", cm_section, NO_BRACE_ARGS }, - { "set", cm_set, NO_BRACE_ARGS }, - { "setchapternewpage", cm_ignore_line, NO_BRACE_ARGS }, - { "setchapterstyle", cm_ignore_line, NO_BRACE_ARGS }, - { "setfilename", cm_setfilename, NO_BRACE_ARGS }, - { "settitle", cm_ignore_line, NO_BRACE_ARGS }, - { "shortcontents", do_nothing, NO_BRACE_ARGS }, - { "shorttitlepage", command_name_condition, NO_BRACE_ARGS }, - { "smallbook", cm_ignore_line, NO_BRACE_ARGS }, - { "smallexample", cm_smallexample, NO_BRACE_ARGS }, - { "smalllisp", cm_smalllisp, NO_BRACE_ARGS }, - { "sp", cm_sp, NO_BRACE_ARGS }, - { "strong", cm_strong, BRACE_ARGS }, - { "subheading", cm_subheading, NO_BRACE_ARGS }, - { "subsection", cm_subsection, NO_BRACE_ARGS }, - { "subsubheading", cm_subsubheading, NO_BRACE_ARGS }, - { "subsubsection", cm_subsubsection, NO_BRACE_ARGS }, - { "summarycontents", do_nothing, NO_BRACE_ARGS }, - { "syncodeindex", cm_synindex, NO_BRACE_ARGS }, - { "synindex", cm_synindex, NO_BRACE_ARGS }, - { "t", cm_title, BRACE_ARGS }, - { "table", cm_table, NO_BRACE_ARGS }, - { "tex", command_name_condition, NO_BRACE_ARGS }, - { "tindex", cm_tindex, NO_BRACE_ARGS }, - { "titlefont", cm_titlefont, BRACE_ARGS }, - { "titlepage", command_name_condition, NO_BRACE_ARGS }, - { "titlespec", command_name_condition, NO_BRACE_ARGS }, - { "today", cm_today, BRACE_ARGS }, - { "top", cm_top, NO_BRACE_ARGS }, - { "unmacro", cm_unmacro, NO_BRACE_ARGS }, - { "unnumbered", cm_unnumbered, NO_BRACE_ARGS }, - { "unnumberedsec", cm_unnumberedsec, NO_BRACE_ARGS }, - { "unnumberedsubsec", cm_unnumberedsubsec, NO_BRACE_ARGS }, - { "unnumberedsubsubsec", cm_unnumberedsubsubsec, NO_BRACE_ARGS }, - { "value", cm_value, BRACE_ARGS }, - { "var", cm_var, BRACE_ARGS }, - { "vindex", cm_vindex, NO_BRACE_ARGS }, - { "vtable", cm_vtable, NO_BRACE_ARGS }, - { "w", cm_w, BRACE_ARGS }, - { "xref", cm_xref, BRACE_ARGS }, - { "{", insert_self, NO_BRACE_ARGS }, - { "}", insert_self, NO_BRACE_ARGS }, - - /* Some obsoleted commands. */ - { "infotop", cm_obsolete, NO_BRACE_ARGS }, - { "infounnumbered", cm_obsolete, NO_BRACE_ARGS }, - { "infounnumberedsec", cm_obsolete, NO_BRACE_ARGS }, - { "infounnumberedsubsec", cm_obsolete, NO_BRACE_ARGS }, - { "infounnumberedsubsubsec", cm_obsolete, NO_BRACE_ARGS }, - { "infoappendix", cm_obsolete, NO_BRACE_ARGS }, - { "infoappendixsec", cm_obsolete, NO_BRACE_ARGS }, - { "infoappendixsubsec", cm_obsolete, NO_BRACE_ARGS }, - { "infoappendixsubsubsec", cm_obsolete, NO_BRACE_ARGS }, - { "infochapter", cm_obsolete, NO_BRACE_ARGS }, - { "infosection", cm_obsolete, NO_BRACE_ARGS }, - { "infosubsection", cm_obsolete, NO_BRACE_ARGS }, - { "infosubsubsection", cm_obsolete, NO_BRACE_ARGS }, - - /* Now @include does what this was supposed to. */ - { "infoinclude", cm_infoinclude, NO_BRACE_ARGS }, - { "footnote", cm_footnote, NO_BRACE_ARGS}, /* self-arg eater */ - { "footnotestyle", cm_footnotestyle, NO_BRACE_ARGS }, - { "paragraphindent", cm_paragraphindent, NO_BRACE_ARGS }, - - {(char *) NULL, (FUNCTION *) NULL}, NO_BRACE_ARGS}; - -int major_version = 1; -int minor_version = 55; - -struct option long_options[] = -{ - { "error-limit", 1, 0, 'e' }, /* formerly -el */ - { "fill-column", 1, 0, 'f' }, /* formerly -fc */ - { "footnote-style", 1, 0, 's' }, /* formerly -ft */ - { "no-headers", 0, &no_headers, 1 }, /* Do not output Node: foo */ - { "no-pointer-validate", 0, &validating, 0 }, /* formerly -nv */ - { "no-validate", 0, &validating, 0 }, /* formerly -nv */ - { "no-split", 0, &splitting, 0 }, /* formerly -ns */ - { "no-warn", 0, &print_warnings, 0 }, /* formerly -nw */ - { "number-footnotes", 0, &number_footnotes, 1 }, - { "no-number-footnotes", 0, &number_footnotes, 0 }, - { "output", 1, 0, 'o' }, - { "paragraph-indent", 1, 0, 'p' }, /* formerly -pi */ - { "reference-limit", 1, 0, 'r' }, /* formerly -rl */ - { "verbose", 0, &verbose_mode, 1 }, /* formerly -verbose */ - { "version", 0, 0, 'V' }, - {NULL, 0, NULL, 0} -}; - -/* Values for calling handle_variable_internal (). */ -#define SET 1 -#define CLEAR 2 -#define IFSET 3 -#define IFCLEAR 4 - -/* **************************************************************** */ -/* */ -/* Main () Start of code */ -/* */ -/* **************************************************************** */ - -/* For each file mentioned in the command line, process it, turning - texinfo commands into wonderfully formatted output text. */ -main (argc, argv) - int argc; - char **argv; -{ - extern int errors_printed; - char *filename_part (); - int c, ind; - - /* The name of this program is the last filename in argv[0]. */ - progname = filename_part (argv[0]); - - /* Parse argument flags from the input line. */ - while ((c = getopt_long - (argc, argv, "D:U:I:f:o:p:e:r:s:V", long_options, &ind)) - != EOF) - { - if (c == 0 && long_options[ind].flag == 0) - c = long_options[ind].val; - - switch (c) - { - /* User specified variable to set or clear? */ - case 'D': - case 'U': - handle_variable_internal ((c == 'D') ? SET : CLEAR, optarg); - break; - - /* User specified include file path? */ - case 'I': - if (!include_files_path) - include_files_path = savestring ("."); - - include_files_path = (char *) - xrealloc (include_files_path, - 2 + strlen (include_files_path) + strlen (optarg)); - strcat (include_files_path, ":"); - strcat (include_files_path, optarg); - break; - - /* User specified fill_column? */ - case 'f': - if (sscanf (optarg, "%d", &fill_column) != 1) - usage (); - break; - - /* User specified output file? */ - case 'o': - command_output_filename = savestring (optarg); - break; - - /* User specified paragraph indent (paragraph_start_index)? */ - case 'p': - if (set_paragraph_indent (optarg) < 0) - usage (); - break; - - /* User specified error level? */ - case 'e': - if (sscanf (optarg, "%d", &max_error_level) != 1) - usage (); - break; - - /* User specified reference warning limit? */ - case 'r': - if (sscanf (optarg, "%d", &reference_warning_limit) != 1) - usage (); - break; - - /* User specified footnote style? */ - case 's': - if (set_footnote_style (optarg) < 0) - usage (); - footnote_style_preset = 1; - break; - - /* User requested version info? */ - case 'V': - print_version_info (); - exit (NO_ERROR); - break; - - case '?': - usage (); - } - } - - if (optind == argc) - usage (); - else if (verbose_mode) - print_version_info (); - - /* Remaining arguments are file names of texinfo files. - Convert them, one by one. */ - while (optind != argc) - convert (argv[optind++]); - - if (errors_printed) - exit (SYNTAX); - else - exit (NO_ERROR); -} - -/* Display the version info of this invocation of Makeinfo. */ -print_version_info () -{ - fprintf (stderr, "This is GNU Makeinfo version %d.%d.\n", - major_version, minor_version); -} - -/* **************************************************************** */ -/* */ -/* Generic Utilities */ -/* */ -/* **************************************************************** */ - -/* Just like malloc, but kills the program in case of fatal error. */ -void * -xmalloc (nbytes) - int nbytes; -{ - void *temp = (void *) malloc (nbytes); - - if (nbytes && temp == (void *)NULL) - memory_error ("xmalloc", nbytes); - - return (temp); -} - -/* Like realloc (), but barfs if there isn't enough memory. */ -void * -xrealloc (pointer, nbytes) - void *pointer; - int nbytes; -{ - void *temp; - - if (!pointer) - temp = (void *)xmalloc (nbytes); - else - temp = (void *)realloc (pointer, nbytes); - - if (nbytes && !temp) - memory_error ("xrealloc", nbytes); - - return (temp); -} - -memory_error (callers_name, bytes_wanted) - char *callers_name; - int bytes_wanted; -{ - char printable_string[80]; - - sprintf (printable_string, - "Virtual memory exhausted in %s ()! Needed %d bytes.", - callers_name, bytes_wanted); - - error (printable_string); - abort (); -} - -/* Tell the user how to use this program. */ -usage () -{ - fprintf (stderr, "Usage: %s [options] texinfo-file...\n\ -\n\ -This program accepts as input files of texinfo commands and text\n\ -and outputs a file suitable for reading with GNU Info.\n\ -\n\ -The options are:\n\ -`-I DIR' to add DIR to the directory search list for including\n\ - files with the `@include' command.\n\ --D VAR to define a variable, as with `@set'.\n\ --U VAR to undefine a variable, as with `@clear'.\n\ -`--no-validate' to suppress node cross reference validation.\n\ -`--no-warn' to suppress warning messages (errors are still output).\n\ -`--no-split' to suppress the splitting of large files.\n\ -`--no-headers' to suppress the output of Node: Foo headers.\n\ -`--verbose' to print information about what is being done.\n\ -`--version' to print the version number of Makeinfo.\n\ -`--output FILE' or `-o FILE'\n\ - to specify the output file. When you specify the\n\ - output file in this way, any `@setfilename' in the\n\ - input file is ignored.\n\ -`--paragraph-indent NUM'\n\ - to set the paragraph indent to NUM (default %d).\n\ -`--fill-column NUM' to set the filling column to NUM (default %d).\n\ -`--error-limit NUM' to set the error limit to NUM (default %d).\n\ -`--reference-limit NUM'\n\ - to set the reference warning limit to NUM (default %d).\n\ -`--footnote-style STYLE'\n\ - to set the footnote style to STYLE. STYLE should\n\ - either be `separate' to place footnotes in their own\n\ - node, or `end', to place the footnotes at the end of\n\ - the node in which they are defined (the default).\n\n", - progname, paragraph_start_indent, - fill_column, max_error_level, reference_warning_limit); - exit (FATAL); -} - -/* **************************************************************** */ -/* */ -/* Manipulating Lists */ -/* */ -/* **************************************************************** */ - -typedef struct generic_list { - struct generic_list *next; -} GENERIC_LIST; - -/* Reverse the chain of structures in LIST. Output the new head - of the chain. You should always assign the output value of this - function to something, or you will lose the chain. */ -GENERIC_LIST * -reverse_list (list) - register GENERIC_LIST *list; -{ - register GENERIC_LIST *next; - register GENERIC_LIST *prev = (GENERIC_LIST *) NULL; - - while (list) - { - next = list->next; - list->next = prev; - prev = list; - list = next; - } - return (prev); -} - - -/* **************************************************************** */ -/* */ -/* Pushing and Popping Files */ -/* */ -/* **************************************************************** */ - -/* Find and load the file named FILENAME. Return a pointer to - the loaded file, or NULL if it can't be loaded. */ -char * -find_and_load (filename) - char *filename; -{ - struct stat fileinfo; - int file = -1, n, i, count = 0; - char *fullpath, *result, *get_file_info_in_path (); - - result = fullpath = (char *)NULL; - - fullpath = get_file_info_in_path (filename, include_files_path, &fileinfo); - - if (!fullpath) - goto error_exit; - - filename = fullpath; - - file = open (filename, O_RDONLY); - if (file < 0) - goto error_exit; - - /* Load the file. */ - result = (char *)xmalloc (1 + fileinfo.st_size); - - /* VMS stat lies about the st_size value. The actual number of - readable bytes is always less than this value. The arcane - mysteries of VMS/RMS are too much to probe, so this hack - suffices to make things work. */ -#if defined (VMS) - while ((n = read (file, result + count, fileinfo.st_size)) > 0) - count += n; - if (n == -1) -#else /* !VMS */ - count = fileinfo.st_size; - if (read (file, result, fileinfo.st_size) != fileinfo.st_size) -#endif /* !VMS */ - error_exit: - { - if (result) - free (result); - - if (fullpath) - free (fullpath); - - if (file != -1) - close (file); - - return ((char *) NULL); - } - close (file); - - /* Set the globals to the new file. */ - input_text = result; - size_of_input_text = count; - input_filename = savestring (fullpath); - node_filename = savestring (fullpath); - input_text_offset = 0; - line_number = 1; - /* Not strictly necessary. This magic prevents read_token () from doing - extra unnecessary work each time it is called (that is a lot of times). - The SIZE_OF_INPUT_TEXT is one past the actual end of the text. */ - input_text[size_of_input_text] = '\n'; - return (result); -} - -/* Save the state of the current input file. */ -pushfile () -{ - FSTACK *newstack = (FSTACK *) xmalloc (sizeof (FSTACK)); - newstack->filename = input_filename; - newstack->text = input_text; - newstack->size = size_of_input_text; - newstack->offset = input_text_offset; - newstack->line_number = line_number; - newstack->next = filestack; - - filestack = newstack; - push_node_filename (); -} - -/* Make the current file globals be what is on top of the file stack. */ -popfile () -{ - extern int executing_string; - FSTACK *temp = filestack; - - if (!filestack) - abort (); /* My fault. I wonder what I did? */ - - /* Make sure that commands with braces have been satisfied. */ - if (!executing_string) - discard_braces (); - - /* Get the top of the stack into the globals. */ - input_filename = filestack->filename; - input_text = filestack->text; - size_of_input_text = filestack->size; - input_text_offset = filestack->offset; - line_number = filestack->line_number; - - /* Pop the stack. */ - filestack = filestack->next; - free (temp); - pop_node_filename (); -} - -/* Flush all open files on the file stack. */ -flush_file_stack () -{ - while (filestack) - { - free (input_filename); - free (input_text); - popfile (); - } -} - -int node_filename_stack_index = 0; -int node_filename_stack_size = 0; -char **node_filename_stack = (char **)NULL; - -push_node_filename () -{ - if (node_filename_stack_index + 1 > node_filename_stack_size) - { - if (!node_filename_stack) - node_filename_stack = - (char **)xmalloc ((node_filename_stack_size += 10) - * sizeof (char *)); - else - node_filename_stack = - (char **)xrealloc (node_filename_stack, - (node_filename_stack_size + 10) - * sizeof (char *)); - } - - node_filename_stack[node_filename_stack_index] = node_filename; - node_filename_stack_index++; -} - -pop_node_filename () -{ - node_filename = node_filename_stack[--node_filename_stack_index]; -} - -/* Return just the simple part of the filename; i.e. the - filename without the path information, or extensions. - This conses up a new string. */ -char * -filename_part (filename) - char *filename; -{ - char *basename; - - basename = strrchr (filename, '/'); - if (!basename) - basename = filename; - else - basename++; - - basename = savestring (basename); -#if defined (REMOVE_OUTPUT_EXTENSIONS) - - /* See if there is an extension to remove. If so, remove it. */ - { - char *temp; - - temp = strrchr (basename, '.'); - if (temp) - *temp = '\0'; - } -#endif /* REMOVE_OUTPUT_EXTENSIONS */ - return (basename); -} - -/* Return the pathname part of filename. This can be NULL. */ -char * -pathname_part (filename) - char *filename; -{ - char *expand_filename (); - char *result = (char *) NULL; - register int i; - - filename = expand_filename (filename, ""); - - i = strlen (filename) - 1; - - while (i && filename[i] != '/') - i--; - if (filename[i] == '/') - i++; - - if (i) - { - result = (char *)xmalloc (1 + i); - strncpy (result, filename, i); - result[i] = '\0'; - } - free (filename); - return (result); -} - -/* Return the expansion of FILENAME. */ -char * -expand_filename (filename, input_name) - char *filename, *input_name; -{ - char *full_pathname (); - filename = full_pathname (filename); - - if (filename[0] == '.') - return (filename); - - if (filename[0] != '/' && input_name[0] == '/') - { - /* Make it so that relative names work. */ - char *result; - int i = strlen (input_name) - 1; - - result = (char *)xmalloc (1 + strlen (input_name) + strlen (filename)); - strcpy (result, input_name); - - while (result[i] != '/' && i) - i--; - - if (result[i] == '/') - i++; - - strcpy (&result[i], filename); - free (filename); - return (result); - } - return (filename); -} - -/* Return the full path to FILENAME. */ -char * -full_pathname (filename) - char *filename; -{ - int initial_character; - - if (filename && (initial_character = *filename)) - { - if (initial_character == '/') - return (savestring (filename)); - if (initial_character != '~') - { - return (savestring (filename)); - } - else - { - if (filename[1] == '/') - { - /* Return the concatenation of HOME and the rest of the string. */ - char *temp_home; - char *temp_name; - - temp_home = (char *) getenv ("HOME"); - temp_name = (char *)xmalloc (strlen (&filename[2]) - + 1 - + temp_home ? strlen (temp_home) - : 0); - if (temp_home) - strcpy (temp_name, temp_home); - - strcat (temp_name, &filename[2]); - return (temp_name); - } - else - { - struct passwd *user_entry; - int i, c; - char *username = (char *)xmalloc (257); - char *temp_name; - - for (i = 1; c = filename[i]; i++) - { - if (c == '/') - break; - else - username[i - 1] = c; - } - if (c) - username[i - 1] = '\0'; - - user_entry = getpwnam (username); - - if (!user_entry) - return (savestring (filename)); - - temp_name = (char *)xmalloc (1 + strlen (user_entry->pw_dir) - + strlen (&filename[i])); - strcpy (temp_name, user_entry->pw_dir); - strcat (temp_name, &filename[i]); - return (temp_name); - } - } - } - else - { - return (savestring (filename)); - } -} - -/* **************************************************************** */ -/* */ -/* Error Handling */ -/* */ -/* **************************************************************** */ - -/* Number of errors encountered. */ -int errors_printed = 0; - -/* Print the last error gotten from the file system. */ -fs_error (filename) - char *filename; -{ - remember_error (); - perror (filename); - return (0); -} - -/* Print an error message, and return false. */ -#if defined (HAVE_VARARGS_H) && defined (HAVE_VFPRINTF) - -int -error (va_alist) - va_dcl -{ - char *format; - va_list args; - - remember_error (); - va_start (args); - format = va_arg (args, char *); - vfprintf (stderr, format, args); - va_end (args); - fprintf (stderr, "\n"); -} - -/* Just like error (), but print the line number as well. */ -int -line_error (va_alist) - va_dcl -{ - char *format; - va_list args; - - remember_error (); - va_start (args); - format = va_arg (args, char *); - fprintf (stderr, "%s:%d: ", input_filename, line_number); - vfprintf (stderr, format, args); - fprintf (stderr, ".\n"); - va_end (args); - return ((int) 0); -} - -int -warning (va_alist) - va_dcl -{ - char *format; - va_list args; - - va_start (args); - format = va_arg (args, char *); - if (print_warnings) - { - fprintf (stderr, "%s:%d: Warning: ", input_filename, line_number); - vfprintf (stderr, format, args); - fprintf (stderr, ".\n"); - } - va_end (args); - return ((int) 0); -} - -#else /* !(HAVE_VARARGS_H && HAVE_VFPRINTF) */ - -int -error (format, arg1, arg2, arg3, arg4, arg5) - char *format; -{ - remember_error (); - fprintf (stderr, format, arg1, arg2, arg3, arg4, arg5); - fprintf (stderr, "\n"); - return ((int) 0); -} - -/* Just like error (), but print the line number as well. */ -int -line_error (format, arg1, arg2, arg3, arg4, arg5) - char *format; -{ - remember_error (); - fprintf (stderr, "%s:%d: ", input_filename, line_number); - fprintf (stderr, format, arg1, arg2, arg3, arg4, arg5); - fprintf (stderr, ".\n"); - return ((int) 0); -} - -int -warning (format, arg1, arg2, arg3, arg4, arg5) - char *format; -{ - if (print_warnings) - { - fprintf (stderr, "%s:%d: Warning: ", input_filename, line_number); - fprintf (stderr, format, arg1, arg2, arg3, arg4, arg5); - fprintf (stderr, ".\n"); - } - return ((int) 0); -} - -#endif /* !(HAVE_VARARGS_H && HAVE_VFPRINTF) */ - -/* Remember that an error has been printed. If this is the first - error printed, then tell them which program is printing them. - If more than max_error_level have been printed, then exit the - program. */ -remember_error () -{ - errors_printed++; - if (max_error_level && (errors_printed > max_error_level)) - { - fprintf (stderr, "Too many errors! Gave up.\n"); - flush_file_stack (); - cm_bye (); - exit (1); - } -} - -/* **************************************************************** */ -/* */ -/* Hacking Tokens and Strings */ -/* */ -/* **************************************************************** */ - -/* Return the next token as a string pointer. We cons the - string. */ -char * -read_token () -{ - int i, character; - char *result; - - /* If the first character to be read is self-delimiting, then that - is the command itself. */ - character = curchar (); - if (self_delimiting (character)) - { - input_text_offset++; - result = savestring (" "); - *result = character; - return (result); - } - - for (i = 0; ((input_text_offset != size_of_input_text) - && (character = curchar ()) - && command_char (character)); - i++, input_text_offset++); - result = (char *)xmalloc (i + 1); - memcpy (result, &input_text[input_text_offset - i], i); - result[i] = '\0'; - return (result); -} - -/* Return non-zero if CHARACTER is self-delimiting. */ -int -self_delimiting (character) - int character; -{ - return (member (character, "{}:.@*'`,!?; \n")); -} - -/* Clear whitespace from the front and end of string. */ -canon_white (string) - char *string; -{ - int len = strlen (string); - int x; - - if (!len) - return; - - for (x = 0; x < len; x++) - { - if (!cr_or_whitespace (string[x])) - { - strcpy (string, string + x); - break; - } - } - len = strlen (string); - if (len) - len--; - while (len > -1 && cr_or_whitespace (string[len])) - len--; - string[len + 1] = '\0'; -} - -/* Bash STRING, replacing all whitespace with just one space. */ -fix_whitespace (string) - char *string; -{ - char *temp = (char *)xmalloc (strlen (string) + 1); - int string_index = 0; - int temp_index = 0; - int c; - - canon_white (string); - - while (string[string_index]) - { - c = temp[temp_index++] = string[string_index++]; - - if (c == ' ' || c == '\n' || c == '\t') - { - temp[temp_index - 1] = ' '; - while ((c = string[string_index]) && (c == ' ' || - c == '\t' || - c == '\n')) - string_index++; - } - } - temp[temp_index] = '\0'; - strcpy (string, temp); - free (temp); -} - -/* Discard text until the desired string is found. The string is - included in the discarded text. */ -discard_until (string) - char *string; -{ - int temp = search_forward (string, input_text_offset); - - int tt = (temp < 0) ? size_of_input_text : temp + strlen (string); - int from = input_text_offset; - - /* Find out what line we are on. */ - while (from != tt) - if (input_text[from++] == '\n') - line_number++; - - if (temp < 0) - { - input_text_offset = size_of_input_text - strlen (string); - - if (strcmp (string, "\n") != 0) - { - line_error ("Expected `%s'", string); - return; - } - } - else - input_text_offset = temp; - - input_text_offset += strlen (string); -} - -/* Read characters from the file until we are at MATCH. - Place the characters read into STRING. - On exit input_text_offset is after the match string. - Return the offset where the string starts. */ -int -get_until (match, string) - char *match, **string; -{ - int len, current_point, x, new_point, tem; - - current_point = x = input_text_offset; - new_point = search_forward (match, input_text_offset); - - if (new_point < 0) - new_point = size_of_input_text; - len = new_point - current_point; - - /* Keep track of which line number we are at. */ - tem = new_point + (strlen (match) - 1); - while (x != tem) - if (input_text[x++] == '\n') - line_number++; - - *string = (char *)xmalloc (len + 1); - - memcpy (*string, &input_text[current_point], len); - (*string)[len] = '\0'; - - /* Now leave input_text_offset in a consistent state. */ - input_text_offset = tem; - - if (input_text_offset > size_of_input_text) - input_text_offset = size_of_input_text; - - return (new_point); -} - -/* Read characters from the file until we are at MATCH or end of line. - Place the characters read into STRING. */ -get_until_in_line (match, string) - char *match, **string; -{ - int real_bottom, temp; - - real_bottom = size_of_input_text; - temp = search_forward ("\n", input_text_offset); - - if (temp < 0) - temp = size_of_input_text; - - size_of_input_text = temp; - get_until (match, string); - size_of_input_text = real_bottom; -} - -get_rest_of_line (string) - char **string; -{ - get_until ("\n", string); - canon_white (*string); - - if (curchar () == '\n') /* as opposed to the end of the file... */ - { - line_number++; - input_text_offset++; - } -} - -/* Backup the input pointer to the previous character, keeping track - of the current line number. */ -backup_input_pointer () -{ - if (input_text_offset) - { - input_text_offset--; - if (curchar () == '\n') - line_number--; - } -} - -/* Read characters from the file until we are at MATCH or closing brace. - Place the characters read into STRING. */ -get_until_in_braces (match, string) - char *match, **string; -{ - int i, brace = 0; - int match_len = strlen (match); - char *temp; - - for (i = input_text_offset; i < size_of_input_text; i++) - { - if (input_text[i] == '{') - brace++; - else if (input_text[i] == '}') - brace--; - else if (input_text[i] == '\n') - line_number++; - - if (brace < 0 || - (brace == 0 && strncmp (input_text + i, match, match_len) == 0)) - break; - } - - match_len = i - input_text_offset; - temp = (char *)xmalloc (2 + match_len); - strncpy (temp, input_text + input_text_offset, match_len); - temp[match_len] = '\0'; - input_text_offset = i; - *string = temp; -} - -/* **************************************************************** */ -/* */ -/* Converting the File */ -/* */ -/* **************************************************************** */ - -/* Convert the file named by NAME. The output is saved on the file - named as the argument to the @setfilename command. */ -static char *suffixes[] = { - "", - ".texinfo", - ".texi", - ".txinfo", - (char *)NULL -}; - -convert (name) - char *name; -{ - char *real_output_filename, *expand_filename (), *filename_part (); - char *filename = (char *)xmalloc (strlen (name) + 50); - register int i; - - init_tag_table (); - init_indices (); - init_internals (); - init_paragraph (); - - /* Try to load the file specified by NAME. If the file isn't found, and - there is no suffix in NAME, then try NAME.texinfo, and NAME.texi. */ - for (i = 0; suffixes[i]; i++) - { - strcpy (filename, name); - strcat (filename, suffixes[i]); - - if (find_and_load (filename)) - break; - - if (!suffixes[i][0] && strrchr (filename, '.')) - { - fs_error (filename); - free (filename); - return; - } - } - - if (!suffixes[i]) - { - fs_error (name); - free (filename); - return; - } - - input_filename = filename; - - /* Search this file looking for the special string which starts conversion. - Once found, we may truly begin. */ - - input_text_offset = search_forward ("@setfilename", 0); - - if (input_text_offset < 0) - { - if (!command_output_filename) - { - error ("No `@setfilename' found in `%s'", name); - goto finished; - } - } - else - input_text_offset += strlen ("@setfilename"); - - real_output_filename = (char *)NULL; - - if (!command_output_filename) - get_until ("\n", &output_filename); - else - { - if (input_text_offset != -1) - discard_until ("\n"); - else - input_text_offset = 0; - - real_output_filename = output_filename = command_output_filename; - command_output_filename = (char *)NULL; - } - - canon_white (output_filename); - printf ("Making info file `%s' from `%s'.\n", output_filename, name); - - if (verbose_mode) - fprintf (stderr, " The input file contains %d characters.\n", - size_of_input_text); - - if (real_output_filename && - strcmp (real_output_filename, "-") == 0) - { - output_stream = stdout; - } - else - { - if (!real_output_filename) - real_output_filename = expand_filename (output_filename, name); - - output_stream = fopen (real_output_filename, "w"); - } - - if (output_stream == NULL) - { - fs_error (real_output_filename); - goto finished; - } - - /* Make the displayable filename from output_filename. Only the base - portion of the filename need be displayed. */ - pretty_output_filename = filename_part (output_filename); - - /* For this file only, count the number of newlines from the top of - the file to here. This way, we keep track of line numbers for - error reporting. Line_number starts at 1, since the user isn't - zero-based. */ - { - int temp = 0; - line_number = 1; - while (temp != input_text_offset) - if (input_text[temp++] == '\n') - line_number++; - } - - if (!no_headers) - { - add_word_args ("This is Info file %s, produced by Makeinfo-%d.%d from ", - output_filename, major_version, minor_version); - add_word_args ("the input file %s.\n", input_filename); - } - - close_paragraph (); - reader_loop (); - -finished: - close_paragraph (); - flush_file_stack (); - if (output_stream != NULL) - { - output_pending_notes (); - free_pending_notes (); - if (tag_table != NULL) - { - tag_table = (TAG_ENTRY *) reverse_list (tag_table); - if (!no_headers) - write_tag_table (); - } - - if (output_stream != stdout) - fclose (output_stream); - - /* If validating, then validate the entire file right now. */ - if (validating) - validate_file (real_output_filename, tag_table); - - /* This used to test && !errors_printed. - But some files might have legit warnings. So split anyway. */ - if (splitting) - split_file (real_output_filename, 0); - } -} - -free_and_clear (pointer) - char **pointer; -{ - if ((*pointer) != (char *) NULL) - { - free (*pointer); - *pointer = (char *) NULL; - } -} - - /* Initialize some state. */ -init_internals () -{ - free_and_clear (¤t_node); - free_and_clear (&output_filename); - free_and_clear (&command); - free_and_clear (&input_filename); - free_node_references (); - init_insertion_stack (); - init_brace_stack (); - command_index = 0; - in_menu = 0; -} - -init_paragraph () -{ - free_and_clear (&output_paragraph); - output_paragraph = (unsigned char *)xmalloc (paragraph_buffer_len); - output_position = 0; - output_paragraph[0] = '\0'; - output_paragraph_offset = 0; - output_column = 0; - paragraph_is_open = 0; - current_indent = 0; -} - -/* Okay, we are ready to start the conversion. Call the reader on - some text, and fill the text as it is output. Handle commands by - remembering things like open braces and the current file position on a - stack, and when the corresponding close brace is found, you can call - the function with the proper arguments. */ -reader_loop () -{ - int character; - int done = 0; - int dash_count = 0; - - while (!done) - { - if (input_text_offset >= size_of_input_text) - { - if (filestack) - { - free (input_filename); - free (input_text); - popfile (); - } - else - break; - } - - character = curchar (); - - if (!in_fixed_width_font && - (character == '\'' || character == '`') && - input_text[input_text_offset + 1] == character) - { - input_text_offset++; - character = '"'; - } - - if (character == '-') - { - dash_count++; - if (dash_count == 2 && !in_fixed_width_font) - { - input_text_offset++; - continue; - } - } - else - { - dash_count = 0; - } - - /* If this is a whitespace character, then check to see if the line - is blank. If so, advance to the carriage return. */ - if (whitespace (character)) - { - register int i = input_text_offset + 1; - - while (i < size_of_input_text && whitespace (input_text[i])) - i++; - - if (i == size_of_input_text || input_text[i] == '\n') - { - if (i == size_of_input_text) - i--; - - input_text_offset = i; - character = curchar (); - } - } - - if (character == '\n') - { - line_number++; - - /* Check for a menu entry here, since the "escape sequence" - that begins menu entrys is "\n* ". */ - if (in_menu && input_text_offset + 1 < size_of_input_text) - { - char *glean_node_from_menu (), *tem; - - /* Note that the value of TEM is discarded, since it is - gauranteed to be NULL when glean_node_from_menu () is - called with a non-zero argument. */ - tem = glean_node_from_menu (1); - } - } - - switch (character) - { - case COMMAND_PREFIX: - read_command (); - if (strcmp (command, "bye") == 0) - { - done = 1; - continue; - } - break; - - case '{': - - /* Special case. I'm not supposed to see this character by itself. - If I do, it means there is a syntax error in the input text. - Report the error here, but remember this brace on the stack so - you can ignore its partner. */ - - line_error ("Misplaced `{'"); - remember_brace (misplaced_brace); - - /* Don't advance input_text_offset since this happens in - remember_brace (). - input_text_offset++; - */ - break; - - case '}': - pop_and_call_brace (); - input_text_offset++; - break; - - default: - add_char (character); - input_text_offset++; - } - } -} - -/* Find the command corresponding to STRING. If the command - is found, return a pointer to the data structure. Otherwise - return (-1). */ -COMMAND * -get_command_entry (string) - char *string; -{ - register int i; - - for (i = 0; CommandTable[i].name; i++) - if (strcmp (CommandTable[i].name, string) == 0) - return (&CommandTable[i]); - - /* This command is not in our predefined command table. Perhaps - it is a user defined command. */ - for (i = 0; i < user_command_array_len; i++) - if (user_command_array[i] && - (strcmp (user_command_array[i]->name, string) == 0)) - return (user_command_array[i]); - - /* Nope, we never heard of this command. */ - return ((COMMAND *) -1); -} - -/* input_text_offset is right at the command prefix character. - Read the next token to determine what to do. */ -read_command () -{ - COMMAND *entry; - input_text_offset++; - free_and_clear (&command); - command = read_token (); - -#if defined (HAVE_MACROS) - /* Check to see if this command is a macro. If so, execute it here. */ - { - MACRO_DEF *def; - - def = find_macro (command); - - if (def) - { - execute_macro (def); - return; - } - } -#endif /* HAVE_MACROS */ - - entry = get_command_entry (command); - - if ((int) entry == -1) - { - line_error ("Unknown info command `%s'", command); - return; - } - - if (entry->argument_in_braces) - remember_brace (entry->proc); - - (*(entry->proc)) (START); -} - -/* Return the string which invokes PROC; a pointer to a function. */ -char * -find_proc_name (proc) - FUNCTION *proc; -{ - register int i; - - for (i = 0; CommandTable[i].name; i++) - if (proc == CommandTable[i].proc) - return (CommandTable[i].name); - return ("NO_NAME!"); -} - -init_brace_stack () -{ - brace_stack = (BRACE_ELEMENT *) NULL; -} - -remember_brace (proc) - FUNCTION *proc; -{ - if (curchar () != '{') - line_error ("@%s expected `{..}'", command); - else - input_text_offset++; - remember_brace_1 (proc, output_paragraph_offset); -} - -/* Remember the current output position here. Save PROC - along with it so you can call it later. */ -remember_brace_1 (proc, position) - FUNCTION *proc; - int position; -{ - BRACE_ELEMENT *new = (BRACE_ELEMENT *) xmalloc (sizeof (BRACE_ELEMENT)); - new->next = brace_stack; - new->proc = proc; - new->pos = position; - new->line = line_number; - brace_stack = new; -} - -/* Pop the top of the brace stack, and call the associated function - with the args END and POS. */ -pop_and_call_brace () -{ - BRACE_ELEMENT *temp; - FUNCTION *proc; - int pos; - - if (brace_stack == (BRACE_ELEMENT *) NULL) - return (line_error ("Unmatched close brace")); - - pos = brace_stack->pos; - proc = brace_stack->proc; - temp = brace_stack->next; - free (brace_stack); - brace_stack = temp; - - return ((*proc) (END, pos, output_paragraph_offset)); -} - -/* You call discard_braces () when you shouldn't have any braces on the stack. - I used to think that this happens for commands that don't take arguments - in braces, but that was wrong because of things like @code{foo @@}. So now - I only detect it at the beginning of nodes. */ -discard_braces () -{ - int temp_line_number = line_number; - char *proc_name; - - if (!brace_stack) - return; - - while (brace_stack) - { - line_number = brace_stack->line; - proc_name = find_proc_name (brace_stack->proc); - line_error ("@%s missing close brace", proc_name); - line_number = temp_line_number; - pop_and_call_brace (); - } -} - -get_char_len (character) - int character; -{ - /* Return the printed length of the character. */ - int len; - - switch (character) - { - case '\t': - len = (output_column + 8) & 0xf7; - if (len > fill_column) - len = fill_column - output_column; - else - len = len - output_column; - break; - - case '\n': - len = fill_column - output_column; - break; - - default: - if (character < ' ') - len = 2; - else - len = 1; - } - return (len); -} - -#if defined (HAVE_VARARGS_H) && defined (HAVE_VSPRINTF) - -add_word_args (va_alist) - va_dcl -{ - char buffer[1000]; - char *format; - va_list args; - - va_start (args); - format = va_arg (args, char *); - vsprintf (buffer, format, args); - va_end (args); - add_word (buffer); -} - -#else /* !(HAVE_VARARGS_H && HAVE_VSPRINTF) */ - -add_word_args (format, arg1, arg2, arg3, arg4, arg5) - char *format; -{ - char buffer[1000]; - sprintf (buffer, format, arg1, arg2, arg3, arg4, arg5); - add_word (buffer); -} - -#endif /* !(HAVE_VARARGS_H && HAVE_VSPRINTF) */ - -/* Add STRING to output_paragraph. */ -add_word (string) - char *string; -{ - while (*string) - add_char (*string++); -} - -/* Non-zero if the last character inserted has the syntax class of NEWLINE. */ -int last_char_was_newline = 1; - -/* The actual last inserted character. Note that this may be something - other than NEWLINE even if last_char_was_newline is 1. */ -int last_inserted_character = 0; - -/* Non-zero means that a newline character has already been - inserted, so close_paragraph () should insert one less. */ -int line_already_broken = 0; - -/* When non-zero we have finished an insertion (see end_insertion ()) and we - want to ignore false continued paragraph closings. */ -int insertion_paragraph_closed = 0; - -/* Add the character to the current paragraph. If filling_enabled is - non-zero, then do filling as well. */ -add_char (character) - int character; -{ - /* If we are avoiding outputting headers, and we are currently - in a menu, then simply return. */ - if (no_headers && in_menu) - return; - - /* If we are adding a character now, then we don't have to - ignore close_paragraph () calls any more. */ - if (must_start_paragraph && character != '\n') - { - must_start_paragraph = 0; - line_already_broken = 0; /* The line is no longer broken. */ - if (current_indent > output_column) - { - indent (current_indent - output_column); - output_column = current_indent; - } - } - - if (non_splitting_words && member (character, " \t\n")) - character = ' ' | 0x80; - - insertion_paragraph_closed = 0; - - switch (character) - { - case '\n': - if (!filling_enabled) - { - insert ('\n'); - - if (force_flush_right) - { - close_paragraph (); - /* Hack to force single blank lines out in this mode. */ - flush_output (); - } - - output_column = 0; - - if (!no_indent && paragraph_is_open) - indent (output_column = current_indent); - break; - } - else /* CHARACTER is newline, and filling is enabled. */ - { - if (sentence_ender (last_inserted_character)) - { - insert (' '); - output_column++; - last_inserted_character = character; - } - } - - if (last_char_was_newline) - { - close_paragraph (); - pending_indent = 0; - } - else - { - last_char_was_newline = 1; - insert (' '); - output_column++; - } - break; - - default: - { - int len = get_char_len (character); - int suppress_insert = 0; - - if ((character == ' ') && (last_char_was_newline)) - { - if (!paragraph_is_open) - { - pending_indent++; - return; - } - } - - if (!paragraph_is_open) - { - start_paragraph (); - - /* If the paragraph is supposed to be indented a certain way, - then discard all of the pending whitespace. Otherwise, we - let the whitespace stay. */ - if (!paragraph_start_indent) - indent (pending_indent); - pending_indent = 0; - } - - if ((output_column += len) > fill_column) - { - if (filling_enabled) - { - int temp = output_paragraph_offset; - while (--temp > 0 && output_paragraph[temp] != '\n') - { - /* If we have found a space, we have the place to break - the line. */ - if (output_paragraph[temp] == ' ') - { - /* Remove trailing whitespace from output. */ - while (temp && whitespace (output_paragraph[temp - 1])) - temp--; - - output_paragraph[temp++] = '\n'; - - /* We have correctly broken the line where we want - to. What we don't want is spaces following where - we have decided to break the line. We get rid of - them. */ - { - int t1 = temp; - - for (;; t1++) - { - if (t1 == output_paragraph_offset) - { - if (whitespace (character)) - suppress_insert = 1; - break; - } - if (!whitespace (output_paragraph[t1])) - break; - } - - if (t1 != temp) - { - strncpy ((char *) &output_paragraph[temp], - (char *) &output_paragraph[t1], - (output_paragraph_offset - t1)); - output_paragraph_offset -= (t1 - temp); - } - } - - /* Filled, but now indent if that is right. */ - if (indented_fill && current_indent) - { - int buffer_len = ((output_paragraph_offset - temp) - + current_indent); - char *temp_buffer = (char *)xmalloc (buffer_len); - int indentation = 0; - - /* We have to shift any markers that are in - front of the wrap point. */ - { - register BRACE_ELEMENT *stack = brace_stack; - - while (stack) - { - if (stack->pos >= temp) - stack->pos += current_indent; - stack = stack->next; - } - } - - while (current_indent > 0 && - indentation != current_indent) - temp_buffer[indentation++] = ' '; - - strncpy ((char *) &temp_buffer[current_indent], - (char *) &output_paragraph[temp], - buffer_len - current_indent); - - if (output_paragraph_offset + buffer_len - >= paragraph_buffer_len) - { - unsigned char *tt = xrealloc - (output_paragraph, - (paragraph_buffer_len += buffer_len)); - output_paragraph = tt; - } - strncpy ((char *) &output_paragraph[temp], - temp_buffer, buffer_len); - output_paragraph_offset += current_indent; - free (temp_buffer); - } - output_column = 0; - while (temp < output_paragraph_offset) - output_column += - get_char_len (output_paragraph[temp++]); - output_column += len; - break; - } - } - } - } - - if (!suppress_insert) - { - insert (character); - last_inserted_character = character; - } - last_char_was_newline = 0; - line_already_broken = 0; - } - } -} - -/* Insert CHARACTER into OUTPUT_PARAGRAPH. */ -insert (character) - int character; -{ - output_paragraph[output_paragraph_offset++] = character; - if (output_paragraph_offset == paragraph_buffer_len) - { - output_paragraph = - xrealloc (output_paragraph, (paragraph_buffer_len += 100)); - } -} - -/* Remove upto COUNT characters of whitespace from the - the current output line. If COUNT is less than zero, - then remove until none left. */ -kill_self_indent (count) - int count; -{ - /* Handle infinite case first. */ - if (count < 0) - { - output_column = 0; - while (output_paragraph_offset) - { - if (whitespace (output_paragraph[output_paragraph_offset - 1])) - output_paragraph_offset--; - else - break; - } - } - else - { - while (output_paragraph_offset && count--) - if (whitespace (output_paragraph[output_paragraph_offset - 1])) - output_paragraph_offset--; - else - break; - } -} - -/* Non-zero means do not honor calls to flush_output (). */ -static int flushing_ignored = 0; - -/* Prevent calls to flush_output () from having any effect. */ -inhibit_output_flushing () -{ - flushing_ignored++; -} - -/* Allow calls to flush_output () to write the paragraph data. */ -uninhibit_output_flushing () -{ - flushing_ignored--; -} - -flush_output () -{ - register int i; - - if (!output_paragraph_offset || flushing_ignored) - return; - - for (i = 0; i < output_paragraph_offset; i++) - { - if (output_paragraph[i] == (unsigned char)(' ' | 0x80) || - output_paragraph[i] == (unsigned char)('\t' | 0x80) || - output_paragraph[i] == (unsigned char)('\n' | 0x80) || - sentence_ender (UNMETA (output_paragraph[i]))) - output_paragraph[i] &= 0x7f; - } - - fwrite (output_paragraph, 1, output_paragraph_offset, output_stream); - - output_position += output_paragraph_offset; - output_paragraph_offset = 0; -} - -/* How to close a paragraph controlling the number of lines between - this one and the last one. */ - -/* Paragraph spacing is controlled by this variable. It is the number of - blank lines that you wish to appear between paragraphs. A value of - 1 creates a single blank line between paragraphs. */ -int paragraph_spacing = DEFAULT_PARAGRAPH_SPACING; - -/* Close the current paragraph, leaving no blank lines between them. */ -close_single_paragraph () -{ - close_paragraph_with_lines (0); -} - -/* Close a paragraph after an insertion has ended. */ -close_insertion_paragraph () -{ - if (!insertion_paragraph_closed) - { - /* Close the current paragraph, breaking the line. */ - close_single_paragraph (); - - /* Start a new paragraph here, inserting whatever indention is correct - for the now current insertion level (one above the one that we are - ending). */ - start_paragraph (); - - /* Tell close_paragraph () that the previous line has already been - broken, so it should insert one less newline. */ - line_already_broken = 1; - - /* Let functions such as add_char () know that we have already found a - newline. */ - ignore_blank_line (); - } - else - { - /* If the insertion paragraph is closed already, then we are seeing - two `@end' commands in a row. Note that the first one we saw was - handled in the first part of this if-then-else clause, and at that - time start_paragraph () was called, partially to handle the proper - indentation of the current line. However, the indentation level - may have just changed again, so we may have to outdent the current - line to the new indentation level. */ - if (current_indent < output_column) - kill_self_indent (output_column - current_indent); - } - - insertion_paragraph_closed = 1; -} - -close_paragraph_with_lines (lines) - int lines; -{ - int old_spacing = paragraph_spacing; - paragraph_spacing = lines; - close_paragraph (); - paragraph_spacing = old_spacing; -} - -/* Close the currently open paragraph. */ -close_paragraph () -{ - register int i; - - /* The insertion paragraph is no longer closed. */ - insertion_paragraph_closed = 0; - - if (paragraph_is_open && !must_start_paragraph) - { - register int tindex, c; - - tindex = output_paragraph_offset; - - /* Back up to last non-newline/space character, forcing all such - subsequent characters to be newlines. This isn't strictly - necessary, but a couple of functions use the presence of a newline - to make decisions. */ - for (tindex = output_paragraph_offset - 1; tindex >= 0; --tindex) - { - c = output_paragraph[tindex]; - - if (c == ' '|| c == '\n') - output_paragraph[tindex] = '\n'; - else - break; - } - - /* All trailing whitespace is ignored. */ - output_paragraph_offset = ++tindex; - - /* Break the line if that is appropriate. */ - if (paragraph_spacing >= 0) - insert ('\n'); - - /* Add as many blank lines as is specified in PARAGRAPH_SPACING. */ - if (!force_flush_right) - { - for (i = 0; i < (paragraph_spacing - line_already_broken); i++) - insert ('\n'); - } - - /* If we are doing flush right indentation, then do it now - on the paragraph (really a single line). */ - if (force_flush_right) - do_flush_right_indentation (); - - flush_output (); - paragraph_is_open = 0; - no_indent = 0; - output_column = 0; - } - ignore_blank_line (); -} - -/* Make the last line just read look as if it were only a newline. */ -ignore_blank_line () -{ - last_inserted_character = '\n'; - last_char_was_newline = 1; -} - -/* Align the end of the text in output_paragraph with fill_column. */ -do_flush_right_indentation () -{ - char *temp; - int temp_len; - - kill_self_indent (-1); - - if (output_paragraph[0] != '\n') - { - output_paragraph[output_paragraph_offset] = '\0'; - - if (output_paragraph_offset < fill_column) - { - register int i; - - if (fill_column >= paragraph_buffer_len) - output_paragraph = - xrealloc (output_paragraph, - (paragraph_buffer_len += fill_column)); - - temp_len = strlen ((char *)output_paragraph); - temp = (char *)xmalloc (temp_len + 1); - memcpy (temp, (char *)output_paragraph, temp_len); - - for (i = 0; i < fill_column - output_paragraph_offset; i++) - output_paragraph[i] = ' '; - - memcpy ((char *)output_paragraph + i, temp, temp_len); - free (temp); - output_paragraph_offset = fill_column; - } - } -} - -/* Begin a new paragraph. */ -start_paragraph () -{ - /* First close existing one. */ - if (paragraph_is_open) - close_paragraph (); - - /* In either case, the insertion paragraph is no longer closed. */ - insertion_paragraph_closed = 0; - - /* However, the paragraph is open! */ - paragraph_is_open = 1; - - /* If we MUST_START_PARAGRAPH, that simply means that start_paragraph () - had to be called before we would allow any other paragraph operations - to have an effect. */ - if (!must_start_paragraph) - { - int amount_to_indent = 0; - - /* If doing indentation, then insert the appropriate amount. */ - if (!no_indent) - { - if (inhibit_paragraph_indentation) - { - amount_to_indent = current_indent; - if (inhibit_paragraph_indentation < 0) - inhibit_paragraph_indentation++; - } - else if (paragraph_start_indent < 0) - amount_to_indent = current_indent; - else - amount_to_indent = current_indent + paragraph_start_indent; - - if (amount_to_indent >= output_column) - { - amount_to_indent -= output_column; - indent (amount_to_indent); - output_column += amount_to_indent; - } - } - } - else - must_start_paragraph = 0; -} - -/* Insert the indentation specified by AMOUNT. */ -indent (amount) - int amount; -{ - register BRACE_ELEMENT *elt = brace_stack; - - /* For every START_POS saved within the brace stack which will be affected - by this indentation, bump that start pos forward. */ - while (elt) - { - if (elt->pos >= output_paragraph_offset) - elt->pos += amount; - elt = elt->next; - } - - while (--amount >= 0) - insert (' '); -} - -/* Search forward for STRING in input_text. - FROM says where where to start. */ -search_forward (string, from) - char *string; - int from; -{ - int len = strlen (string); - - while (from < size_of_input_text) - { - if (strncmp (input_text + from, string, len) == 0) - return (from); - from++; - } - return (-1); -} - -/* Whoops, Unix doesn't have stricmp. */ - -/* Case independent string compare. */ -stricmp (string1, string2) - char *string1, *string2; -{ - char ch1, ch2; - - for (;;) - { - ch1 = *string1++; - ch2 = *string2++; - - if (!(ch1 | ch2)) - return (0); - - ch1 = coerce_to_upper (ch1); - ch2 = coerce_to_upper (ch2); - - if (ch1 != ch2) - return (ch1 - ch2); - } -} - -enum insertion_type { menu, quotation, lisp, smalllisp, example, - smallexample, display, itemize, format, enumerate, cartouche, table, - ftable, vtable, group, ifinfo, flushleft, flushright, ifset, ifclear, deffn, - defun, defmac, defspec, defvr, defvar, defopt, deftypefn, - deftypefun, deftypevr, deftypevar, defcv, defivar, defop, defmethod, - deftypemethod, deftp, bad_type }; - -char *insertion_type_names[] = { "menu", "quotation", "lisp", - "smalllisp", "example", "smallexample", "display", "itemize", - "format", "enumerate", "cartouche", "table", "ftable", "vtable", "group", - "ifinfo", "flushleft", "flushright", "ifset", "ifclear", "deffn", - "defun", "defmac", "defspec", "defvr", "defvar", "defopt", - "deftypefn", "deftypefun", "deftypevr", "deftypevar", "defcv", - "defivar", "defop", "defmethod", "deftypemethod", "deftp", - "bad_type" }; - -int insertion_level = 0; -typedef struct istack_elt -{ - struct istack_elt *next; - char *item_function; - int line_number; - int filling_enabled; - int indented_fill; - enum insertion_type insertion; - int inhibited; -} INSERTION_ELT; - -INSERTION_ELT *insertion_stack = (INSERTION_ELT *) NULL; - -init_insertion_stack () -{ - insertion_stack = (INSERTION_ELT *) NULL; -} - -/* Return the type of the current insertion. */ -enum insertion_type -current_insertion_type () -{ - if (!insertion_level) - return (bad_type); - else - return (insertion_stack->insertion); -} - -/* Return a pointer to the string which is the function to wrap around - items. */ -char * -current_item_function () -{ - register int level, done; - register INSERTION_ELT *elt; - - level = insertion_level; - elt = insertion_stack; - done = 0; - - /* Skip down through the stack until we find a non-conditional insertion. */ - while (!done) - { - switch (elt->insertion) - { - case ifinfo: - case ifset: - case ifclear: - case cartouche: - elt = elt->next; - level--; - break; - - default: - done = 1; - } - } - - if (!level) - return ((char *) NULL); - else - return (elt->item_function); -} - -char * -get_item_function () -{ - char *item_function; - get_rest_of_line (&item_function); - backup_input_pointer (); - canon_white (item_function); - return (item_function); -} - - /* Push the state of the current insertion on the stack. */ -push_insertion (type, item_function) - enum insertion_type type; - char *item_function; -{ - INSERTION_ELT *new = (INSERTION_ELT *) xmalloc (sizeof (INSERTION_ELT)); - - new->item_function = item_function; - new->filling_enabled = filling_enabled; - new->indented_fill = indented_fill; - new->insertion = type; - new->line_number = line_number; - new->inhibited = inhibit_paragraph_indentation; - new->next = insertion_stack; - insertion_stack = new; - insertion_level++; -} - - /* Pop the value on top of the insertion stack into the - global variables. */ -pop_insertion () -{ - INSERTION_ELT *temp = insertion_stack; - - if (temp == (INSERTION_ELT *) NULL) - return; - - inhibit_paragraph_indentation = temp->inhibited; - filling_enabled = temp->filling_enabled; - indented_fill = temp->indented_fill; - free_and_clear (&(temp->item_function)); - insertion_stack = insertion_stack->next; - free (temp); - insertion_level--; -} - - /* Return a pointer to the print name of this - enumerated type. */ -char * -insertion_type_pname (type) - enum insertion_type type; -{ - if ((int) type < (int) bad_type) - return (insertion_type_names[(int) type]); - else - return ("Broken-Type in insertion_type_pname"); -} - -/* Return the insertion_type associated with NAME. - If the type is not one of the known ones, return BAD_TYPE. */ -enum insertion_type -find_type_from_name (name) - char *name; -{ - int index = 0; - while (index < (int) bad_type) - { - if (strcmp (name, insertion_type_names[index]) == 0) - return (enum insertion_type) index; - index++; - } - return (bad_type); -} - -do_nothing () -{ -} - -int -defun_insertion (type) - enum insertion_type type; -{ - return - ((type == deffn) - || (type == defun) - || (type == defmac) - || (type == defspec) - || (type == defvr) - || (type == defvar) - || (type == defopt) - || (type == deftypefn) - || (type == deftypefun) - || (type == deftypevr) - || (type == deftypevar) - || (type == defcv) - || (type == defivar) - || (type == defop) - || (type == defmethod) - || (type == deftypemethod) - || (type == deftp)); -} - -/* MAX_NS is the maximum nesting level for enumerations. I picked 100 - which seemed reasonable. This doesn't control the number of items, - just the number of nested lists. */ -#define max_stack_depth 100 -#define ENUM_DIGITS 1 -#define ENUM_ALPHA 2 -typedef struct { - int enumtype; - int enumval; -} DIGIT_ALPHA; - -DIGIT_ALPHA enumstack[max_stack_depth]; -int enumstack_offset = 0; -int current_enumval = 1; -int current_enumtype = ENUM_DIGITS; -char *enumeration_arg = (char *)NULL; - -start_enumerating (at, type) - int at, type; -{ - if ((enumstack_offset + 1) == max_stack_depth) - { - line_error ("Enumeration stack overflow"); - return; - } - enumstack[enumstack_offset].enumtype = current_enumtype; - enumstack[enumstack_offset].enumval = current_enumval; - enumstack_offset++; - current_enumval = at; - current_enumtype = type; -} - -stop_enumerating () -{ - --enumstack_offset; - if (enumstack_offset < 0) - enumstack_offset = 0; - - current_enumval = enumstack[enumstack_offset].enumval; - current_enumtype = enumstack[enumstack_offset].enumtype; -} - -/* Place a letter or digits into the output stream. */ -enumerate_item () -{ - char temp[10]; - - if (current_enumtype == ENUM_ALPHA) - { - if (current_enumval == ('z' + 1) || current_enumval == ('Z' + 1)) - { - current_enumval = ((current_enumval - 1) == 'z' ? 'a' : 'A'); - warning ("Lettering overflow, restarting at %c", current_enumval); - } - sprintf (temp, "%c. ", current_enumval); - } - else - sprintf (temp, "%d. ", current_enumval); - - indent (output_column += (current_indent - strlen (temp))); - add_word (temp); - current_enumval++; -} - -/* This is where the work for all the "insertion" style - commands is done. A huge switch statement handles the - various setups, and generic code is on both sides. */ -begin_insertion (type) - enum insertion_type type; -{ - int no_discard = 0; - - if (defun_insertion (type)) - { - push_insertion (type, savestring ("")); - no_discard++; - } - else - push_insertion (type, get_item_function ()); - - switch (type) - { - case menu: - if (!no_headers) - close_paragraph (); - - filling_enabled = no_indent = 0; - inhibit_paragraph_indentation = 1; - - if (!no_headers) - add_word ("* Menu:\n"); - - in_menu++; - no_discard++; - break; - - /* I think @quotation is meant to do filling. - If you don't want filling, then use @example. */ - case quotation: - close_single_paragraph (); - last_char_was_newline = no_indent = 0; - indented_fill = filling_enabled = 1; - inhibit_paragraph_indentation = 1; - current_indent += default_indentation_increment; - break; - - case display: - case example: - case smallexample: - case lisp: - case smalllisp: - /* Just like @example, but no indentation. */ - case format: - - close_single_paragraph (); - inhibit_paragraph_indentation = 1; - in_fixed_width_font++; - filling_enabled = 0; - last_char_was_newline = 0; - - if (type != format) - current_indent += default_indentation_increment; - - break; - - case table: - case ftable: - case vtable: - case itemize: - close_single_paragraph (); - current_indent += default_indentation_increment; - filling_enabled = indented_fill = 1; -#if defined (INDENT_PARAGRAPHS_IN_TABLE) - inhibit_paragraph_indentation = 0; -#else - inhibit_paragraph_indentation = 1; -#endif /* !INDENT_PARAGRAPHS_IN_TABLE */ - - /* Make things work for losers who forget the itemize syntax. */ - if (type == itemize) - { - if (!(*insertion_stack->item_function)) - { - free (insertion_stack->item_function); - insertion_stack->item_function = savestring ("@bullet"); - } - } - break; - - case enumerate: - close_single_paragraph (); - no_indent = 0; -#if defined (INDENT_PARAGRAPHS_IN_TABLE) - inhibit_paragraph_indentation = 0; -#else - inhibit_paragraph_indentation = 1; -#endif /* !INDENT_PARAGRAPHS_IN_TABLE */ - - current_indent += default_indentation_increment; - filling_enabled = indented_fill = 1; - - if (isdigit (*enumeration_arg)) - start_enumerating (atoi (enumeration_arg), ENUM_DIGITS); - else - start_enumerating (*enumeration_arg, ENUM_ALPHA); - break; - - /* Does nothing special in makeinfo. */ - case group: - /* Only close the paragraph if we are not inside of an @example. */ - if (!insertion_stack->next || - insertion_stack->next->insertion != example) - close_single_paragraph (); - break; - - /* Insertions that are no-ops in info, but do something in TeX. */ - case ifinfo: - case ifset: - case ifclear: - case cartouche: - if (in_menu) - no_discard++; - break; - - case deffn: - case defun: - case defmac: - case defspec: - case defvr: - case defvar: - case defopt: - case deftypefn: - case deftypefun: - case deftypevr: - case deftypevar: - case defcv: - case defivar: - case defop: - case defmethod: - case deftypemethod: - case deftp: - inhibit_paragraph_indentation = 1; - filling_enabled = indented_fill = 1; - current_indent += default_indentation_increment; - no_indent = 0; - break; - - case flushleft: - close_single_paragraph (); - inhibit_paragraph_indentation = 1; - filling_enabled = indented_fill = no_indent = 0; - break; - - case flushright: - close_single_paragraph (); - filling_enabled = indented_fill = no_indent = 0; - inhibit_paragraph_indentation = 1; - force_flush_right++; - break; - } - - if (!no_discard) - discard_until ("\n"); -} - -/* Try to end the insertion with the specified TYPE. - TYPE, with a value of bad_type, gets translated to match - the value currently on top of the stack. - Otherwise, if TYPE doesn't match the top of the insertion stack, - give error. */ -end_insertion (type) - enum insertion_type type; -{ - enum insertion_type temp_type; - - if (!insertion_level) - return; - - temp_type = current_insertion_type (); - - if (type == bad_type) - type = temp_type; - - if (type != temp_type) - { - line_error - ("`%cend' expected `%s', but saw `%s'.", COMMAND_PREFIX, - insertion_type_pname (temp_type), insertion_type_pname (type)); - return; - } - - pop_insertion (); - - switch (type) - { - /* Insertions which have no effect on paragraph formatting. */ - case ifinfo: - case ifset: - case ifclear: - break; - - case menu: - in_menu--; /* No longer hacking menus. */ - if (!no_headers) - close_insertion_paragraph (); - break; - - case enumerate: - stop_enumerating (); - close_insertion_paragraph (); - current_indent -= default_indentation_increment; - break; - - case flushleft: - case group: - case cartouche: - close_insertion_paragraph (); - break; - - case format: - case display: - case example: - case smallexample: - case lisp: - case smalllisp: - case quotation: - - /* @quotation is the only one of the above without a fixed width - font. */ - if (type != quotation) - in_fixed_width_font--; - - /* @format is the only fixed_width insertion without a change - in indentation. */ - if (type != format) - current_indent -= default_indentation_increment; - - /* The ending of one of these insertions always marks the - start of a new paragraph. */ - close_insertion_paragraph (); - break; - - case table: - case ftable: - case vtable: - case itemize: - current_indent -= default_indentation_increment; - break; - - case flushright: - force_flush_right--; - close_insertion_paragraph (); - break; - - /* Handle the @defun style insertions with a default clause. */ - default: - current_indent -= default_indentation_increment; - close_insertion_paragraph (); - break; - } -} - -/* Insertions cannot cross certain boundaries, such as node beginnings. In - code that creates such boundaries, you should call discard_insertions () - before doing anything else. It prints the errors for you, and cleans up - the insertion stack. */ -discard_insertions () -{ - int real_line_number = line_number; - while (insertion_stack) - { - if (insertion_stack->insertion == ifinfo || - insertion_stack->insertion == ifset || - insertion_stack->insertion == ifclear || - insertion_stack->insertion == cartouche) - break; - else - { - char *offender = (char *) - insertion_type_pname (insertion_stack->insertion); - - line_number = insertion_stack->line_number; - line_error ("This `%s' doesn't have a matching `%cend %s'", offender, - COMMAND_PREFIX, offender); - pop_insertion (); - } - } - line_number = real_line_number; -} - -/* The actual commands themselves. */ - -/* Commands which insert themselves. */ -insert_self () -{ - add_word (command); -} - -/* Force a line break in the output. */ -cm_asterisk () -{ - close_single_paragraph (); -#if !defined (ASTERISK_NEW_PARAGRAPH) - cm_noindent (); -#endif /* ASTERISK_NEW_PARAGRAPH */ -} - -/* Insert ellipsis. */ -cm_dots (arg) - int arg; -{ - if (arg == START) - add_word ("..."); -} - -cm_bullet (arg) - int arg; -{ - if (arg == START) - add_char ('*'); -} - -cm_minus (arg) - int arg; -{ - if (arg == START) - add_char ('-'); -} - -/* Insert "TeX". */ -cm_TeX (arg) - int arg; -{ - if (arg == START) - add_word ("TeX"); -} - -cm_copyright (arg) - int arg; -{ - if (arg == START) - add_word ("(C)"); -} - -cm_today (arg) - int arg; -{ - static char * months [12] = - { "January", "February", "March", "April", "May", "June", "July", - "August", "September", "October", "November", "December" }; - if (arg == START) - { - long timer = (time (0)); - struct tm *ts = (localtime (&timer)); - add_word_args - ("%d %s %d", - (ts -> tm_mday), - (months [ts -> tm_mon]), - ((ts -> tm_year) + 1900)); - } -} - -cm_code (arg) - int arg; -{ - extern int printing_index; - - if (printing_index) - return; - - if (arg == START) - { - in_fixed_width_font++; - add_char ('`'); - } - else - { - add_word ("'"); - in_fixed_width_font--; - } -} - -cm_samp (arg) - int arg; -{ - cm_code (arg); -} - -cm_file (arg) - int arg; -{ - cm_code (arg); -} - -cm_kbd (arg) - int arg; -{ - cm_code (arg); -} - -cm_key (arg) - int arg; -{ -} - -/* Convert the character at position into CTL. */ -cm_ctrl (arg, position) - int arg, position; -{ - if (arg == END) - output_paragraph[position - 1] = CTL (output_paragraph[position]); -} - -/* Small Caps in makeinfo just does all caps. */ -cm_sc (arg, start_pos, end_pos) - int arg, start_pos, end_pos; -{ - if (arg == END) - { - while (start_pos < end_pos) - { - output_paragraph[start_pos] = - coerce_to_upper (output_paragraph[start_pos]); - start_pos++; - } - } -} - -/* @var in makeinfo just uppercases the text. */ -cm_var (arg, start_pos, end_pos) - int arg, start_pos, end_pos; -{ - if (arg == END) - { - while (start_pos < end_pos) - { - output_paragraph[start_pos] = - coerce_to_upper (output_paragraph[start_pos]); - start_pos++; - } - } -} - -cm_dfn (arg, position) - int arg, position; -{ - add_char ('"'); -} - -cm_emph (arg) - int arg; -{ - add_char ('*'); -} - -cm_strong (arg, position) - int arg, position; -{ - cm_emph (arg); -} - -cm_cite (arg, position) - int arg, position; -{ - if (arg == START) - add_word ("`"); - else - add_word ("'"); -} - -/* Current text is italicized. */ -cm_italic (arg, start, end) - int arg, start, end; -{ -} - -/* Current text is highlighted. */ -cm_bold (arg, start, end) - int arg, start, end; -{ - cm_italic (arg); -} - -/* Current text is in roman font. */ -cm_roman (arg, start, end) - int arg, start, end; -{ -} - -/* Current text is in roman font. */ -cm_titlefont (arg, start, end) - int arg, start, end; -{ -} - -/* Italicize titles. */ -cm_title (arg, start, end) - int arg, start, end; -{ - cm_italic (arg); -} - -/* @refill is a NOP. */ -cm_refill () -{ -} - -/* Prevent the argument from being split across two lines. */ -cm_w (arg, start, end) - int arg, start, end; -{ - if (arg == START) - non_splitting_words++; - else - non_splitting_words--; -} - - -/* Explain that this command is obsolete, thus the user shouldn't - do anything with it. */ -cm_obsolete (arg, start, end) - int arg, start, end; -{ - if (arg == START) - warning ("The command `@%s' is obsolete", command); -} - -/* Insert the text following input_text_offset up to the end of the line - in a new, separate paragraph. Directly underneath it, insert a - line of WITH_CHAR, the same length of the inserted text. */ -insert_and_underscore (with_char) - int with_char; -{ - int len, i, old_no_indent; - int starting_pos, ending_pos; - char *temp; - - close_paragraph (); - filling_enabled = indented_fill = 0; - old_no_indent = no_indent; - no_indent = 1; - get_rest_of_line (&temp); - - starting_pos = output_position + output_paragraph_offset; - execute_string ("%s\n", temp); - ending_pos = output_position + output_paragraph_offset; - free (temp); - - len = (ending_pos - starting_pos) - 1; - for (i = 0; i < len; i++) - add_char (with_char); - insert ('\n'); - close_paragraph (); - filling_enabled = 1; - no_indent = old_no_indent; -} - -/* Here is a structure which associates sectioning commands with - an integer, hopefully to reflect the `depth' of the current - section. */ -struct { - char *name; - int level; -} section_alist[] = { - { "unnumberedsubsubsec", 5 }, - { "unnumberedsubsec", 4 }, - { "unnumberedsec", 3 }, - { "unnumbered", 2 }, - { "appendixsubsubsec", 5 }, - { "appendixsubsec", 4 }, - { "appendixsec", 3 }, - { "appendixsection", 3 }, - { "appendix", 2 }, - { "subsubsec", 5 }, - { "subsubsection", 5 }, - { "subsection", 4 }, - { "section", 3 }, - { "chapter", 2 }, - { "top", 1 }, - - { (char *)NULL, 0 } -}; - -/* Amount to offset the name of sectioning commands to levels by. */ -int section_alist_offset = 0; - -/* Shift the meaning of @section to @chapter. */ -cm_raisesections () -{ - discard_until ("\n"); - section_alist_offset--; -} - -/* Shift the meaning of @chapter to @section. */ -cm_lowersections () -{ - discard_until ("\n"); - section_alist_offset++; -} - -/* Return an integer which identifies the type section present in TEXT. */ -int -what_section (text) - char *text; -{ - register int i, j; - char *t; - - find_section_command: - for (j = 0; text[j] && cr_or_whitespace (text[j]); j++); - if (text[j] != '@') - return (-1); - - text = text + j + 1; - - /* We skip @c, @comment, and @?index commands. */ - if ((strncmp (text, "comment", strlen ("comment")) == 0) || - (text[0] == 'c' && cr_or_whitespace (text[1])) || - (strcmp (text + 1, "index") == 0)) - { - while (*text++ != '\n'); - goto find_section_command; - } - - /* Handle italicized sectioning commands. */ - if (*text == 'i') - text++; - - for (j = 0; text[j] && !cr_or_whitespace (text[j]); j++); - - for (i = 0; t = section_alist[i].name; i++) - { - if (j == strlen (t) && strncmp (t, text, j) == 0) - { - int return_val; - - return_val = (section_alist[i].level + section_alist_offset); - - if (return_val < 0) - return_val = 0; - else if (return_val > 5) - return_val = 5; - return (return_val); - } - } - return (-1); -} - -/* Treat this just like @unnumbered. The only difference is - in node defaulting. */ -cm_top () -{ - static int top_encountered = 0; - cm_unnumbered (); - - /* It is an error to have more than one @top. */ - if (top_encountered) - { - TAG_ENTRY *tag = tag_table; - - line_error ("There already is a node having @top as a section"); - - while (tag != (TAG_ENTRY *)NULL) - { - if ((tag->flags & IS_TOP)) - { - int old_line_number = line_number; - char *old_input_filename = input_filename; - - line_number = tag->line_no; - input_filename = tag->filename; - line_error ("Here is the @top node."); - input_filename = old_input_filename; - line_number = old_line_number; - return; - } - tag = tag->next_ent; - } - } - else - { - top_encountered = 1; - - /* The most recently defined node is the top node. */ - if (tag_table) - tag_table->flags |= IS_TOP; - - /* Now set the logical hierarchical level of the Top node. */ - { - int orig_offset = input_text_offset; - - input_text_offset = search_forward ("\n@node", orig_offset); - - if (input_text_offset > 0) - { - int this_section; - - /* Move to the end of this line, and find out what the - sectioning command is here. */ - while (input_text[input_text_offset] != '\n') - input_text_offset++; - - if (input_text_offset < size_of_input_text) - input_text_offset++; - - this_section = what_section (input_text + input_text_offset); - - /* If we found a sectioning command, then give the top section - a level of this section - 1. */ - if (this_section != -1) - { - register int i; - - for (i = 0; section_alist[i].name; i++) - if (strcmp (section_alist[i].name, "Top") == 0) - { - section_alist[i].level = this_section - 1; - break; - } - } - } - input_text_offset = orig_offset; - } - } -} - -/* Organized by level commands. That is, "*" == chapter, "=" == section. */ -char *scoring_characters = "*=-."; - -void -sectioning_underscore (command) - char *command; -{ - char character; - int level; - - level = what_section (command); - level -= 2; - - if (level < 0) - level = 0; - - character = scoring_characters[level]; - - insert_and_underscore (character); -} - -/* The remainder of the text on this line is a chapter heading. */ -cm_chapter () -{ - sectioning_underscore ("@chapter"); -} - -/* The remainder of the text on this line is a section heading. */ -cm_section () -{ - sectioning_underscore ("@section"); -} - -/* The remainder of the text on this line is a subsection heading. */ -cm_subsection () -{ - sectioning_underscore ("@subsection"); -} - -/* The remainder of the text on this line is a subsubsection heading. */ -cm_subsubsection () -{ - sectioning_underscore ("@subsubsection"); -} - -/* The remainder of the text on this line is an unnumbered heading. */ -cm_unnumbered () -{ - cm_chapter (); -} - -/* The remainder of the text on this line is an unnumbered section heading. */ -cm_unnumberedsec () -{ - cm_section (); -} - -/* The remainder of the text on this line is an unnumbered - subsection heading. */ -cm_unnumberedsubsec () -{ - cm_subsection (); -} - -/* The remainder of the text on this line is an unnumbered - subsubsection heading. */ -cm_unnumberedsubsubsec () -{ - cm_subsubsection (); -} - -/* The remainder of the text on this line is an appendix heading. */ -cm_appendix () -{ - cm_chapter (); -} - -/* The remainder of the text on this line is an appendix section heading. */ -cm_appendixsec () -{ - cm_section (); -} - -/* The remainder of the text on this line is an appendix subsection heading. */ -cm_appendixsubsec () -{ - cm_subsection (); -} - -/* The remainder of the text on this line is an appendix - subsubsection heading. */ -cm_appendixsubsubsec () -{ - cm_subsubsection (); -} - -/* Compatibility functions substitute for chapter, section, etc. */ -cm_majorheading () -{ - cm_chapheading (); -} - -cm_chapheading () -{ - cm_chapter (); -} - -cm_heading () -{ - cm_section (); -} - -cm_subheading () -{ - cm_subsection (); -} - -cm_subsubheading () -{ - cm_subsubsection (); -} - - -/* **************************************************************** */ -/* */ -/* Adding nodes, and making tags */ -/* */ -/* **************************************************************** */ - -/* Start a new tag table. */ -init_tag_table () -{ - while (tag_table != (TAG_ENTRY *) NULL) - { - TAG_ENTRY *temp = tag_table; - free (temp->node); - free (temp->prev); - free (temp->next); - free (temp->up); - tag_table = tag_table->next_ent; - free (temp); - } -} - -write_tag_table () -{ - return (write_tag_table_internal (0)); /* Not indirect. */ -} - -write_tag_table_indirect () -{ - return (write_tag_table_internal (1)); -} - -/* Write out the contents of the existing tag table. - INDIRECT_P says how to format the output. */ -write_tag_table_internal (indirect_p) - int indirect_p; -{ - TAG_ENTRY *node = tag_table; - int old_indent = no_indent; - - no_indent = 1; - filling_enabled = 0; - must_start_paragraph = 0; - close_paragraph (); - - if (!indirect_p) - { - no_indent = 1; - insert ('\n'); - } - - add_word_args ("\037\nTag Table:\n%s", indirect_p ? "(Indirect)\n" : ""); - - while (node != (TAG_ENTRY *) NULL) - { - add_word_args ("Node: %s\177%d\n", node->node, node->position); - node = node->next_ent; - } - - add_word ("\037\nEnd Tag Table\n"); - flush_output (); - no_indent = old_indent; -} - -char * -get_node_token () -{ - char *string; - - get_until_in_line (",", &string); - - if (curchar () == ',') - input_text_offset++; - - canon_white (string); - - /* Allow things like @@nodename. */ - normalize_node_name (string); - - return (string); -} - -/* Given a node name in STRING, remove double @ signs, replacing them - with just one. Convert "top" and friends into "Top". */ -normalize_node_name (string) - char *string; -{ - register int i, l = strlen (string); - - for (i = 0; i < l; i++) - { - if (string[i] == '@' && string[i + 1] == '@') - { - strncpy (string + i, string + i + 1, l - i); - l--; - } - } - if (stricmp (string, "Top") == 0) - strcpy (string, "Top"); -} - -/* Look up NAME in the tag table, and return the associated - tag_entry. If the node is not in the table return NULL. */ -TAG_ENTRY * -find_node (name) - char *name; -{ - TAG_ENTRY *tag = tag_table; - - while (tag != (TAG_ENTRY *) NULL) - { - if (strcmp (tag->node, name) == 0) - return (tag); - tag = tag->next_ent; - } - return ((TAG_ENTRY *) NULL); -} - -/* Remember NODE and associates. */ -remember_node (node, prev, next, up, position, line_no, no_warn) - char *node, *prev, *next, *up; - int position, line_no, no_warn; -{ - /* Check for existence of this tag already. */ - if (validating) - { - register TAG_ENTRY *tag = find_node (node); - if (tag) - { - line_error ("Node `%s' multiply defined (%d is first definition)", - node, tag->line_no); - return; - } - } - - /* First, make this the current node. */ - current_node = node; - - /* Now add it to the list. */ - { - TAG_ENTRY *new = (TAG_ENTRY *) xmalloc (sizeof (TAG_ENTRY)); - new->node = node; - new->prev = prev; - new->next = next; - new->up = up; - new->position = position; - new->line_no = line_no; - new->filename = node_filename; - new->touched = 0; /* not yet referenced. */ - new->flags = 0; - if (no_warn) - new->flags |= NO_WARN; - new->next_ent = tag_table; - tag_table = new; - } -} - -/* The order is: nodename, nextnode, prevnode, upnode. - If all of the NEXT, PREV, and UP fields are empty, they are defaulted. - You must follow a node command which has those fields defaulted - with a sectioning command (e.g. @chapter) giving the "level" of that node. - It is an error not to do so. - The defaults come from the menu in this nodes parent. */ -cm_node () -{ - char *node, *prev, *next, *up; - int new_node_pos, defaulting, this_section, no_warn = 0; - extern int already_outputting_pending_notes; - - if (strcmp (command, "nwnode") == 0) - no_warn = 1; - - /* Get rid of unmatched brace arguments from previous commands. */ - discard_braces (); - - /* There also might be insertions left lying around that haven't been - ended yet. Do that also. */ - discard_insertions (); - - if (!already_outputting_pending_notes) - { - close_paragraph (); - output_pending_notes (); - free_pending_notes (); - } - - filling_enabled = indented_fill = 0; - new_node_pos = output_position; - current_footnote_number = 1; - - node = get_node_token (); - next = get_node_token (); - prev = get_node_token (); - up = get_node_token (); - - no_indent = 1; - if (!no_headers) - add_word_args ("\037\nFile: %s, Node: %s", pretty_output_filename, node); - - /* Check for defaulting of this node's next, prev, and up fields. */ - defaulting = ((strlen (next) == 0) && - (strlen (prev) == 0) && - (strlen (up) == 0)); - - this_section = what_section (input_text + input_text_offset); - - /* If we are defaulting, then look at the immediately following - sectioning command (error if none) to determine the node's - level. Find the node that contains the menu mentioning this node - that is one level up (error if not found). That node is the "Up" - of this node. Default the "Next" and "Prev" from the menu. */ - if (defaulting) - { - NODE_REF *last_ref = (NODE_REF *)NULL; - NODE_REF *ref = node_references; - - if (this_section < 0) - { - char *polite_section_name = "top"; - int i; - - for (i = 0; section_alist[i].name; i++) - if (section_alist[i].level == current_section + 1) - { - polite_section_name = section_alist[i].name; - break; - } - - line_error - ("Node `%s' requires a sectioning command (e.g. @%s)", - node, polite_section_name); - } - else - { - if (stricmp (node, "Top") == 0) - { - /* Default the NEXT pointer to be the first menu item in - this node, if there is a menu in this node. */ - { - int orig_offset, orig_size; - char *glean_node_from_menu (); - - orig_offset = input_text_offset; - orig_size = search_forward ("\n@node ", orig_offset); - - if (orig_size < 0) - orig_size = size_of_input_text; - - input_text_offset = search_forward ("\n@menu", orig_offset); - if (input_text_offset > -1) - { - char *nodename_from_menu = (char *)NULL; - - input_text_offset = - search_forward ("\n* ", input_text_offset); - - if (input_text_offset != -1) - nodename_from_menu = glean_node_from_menu (0); - - if (nodename_from_menu) - { - free (next); - next = nodename_from_menu; - prev = savestring ("(DIR)"); - up = savestring ("(DIR)"); - } - } - input_text_offset = orig_offset; - } - } - - while (ref) - { - if (ref->section == (this_section - 1) && - ref->type == menu_reference && - strcmp (ref->node, node) == 0) - { - char *containing_node = ref->containing_node; - - free (up); - up = savestring (containing_node); - - if (last_ref && - last_ref->type == menu_reference && - (strcmp (last_ref->containing_node, - containing_node) == 0)) - { - free (next); - next = savestring (last_ref->node); - } - - while ((ref->section == this_section - 1) && - (ref->next) && - (ref->next->type != menu_reference)) - ref = ref->next; - - if (ref->next && ref->type == menu_reference && - (strcmp (ref->next->containing_node, - containing_node) == 0)) - { - free (prev); - prev = savestring (ref->next->node); - } - else if (!ref->next && - stricmp (ref->containing_node, "Top") == 0) - { - free (prev); - prev = savestring (ref->containing_node); - } - break; - } - last_ref = ref; - ref = ref->next; - } - } - } - - if (!no_headers) - { - if (*next) - add_word_args (", Next: %s", next); - - if (*prev) - add_word_args (", Prev: %s", prev); - - if (*up) - add_word_args (", Up: %s", up); - } - - close_paragraph (); - no_indent = 0; - - if (!*node) - { - line_error ("No node name specified for `@%s' command", command); - free (node); - free (next); - free (prev); - free (up); - } - else - { - if (!*next) { free (next); next = (char *)NULL; } - if (!*prev) { free (prev); prev = (char *)NULL; } - if (!*up) { free (up); up = (char *)NULL; } - remember_node (node, prev, next, up, new_node_pos, line_number, no_warn); - } - - /* Change the section only if there was a sectioning command. */ - if (this_section >= 0) - current_section = this_section; - - filling_enabled = 1; -} - -/* Validation of an info file. - Scan through the list of tag entrys touching the Prev, Next, and Up - elements of each. It is an error not to be able to touch one of them, - except in the case of external node references, such as "(DIR)". - - If the Prev is different from the Up, - then the Prev node must have a Next pointing at this node. - - Every node except Top must have an Up. - The Up node must contain some sort of reference, other than a Next, - to this node. - - If the Next is different from the Next of the Up, - then the Next node must have a Prev pointing at this node. */ -validate_file (filename, tag_table) - char *filename; - TAG_ENTRY *tag_table; -{ - char *old_input_filename = input_filename; - TAG_ENTRY *tags = tag_table; - - while (tags != (TAG_ENTRY *) NULL) - { - register TAG_ENTRY *temp_tag; - - input_filename = tags->filename; - line_number = tags->line_no; - - /* If this is a "no warn" node, don't validate it in any way. */ - if (tags->flags & NO_WARN) - { - tags = tags->next_ent; - continue; - } - - /* If this node has a Next, then make sure that the Next exists. */ - if (tags->next) - { - validate (tags->next, tags->line_no, "Next"); - - /* If the Next node exists, and there is no Up, then make - sure that the Prev of the Next points back. */ - if (temp_tag = find_node (tags->next)) - { - char *prev; - - if (temp_tag->flags & NO_WARN) - { - /* Do nothing if we aren't supposed to issue warnings - about this node. */ - } - else - { - prev = temp_tag->prev; - if (!prev || (strcmp (prev, tags->node) != 0)) - { - line_error ("Node `%s''s Next field not pointed back to", - tags->node); - line_number = temp_tag->line_no; - input_filename = temp_tag->filename; - line_error - ("This node (`%s') is the one with the bad `Prev'", - temp_tag->node); - input_filename = tags->filename; - line_number = tags->line_no; - temp_tag->flags |= PREV_ERROR; - } - } - } - } - - /* Validate the Prev field if there is one, and we haven't already - complained about it in some way. You don't have to have a Prev - field at this stage. */ - if (!(tags->flags & PREV_ERROR) && tags->prev) - { - int valid = validate (tags->prev, tags->line_no, "Prev"); - - if (!valid) - tags->flags |= PREV_ERROR; - else - { - /* If the Prev field is not the same as the Up field, - then the node pointed to by the Prev field must have - a Next field which points to this node. */ - if (tags->up && (strcmp (tags->prev, tags->up) != 0)) - { - temp_tag = find_node (tags->prev); - - /* If we aren't supposed to issue warnings about the - target node, do nothing. */ - if (!temp_tag || (temp_tag->flags & NO_WARN)) - { - /* Do nothing. */ - } - else - { - if (!temp_tag->next || - (strcmp (temp_tag->next, tags->node) != 0)) - { - line_error - ("Node `%s''s Prev field not pointed back to", - tags->node); - line_number = temp_tag->line_no; - input_filename = temp_tag->filename; - line_error - ("This node (`%s') is the one with the bad `Next'", - temp_tag->node); - input_filename = tags->filename; - line_number = tags->line_no; - temp_tag->flags |= NEXT_ERROR; - } - } - } - } - } - - if (!tags->up && (stricmp (tags->node, "Top") != 0)) - line_error ("Node `%s' is missing an \"Up\" field", tags->node); - else if (tags->up) - { - int valid = validate (tags->up, tags->line_no, "Up"); - - /* If node X has Up: Y, then warn if Y fails to have a menu item - or note pointing at X, if Y isn't of the form "(Y)". */ - if (valid && *tags->up != '(') - { - NODE_REF *nref, *tref, *list; - NODE_REF *find_node_reference (); - - tref = (NODE_REF *) NULL; - list = node_references; - - for (;;) - { - if (!(nref = find_node_reference (tags->node, list))) - break; - - if (strcmp (nref->containing_node, tags->up) == 0) - { - if (nref->type != menu_reference) - { - tref = nref; - list = nref->next; - } - else - break; - } - list = nref->next; - } - - if (!nref) - { - temp_tag = find_node (tags->up); - line_number = temp_tag->line_no; - filename = temp_tag->filename; - if (!tref) - line_error ( -"`%s' has an Up field of `%s', but `%s' has no menu item for `%s'", - tags->node, tags->up, tags->up, tags->node); - line_number = tags->line_no; - filename = tags->filename; - } - } - } - tags = tags->next_ent; - } - - validate_other_references (node_references); - /* We have told the user about the references which didn't exist. - Now tell him about the nodes which aren't referenced. */ - - tags = tag_table; - while (tags != (TAG_ENTRY *) NULL) - { - /* If this node is a "no warn" node, do nothing. */ - if (tags->flags & NO_WARN) - { - tags = tags->next_ent; - continue; - } - - /* Special hack. If the node in question appears to have - been referenced more than REFERENCE_WARNING_LIMIT times, - give a warning. */ - if (tags->touched > reference_warning_limit) - { - input_filename = tags->filename; - line_number = tags->line_no; - warning ("Node `%s' has been referenced %d times", - tags->node, tags->touched); - } - - if (tags->touched == 0) - { - input_filename = tags->filename; - line_number = tags->line_no; - - /* Notice that the node "Top" is special, and doesn't have to - be referenced. */ - if (stricmp (tags->node, "Top") != 0) - warning ("Unreferenced node `%s'", tags->node); - } - tags = tags->next_ent; - } - input_filename = old_input_filename; -} - -/* Return 1 if tag correctly validated, or 0 if not. */ -validate (tag, line, label) - char *tag; - int line; - char *label; -{ - TAG_ENTRY *result; - - /* If there isn't a tag to verify, or if the tag is in another file, - then it must be okay. */ - if (!tag || !*tag || *tag == '(') - return (1); - - /* Otherwise, the tag must exist. */ - result = find_node (tag); - - if (!result) - { - line_number = line; - line_error ( -"Validation error. `%s' field points to node `%s', which doesn't exist", - label, tag); - return (0); - } - result->touched++; - return (1); -} - -/* Split large output files into a series of smaller files. Each file - is pointed to in the tag table, which then gets written out as the - original file. The new files have the same name as the original file - with a "-num" attached. SIZE is the largest number of bytes to allow - in any single split file. */ -split_file (filename, size) - char *filename; - int size; -{ - char *root_filename, *root_pathname; - char *the_file, *filename_part (); - struct stat fileinfo; - char *the_header; - int header_size; - - /* Can only do this to files with tag tables. */ - if (!tag_table) - return; - - if (size == 0) - size = DEFAULT_SPLIT_SIZE; - - if ((stat (filename, &fileinfo) != 0) || - (fileinfo.st_size < SPLIT_SIZE_THRESHOLD)) - return; - - the_file = find_and_load (filename); - if (!the_file) - return; - - root_filename = filename_part (filename); - root_pathname = pathname_part (filename); - - if (!root_pathname) - root_pathname = savestring (""); - - /* Start splitting the file. Walk along the tag table - outputting sections of the file. When we have written - all of the nodes in the tag table, make the top-level - pointer file, which contains indirect pointers and - tags for the nodes. */ - { - int which_file = 1; - TAG_ENTRY *tags = tag_table; - char *indirect_info = (char *)NULL; - - /* Remember the `header' of this file. The first tag in the file is - the bottom of the header; the top of the file is the start. */ - the_header = (char *)xmalloc (1 + (header_size = tags->position)); - memcpy (the_header, the_file, header_size); - - while (tags) - { - int file_top, file_bot, limit; - - /* Have to include the Control-_. */ - file_top = file_bot = tags->position; - limit = file_top + size; - - /* If the rest of this file is only one node, then - that is the entire subfile. */ - if (!tags->next_ent) - { - int i = tags->position + 1; - char last_char = the_file[i]; - - while (i < fileinfo.st_size) - { - if ((the_file[i] == '\037') && - ((last_char == '\n') || - (last_char == '\014'))) - break; - else - last_char = the_file[i]; - i++; - } - file_bot = i; - tags = tags->next_ent; - goto write_region; - } - - /* Otherwise, find the largest number of nodes that can fit in - this subfile. */ - for (; tags; tags = tags->next_ent) - { - if (!tags->next_ent) - { - /* This entry is the last node. Search forward for the end - of this node, and that is the end of this file. */ - int i = tags->position + 1; - char last_char = the_file[i]; - - while (i < fileinfo.st_size) - { - if ((the_file[i] == '\037') && - ((last_char == '\n') || - (last_char == '\014'))) - break; - else - last_char = the_file[i]; - i++; - } - file_bot = i; - - if (file_bot < limit) - { - tags = tags->next_ent; - goto write_region; - } - else - { - /* Here we want to write out everything before the last - node, and then write the last node out in a file - by itself. */ - file_bot = tags->position; - goto write_region; - } - } - - if (tags->next_ent->position > limit) - { - if (tags->position == file_top) - tags = tags->next_ent; - - file_bot = tags->position; - - write_region: - { - int fd; - char *split_filename; - - split_filename = (char *) xmalloc - (10 + strlen (root_pathname) + strlen (root_filename)); - sprintf - (split_filename, - "%s%s-%d", root_pathname, root_filename, which_file); - - fd = open - (split_filename, O_WRONLY | O_TRUNC | O_CREAT, 0666); - - if ((fd < 0) || - (write (fd, the_header, header_size) != header_size) || - (write (fd, the_file + file_top, file_bot - file_top) - != (file_bot - file_top)) || - ((close (fd)) < 0)) - { - perror (split_filename); - if (fd != -1) - close (fd); - exit (FATAL); - } - - if (!indirect_info) - { - indirect_info = the_file + file_top; - sprintf (indirect_info, "\037\nIndirect:\n"); - indirect_info += strlen (indirect_info); - } - - sprintf (indirect_info, "%s-%d: %d\n", - root_filename, which_file, file_top); - - free (split_filename); - indirect_info += strlen (indirect_info); - which_file++; - break; - } - } - } - } - - /* We have sucessfully created the subfiles. Now write out the - original again. We must use `output_stream', or - write_tag_table_indirect () won't know where to place the output. */ - output_stream = fopen (filename, "w"); - if (!output_stream) - { - perror (filename); - exit (FATAL); - } - - { - int distance = indirect_info - the_file; - fwrite (the_file, 1, distance, output_stream); - - /* Inhibit newlines. */ - paragraph_is_open = 0; - - write_tag_table_indirect (); - fclose (output_stream); - free (the_header); - free (the_file); - return; - } - } -} - -/* Some menu hacking. This is used to remember menu references while - reading the input file. After the output file has been written, if - validation is on, then we use the contents of NODE_REFERENCES as a - list of nodes to validate. */ -char * -reftype_type_string (type) - enum reftype type; -{ - switch (type) - { - case menu_reference: - return ("Menu"); - case followed_reference: - return ("Followed-Reference"); - default: - return ("Internal-bad-reference-type"); - } -} - -/* Remember this node name for later validation use. */ -remember_node_reference (node, line, type) - char *node; - int line; - enum reftype type; -{ - NODE_REF *temp = (NODE_REF *) xmalloc (sizeof (NODE_REF)); - - temp->next = node_references; - temp->node = savestring (node); - temp->line_no = line; - temp->section = current_section; - temp->type = type; - temp->containing_node = savestring (current_node); - temp->filename = node_filename; - - node_references = temp; -} - -validate_other_references (ref_list) - register NODE_REF *ref_list; -{ - char *old_input_filename = input_filename; - - while (ref_list != (NODE_REF *) NULL) - { - input_filename = ref_list->filename; - validate (ref_list->node, ref_list->line_no, - reftype_type_string (ref_list->type)); - ref_list = ref_list->next; - } - input_filename = old_input_filename; -} - -/* Find NODE in REF_LIST. */ -NODE_REF * -find_node_reference (node, ref_list) - char *node; - register NODE_REF *ref_list; -{ - while (ref_list) - { - if (strcmp (node, ref_list->node) == 0) - break; - ref_list = ref_list->next; - } - return (ref_list); -} - -free_node_references () -{ - register NODE_REF *list, *temp; - - list = node_references; - - while (list) - { - temp = list; - free (list->node); - free (list->containing_node); - list = list->next; - free (temp); - } - node_references = (NODE_REF *) NULL; -} - - /* This function gets called at the start of every line while inside of - a menu. It checks to see if the line starts with "* ", and if so, - remembers the node reference that this menu refers to. - input_text_offset is at the \n just before the line start. */ -#define menu_starter "* " -char * -glean_node_from_menu (remember_reference) - int remember_reference; -{ - int i, orig_offset = input_text_offset; - char *nodename; - - if (strncmp (&input_text[input_text_offset + 1], - menu_starter, - strlen (menu_starter)) != 0) - return ((char *)NULL); - else - input_text_offset += strlen (menu_starter) + 1; - - get_until_in_line (":", &nodename); - if (curchar () == ':') - input_text_offset++; - canon_white (nodename); - - if (curchar () == ':') - goto save_node; - - free (nodename); - get_rest_of_line (&nodename); - - /* Special hack: If the nodename follows the menu item name, - then we have to read the rest of the line in order to find - out what the nodename is. But we still have to read the - line later, in order to process any formatting commands that - might be present. So un-count the carriage return that has just - been counted. */ - line_number--; - - isolate_nodename (nodename); - -save_node: - input_text_offset = orig_offset; - normalize_node_name (nodename); - i = strlen (nodename); - if (i && nodename[i - 1] == ':') - nodename[i - 1] = '\0'; - - if (remember_reference) - { - remember_node_reference (nodename, line_number, menu_reference); - free (nodename); - return ((char *)NULL); - } - else - return (nodename); -} - -static void -isolate_nodename (nodename) - char *nodename; -{ - register int i, c; - int paren_seen, paren; - - if (!nodename) - return; - - canon_white (nodename); - paren_seen = paren = i = 0; - - if (*nodename == '.' || !*nodename) - { - *nodename = '\0'; - return; - } - - if (*nodename == '(') - { - paren++; - paren_seen++; - i++; - } - - for (; c = nodename[i]; i++) - { - if (paren) - { - if (c == '(') - paren++; - else if (c == ')') - paren--; - - continue; - } - - /* If the character following the close paren is a space, then this - node has no more characters associated with it. */ - if (c == '\t' || - c == '\n' || - c == ',' || - ((paren_seen && nodename[i - 1] == ')') && - (c == ' ' || c == '.')) || - (c == '.' && - ((!nodename[i + 1] || - (cr_or_whitespace (nodename[i + 1])) || - (nodename[i + 1] == ')'))))) - break; - } - nodename[i] = '\0'; -} - -cm_menu () -{ - begin_insertion (menu); -} - - -/* **************************************************************** */ -/* */ -/* Cross Reference Hacking */ -/* */ -/* **************************************************************** */ - -char * -get_xref_token () -{ - char *string; - - get_until_in_braces (",", &string); - if (curchar () == ',') - input_text_offset++; - fix_whitespace (string); - return (string); -} - -int px_ref_flag = 0; /* Controls initial output string. */ - -/* Make a cross reference. */ -cm_xref (arg) -{ - if (arg == START) - { - char *arg1, *arg2, *arg3, *arg4, *arg5; - - arg1 = get_xref_token (); - arg2 = get_xref_token (); - arg3 = get_xref_token (); - arg4 = get_xref_token (); - arg5 = get_xref_token (); - - add_word_args ("%s", px_ref_flag ? "*note " : "*Note "); - - if (*arg5 || *arg4) - { - char *node_name; - - if (!*arg2) - { - if (*arg3) - node_name = arg3; - else - node_name = arg1; - } - else - node_name = arg2; - - execute_string ("%s: (%s)%s", node_name, arg4, arg1); - return; - } - else - remember_node_reference (arg1, line_number, followed_reference); - - if (*arg3) - { - if (!*arg2) - execute_string ("%s: %s", arg3, arg1); - else - execute_string ("%s: %s", arg2, arg1); - return; - } - - if (*arg2) - execute_string ("%s: %s", arg2, arg1); - else - execute_string ("%s::", arg1); - } - else - { - - /* Check to make sure that the next non-whitespace character is either - a period or a comma. input_text_offset is pointing at the "}" which - ended the xref or pxref command. */ - int temp = input_text_offset + 1; - - if (output_paragraph[output_paragraph_offset - 2] == ':' && - output_paragraph[output_paragraph_offset - 1] == ':') - return; - while (temp < size_of_input_text) - { - if (cr_or_whitespace (input_text[temp])) - temp++; - else - { - if (input_text[temp] == '.' || - input_text[temp] == ',' || - input_text[temp] == '\t') - return; - else - { - line_error ( - "Cross-reference must be terminated with a period or a comma"); - return; - } - } - } - } -} - -cm_pxref (arg) - int arg; -{ - if (arg == START) - { - px_ref_flag++; - cm_xref (arg); - px_ref_flag--; - } - else - add_char ('.'); -} - -cm_inforef (arg) - int arg; -{ - if (arg == START) - { - char *node, *pname, *file; - - node = get_xref_token (); - pname = get_xref_token (); - file = get_xref_token (); - - execute_string ("*note %s: (%s)%s", pname, file, node); - } -} - -/* **************************************************************** */ -/* */ -/* Insertion Command Stubs */ -/* */ -/* **************************************************************** */ - -cm_quotation () -{ - begin_insertion (quotation); -} - -cm_example () -{ - begin_insertion (example); -} - -cm_smallexample () -{ - begin_insertion (smallexample); -} - -cm_lisp () -{ - begin_insertion (lisp); -} - -cm_smalllisp () -{ - begin_insertion (smalllisp); -} - -/* @cartouche/@end cartouche draws box with rounded corners in - TeX output. Right now, just a NOP insertion. */ -cm_cartouche () -{ - begin_insertion (cartouche); -} - -cm_format () -{ - begin_insertion (format); -} - -cm_display () -{ - begin_insertion (display); -} - -cm_itemize () -{ - begin_insertion (itemize); -} - -cm_enumerate () -{ - do_enumeration (enumerate, "1"); -} - -/* Start an enumeration insertion of type TYPE. If the user supplied - no argument on the line, then use DEFAULT_STRING as the initial string. */ -do_enumeration (type, default_string) - int type; - char *default_string; -{ - get_until_in_line (".", &enumeration_arg); - canon_white (enumeration_arg); - - if (!*enumeration_arg) - { - free (enumeration_arg); - enumeration_arg = savestring (default_string); - } - - if (!isdigit (*enumeration_arg) && !isletter (*enumeration_arg)) - { - warning ("%s requires a letter or a digit", insertion_type_pname (type)); - - switch (type) - { - case enumerate: - default_string = "1"; - break; - } - enumeration_arg = savestring (default_string); - } - begin_insertion (type); -} - -cm_table () -{ - begin_insertion (table); -} - -cm_ftable () -{ - begin_insertion (ftable); -} - -cm_vtable () -{ - begin_insertion (vtable); -} - -cm_group () -{ - begin_insertion (group); -} - -cm_ifinfo () -{ - begin_insertion (ifinfo); -} - -/* Begin an insertion where the lines are not filled or indented. */ -cm_flushleft () -{ - begin_insertion (flushleft); -} - -/* Begin an insertion where the lines are not filled, and each line is - forced to the right-hand side of the page. */ -cm_flushright () -{ - begin_insertion (flushright); -} - - -/* **************************************************************** */ -/* */ -/* Conditional Handling */ -/* */ -/* **************************************************************** */ - -/* A structure which contains `defined' variables. */ -typedef struct _defines { - struct _defines *next; - char *name; - char *value; -} DEFINE; - -/* The linked list of `set' defines. */ -DEFINE *defines = (DEFINE *)NULL; - -/* Add NAME to the list of `set' defines. */ -set (name, value) - char *name; - char *value; -{ - DEFINE *temp; - - for (temp = defines; temp; temp = temp->next) - if (strcmp (name, temp->name) == 0) - { - free (temp->value); - temp->value = savestring (value); - return; - } - - temp = (DEFINE *)xmalloc (sizeof (DEFINE)); - temp->next = defines; - temp->name = savestring (name); - temp->value = savestring (value); - defines = temp; -} - -/* Remove NAME from the list of `set' defines. */ -clear (name) - char *name; -{ - register DEFINE *temp, *last; - - last = (DEFINE *)NULL; - temp = defines; - - while (temp) - { - if (strcmp (temp->name, name) == 0) - { - if (last) - last->next = temp->next; - else - defines = temp->next; - - free (temp->name); - free (temp->value); - free (temp); - break; - } - last = temp; - temp = temp->next; - } -} - -/* Return the value of NAME. The return value is NULL if NAME is unset. */ -char * -set_p (name) - char *name; -{ - register DEFINE *temp; - - for (temp = defines; temp; temp = temp->next) - if (strcmp (temp->name, name) == 0) - return (temp->value); - - return ((char *)NULL); -} - -/* Conditionally parse based on the current command name. */ -command_name_condition () -{ - char *discarder; - - discarder = (char *)xmalloc (8 + strlen (command)); - - sprintf (discarder, "\n@end %s", command); - discard_until (discarder); - discard_until ("\n"); - - free (discarder); -} - -/* Create a variable whose name appears as the first word on this line. */ -cm_set () -{ - handle_variable (SET); -} - -/* Remove a variable whose name appears as the first word on this line. */ -cm_clear () -{ - handle_variable (CLEAR); -} - -cm_ifset () -{ - handle_variable (IFSET); -} - -cm_ifclear () -{ - handle_variable (IFCLEAR); -} - -cm_value (arg, start_pos, end_pos) - int arg, start_pos, end_pos; -{ - if (arg == END) - { - char *name, *value; - name = (char *)&output_paragraph[start_pos]; - output_paragraph[end_pos] = '\0'; - name = savestring (name); - value = set_p (name); - output_column -= end_pos - start_pos; - output_paragraph_offset = start_pos; - - if (value) - execute_string ("%s", value); - else - add_word_args ("{No Value For \"%s\"}", name); - - free (name); - } -} - -/* Set, clear, or conditionalize based on ACTION. */ -handle_variable (action) - int action; -{ - char *name; - - get_rest_of_line (&name); - backup_input_pointer (); - canon_white (name); - handle_variable_internal (action, name); - free (name); -} - -handle_variable_internal (action, name) - int action; - char *name; -{ - char *temp; - int delimiter, additional_text_present = 0; - - /* Only the first word of NAME is a valid tag. */ - temp = name; - delimiter = 0; - while (*temp && (delimiter || !whitespace (*temp))) - { -#if defined (SET_WITH_EQUAL) - if (*temp == '"' || *temp == '\'') - { - if (*temp == delimiter) - delimiter = 0; - else - delimiter = *temp; - } -#endif /* SET_WITH_EQUAL */ - temp++; - } - - if (*temp) - additional_text_present++; - - *temp = '\0'; - - if (!*name) - line_error ("@%s requires a name", command); - else - { - switch (action) - { - case SET: - { - char *value; - -#if defined (SET_WITH_EQUAL) - /* Allow a value to be saved along with a variable. The value is - the text following an `=' sign in NAME, if any is present. */ - - for (value = name; *value && *value != '='; value++); - - if (*value) - *value++ = '\0'; - - if (*value == '"' || *value == '\'') - { - value++; - value[strlen (value) - 1] = '\0'; - } - -#else /* !SET_WITH_EQUAL */ - /* The VALUE of NAME is the remainder of the line sans - whitespace. */ - if (additional_text_present) - { - value = temp + 1; - canon_white (value); - } - else - value = ""; -#endif /* !SET_WITH_VALUE */ - - set (name, value); - } - break; - - case CLEAR: - clear (name); - break; - - case IFSET: - case IFCLEAR: - /* If IFSET and NAME is not set, or if IFCLEAR and NAME is set, - read lines from the the file until we reach a matching - "@end CONDITION". This means that we only take note of - "@ifset/clear" and "@end" commands. */ - { - char condition[8]; - int condition_len; - - if (action == IFSET) - strcpy (condition, "ifset"); - else - strcpy (condition, "ifclear"); - - condition_len = strlen (condition); - - if ((action == IFSET && !set_p (name)) || - (action == IFCLEAR && set_p (name))) - { - int level = 0, done = 0; - - while (!done) - { - char *freeable_line, *line; - - get_rest_of_line (&freeable_line); - - for (line = freeable_line; whitespace (*line); line++); - - if (*line == COMMAND_PREFIX && - (strncmp (line + 1, condition, condition_len) == 0)) - level++; - else if (strncmp (line, "@end", 4) == 0) - { - char *cname = line + 4; - char *temp; - - while (*cname && whitespace (*cname)) - cname++; - temp = cname; - - while (*temp && !whitespace (*temp)) - temp++; - *temp = '\0'; - - if (strcmp (cname, condition) == 0) - { - if (!level) - { - done = 1; - } - else - level--; - } - } - free (freeable_line); - } - /* We found the end of a false @ifset/ifclear. If we are - in a menu, back up over the newline that ends the ifset, - since that newline may also begin the next menu entry. */ - break; - } - else - { - if (action == IFSET) - begin_insertion (ifset); - else - begin_insertion (ifclear); - } - } - break; - } - } -} - -/* **************************************************************** */ -/* */ -/* @itemx, @item */ -/* */ -/* **************************************************************** */ - -/* Non-zero means a string is in execution, as opposed to a file. */ -int executing_string = 0; - -/* Execute the string produced by formatting the ARGs with FORMAT. This - is like submitting a new file with @include. */ -#if defined (HAVE_VARARGS_H) && defined(HAVE_VSPRINTF) - -execute_string (va_alist) - va_dcl -{ - static char temp_string[4000]; - char *format; - va_list args; - - va_start (args); - format = va_arg (args, char *); - vsprintf (temp_string, format, args); - va_end (args); - -#else /* !(HAVE_VARARGS_H && HAVE_VSPRINTF) */ - -execute_string (format, arg1, arg2, arg3, arg4, arg5) - char *format; -{ - static char temp_string[4000]; - sprintf (temp_string, format, arg1, arg2, arg3, arg4, arg5); - -#endif /* !(HAVE_VARARGS_H && HAVE_VSPRINTF) */ - - strcat (temp_string, "@bye\n"); - pushfile (); - input_text_offset = 0; - input_text = temp_string; - input_filename = savestring (input_filename); - size_of_input_text = strlen (temp_string); - - executing_string++; - reader_loop (); - - popfile (); - executing_string--; - - free_and_clear (&command); - command = savestring ("not bye"); -} - -int itemx_flag = 0; - -cm_itemx () -{ - itemx_flag++; - cm_item (); - itemx_flag--; -} - -cm_item () -{ - char *rest_of_line, *item_func; - - /* Can only hack "@item" while inside of an insertion. */ - if (insertion_level) - { - INSERTION_ELT *stack = insertion_stack; - int original_input_text_offset; - - skip_whitespace (); - original_input_text_offset = input_text_offset; - - get_rest_of_line (&rest_of_line); - canon_white (rest_of_line); - item_func = current_item_function (); - - /* Okay, do the right thing depending on which insertion function - is active. */ - - switch_top: - switch (stack->insertion) - { - case ifinfo: - case ifset: - case ifclear: - case cartouche: - stack = stack->next; - if (!stack) - goto no_insertion; - else - goto switch_top; - break; - - case menu: - case quotation: - case example: - case smallexample: - case lisp: - case format: - case display: - case group: - line_error ("The `@%s' command is meaningless within a `@%s' block", - command, - insertion_type_pname (current_insertion_type ())); - break; - - case itemize: - case enumerate: - if (itemx_flag) - { - line_error ("@itemx is not meaningful inside of a `%s' block", - insertion_type_pname (current_insertion_type ())); - } - else - { - start_paragraph (); - kill_self_indent (-1); - filling_enabled = indented_fill = 1; - - if (current_insertion_type () == itemize) - { - indent (output_column = current_indent - 2); - - /* I need some way to determine whether this command - takes braces or not. I believe the user can type - either "@bullet" or "@bullet{}". Of course, they - can also type "o" or "#" or whatever else they want. */ - if (item_func && *item_func) - { - if (*item_func == '@') - if (item_func[strlen (item_func) - 1] != '}') - execute_string ("%s{}", item_func); - else - execute_string ("%s", item_func); - else - execute_string ("%s", item_func); - } - insert (' '); - output_column++; - } - else - enumerate_item (); - - /* Special hack. This makes close paragraph ignore you until - the start_paragraph () function has been called. */ - must_start_paragraph = 1; - - /* Ultra special hack. It appears that some people incorrectly - place text directly after the @item, instead of on a new line - by itself. This happens to work in TeX, so I make it work - here. */ - if (*rest_of_line) - { - line_number--; - input_text_offset = original_input_text_offset; - } - } - break; - - case table: - case ftable: - case vtable: - { - /* Get rid of extra characters. */ - kill_self_indent (-1); - - /* close_paragraph () almost does what we want. The problem - is when paragraph_is_open, and last_char_was_newline, and - the last newline has been turned into a space, because - filling_enabled. I handle it here. */ - if (last_char_was_newline && filling_enabled && paragraph_is_open) - insert ('\n'); - close_paragraph (); - -#if defined (INDENT_PARAGRAPHS_IN_TABLE) - /* Indent on a new line, but back up one indentation level. */ - { - int t; - - t = inhibit_paragraph_indentation; - inhibit_paragraph_indentation = 1; - /* At this point, inserting any non-whitespace character will - force the existing indentation to be output. */ - add_char ('i'); - inhibit_paragraph_indentation = t; - } -#else /* !INDENT_PARAGRAPHS_IN_TABLE */ - add_char ('i'); -#endif /* !INDENT_PARAGRAPHS_IN_TABLE */ - - output_paragraph_offset--; - kill_self_indent (default_indentation_increment + 1); - - /* Add item's argument to the line. */ - filling_enabled = 0; - if (item_func && *item_func) - execute_string ("%s{%s}", item_func, rest_of_line); - else - execute_string ("%s", rest_of_line); - - if (current_insertion_type () == ftable) - execute_string ("@findex %s\n", rest_of_line); - - if (current_insertion_type () == vtable) - execute_string ("@vindex %s\n", rest_of_line); - - /* Start a new line, and let start_paragraph () - do the indenting of it for you. */ - close_single_paragraph (); - indented_fill = filling_enabled = 1; - } - } - free (rest_of_line); - } - else - { - no_insertion: - line_error ("@%s found outside of an insertion block", command); - } -} - - -/* **************************************************************** */ -/* */ -/* Defun and Friends */ -/* */ -/* **************************************************************** */ - -#define DEFUN_SELF_DELIMITING(c) \ - (((c) == '(') \ - || ((c) == ')') \ - || ((c) == '[') \ - || ((c) == ']')) - -struct token_accumulator -{ - unsigned int length; - unsigned int index; - char **tokens; -}; - -void -initialize_token_accumulator (accumulator) - struct token_accumulator *accumulator; -{ - (accumulator->length) = 0; - (accumulator->index) = 0; - (accumulator->tokens) = NULL; -} - -void -accumulate_token (accumulator, token) - struct token_accumulator *accumulator; - char *token; -{ - if ((accumulator->index) >= (accumulator->length)) - { - (accumulator->length) += 10; - (accumulator->tokens) = (char **) xrealloc - (accumulator->tokens, (accumulator->length * sizeof (char *))); - } - accumulator->tokens[accumulator->index] = token; - accumulator->index += 1; -} - -char * -copy_substring (start, end) - char *start; - char *end; -{ - char *result, *scan, *scan_result; - - result = (char *) xmalloc ((end - start) + 1); - scan_result = result; - scan = start; - - while (scan < end) - *scan_result++ = *scan++; - - *scan_result = '\0'; - return (result); -} - -/* Given `string' pointing at an open brace, skip forward and return a - pointer to just past the matching close brace. */ -int -scan_group_in_string (string_pointer) - char **string_pointer; -{ - register int c; - register char *scan_string; - register unsigned int level = 1; - - scan_string = (*string_pointer) + 1; - - while (1) - { - if (level == 0) - { - (*string_pointer) = scan_string; - return (1); - } - c = (*scan_string++); - if (c == '\0') - { - /* Tweak line_number to compensate for fact that - we gobbled the whole line before coming here. */ - line_number -= 1; - line_error ("Missing `}' in @def arg"); - line_number += 1; - (*string_pointer) = (scan_string - 1); - return (0); - } - if (c == '{') - level += 1; - if (c == '}') - level -= 1; - } -} - -/* Return a list of tokens from the contents of `string'. - Commands and brace-delimited groups count as single tokens. - Contiguous whitespace characters are converted to a token - consisting of a single space. */ -char ** -args_from_string (string) - char *string; -{ - struct token_accumulator accumulator; - register char *scan_string = string; - char *token_start, *token_end; - - initialize_token_accumulator (&accumulator); - - while ((*scan_string) != '\0') - { - /* Replace arbitrary whitespace by a single space. */ - if (whitespace (*scan_string)) - { - scan_string += 1; - while (whitespace (*scan_string)) - scan_string += 1; - accumulate_token ((&accumulator), (savestring (" "))); - continue; - } - - /* Commands count as single tokens. */ - if ((*scan_string) == COMMAND_PREFIX) - { - token_start = scan_string; - scan_string += 1; - if (self_delimiting (*scan_string)) - scan_string += 1; - else - { - register int c; - while (1) - { - c = *scan_string++; - - if ((c == '\0') || (c == '{') || (whitespace (c))) - { - scan_string -= 1; - break; - } - } - - if (*scan_string == '{') - { - char *s = scan_string; - (void) scan_group_in_string (&s); - scan_string = s; - } - } - token_end = scan_string; - } - - /* Parentheses and brackets are self-delimiting. */ - else if (DEFUN_SELF_DELIMITING (*scan_string)) - { - token_start = scan_string; - scan_string += 1; - token_end = scan_string; - } - - /* Open brace introduces a group that is a single token. */ - else if (*scan_string == '{') - { - char *s = scan_string; - int balanced = scan_group_in_string (&s); - - token_start = scan_string + 1; - scan_string = s; - token_end = balanced ? (scan_string - 1) : scan_string; - } - - /* Otherwise a token is delimited by whitespace, parentheses, - brackets, or braces. A token is also ended by a command. */ - else - { - token_start = scan_string; - - while (1) - { - register int c; - - c = *scan_string++; - - if (!c || - (whitespace (c) || DEFUN_SELF_DELIMITING (c) || - c == '{' || c == '}')) - { - scan_string--; - break; - } - - /* If we encounter a command imbedded within a token, - then end the token. */ - if (c == COMMAND_PREFIX) - { - scan_string--; - break; - } - } - token_end = scan_string; - } - - accumulate_token - (&accumulator, copy_substring (token_start, token_end)); - } - accumulate_token (&accumulator, NULL); - return (accumulator.tokens); -} - -void -process_defun_args (defun_args, auto_var_p) - char **defun_args; - int auto_var_p; -{ - int pending_space = 0; - - while (1) - { - char *defun_arg = *defun_args++; - - if (defun_arg == NULL) - break; - - if (defun_arg[0] == ' ') - { - pending_space = 1; - continue; - } - - if (pending_space) - { - add_char (' '); - pending_space = 0; - } - - if (DEFUN_SELF_DELIMITING (defun_arg[0])) - add_char (defun_arg[0]); - else if (defun_arg[0] == '&') - add_word (defun_arg); - else if (defun_arg[0] == COMMAND_PREFIX) - execute_string ("%s", defun_arg); - else if (auto_var_p) - execute_string ("@var{%s}", defun_arg); - else - add_word (defun_arg); - } -} - -char * -next_nonwhite_defun_arg (arg_pointer) - char ***arg_pointer; -{ - char **scan = (*arg_pointer); - char *arg = (*scan++); - - if ((arg != 0) && (*arg == ' ')) - arg = *scan++; - - if (arg == 0) - scan -= 1; - - *arg_pointer = scan; - - return ((arg == 0) ? "" : arg); -} - -/* Make the defun type insertion. - TYPE says which insertion this is. - X_P says not to start a new insertion if non-zero. */ -void -defun_internal (type, x_p) - enum insertion_type type; - int x_p; -{ - enum insertion_type base_type; - char **defun_args, **scan_args; - char *category, *defined_name, *type_name, *type_name2; - - { - char *line; - get_rest_of_line (&line); - defun_args = (args_from_string (line)); - free (line); - } - - scan_args = defun_args; - - switch (type) - { - case defun: - category = "Function"; - base_type = deffn; - break; - case defmac: - category = "Macro"; - base_type = deffn; - break; - case defspec: - category = "Special Form"; - base_type = deffn; - break; - case defvar: - category = "Variable"; - base_type = defvr; - break; - case defopt: - category = "User Option"; - base_type = defvr; - break; - case deftypefun: - category = "Function"; - base_type = deftypefn; - break; - case deftypevar: - category = "Variable"; - base_type = deftypevr; - break; - case defivar: - category = "Instance Variable"; - base_type = defcv; - break; - case defmethod: - category = "Method"; - base_type = defop; - break; - case deftypemethod: - category = "Method"; - base_type = deftypemethod; - break; - default: - category = next_nonwhite_defun_arg (&scan_args); - base_type = type; - break; - } - - if ((base_type == deftypefn) - || (base_type == deftypevr) - || (base_type == defcv) - || (base_type == defop) - || (base_type == deftypemethod)) - type_name = next_nonwhite_defun_arg (&scan_args); - - if (base_type == deftypemethod) - type_name2 = next_nonwhite_defun_arg (&scan_args); - - defined_name = next_nonwhite_defun_arg (&scan_args); - - /* This hack exists solely for the purposes of formatting the texinfo - manual. I couldn't think of a better way. The token might be - a simple @@ followed immediately by more text. If this is the case, - then the next defun arg is part of this one, and we should concatenate - them. */ - if (*scan_args && **scan_args && !whitespace (**scan_args) && - (strcmp (defined_name, "@@") == 0)) - { - char *tem = (char *)xmalloc (3 + strlen (scan_args[0])); - - sprintf (tem, "@@%s", scan_args[0]); - - free (scan_args[0]); - scan_args[0] = tem; - scan_args++; - defined_name = tem; - } - - if (!x_p) - begin_insertion (type); - - /* Write the definition header line. - This should start at the normal indentation. */ - current_indent -= default_indentation_increment; - start_paragraph (); - - switch (base_type) - { - case deffn: - case defvr: - case deftp: - execute_string (" -- %s: %s", category, defined_name); - break; - case deftypefn: - case deftypevr: - execute_string (" -- %s: %s %s", category, type_name, defined_name); - break; - case defcv: - execute_string (" -- %s of %s: %s", category, type_name, defined_name); - break; - case defop: - execute_string (" -- %s on %s: %s", category, type_name, defined_name); - break; - case deftypemethod: - execute_string (" -- %s on %s: %s %s", category, type_name, type_name2, - defined_name); - break; - } - current_indent += default_indentation_increment; - - /* Now process the function arguments, if any. - If these carry onto the next line, they should be indented by two - increments to distinguish them from the body of the definition, - which is indented by one increment. */ - current_indent += default_indentation_increment; - - switch (base_type) - { - case deffn: - case defop: - process_defun_args (scan_args, 1); - break; - case deftp: - case deftypefn: - case deftypemethod: - process_defun_args (scan_args, 0); - break; - } - current_indent -= default_indentation_increment; - close_single_paragraph (); - - /* Make an entry in the appropriate index. */ - switch (base_type) - { - case deffn: - case deftypefn: - execute_string ("@findex %s\n", defined_name); - break; - case defvr: - case deftypevr: - case defcv: - execute_string ("@vindex %s\n", defined_name); - break; - case defop: - case deftypemethod: - execute_string ("@findex %s on %s\n", defined_name, type_name); - break; - case deftp: - execute_string ("@tindex %s\n", defined_name); - break; - } - - /* Deallocate the token list. */ - scan_args = defun_args; - while (1) - { - char * arg = (*scan_args++); - if (arg == NULL) - break; - free (arg); - } - free (defun_args); -} - -/* Add an entry for a function, macro, special form, variable, or option. - If the name of the calling command ends in `x', then this is an extra - entry included in the body of an insertion of the same type. */ -cm_defun () -{ - int x_p; - enum insertion_type type; - char *temp = savestring (command); - - x_p = (command[strlen (command) - 1] == 'x'); - - if (x_p) - temp[strlen (temp) - 1] = '\0'; - - type = find_type_from_name (temp); - free (temp); - - /* If we are adding to an already existing insertion, then make sure - that we are already in an insertion of type TYPE. */ - if (x_p && - (!insertion_level || insertion_stack->insertion != type)) - { - line_error ("Must be in a `%s' insertion in order to use `%s'x", - command, command); - discard_until ("\n"); - return; - } - - defun_internal (type, x_p); -} - -/* End existing insertion block. */ -cm_end () -{ - char *temp; - enum insertion_type type; - - if (!insertion_level) - { - line_error ("Unmatched `@%s'", command); - return; - } - - get_rest_of_line (&temp); - canon_white (temp); - - if (strlen (temp) == 0) - line_error ("`@%s' needs something after it", command); - - type = find_type_from_name (temp); - - if (type == bad_type) - { - line_error ("Bad argument to `%s', `%s', using `%s'", - command, temp, insertion_type_pname (current_insertion_type ())); - } - end_insertion (type); - free (temp); -} - - -/* **************************************************************** */ -/* */ -/* Other Random Commands */ -/* */ -/* **************************************************************** */ - -/* This says to inhibit the indentation of the next paragraph, but - not of following paragraphs. */ -cm_noindent () -{ - if (!inhibit_paragraph_indentation) - inhibit_paragraph_indentation = -1; -} - -/* I don't know exactly what to do with this. Should I allow - someone to switch filenames in the middle of output? Since the - file could be partially written, this doesn't seem to make sense. - Another option: ignore it, since they don't *really* want to - switch files. Finally, complain, or at least warn. */ -cm_setfilename () -{ - char *filename; - get_rest_of_line (&filename); - /* warning ("`@%s %s' encountered and ignored", command, filename); */ - free (filename); -} - -cm_ignore_line () -{ - discard_until ("\n"); -} - -/* @br can be immediately followed by `{}', so we have to read those here. - It should simply close the paragraph. */ -cm_br () -{ - if (looking_at ("{}")) - input_text_offset += 2; - - if (curchar () == '\n') - { - input_text_offset++; - line_number++; - } - - close_paragraph (); -} - - /* Insert the number of blank lines passed as argument. */ -cm_sp () -{ - int lines; - char *line; - - get_rest_of_line (&line); - - if (sscanf (line, "%d", &lines) != 1) - { - line_error ("%csp requires a positive numeric argument", COMMAND_PREFIX); - } - else - { - if (lines < 0) - lines = 0; - - while (lines--) - add_char ('\n'); - } - free (line); -} - -/* Start a new line with just this text on it. - Then center the line of text. - This always ends the current paragraph. */ -cm_center () -{ - register int i, start, length; - int fudge_factor = 1; - unsigned char *line; - - close_paragraph (); - filling_enabled = indented_fill = 0; - cm_noindent (); - start = output_paragraph_offset; - inhibit_output_flushing (); - get_rest_of_line ((char **)&line); - execute_string ((char *)line); - free (line); - uninhibit_output_flushing (); - - i = output_paragraph_offset - 1; - while (i > (start - 1) && output_paragraph[i] == '\n') - i--; - - output_paragraph_offset = ++i; - length = output_paragraph_offset - start; - - if (length < (fill_column - fudge_factor)) - { - line = (unsigned char *)xmalloc (1 + length); - memcpy (line, (char *)(output_paragraph + start), length); - - i = (fill_column - fudge_factor - length) / 2; - output_paragraph_offset = start; - - while (i--) - insert (' '); - - for (i = 0; i < length; i++) - insert (line[i]); - - free (line); - } - - insert ('\n'); - close_paragraph (); - filling_enabled = 1; -} - -/* Show what an expression returns. */ -cm_result (arg) - int arg; -{ - if (arg == END) - add_word ("=>"); -} - -/* What an expression expands to. */ -cm_expansion (arg) - int arg; -{ - if (arg == END) - add_word ("==>"); -} - -/* Indicates two expressions are equivalent. */ -cm_equiv (arg) - int arg; -{ - if (arg == END) - add_word ("=="); -} - -/* What an expression may print. */ -cm_print (arg) - int arg; -{ - if (arg == END) - add_word ("-|"); -} - -/* An error signaled. */ -cm_error (arg) - int arg; -{ - if (arg == END) - add_word ("error-->"); -} - -/* The location of point in an example of a buffer. */ -cm_point (arg) - int arg; -{ - if (arg == END) - add_word ("-!-"); -} - -/* Start a new line with just this text on it. - The text is outdented one level if possible. */ -cm_exdent () -{ - char *line; - int i = current_indent; - - if (current_indent) - current_indent -= default_indentation_increment; - - get_rest_of_line (&line); - close_single_paragraph (); - execute_string ("%s", line); - current_indent = i; - free (line); - close_single_paragraph (); -} - -cm_include () -{ - cm_infoinclude (); -} - -/* Remember this file, and move onto the next. */ -cm_infoinclude () -{ - char *filename; - - close_paragraph (); - get_rest_of_line (&filename); - pushfile (); - - /* In verbose mode we print info about including another file. */ - if (verbose_mode) - { - register int i = 0; - register FSTACK *stack = filestack; - - for (i = 0, stack = filestack; stack; stack = stack->next, i++); - - i *= 2; - - printf ("%*s", i, ""); - printf ("%c%s %s\n", COMMAND_PREFIX, command, filename); - fflush (stdout); - } - - if (!find_and_load (filename)) - { - extern const char * const sys_errlist[]; - extern int errno, sys_nerr; - popfile (); - - /* Cannot "@include foo", in line 5 of "/wh/bar". */ - line_error ("`%c%s %s': %s", COMMAND_PREFIX, command, filename, - ((errno < sys_nerr) ? - sys_errlist[errno] : "Unknown file system error")); - } - free (filename); -} - -/* The other side of a malformed expression. */ -misplaced_brace () -{ - line_error ("Misplaced `}'"); -} - -/* Don't let the filling algorithm insert extra whitespace here. */ -cm_force_abbreviated_whitespace () -{ -} - -/* Do not let this character signify the end of a sentence, though - if it was seen without the command prefix it normally would. We - do this by turning on the 8th bit of the character. */ -cm_ignore_sentence_ender () -{ - add_char (META ((*command))); -} - -/* Signals end of processing. Easy to make this happen. */ -cm_bye () -{ - input_text_offset = size_of_input_text; -} - -cm_asis () -{ -} - -cm_math () -{ -} - - -/* **************************************************************** */ -/* */ -/* Indexing Stuff */ -/* */ -/* **************************************************************** */ - - -/* An index element... */ -typedef struct index_elt -{ - struct index_elt *next; - char *entry; /* The index entry itself. */ - char *node; /* The node from whence it came. */ - int code; /* Non-zero means add `@code{...}' when - printing this element. */ - int defining_line; /* Line number where this entry was written. */ -} INDEX_ELT; - -/* A list of short-names for each index, and the index to that index in our - index array, the_indices. In addition, for each index, it is remembered - whether that index is a code index or not. Code indices have @code{} - inserted around the first word when they are printed with printindex. */ -typedef struct -{ - char *name; - int index; - int code; -} INDEX_ALIST; - -INDEX_ALIST **name_index_alist = (INDEX_ALIST **) NULL; - -/* An array of pointers. Each one is for a different index. The - "synindex" command changes which array slot is pointed to by a - given "index". */ -INDEX_ELT **the_indices = (INDEX_ELT **) NULL; - -/* The number of defined indices. */ -int defined_indices = 0; - -/* We predefine these. */ -#define program_index 0 -#define function_index 1 -#define concept_index 2 -#define variable_index 3 -#define datatype_index 4 -#define key_index 5 - -init_indices () -{ - int i; - - /* Create the default data structures. */ - - /* Initialize data space. */ - if (!the_indices) - { - the_indices = (INDEX_ELT **) xmalloc ((1 + defined_indices) * - sizeof (INDEX_ELT *)); - the_indices[defined_indices] = (INDEX_ELT *) NULL; - - name_index_alist = (INDEX_ALIST **) xmalloc ((1 + defined_indices) * - sizeof (INDEX_ALIST *)); - name_index_alist[defined_indices] = (INDEX_ALIST *) NULL; - } - - /* If there were existing indices, get rid of them now. */ - for (i = 0; i < defined_indices; i++) - undefindex (name_index_alist[i]->name); - - /* Add the default indices. */ - defindex ("pg", 0); - defindex ("fn", 1); /* "fn" is a code index. */ - defindex ("cp", 0); - defindex ("vr", 0); - defindex ("tp", 0); - defindex ("ky", 0); - -} - -/* Find which element in the known list of indices has this name. - Returns -1 if NAME isn't found. */ -int -find_index_offset (name) - char *name; -{ - register int i; - for (i = 0; i < defined_indices; i++) - if (name_index_alist[i] && - strcmp (name, name_index_alist[i]->name) == 0) - return (name_index_alist[i]->index); - return (-1); -} - -/* Return a pointer to the entry of (name . index) for this name. - Return NULL if the index doesn't exist. */ -INDEX_ALIST * -find_index (name) - char *name; -{ - int offset = find_index_offset (name); - if (offset > -1) - return (name_index_alist[offset]); - else - return ((INDEX_ALIST *) NULL); -} - -/* Given an index name, return the offset in the_indices of this index, - or -1 if there is no such index. */ -translate_index (name) - char *name; -{ - INDEX_ALIST *which = find_index (name); - - if (which) - return (which->index); - else - return (-1); -} - -/* Return the index list which belongs to NAME. */ -INDEX_ELT * -index_list (name) - char *name; -{ - int which = translate_index (name); - if (which < 0) - return ((INDEX_ELT *) - 1); - else - return (the_indices[which]); -} - -/* Please release me, let me go... */ -free_index (index) - INDEX_ELT *index; -{ - INDEX_ELT *temp; - - while ((temp = index) != (INDEX_ELT *) NULL) - { - free (temp->entry); - free (temp->node); - index = index->next; - free (temp); - } -} - -/* Flush an index by name. */ -undefindex (name) - char *name; -{ - int i; - int which = find_index_offset (name); - - if (which < 0) - return (which); - - i = name_index_alist[which]->index; - - - free_index (the_indices[i]); - the_indices[i] = (INDEX_ELT *) NULL; - - free (name_index_alist[which]->name); - free (name_index_alist[which]); - name_index_alist[which] = (INDEX_ALIST *) NULL; -} - -/* Define an index known as NAME. We assign the slot number. - CODE if non-zero says to make this a code index. */ -defindex (name, code) - char *name; - int code; -{ - register int i, slot; - - /* If it already exists, flush it. */ - undefindex (name); - - /* Try to find an empty slot. */ - slot = -1; - for (i = 0; i < defined_indices; i++) - if (!name_index_alist[i]) - { - slot = i; - break; - } - - if (slot < 0) - { - /* No such luck. Make space for another index. */ - slot = defined_indices; - defined_indices++; - - name_index_alist = (INDEX_ALIST **) - xrealloc ((char *)name_index_alist, - (1 + defined_indices) * sizeof (INDEX_ALIST *)); - the_indices = (INDEX_ELT **) - xrealloc ((char *)the_indices, - (1 + defined_indices) * sizeof (INDEX_ELT *)); - } - - /* We have a slot. Start assigning. */ - name_index_alist[slot] = (INDEX_ALIST *) xmalloc (sizeof (INDEX_ALIST)); - name_index_alist[slot]->name = savestring (name); - name_index_alist[slot]->index = slot; - name_index_alist[slot]->code = code; - - the_indices[slot] = (INDEX_ELT *) NULL; -} - -/* Add the arguments to the current index command to the index NAME. */ -index_add_arg (name) - char *name; -{ - int which; - char *index_entry; - INDEX_ALIST *tem; - - tem = find_index (name); - - which = tem ? tem->index : -1; - - get_rest_of_line (&index_entry); - ignore_blank_line (); - - if (which < 0) - { - line_error ("Unknown index reference `%s'", name); - free (index_entry); - } - else - { - INDEX_ELT *new = (INDEX_ELT *) xmalloc (sizeof (INDEX_ELT)); - new->next = the_indices[which]; - new->entry = index_entry; - new->node = current_node; - new->code = tem->code; - new->defining_line = line_number - 1; - the_indices[which] = new; - } -} - -#define INDEX_COMMAND_SUFFIX "index" - -/* The function which user defined index commands call. */ -gen_index () -{ - char *name = savestring (command); - if (strlen (name) >= strlen ("index")) - name[strlen (name) - strlen ("index")] = '\0'; - index_add_arg (name); - free (name); -} - -/* Define a new index command. Arg is name of index. */ -cm_defindex () -{ - gen_defindex (0); -} - -cm_defcodeindex () -{ - gen_defindex (1); -} - -gen_defindex (code) - int code; -{ - char *name; - get_rest_of_line (&name); - - if (find_index (name)) - { - line_error ("Index `%s' already exists", name); - free (name); - return; - } - else - { - char *temp = (char *) alloca (1 + strlen (name) + strlen ("index")); - sprintf (temp, "%sindex", name); - define_user_command (temp, gen_index, 0); - defindex (name, code); - free (name); - } -} - -/* Append LIST2 to LIST1. Return the head of the list. */ -INDEX_ELT * -index_append (head, tail) - INDEX_ELT *head, *tail; -{ - register INDEX_ELT *t_head = head; - - if (!t_head) - return (tail); - - while (t_head->next) - t_head = t_head->next; - t_head->next = tail; - return (head); -} - -/* Expects 2 args, on the same line. Both are index abbreviations. - Make the first one be a synonym for the second one, i.e. make the - first one have the same index as the second one. */ -cm_synindex () -{ - int redirector, redirectee; - char *temp; - - skip_whitespace (); - get_until_in_line (" ", &temp); - redirectee = find_index_offset (temp); - skip_whitespace (); - free_and_clear (&temp); - get_until_in_line (" ", &temp); - redirector = find_index_offset (temp); - free (temp); - if (redirector < 0 || redirectee < 0) - { - line_error ("Unknown index reference"); - } - else - { - /* I think that we should let the user make indices synonymous to - each other without any lossage of info. This means that one can - say @synindex cp dt anywhere in the file, and things that used to - be in cp will go into dt. */ - INDEX_ELT *i1 = the_indices[redirectee], *i2 = the_indices[redirector]; - - if (i1 || i2) - { - if (i1) - the_indices[redirectee] = index_append (i1, i2); - else - the_indices[redirectee] = index_append (i2, i1); - } - - name_index_alist[redirectee]->index = - name_index_alist[redirector]->index; - } -} - -cm_pindex () /* Pinhead index. */ -{ - index_add_arg ("pg"); -} - -cm_vindex () /* Variable index. */ -{ - index_add_arg ("vr"); -} - -cm_kindex () /* Key index. */ -{ - index_add_arg ("ky"); -} - -cm_cindex () /* Concept index. */ -{ - index_add_arg ("cp"); -} - -cm_findex () /* Function index. */ -{ - index_add_arg ("fn"); -} - -cm_tindex () /* Data Type index. */ -{ - index_add_arg ("tp"); -} - -/* Sorting the index. */ -index_element_compare (element1, element2) - INDEX_ELT **element1, **element2; -{ - /* This needs to ignore leading non-text characters. */ - return (stricmp ((*element1)->entry, (*element2)->entry)); -} - -/* Sort the index passed in INDEX, returning an array of - pointers to elements. The array is terminated with a NULL - pointer. We call qsort because it's supposed to be fast. - I think this looks bad. */ -INDEX_ELT ** -sort_index (index) - INDEX_ELT *index; -{ - INDEX_ELT *temp = index; - INDEX_ELT **array; - int count = 0; - - while (temp != (INDEX_ELT *) NULL) - { - count++; - temp = temp->next; - } - - /* We have the length. Make an array. */ - - array = (INDEX_ELT **) xmalloc ((count + 1) * sizeof (INDEX_ELT *)); - count = 0; - temp = index; - - while (temp != (INDEX_ELT *) NULL) - { - array[count++] = temp; - temp = temp->next; - } - array[count] = (INDEX_ELT *) NULL; /* terminate the array. */ - - /* Sort the array. */ - qsort (array, count, sizeof (INDEX_ELT *), index_element_compare); - - return (array); -} - -/* Non-zero means that we are in the middle of printing an index. */ -int printing_index = 0; - -/* Takes one arg, a short name of an index to print. - Outputs a menu of the sorted elements of the index. */ -cm_printindex () -{ - int item; - INDEX_ELT *index; - INDEX_ELT **array; - char *index_name; - int old_inhibitions = inhibit_paragraph_indentation; - int previous_filling_enabled_value = filling_enabled; - - close_paragraph (); - get_rest_of_line (&index_name); - - index = index_list (index_name); - if ((int) index == -1) - { - line_error ("Unknown index name `%s'", index_name); - free (index_name); - return; - } - else - free (index_name); - - array = sort_index (index); - - filling_enabled = 0; - inhibit_paragraph_indentation = 1; - close_paragraph (); - add_word ("* Menu:\n\n"); - - printing_index = 1; - for (item = 0; (index = array[item]); item++) - { - int real_line_number = line_number; - - /* Let errors generated while making the index entry point back - at the line which contains the entry. */ - line_number = index->defining_line; - - /* If this particular entry should be printed as a "code" index, - then wrap the entry with "@code{...}". */ - if (index->code) - execute_string ("* @code{%s}: ", index->entry); - else - execute_string ("* %s: ", index->entry); - - /* Pad the front of the destination nodename so that - the output looks nice. */ - if (fill_column > 40 && output_column < 40) - indent (40 - output_column); - - execute_string ("%s.\n", index->node); - - line_number = real_line_number; - flush_output (); - } - - printing_index = 0; - free (array); - close_single_paragraph (); - filling_enabled = previous_filling_enabled_value; - inhibit_paragraph_indentation = old_inhibitions; -} - - -/* **************************************************************** */ -/* */ -/* Making User Defined Commands */ -/* */ -/* **************************************************************** */ - -define_user_command (name, proc, needs_braces_p) - char *name; - FUNCTION *proc; - int needs_braces_p; -{ - int slot = user_command_array_len; - user_command_array_len++; - - if (!user_command_array) - user_command_array = (COMMAND **) xmalloc (1 * sizeof (COMMAND *)); - - user_command_array = (COMMAND **) xrealloc (user_command_array, - (1 + user_command_array_len) * - sizeof (COMMAND *)); - - user_command_array[slot] = (COMMAND *) xmalloc (sizeof (COMMAND)); - user_command_array[slot]->name = savestring (name); - user_command_array[slot]->proc = proc; - user_command_array[slot]->argument_in_braces = needs_braces_p; -} - -/* Make ALIAS run the named FUNCTION. Copies properties from FUNCTION. */ -define_alias (alias, function) - char *alias, *function; -{ -} - -/* Set the paragraph indentation variable to the value specified in STRING. - Values can be: - `asis': Don't change existing indentation. - `none': Remove existing indentation. - NUM: Indent NUM spaces at the starts of paragraphs. - Note that if NUM is zero, we assume `none'. - - Returns 0 if successful, or non-zero if STRING isn't one of the above. */ -int -set_paragraph_indent (string) - char *string; -{ - if (strcmp (string, "asis") == 0) - paragraph_start_indent = 0; - else if (strcmp (string, "none") == 0) - paragraph_start_indent = -1; - else - { - if (sscanf (string, "%d", ¶graph_start_indent) != 1) - return (-1); - else - { - if (paragraph_start_indent == 0) - paragraph_start_indent = -1; - } - } - return (0); -} - -cm_paragraphindent () -{ - char *arg; - - get_rest_of_line (&arg); - if (set_paragraph_indent (arg) != 0) - line_error ("Bad argument to @paragraphindent"); - - free (arg); -} - -/* Some support for footnotes. */ - -/* Footnotes are a new construct in Info. We don't know the best method - of implementing them for sure, so we present two possiblities. - - SeparateNode: - Make them look like followed references, with the reference - destinations in a makeinfo manufactured node or, - - EndNode: - Make them appear at the bottom of the node that they originally - appeared in. */ -#define SeparateNode 0 -#define EndNode 1 - -int footnote_style = EndNode; -int first_footnote_this_node = 1; -int footnote_count = 0; - -/* Set the footnote style based on he style identifier in STRING. */ -int -set_footnote_style (string) - char *string; -{ - if ((stricmp (string, "separate") == 0) || - (stricmp (string, "MN") == 0)) - footnote_style = SeparateNode; - else if ((stricmp (string, "end") == 0) || - (stricmp (string, "EN") == 0)) - footnote_style = EndNode; - else - return (-1); - - return (0); -} - -cm_footnotestyle () -{ - char *arg; - - get_rest_of_line (&arg); - - if (set_footnote_style (arg) != 0) - line_error ("Bad argument to @footnotestyle"); - - free (arg); -} - -typedef struct fn -{ - struct fn *next; - char *marker; - char *note; -} FN; - -FN *pending_notes = (FN *) NULL; - -/* A method for remembering footnotes. Note that this list gets output - at the end of the current node. */ -remember_note (marker, note) - char *marker, *note; -{ - FN *temp = (FN *) xmalloc (sizeof (FN)); - - temp->marker = savestring (marker); - temp->note = savestring (note); - temp->next = pending_notes; - pending_notes = temp; - footnote_count++; -} - -/* How to get rid of existing footnotes. */ -free_pending_notes () -{ - FN *temp; - - while ((temp = pending_notes) != (FN *) NULL) - { - free (temp->marker); - free (temp->note); - pending_notes = pending_notes->next; - free (temp); - } - first_footnote_this_node = 1; - footnote_count = 0; -} - -/* What to do when you see a @footnote construct. */ - - /* Handle a "footnote". - footnote *{this is a footnote} - where "*" is the marker character for this note. */ -cm_footnote () -{ - char *marker; - char *note; - - get_until ("{", &marker); - canon_white (marker); - - /* Read the argument in braces. */ - if (curchar () != '{') - { - line_error ("`@%s' expected more than just `%s'. It needs something in `{...}'", command, marker); - free (marker); - return; - } - else - { - int braces = 1; - int temp = ++input_text_offset; - int len; - - while (braces) - { - if (temp == size_of_input_text) - { - line_error ("No closing brace for footnote `%s'", marker); - return; - } - - if (input_text[temp] == '{') - braces++; - else if (input_text[temp] == '}') - braces--; - else if (input_text[temp] == '\n') - line_number ++; - - temp++; - } - - len = (temp - input_text_offset) - 1; - note = (char *)xmalloc (len + 1); - strncpy (note, &input_text[input_text_offset], len); - note[len] = '\0'; - input_text_offset = temp; - } - - if (!current_node || !*current_node) - { - line_error ("Footnote defined without parent node"); - free (marker); - free (note); - return; - } - - if (!*marker) - { - free (marker); - - if (number_footnotes) - { - marker = (char *)xmalloc (10); - sprintf (marker, "%d", current_footnote_number); - current_footnote_number++; - } - else - marker = savestring ("*"); - } - - remember_note (marker, note); - - /* Your method should at least insert MARKER. */ - switch (footnote_style) - { - case SeparateNode: - add_word_args ("(%s)", marker); - if (first_footnote_this_node) - { - char *temp_string; - - temp_string = (char *) - xmalloc ((strlen (current_node)) + (strlen ("-Footnotes")) + 1); - - add_word_args (" (*note %s-Footnotes::)", current_node); - strcpy (temp_string, current_node); - strcat (temp_string, "-Footnotes"); - remember_node_reference (temp_string, line_number, followed_reference); - free (temp_string); - first_footnote_this_node = 0; - } - break; - - case EndNode: - add_word_args ("(%s)", marker); - break; - - default: - break; - } - free (marker); - free (note); -} - -/* Non-zero means that we are currently in the process of outputting - footnotes. */ -int already_outputting_pending_notes = 0; - -/* Output the footnotes. We are at the end of the current node. */ -output_pending_notes () -{ - FN *footnote = pending_notes; - - if (!pending_notes) - return; - - switch (footnote_style) - { - - case SeparateNode: - { - char *old_current_node = current_node; - char *old_command = savestring (command); - - already_outputting_pending_notes++; - execute_string ("@node %s-Footnotes,,,%s\n", current_node, current_node); - already_outputting_pending_notes--; - current_node = old_current_node; - free (command); - command = old_command; - } - break; - - case EndNode: - close_paragraph (); - in_fixed_width_font++; - execute_string ("---------- Footnotes ----------\n\n"); - in_fixed_width_font--; - break; - } - - /* Handle the footnotes in reverse order. */ - { - FN **array = (FN **) xmalloc ((footnote_count + 1) * sizeof (FN *)); - - array[footnote_count] = (FN *) NULL; - - while (--footnote_count > -1) - { - array[footnote_count] = footnote; - footnote = footnote->next; - } - - filling_enabled = 1; - indented_fill = 1; - - while (footnote = array[++footnote_count]) - { - - switch (footnote_style) - { - case SeparateNode: - case EndNode: - execute_string ("(%s) %s", footnote->marker, footnote->note); - close_paragraph (); - break; - } - } - close_paragraph (); - free (array); - } -} - - -/* **************************************************************** */ -/* */ -/* User definable Macros (text substitution) */ -/* */ -/* **************************************************************** */ - -#if defined (HAVE_MACROS) - -/* Array of macros and definitions. */ -MACRO_DEF **macro_list = (MACRO_DEF **)NULL; - -int macro_list_len = 0; /* Number of elements. */ -int macro_list_size = 0; /* Number of slots in total. */ - -/* Return the macro definition of NAME or NULL if NAME is not defined. */ -MACRO_DEF * -find_macro (name) - char *name; -{ - register int i; - register MACRO_DEF *def; - - def = (MACRO_DEF *)NULL; - for (i = 0; macro_list && (def = macro_list[i]); i++) - if (strcmp (def->name, name) == 0) - break; - - return (def); -} - -/* Add the macro NAME with DEFINITION to macro_list. FILENAME is - the name of the file where this definition can be found, and - LINENO is the line number within that file. If a macro already - exists with NAME, then a warning is produced, and that previous - definition is overwritten. */ -void -add_macro (name, definition, filename, lineno) - char *name, *definition; - char *filename; - int lineno; -{ - register MACRO_DEF *def; - - def = find_macro (name); - - if (!def) - { - if (macro_list_len + 2 >= macro_list_size) - macro_list = (MACRO_DEF **)xrealloc - (macro_list, ((macro_list_size += 10) * sizeof (MACRO_DEF *))); - - macro_list[macro_list_len] = (MACRO_DEF *)xmalloc (sizeof (MACRO_DEF)); - macro_list[macro_list_len + 1] = (MACRO_DEF *)NULL; - - def = macro_list[macro_list_len]; - macro_list_len += 1; - def->name = savestring (name); - } - else - { - char *temp_filename = input_filename; - int temp_line = line_number; - - warning ("The macro `%s' is previously defined.", name); - - input_filename = def->filename; - line_number = def->lineno; - - warning ("Here is the previous definition of `%s'.", name); - - input_filename = temp_filename; - line_number = temp_line; - - free (def->filename); - free (def->definition); - } - - def->filename = savestring (filename); - def->lineno = lineno; - def->definition = savestring (definition); -} - - -/* Delete the macro with name NAME. The macro is deleted from the list, - but it is also returned. If there was no macro defined, NULL is - returned. */ -MACRO_DEF * -delete_macro (name) - char *name; -{ - register int i; - register MACRO_DEF *def; - - def = (MACRO_DEF *)NULL; - for (i = 0; macro_list && (def = macro_list[i]); i++) - if (strcmp (def->name, name) == 0) - { - memcpy (macro_list + i, macro_list + i + 1, - ((macro_list_len + 1) - i) * sizeof (MACRO_DEF *)); - break; - } - return (def); -} - -/* Execute the macro passed in DEF, a pointer to a MACRO_DEF. */ -void -execute_macro (def) - MACRO_DEF *def; -{ - - if (def != (MACRO_DEF *)NULL) - { - char *line, *string; - - get_until ("\n", &line); - - if (curchar () == '\n') /* as opposed to the end of the file... */ - { - line_number++; - input_text_offset++; - } - string = (char *)xmalloc (1 + strlen (def->definition) + strlen (line)); - strcpy (string, def->definition); - strcat (string, line); - free (line); - - execute_string ("%s\n", string); - free (string); - } -} - -int -cm_macro () -{ - register int i; - char *line, *name, *expansion; - - get_rest_of_line (&line); - canon_white (line); - - for (i = 0; line[i] && !whitespace (line[i]); i++); - name = (char *)xmalloc (i); - strncpy (name, line, i); - name[i] = '\0'; - - while (whitespace (line[i])) - i++; - - add_macro (name, line + i, input_filename, line_number - 1); - free (line); - free (name); -} - -int -cm_unmacro () -{ - register int i; - char *line, *name; - MACRO_DEF *def; - - get_rest_of_line (&line); - canon_white (line); - - for (i = 0; line[i] && !whitespace (line[i]); i++); - name = (char *)xmalloc (i); - strncpy (name, line, i); - name[i] = '\0'; - - def = delete_macro (name); - - if (def) - { - free (def->filename); - free (def->name); - free (def->definition); - free (def); - } - - free (line); - free (name); -} -#endif /* HAVE_MACROS */ - -/* **************************************************************** */ -/* */ -/* Looking For Include Files */ -/* */ -/* **************************************************************** */ - -/* Given a string containing units of information separated by colons, - return the next one pointed to by INDEX, or NULL if there are no more. - Advance INDEX to the character after the colon. */ -char * -extract_colon_unit (string, index) - char *string; - int *index; -{ - int i, start; - - i = *index; - - if (!string || (i >= strlen (string))) - return ((char *)NULL); - - /* Each call to this routine leaves the index pointing at a colon if - there is more to the path. If I is > 0, then increment past the - `:'. If I is 0, then the path has a leading colon. Trailing colons - are handled OK by the `else' part of the if statement; an empty - string is returned in that case. */ - if (i && string[i] == ':') - i++; - - start = i; - - while (string[i] && string[i] != ':') i++; - - *index = i; - - if (i == start) - { - if (string[i]) - (*index)++; - - /* Return "" in the case of a trailing `:'. */ - return (savestring ("")); - } - else - { - char *value; - - value = (char *)xmalloc (1 + (i - start)); - strncpy (value, &string[start], (i - start)); - value [i - start] = '\0'; - - return (value); - } -} - -/* Return the full pathname for FILENAME by searching along PATH. - When found, return the stat () info for FILENAME in FINFO. - If PATH is NULL, only the current directory is searched. - If the file could not be found, return a NULL pointer. */ -char * -get_file_info_in_path (filename, path, finfo) - char *filename, *path; - struct stat *finfo; -{ - char *dir; - int result, index = 0; - - if (path == (char *)NULL) - path = "."; - - /* Handle absolute pathnames. "./foo", "/foo", "../foo". */ - if (*filename == '/' || - (*filename == '.' && - (filename[1] == '/' || - (filename[1] == '.' && filename[2] == '/')))) - { - if (stat (filename, finfo) == 0) - return (savestring (filename)); - else - return ((char *)NULL); - } - - while (dir = extract_colon_unit (path, &index)) - { - char *fullpath; - - if (!*dir) - { - free (dir); - dir = savestring ("."); - } - - fullpath = (char *)xmalloc (2 + strlen (dir) + strlen (filename)); - sprintf (fullpath, "%s/%s", dir, filename); - free (dir); - - result = stat (fullpath, finfo); - - if (result == 0) - return (fullpath); - else - free (fullpath); - } - return ((char *)NULL); -} diff --git a/gnu/usr.bin/texinfo/misc/Makefile b/gnu/usr.bin/texinfo/misc/Makefile deleted file mode 100644 index c53561d..0000000 --- a/gnu/usr.bin/texinfo/misc/Makefile +++ /dev/null @@ -1,96 +0,0 @@ -# Generated automatically from Makefile.in by configure. -# Makefile for GNU Texindex. -# Copyright (C) 1990, 1991, 1992 Free Software Foundation, Inc. - -# This program 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 program 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 program; if not, write to the Free Software -# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - -#### Start of system configuration section. #### - -srcdir = . -VPATH = $(srcdir):$(common) - -common = $(srcdir)/../libtxi - -CC = gcc -INSTALL = /usr/bin/install -c -INSTALL_PROGRAM = $(INSTALL) -INSTALL_DATA = $(INSTALL) -m 644 - -LN = ln -RM = rm -f -TAR = tar -MKDIR = mkdir - -DEFS = -DSTDC_HEADERS=1 -DHAVE_UNISTD_H=1 -DHAVE_STRING_H=1 -DHAVE_VARARGS_H=1 -DHAVE_SYS_TIME_H=1 -DHAVE_SYS_FCNTL_H=1 -DHAVE_SETVBUF=1 -DHAVE_GETCWD=1 -DHAVE_BZERO=1 -DHAVE_RINDEX=1 -DHAVE_VFPRINTF=1 -DHAVE_VSPRINTF=1 -LIBS = -L../libtxi -ltxi -LOADLIBES = $(LIBS) - -SHELL = /bin/sh - -CFLAGS = -O2 -LDFLAGS = -O2 - -prefix = /usr/local -exec_prefix = $(prefix) -bindir = $(exec_prefix)/bin -# Prefix for each installed program, normally empty or `g'. -binprefix = -libdir = $(prefix)/lib -# Prefix for each installed man page, normally empty or `g'. -manprefix = -mandir = $(prefix)/man/man1 -manext = 1 -infodir = $(prefix)/info - -#### End of system configuration section. #### - -all: texindex -sub-all: all - -.c.o: - $(CC) -c $(CPPFLAGS) $(DEFS) -I. -I$(srcdir) -I$(common) $(CFLAGS) $< - - -install: all - $(INSTALL_PROGRAM) texindex $(bindir)/texindex - $(INSTALL_PROGRAM) $(srcdir)/texi2dvi $(bindir)/texi2dvi - -uninstall: - rm -f $(bindir)/texindex $(bindir)/texi2dvi - -Makefile: Makefile.in ../config.status - cd ..; sh config.status - -TAGS: - etags *.c *.h $(common)/getopt*.c $(common)/getopt.h - -clean: - rm -f *.o a.out core core.* texindex - -mostlyclean: clean - -distclean: clean - rm -f Makefile config.status - -realclean: distclean - rm -f TAGS - -texindex: texindex.o ../libtxi/libtxi.a - $(CC) $(LDFLAGS) -o texindex texindex.o $(LOADLIBES) - -texindex.o: texindex.c $(common)/getopt.h - -# Prevent GNU make v3 from overflowing arg limit on SysV. -.NOEXPORT: diff --git a/gnu/usr.bin/texinfo/misc/Makefile.in b/gnu/usr.bin/texinfo/misc/Makefile.in deleted file mode 100644 index 2d8f769..0000000 --- a/gnu/usr.bin/texinfo/misc/Makefile.in +++ /dev/null @@ -1,95 +0,0 @@ -# Makefile for GNU Texindex. -# Copyright (C) 1990, 1991, 1992 Free Software Foundation, Inc. - -# This program 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 program 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 program; if not, write to the Free Software -# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - -#### Start of system configuration section. #### - -srcdir = @srcdir@ -VPATH = $(srcdir):$(common) - -common = $(srcdir)/../libtxi - -CC = @CC@ -INSTALL = @INSTALL@ -INSTALL_PROGRAM = @INSTALL_PROGRAM@ -INSTALL_DATA = @INSTALL_DATA@ - -LN = ln -RM = rm -f -TAR = tar -MKDIR = mkdir - -DEFS = @DEFS@ -LIBS = -L../libtxi -ltxi @LIBS@ -LOADLIBES = $(LIBS) - -SHELL = /bin/sh - -CFLAGS = -g -LDFLAGS = -g - -prefix = /usr/local -exec_prefix = $(prefix) -bindir = $(exec_prefix)/bin -# Prefix for each installed program, normally empty or `g'. -binprefix = -libdir = $(prefix)/lib -# Prefix for each installed man page, normally empty or `g'. -manprefix = -mandir = $(prefix)/man/man1 -manext = 1 -infodir = $(prefix)/info - -#### End of system configuration section. #### - -all: texindex -sub-all: all - -.c.o: - $(CC) -c $(CPPFLAGS) $(DEFS) -I. -I$(srcdir) -I$(common) $(CFLAGS) $< - - -install: all - $(INSTALL_PROGRAM) texindex $(bindir)/texindex - $(INSTALL_PROGRAM) $(srcdir)/texi2dvi $(bindir)/texi2dvi - -uninstall: - rm -f $(bindir)/texindex $(bindir)/texi2dvi - -Makefile: Makefile.in ../config.status - cd ..; sh config.status - -TAGS: - etags *.c *.h $(common)/getopt*.c $(common)/getopt.h - -clean: - rm -f *.o a.out core core.* texindex - -mostlyclean: clean - -distclean: clean - rm -f Makefile config.status - -realclean: distclean - rm -f TAGS - -texindex: texindex.o ../libtxi/libtxi.a - $(CC) $(LDFLAGS) -o texindex texindex.o $(LOADLIBES) - -texindex.o: texindex.c $(common)/getopt.h - -# Prevent GNU make v3 from overflowing arg limit on SysV. -.NOEXPORT: diff --git a/gnu/usr.bin/texinfo/misc/NEWS b/gnu/usr.bin/texinfo/misc/NEWS deleted file mode 100644 index 00de163..0000000 --- a/gnu/usr.bin/texinfo/misc/NEWS +++ /dev/null @@ -1,171 +0,0 @@ -This release of Info is version 2.8. Please read the file README. - -Changes since 2.5 beta: - -Note that versions 2.6 and 2.7 Beta were only released to a select group. - -* "info-" removed from the front of M-x commands. - -* Automatic footnote display. When you enter a node which contains - footnotes, and the variable "automatic-footnotes" is "On", Info pops - up a window containing the footnotes. Likewise, when you leave that - node, the window containing the footnotes goes away. - -* Cleaner built in documentation, and documentation functions. - - Use: - o `M-x describe-variable' to read a variable's documenation - o `M-x describe-key' to find out what a particular keystroke does. - o `M-x describe-function' to read a function's documentation. - o `M-x where-is' to find out what keys invoke a particular function. - -* Info can "tile" the displayed windows (via "M-x tile-windows"). If - the variable "automatic-tiling" is "On", then splitting a window or - deleting a window causes the remaining windows to be retiled. - -* You can save every keystroke you type in a "dribble file" by using the - `--dribble FILENAME' option. You can initially read keystrokes from an - alternate input stream with `--restore FILENAME', or by redirecting - input on the command line `info < old-dribble'. - -* New behaviour of menu items. If the label is the same as the - target node name, and the node couldn't be found in the current file, - treat the label as a file name. For example, a menu entry in "DIR" - might contain: - - * Emacs:: Cool text-editor. - - Info would not find the node "(dir)Emacs", so just plain "(emacs)" - would be tried. - -* New variable "ISO-Latin" allows you to use European machines with - 8-bit character sets. - -* Cleanups in echo area reading, and redisplay. Cleanups in handling the - window which shows possible completions. - -* Info can now read files that have been compressed. An array in filesys.c - maps extensions to programs that can decompress stdin, and write the results - to stdout. Currently, ".Z"/uncompress, ".z"/gunzip, and ".Y"/unyabba are - supported. The modeline for a compressed file shows "zz" in it. - -* There is a new variable "gc-compressed-files" which, if non-zero, says - it is okay to reclaim the file buffer space allocated to a file which - was compressed, if, and only if, that file's contents do not appear in - any history node. - -* New file `nodemenu.c' implements a few functions for manipulating - previously visited nodes. `C-x C-b' (list-visited-nodes) produces a - menu of the nodes that could be reached by info-history-node in some - window. `C-x b' (select-visited-node) is similar, but reads one of - the node names with completion. - -* Keystroke `M-r' (move_to_screen_line) allows the user to place the cursor at - the start of a specific screen line. Without a numeric argument, place the - cursor on the center line; with an arg, place the cursor on that line. - -* Interruptible display implemented. Basic display speedups and hacks. -* The message "*** Tags Out of Date ***" now means what it says. -* Index searching with `,' (info-index-next) has been improved. -* When scrolling with C-v, C-M-v, or M-v, only "Page Only" scrolling - will happen. - -* Continous scrolling (along with `]' (info-global-next) and `[' - (info-global-prev) works better. `]' and `[' accept numeric - arguments, moving that many nodes in that case. - -* `C-x w' (info-toggle-wrap) controls how lines wider than the width - of the screen are displayed. If a line is too long, a `$' is - displayed in the rightmost column of the window. - -* There are some new variables for controlling the behaviour of Info - interactively. The current list of variables is as follows: - - Variable Name Default Value Description - ------------- ------------- ----------- - `automatic-footnotes' On When "On", footnotes appear and - disappear automatically. - - `automatic-tiling' Off When "On", creating of deleting a - window resizes other windows. - - `visible-bell' Off If non-zero, try to use a visible bell. - - `errors-ring-bell' On If non-zero, errors cause a ring. - - `show-index-match' On If non-zero, the portion of the string - matched is highlighted by changing its - case. - - `scroll-behaviour' Continuous One of "Continuous", "Next Only", or - "Page Only". "Page Only" prevents you from - scrolling past the bottom or top of a node. - "Next Only" causes the Next or Prev node to - be selected when you scroll past the bottom - or top of a node. "Continous" moves - linearly through the files hierchichal - structure. - - `scroll-step' 0 Controls how scrolling is done for you when - the cursor moves out of the current window. - Non-zero means it is the number of lines - you would like the screen to shift. A - value of 0 means to center the line - containing the cursor in the window. - - `gc-compressed-files' Off If non-zero means it is okay to reclaim the - file buffer space allocated to a file which - was compressed, if, and only if, that - file's contents do not appear in the node - list of any window. - - `ISO-Latin' Off Non-zero means that you are using an ISO - Latin character set. By default, standard - ASCII characters are assumed. -________________________________________ -This release of Info is version 2.5 beta. - -Changes since 2.4 beta: - -* Index (i) and (,) commands fully implemented. -* "configure" script now shipped with Info. -* New function "set-variable" allows users to set various variables. -* User-settable behaviour on end or beginning of node scrolling. This - supercedes the SPC and DEL changes in 2.3 beta. - -________________________________________ -This release of Info is version 2.4 beta. - -Changes since 2.3 beta: - -* info-last-node now means move to the last node of this info file. -* info-history-node means move backwards through this window's node history. -* info-first-node moves to the first node in the Info file. This node is - not necessarily "Top"! -* SPC and DEL can select the Next or Prev node after printing an informative - message when pressed at the end/beg of a node. - ----------------------------------------- -This release of Info is version 2.3 beta. - -Changes since 2.2 beta: - -* M-x command lines if NAMED_COMMANDS is #defined. Variable in Makefile. -* Screen height changes made quite robust. -* Interactive function "set-screen-height" implements user height changes. -* Scrolling on some terminals is faster now. -* C-l with numeric arguement is fixed. - ----------------------------------------- -This release of Info is version 2.2 beta. - -Changes since 2.0: - -* C-g can now interrupt multi-file searches. -* Incremental search is fully implemented. -* Loading large tag tables is much faster now. -* makedoc.c replaces shell script, speeding incremental builds. -* Scrolling in redisplay is implemented. -* Recursive uses of the echo area made more robust. -* Garbage collection of unreferenced nodes. - diff --git a/gnu/usr.bin/texinfo/misc/README b/gnu/usr.bin/texinfo/misc/README deleted file mode 100644 index 12cfa62..0000000 --- a/gnu/usr.bin/texinfo/misc/README +++ /dev/null @@ -1,54 +0,0 @@ - Please Emacs, use -*- text -*- mode when editing this file. - - * The file RELEASE contains information about what has changed - since the last release. - - * The file INSTALL contains instructions on how to install Info. - (Type "./configure" and then "make".) - -This is the README file GNU Info version 2.8. This marks the first -non-beta release. - -Thu Jan 21 14:50:52 1993 - ----------------------------------------- -Version 2.7 beta, Wed Dec 30 02:02:38 1992 -Version 2.6 beta, Tue Dec 22 03:58:07 1992 -Version 2.5 beta, Tue Dec 8 14:50:35 1992 -Version 2.4 beta, Sat Nov 28 14:34:02 1992 -Version 2.3 beta, Fri Nov 27 01:04:13 1992 -Version 2.2 beta, Tue Nov 24 09:36:08 1992 -Version 2.1 beta, Tue Nov 17 23:29:36 1992 - -Info 2.0 is a complete rewrite of the original standalone Info I wrote -in 1987, the first program I wrote for rms. That program was -something like my second Unix program ever, and my die-hard machine -language coding habits tended to show through. I found the original -Info hard to read and maintain, and thus decided to write this one. - -The rewrite consists of about 12,000 lines of code written in about 12 -days. I believe this version of Info to be in much better shape than -the original Info, and the only reason it is in Beta test is because -of its short life span. - -Info 2.0 is substantially different from its original standalone -predecessor. It appears almost identical to the GNU Emacs version, -but has the advantages of smaller size, ease of portability, and a -built in library which can be used in other programs (to get or -display documentation from Info files, for example). - -I eagerly await responses to this newer version of Info; comments on -its portability, ease of use and user interface, code quality, and -general usefulness are all of interest to me, and I will appreciate -any comments that you would care to make. - -A full listing of the commands available in Info can be gotten by -typing `?' while within an Info window. This produces a node in a -window which can be viewed just like any Info node. - -So, please send your comments, bug reports, and suggestions to - - bfox@ai.mit.edu - -Thanks for beta testing this software. - diff --git a/gnu/usr.bin/texinfo/misc/deref.c b/gnu/usr.bin/texinfo/misc/deref.c deleted file mode 100644 index c15bc1a..0000000 --- a/gnu/usr.bin/texinfo/misc/deref.c +++ /dev/null @@ -1,238 +0,0 @@ -/* - * deref.c - - * compile command: gcc -g -o deref deref.c - - * execute command: deref filename.texi > newfile.texi - - * To: bob@gnu.ai.mit.edu - * Subject: another tool - * Date: 18 Dec 91 16:03:13 EST (Wed) - * From: gatech!skeeve!arnold@eddie.mit.edu (Arnold D. Robbins) - * - * Here is deref.c. It turns texinfo cross references back into the - * one argument form. It has the same limitations as fixref; one xref per - * line and can't cross lines. You can use it to find references that do - * cross a line boundary this way: - * - * deref < manual > /dev/null 2>errs - * - * (This assumes bash or /bin/sh.) The file errs will have list of lines - * where deref could not find matching braces. - * - * A gawk manual processed by deref goes through makeinfo without complaint. - * Compile with gcc and you should be set. - * - * Enjoy, - * - * Arnold - * ----------- - */ - -/* - * deref.c - * - * Make all texinfo references into the one argument form. - * - * Arnold Robbins - * arnold@skeeve.atl.ga.us - * December, 1991 - * - * Copyright, 1991, Arnold Robbins - */ - -/* - * LIMITATIONS: - * One texinfo cross reference per line. - * Cross references may not cross newlines. - * Use of fgets for input (to be fixed). - */ - -#include <stdio.h> -#include <ctype.h> -#include <errno.h> - -/* for gcc on the 3B1, delete if this gives you grief */ -extern int fclose (FILE * fp); -extern int fprintf (FILE * fp, const char *str,...); - -extern char *strerror (int errno); -extern char *strchr (char *cp, int ch); -extern int strncmp (const char *s1, const char *s2, int count); - -extern int errno; - -void process (FILE * fp); -void repair (char *line, char *ref, int toffset); - -int Errs = 0; -char *Name = "stdin"; -int Line = 0; -char *Me; - -/* main --- handle arguments, global vars for errors */ - -int -main (int argc, char **argv) -{ - FILE *fp; - - Me = argv[0]; - - if (argc == 1) - process (stdin); - else - for (argc--, argv++; *argv != NULL; argc--, argv++) - { - if (argv[0][0] == '-' && argv[0][1] == '\0') - { - Name = "stdin"; - Line = 0; - process (stdin); - } - else if ((fp = fopen (*argv, "r")) != NULL) - { - Name = *argv; - Line = 0; - process (fp); - fclose (fp); - } - else - { - fprintf (stderr, "%s: can not open: %s\n", - *argv, strerror (errno)); - Errs++; - } - } - return Errs != 0; -} - -/* isref --- decide if we've seen a texinfo cross reference */ - -int -isref (char *cp) -{ - if (strncmp (cp, "@ref{", 5) == 0) - return 5; - if (strncmp (cp, "@xref{", 6) == 0) - return 6; - if (strncmp (cp, "@pxref{", 7) == 0) - return 7; - return 0; -} - -/* process --- read files, look for references, fix them up */ - -void -process (FILE * fp) -{ - char buf[BUFSIZ]; - char *cp; - int count; - - while (fgets (buf, sizeof buf, fp) != NULL) - { - Line++; - cp = strchr (buf, '@'); - if (cp == NULL) - { - fputs (buf, stdout); - continue; - } - do - { - count = isref (cp); - if (count == 0) - { - cp++; - cp = strchr (cp, '@'); - if (cp == NULL) - { - fputs (buf, stdout); - goto next; - } - continue; - } - /* got one */ - repair (buf, cp, count); - break; - } - while (cp != NULL); - next:; - } -} - -/* repair --- turn all texinfo cross references into the one argument form */ - -void -repair (char *line, char *ref, int toffset) -{ - int braces = 1; /* have seen first left brace */ - char *cp; - - ref += toffset; - - /* output line up to and including left brace in reference */ - for (cp = line; cp <= ref; cp++) - putchar (*cp); - - /* output node name */ - for (; *cp && *cp != '}' && *cp != ',' && *cp != '\n'; cp++) - putchar (*cp); - - if (*cp != '}') - { /* could have been one arg xref */ - /* skip to matching right brace */ - for (; braces > 0; cp++) - { - switch (*cp) - { - case '@': - cp++; /* blindly skip next character */ - break; - case '{': - braces++; - break; - case '}': - braces--; - break; - case '\n': - case '\0': - Errs++; - fprintf (stderr, - "%s: %s: %d: mismatched braces\n", - Me, Name, Line); - goto out; - default: - break; - } - } - out: - ; - } - - putchar ('}'); - if (*cp == '}') - cp++; - - /* now the rest of the line */ - for (; *cp; cp++) - putchar (*cp); - return; -} - -/* strerror --- return error string, delete if in your library */ - -char * -strerror (int errno) -{ - static char buf[100]; - extern int sys_nerr; - extern char *sys_errlist[]; - - if (errno < sys_nerr && errno >= 0) - return sys_errlist[errno]; - - sprintf (buf, "unknown error %d", errno); - return buf; -} diff --git a/gnu/usr.bin/texinfo/misc/fixfonts b/gnu/usr.bin/texinfo/misc/fixfonts deleted file mode 100755 index ee2ea71..0000000 --- a/gnu/usr.bin/texinfo/misc/fixfonts +++ /dev/null @@ -1,84 +0,0 @@ -#!/bin/sh -# Make links named `lcircle10' for all TFM and GF/PK files, if no -# lcircle10 files already exist. - -# Don't override definition of prefix and/or libdir if they are -# already defined in the environment. -if test "z${prefix}" = "z" ; then - prefix=/usr/local -else - # prefix may contain references to other variables, thanks to make. - eval prefix=\""${prefix}"\" -fi - -if test "z${libdir}" = "z" ; then - libdir="${prefix}/lib/tex" -else - # libdir may contain references to other variables, thanks to make. - eval libdir=\""${libdir}"\" -fi - -texlibdir="${libdir}" -texfontdir="${texlibdir}/fonts" - -# Directories for the different font formats, in case they're not all -# stored in one place. -textfmdir="${textfmdir-${texfontdir}}" -texpkdir="${texpkdir-${texfontdir}}" -texgfdir="${texgfdir-${texfontdir}}" - -test "z${TMPDIR}" = "z" && TMPDIR="/tmp" - -tempfile="${TMPDIR}/circ$$" -tempfile2="${TMPDIR}/circ2$$" - -# EXIT SIGHUP SIGINT SIGQUIT SIGTERM -#trap 'rm -f "${tempfile}" "${tempfile2}"' 0 1 2 3 15 - -# Find all the fonts with names that include `circle'. -(cd "${texfontdir}"; find . -name '*circle*' -print > "${tempfile}") - -# If they have lcircle10.tfm, assume everything is there, and quit. -if grep 'lcircle10\.tfm' "${tempfile}" > /dev/null 2>&1 ; then - echo "Found lcircle10.tfm." - exit 0 -fi - -# No TFM file for lcircle. Make a link to circle10.tfm if it exists, -# and then make a link to the bitmap files. -grep 'circle10\.tfm' "${tempfile}" > "${tempfile2}" \ - || { - echo "I can't find any circle fonts in ${texfontdir}. -If it isn't installed somewhere else, you need to get the Metafont sources -from somewhere, e.g., labrea.stanford.edu:pub/tex/latex/circle10.mf, and -run Metafont on them." - exit 1 - } - -# We have circle10.tfm. (If we have it more than once, take the first -# one.) Make the link. -tempfile2_line1="`sed -ne '1p;q' \"${tempfile2}\"`" -ln "${tempfile2_line1}" "${textfmdir}/lcircle10.tfm" -echo "Linked to ${tempfile2_line1}." - -# Now make a link for the PK files, if any. -(cd "${texpkdir}" - for f in `grep 'circle10.*pk' "${tempfile}"` ; do - set - `echo "$f" \ - | sed -ne '/\//!s/^/.\//;s/\(.*\)\/\([^\/][^\/]*\)$/\1 \2/;p'` - ln "$f" "${1}/l${2}" - echo "Linked to $f." - done -) - -# And finally for the GF files. -(cd "${texgfdir}" - for f in `grep 'circle10.*gf' "${tempfile}"` ; do - set - `echo "$f" \ - | sed -ne '/\//!s/^/.\//;s/\(.*\)\/\([^\/][^\/]*\)$/\1 \2/;p'` - ln "$f" "${1}/l${2}" - echo "Linked to $f." - done -) - -# eof diff --git a/gnu/usr.bin/texinfo/misc/mkinstalldirs b/gnu/usr.bin/texinfo/misc/mkinstalldirs deleted file mode 100755 index 0e29377..0000000 --- a/gnu/usr.bin/texinfo/misc/mkinstalldirs +++ /dev/null @@ -1,35 +0,0 @@ -#!/bin/sh -# Make directory hierarchy. -# Written by Noah Friedman <friedman@prep.ai.mit.edu> -# Public domain. - -defaultIFS=' -' -IFS="${IFS-${defaultIFS}}" - -errstatus=0 - -for file in ${1+"$@"} ; do - oIFS="${IFS}" - # Some sh's can't handle IFS=/ for some reason. - IFS='%' - set - `echo ${file} | sed -e 's@/@%@g' -e 's@^%@/@'` - IFS="${oIFS}" - - pathcomp='' - - for d in ${1+"$@"} ; do - pathcomp="${pathcomp}${d}" - - if test ! -d "${pathcomp}"; then - echo "mkdir $pathcomp" 1>&2 - mkdir "${pathcomp}" || errstatus=$? - fi - - pathcomp="${pathcomp}/" - done -done - -exit $errstatus - -# eof diff --git a/gnu/usr.bin/texinfo/misc/tex3patch b/gnu/usr.bin/texinfo/misc/tex3patch deleted file mode 100755 index 1708c75..0000000 --- a/gnu/usr.bin/texinfo/misc/tex3patch +++ /dev/null @@ -1,71 +0,0 @@ -#!/bin/sh -# Auxiliary script to work around TeX 3.0 bug. ---- tex3patch ---- -# patches texinfo.tex in current directory, or in directory given as arg. - -ANYVERSION=no - -for arg in $1 $2 -do - case $arg in - --dammit | -d ) ANYVERSION=yes ;; - - * ) dir=$arg - esac -done - -if [ -z "$dir" ]; then - dir='.' -fi - -if [ \( 2 -lt $# \) -o \ - \( ! -f $dir/texinfo.tex \) ]; then - echo "To patch texinfo.tex for peaceful coexistence with Unix TeX 3.0," - echo "run $0" - echo "with no arguments in the same directory as texinfo.tex; or run" - echo " $0 DIRECTORY" - echo "(where DIRECTORY is a path leading to texinfo.tex)." - exit -fi - -if [ -z "$TMPDIR" ]; then - TMPDIR=/tmp -fi - -echo "Checking for \`dummy.tfm'" - -( cd $TMPDIR; tex '\relax \batchmode \font\foo=dummy \bye' ) - -grep -s '3.0' $TMPDIR/texput.log -if [ 1 = "$?" -a "$ANYVERSION" != "yes" ]; then - echo "You probably do not need this patch," - echo "since your TeX does not seem to be version 3.0." - echo "If you insist on applying the patch, run $0" - echo "again with the option \`--dammit'" - exit -fi - -grep -s 'file not found' $TMPDIR/texput.log -if [ 0 = $? ]; then - echo "This patch requires the dummy font metric file \`dummy.tfm'," - echo "which does not seem to be part of your TeX installation." - echo "Please get your TeX maintainer to install \`dummy.tfm'," - echo "then run this script again." - exit -fi -rm $TMPDIR/texput.log - -echo "Patching $dir/texinfo.tex" - -sed -e 's/%%*\\font\\nullfont/\\font\\nullfont/' \ - $dir/texinfo.tex >$TMPDIR/texinfo.tex -mv $dir/texinfo.tex $dir/texinfo.tex-distrib; mv $TMPDIR/texinfo.tex $dir - -if [ 0 = $? ]; then - echo "Patched $dir/texinfo.tex to avoid TeX 3.0 bug." - echo "The original version is saved as $dir/texinfo.tex-distrib." -else - echo "Patch failed. Sorry." -fi -----------------------------------------tex3patch ends - - diff --git a/gnu/usr.bin/texinfo/misc/texi2dvi b/gnu/usr.bin/texinfo/misc/texi2dvi deleted file mode 100755 index 12281e5..0000000 --- a/gnu/usr.bin/texinfo/misc/texi2dvi +++ /dev/null @@ -1,263 +0,0 @@ -#!/bin/sh -# texi2dvi -- smartly produce DVI files from texinfo sources -# -# Copyright (C) 1992, 1993 Free Software Foundation. -# -# This program 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 program 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 program; if not, you can either send email to this -# program's author (see below) or write to: -# -# Free Software Foundation, Inc. -# 675 Mass Ave. -# Cambridge, MA 02139, USA. -# -# Please send bug reports, etc. to bug-texinfo@prep.ai.mit.edu -# If possible, please send a copy of the output of the script called with -# the `--debug' option when making a bug report. -# -# Version 0.4 -# Last modified 26-Mar-93 -# - -# Please note that in the interest of general portability, some common -# bourne shell constructs were avoided because they weren't guaranteed to -# be available in some earlier implementations. I've tried to make this as -# portable as possible. -# -# Among the more interesting lossages I noticed with some bourne shells -# are: -# 1) Some don't have an `unset' builtin -# 2) In some implementations the `shift' builtin can't take a -# numerical argument. - -progname=`basename $0` - -usage="Usage: ${progname} {-D} {-h} [file1] {file2} {...} - {--debug} {--help} - - Options in braces are optional. Those in brackets are required. -" - -if test $# -eq 0 ; then - echo "${usage}" 1>&2; - exit 1 -fi - -backup_extension=".bak" -texindex="texindex" -tex="tex" -bq="\`" # To prevent hairy quoting and escaping later. -eq="'" -orig_pwd="`pwd`" - -if test "z${TEXINDEX}" != "z" ; then - texindex="${TEXINDEX}" -fi - -if test "z${TEX}" != "z" ; then - tex="${TEX}" -fi - -# Save this so we can construct a new TEXINPUTS path for each file to be -# processed. -TEXINPUTS_orig="${TEXINPUTS}" -export TEXINPUTS - -# Parse command line options - -# "unset" option variables to make sure they weren't accidentally -# exported -debug="" - -# If you add new commands be sure to change the wildcards below to make -# sure they are unambiguous (i.e. only match one possible long option) -# Be sure to show at least one instance of the full long option name to -# document what the long option is canonically called. -while test $# -gt 0 ; do - case z$1 in - z-D | z--debug | z--d* ) - debug="t" - shift - ;; - z-h | z--help | z--h* ) - echo "${usage}" 1>&2 - exit 1 - ;; - z-- ) - shift - break - ;; - z-* ) - echo "${progname}: ${bq}${1}${eq} is not a valid option." 1>&2 - echo "" 1>&2 - echo "${usage}" 1>&2 - exit 1 - ;; - * ) - break - ;; - esac -done - -# See if there are any command line args left (which will be interpreted as -# filename arguments) -if test $# -eq 0 ; then - echo "${progname}: at least one file name is required as an argument." 1>&2 - echo "" 1>&2 - echo "${usage}" 1>&2 - exit 1 -fi - -test "z${debug}" = "zt" && set -x - -# Texify files -for command_line_filename in ${1+"$@"} ; do - # Roughly equivalent to `dirname ...`, but more portable - directory="`echo ${command_line_filename} | sed 's/\/[^\/]*$//'`" - filename_texi="`basename ${command_line_filename}`" - # Strip off the last extension part (probably .texinfo or .texi) - filename_noext="`echo ${filename_texi} | sed 's/\.[^.]*$//'`" - - # If directory and file are the same, then it's probably because there's - # no pathname component. Set dirname to `.', the current directory. - if test "z${directory}" = "z${command_line_filename}" ; then - directory="." - fi - - # Source file might @include additional texinfo sources. Put `.' and - # directory where source file(s) reside in TEXINPUTS before anything - # else. `.' goes first to ensure that any old .aux, .cps, etc. files in - # ${directory} don't get used in preference to fresher files in `.'. - TEXINPUTS=".:${directory}:${TEXINPUTS_orig}" - - # "Unset" variables that might have values from previous iterations and - # which won't be completely reset later. - definite_index_files="" - - # See if file exists here. If it doesn't we're in trouble since, even - # though the user may be able to reenter a valid filename at the tex - # prompt (assuming they're attending the terminal), this script won't be - # able to find the right index files and so forth. - if test ! -r "${command_line_filename}" ; then - echo "${progname}: ${command_line_filename}: No such file or permission denied." 1>&2 - continue; - fi - - # Find all files having root filename with a two-letter extension, - # determine whether they're really index files, and save them. Foo.aux - # is actually the cross-references file, but we need to keep track of - # that too. - possible_index_files="`eval echo ${filename_noext}.?? ${filename_noext}.aux`" - for this_file in ${possible_index_files} ; do - # If file is empty, forget it. - if test ! -s "${this_file}" ; then - continue; - fi - - # Examine first character of file. If it's not a backslash or - # single quote, then it's definitely not an index or xref file. - first_character="`sed -n '1s/^\(.\).*$/\1/p;q' ${this_file}`" - if test "${first_character}" = "\\" -o "${first_character}" = "'" ; then - definite_index_files="${definite_index_files} ${this_file}" - fi - done - orig_index_files="${definite_index_files}" - orig_index_files_sans_aux="`echo ${definite_index_files} \ - | sed 's/'${filename_noext}'\.aux//; - s/^[ ]*//;s/[ ]*$//;'`" - - # Now save copies of original index files so we have some means of - # comparison later. - for index_file_to_save in ${orig_index_files} ; do - cp "${index_file_to_save}" "${index_file_to_save}${backup_extension}" - done - - # Run texindex on current index files. If they already exist, and - # after running TeX a first time the index files don't change, then - # there's no reason to run TeX again. But we won't know that if the - # index files are out of date or nonexistent. - if test "${orig_index_files_sans_aux}" ; then - ${texindex} ${orig_index_files_sans_aux} - fi - - if ${tex} ${command_line_filename} ; then # TeX run first time - definite_index_files="" - # Get list of new index files - possible_index_files="`eval echo ${filename_noext}.?? ${filename_noext}.aux`" - for this_file in ${possible_index_files} ; do - # If file is empty, forget it. - if test ! -s ${this_file} ; then - continue; - fi - - # Examine first character of file. If it's not a backslash or - # single quote, then it's definitely not an index or xref file. - first_character="`sed -n '1s/^\(.\).*$/\1/p;q' ${this_file}`" - if test "${first_character}" = "\\" -o "${first_character}" = "'" ; then - definite_index_files="${definite_index_files} ${this_file}" - fi - done - new_index_files="${definite_index_files}" - new_index_files_sans_aux="`echo ${definite_index_files} \ - | sed 's/'${filename_noext}'\.aux//; - s/^[ ]*//;s/[ ]*$//;'`" - - # If old and new list don't at least have the same file list, then one - # file or another has definitely changed. - if test "${orig_index_files}" != "${new_index_files}" ; then - index_files_changed_p=t - else - # File list is the same. We must compare each file until we find a - # difference. - index_files_changed_p="" - for this_file in ${new_index_files} ; do - # cmp -s will return nonzero exit status if files differ. - cmp -s "${this_file}" "${this_file}${backup_extension}" - if test $? -ne 0 ; then - # We only need to keep comparing until we find *one* that - # differs, because we'll have to run texindex & tex no - # matter what. - index_files_changed_p=t - break - fi - done - fi - - # If index files have changed since TeX has been run, or if the aux - # file wasn't present originally, run texindex and TeX again. - if test "${index_files_changed_p}" ; then - retval=0 - if test "${new_index_files_sans_aux}" ; then - ${texindex} ${new_index_files_sans_aux} - retval=$? - fi - if test ${retval} -eq 0 ; then - ${tex} "${command_line_filename}" - fi - fi - fi - - # Generate list of files to delete, then call rm once with the entire - # list. This is significantly faster than multiple executions of rm. - file_list="" - for file in ${orig_index_files} ; do - file_list="${file_list} ${file}${backup_extension}" - done - if test "${file_list}" ; then - rm -f ${file_list} - fi -done - -# -# eof -# diff --git a/gnu/usr.bin/texinfo/texindex/Makefile b/gnu/usr.bin/texinfo/texindex/Makefile deleted file mode 100644 index aee14df..0000000 --- a/gnu/usr.bin/texinfo/texindex/Makefile +++ /dev/null @@ -1,21 +0,0 @@ -# -# Bmakefile for GNU info -# -# $Id: Makefile,v 1.2 1994/09/15 13:12:23 jkh Exp $ -# - -PROG= texindex -NOMAN=yes -SRCS+= texindex.c getopt1.c getopt.c -.PATH: ${.CURDIR}/../info - -CFLAGS+= -I${.CURDIR}/../info -I${.CURDIR} -CFLAGS+= -DNAMED_FUNCTIONS=1 -DSTDC_HEADERS=1 -CFLAGS+= -DHAVE_UNISTD_H=1 -DHAVE_STRING_H=1 -DHAVE_VARARGS_H=1 -CFLAGS+= -DHAVE_SYS_FCNTL_H=1 -DHAVE_SETVBUF=1 -DHAVE_GETCWD=1 -DHAVE_BZERO=1 -CFLAGS+= -DHAVE_RINDEX=1 -DHAVE_VFPRINTF=1 -DHAVE_VSPRINTF=1 -CFLAGS+= -DHAVE_SYS_TIME_H=1 -DDEFAULT_INFOPATH='"${INFODIR}"' - -.include "../../Makefile.inc" -.include <bsd.prog.mk> - diff --git a/gnu/usr.bin/texinfo/texindex/texindex.c b/gnu/usr.bin/texinfo/texindex/texindex.c deleted file mode 100644 index f7b0aef..0000000 --- a/gnu/usr.bin/texinfo/texindex/texindex.c +++ /dev/null @@ -1,1700 +0,0 @@ -/* Prepare TeX index dribble output into an actual index. - - Version 1.45 - - Copyright (C) 1987, 1991, 1992 Free Software Foundation, Inc. - - This program 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 program 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 program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */ - - -#include <stdio.h> -#include <ctype.h> -#include <errno.h> -#include "getopt.h" - -#if defined (STDC_HEADERS) -# include <string.h> -# include <stdlib.h> -# if !defined (bzero) -# define bzero(p, n) memset((p), '\0', (n)) -# endif /* !bzero */ -#else /* !STDC_HEADERS */ -extern int errno; -char *getenv (), *malloc (), *realloc (); -void bzero (); -#endif /* !STDC_HEADERS */ - -#if defined (HAVE_UNISTD_H) -# include <unistd.h> -#else /* !HAVE_UNISTD_H */ -long lseek (); -#endif /* !HAVE_UNISTD_H */ - -char *mktemp (); - -#if defined (VMS) -# if !defined (VAX11C) -# define noshare -# endif /* !VAX11C */ -# include <perror.h> -extern noshare int sys_nerr; -extern noshare char *sys_errlist[]; - -# include <file.h> - -# define TI_NO_ERROR ((1 << 28) | 1) -# define TI_FATAL_ERROR ((1 << 28) | 4) -# define unlink delete - -#else /* !VMS */ - -extern int sys_nerr; -extern const char * const sys_errlist[]; - -# if defined (HAVE_SYS_FCNTL_H) -# include <sys/types.h> -# include <sys/fcntl.h> -# endif /* HAVE_SYS_FCNTL_H */ - -# if defined (_AIX) || !defined (_POSIX_VERSION) -# include <sys/file.h> -# else /* !AIX && _POSIX_VERSION */ -# if !defined (HAVE_SYS_FCNTL_H) -# include <fcntl.h> -# endif /* !HAVE_FCNTL_H */ -# endif /* !_AIX && _POSIX_VERSION */ -# define TI_NO_ERROR 0 -# define TI_FATAL_ERROR 1 -#endif /* !VMS */ - -#if !defined (SEEK_SET) -# define SEEK_SET 0 -# define SEEK_CUR 1 -# define SEEK_END 2 -#endif /* !SEEK_SET */ - -/* When sorting in core, this structure describes one line - and the position and length of its first keyfield. */ -struct lineinfo -{ - char *text; /* The actual text of the line. */ - union { - char *text; /* The start of the key (for textual comparison). */ - long number; /* The numeric value (for numeric comparison). */ - } key; - long keylen; /* Length of KEY field. */ -}; - -/* This structure describes a field to use as a sort key. */ -struct keyfield -{ - int startwords; /* Number of words to skip. */ - int startchars; /* Number of additional chars to skip. */ - int endwords; /* Number of words to ignore at end. */ - int endchars; /* Ditto for characters of last word. */ - char ignore_blanks; /* Non-zero means ignore spaces and tabs. */ - char fold_case; /* Non-zero means case doesn't matter. */ - char reverse; /* Non-zero means compare in reverse order. */ - char numeric; /* Non-zeros means field is ASCII numeric. */ - char positional; /* Sort according to file position. */ - char braced; /* Count balanced-braced groupings as fields. */ -}; - -/* Vector of keyfields to use. */ -struct keyfield keyfields[3]; - -/* Number of keyfields stored in that vector. */ -int num_keyfields = 3; - -/* Vector of input file names, terminated with a null pointer. */ -char **infiles; - -/* Vector of corresponding output file names, or NULL, meaning default it - (add an `s' to the end). */ -char **outfiles; - -/* Length of `infiles'. */ -int num_infiles; - -/* Pointer to the array of pointers to lines being sorted. */ -char **linearray; - -/* The allocated length of `linearray'. */ -long nlines; - -/* Directory to use for temporary files. On Unix, it ends with a slash. */ -char *tempdir; - -/* Start of filename to use for temporary files. */ -char *tempbase; - -/* Number of last temporary file. */ -int tempcount; - -/* Number of last temporary file already deleted. - Temporary files are deleted by `flush_tempfiles' in order of creation. */ -int last_deleted_tempcount; - -/* During in-core sort, this points to the base of the data block - which contains all the lines of data. */ -char *text_base; - -/* Additional command switches .*/ - -/* Nonzero means do not delete tempfiles -- for debugging. */ -int keep_tempfiles; - -/* The name this program was run with. */ -char *program_name; - -/* Forward declarations of functions in this file. */ - -void decode_command (); -void sort_in_core (); -void sort_offline (); -char **parsefile (); -char *find_field (); -char *find_pos (); -long find_value (); -char *find_braced_pos (); -char *find_braced_end (); -void writelines (); -int compare_field (); -int compare_full (); -long readline (); -int merge_files (); -int merge_direct (); -void pfatal_with_name (); -void fatal (); -void error (); -void *xmalloc (), *xrealloc (); -char *concat (); -char *maketempname (); -void flush_tempfiles (); -char *tempcopy (); - -#define MAX_IN_CORE_SORT 500000 - -void -main (argc, argv) - int argc; - char **argv; -{ - int i; - - tempcount = 0; - last_deleted_tempcount = 0; - program_name = argv[0]; - - /* Describe the kind of sorting to do. */ - /* The first keyfield uses the first braced field and folds case. */ - keyfields[0].braced = 1; - keyfields[0].fold_case = 1; - keyfields[0].endwords = -1; - keyfields[0].endchars = -1; - - /* The second keyfield uses the second braced field, numerically. */ - keyfields[1].braced = 1; - keyfields[1].numeric = 1; - keyfields[1].startwords = 1; - keyfields[1].endwords = -1; - keyfields[1].endchars = -1; - - /* The third keyfield (which is ignored while discarding duplicates) - compares the whole line. */ - keyfields[2].endwords = -1; - keyfields[2].endchars = -1; - - decode_command (argc, argv); - - tempbase = mktemp (concat ("txiXXXXXX", "", "")); - - /* Process input files completely, one by one. */ - - for (i = 0; i < num_infiles; i++) - { - int desc; - long ptr; - char *outfile; - - desc = open (infiles[i], O_RDONLY, 0); - if (desc < 0) - pfatal_with_name (infiles[i]); - lseek (desc, 0L, SEEK_END); - ptr = lseek (desc, 0L, SEEK_CUR); - - close (desc); - - outfile = outfiles[i]; - if (!outfile) - { - outfile = concat (infiles[i], "s", ""); - } - - if (ptr < MAX_IN_CORE_SORT) - /* Sort a small amount of data. */ - sort_in_core (infiles[i], ptr, outfile); - else - sort_offline (infiles[i], ptr, outfile); - } - - flush_tempfiles (tempcount); - exit (TI_NO_ERROR); -} - -void -usage () -{ - fprintf (stderr, "\ -Usage: %s [-k] infile [-o outfile] ...\n", program_name); - exit (1); -} - -/* Decode the command line arguments to set the parameter variables - and set up the vector of keyfields and the vector of input files. */ - -void -decode_command (argc, argv) - int argc; - char **argv; -{ - int optc; - char **ip; - char **op; - - /* Store default values into parameter variables. */ - - tempdir = getenv ("TMPDIR"); -#ifdef VMS - if (tempdir == NULL) - tempdir = "sys$scratch:"; -#else - if (tempdir == NULL) - tempdir = "/tmp/"; - else - tempdir = concat (tempdir, "/", ""); -#endif - - keep_tempfiles = 0; - - /* Allocate ARGC input files, which must be enough. */ - - infiles = (char **) xmalloc (argc * sizeof (char *)); - outfiles = (char **) xmalloc (argc * sizeof (char *)); - ip = infiles; - op = outfiles; - - while ((optc = getopt (argc, argv, "-ko:")) != EOF) - { - switch (optc) - { - case 1: /* Non-option filename. */ - *ip++ = optarg; - *op++ = NULL; - break; - - case 'k': - keep_tempfiles = 1; - break; - - case 'o': - if (op > outfiles) - *(op - 1) = optarg; - break; - - default: - usage (); - } - } - - /* Record number of keyfields and terminate list of filenames. */ - num_infiles = ip - infiles; - *ip = 0; - if (num_infiles == 0) - usage (); -} - -/* Return a name for a temporary file. */ - -char * -maketempname (count) - int count; -{ - char tempsuffix[10]; - sprintf (tempsuffix, "%d", count); - return concat (tempdir, tempbase, tempsuffix); -} - -/* Delete all temporary files up to TO_COUNT. */ - -void -flush_tempfiles (to_count) - int to_count; -{ - if (keep_tempfiles) - return; - while (last_deleted_tempcount < to_count) - unlink (maketempname (++last_deleted_tempcount)); -} - -/* Copy the input file open on IDESC into a temporary file - and return the temporary file name. */ - -#define BUFSIZE 1024 - -char * -tempcopy (idesc) - int idesc; -{ - char *outfile = maketempname (++tempcount); - int odesc; - char buffer[BUFSIZE]; - - odesc = open (outfile, O_WRONLY | O_CREAT, 0666); - - if (odesc < 0) - pfatal_with_name (outfile); - - while (1) - { - int nread = read (idesc, buffer, BUFSIZE); - write (odesc, buffer, nread); - if (!nread) - break; - } - - close (odesc); - - return outfile; -} - -/* Compare LINE1 and LINE2 according to the specified set of keyfields. */ - -int -compare_full (line1, line2) - char **line1, **line2; -{ - int i; - - /* Compare using the first keyfield; - if that does not distinguish the lines, try the second keyfield; - and so on. */ - - for (i = 0; i < num_keyfields; i++) - { - long length1, length2; - char *start1 = find_field (&keyfields[i], *line1, &length1); - char *start2 = find_field (&keyfields[i], *line2, &length2); - int tem = compare_field (&keyfields[i], start1, length1, *line1 - text_base, - start2, length2, *line2 - text_base); - if (tem) - { - if (keyfields[i].reverse) - return -tem; - return tem; - } - } - - return 0; /* Lines match exactly. */ -} - -/* Compare LINE1 and LINE2, described by structures - in which the first keyfield is identified in advance. - For positional sorting, assumes that the order of the lines in core - reflects their nominal order. */ - -int -compare_prepared (line1, line2) - struct lineinfo *line1, *line2; -{ - int i; - int tem; - char *text1, *text2; - - /* Compare using the first keyfield, which has been found for us already. */ - if (keyfields->positional) - { - if (line1->text - text_base > line2->text - text_base) - tem = 1; - else - tem = -1; - } - else if (keyfields->numeric) - tem = line1->key.number - line2->key.number; - else - tem = compare_field (keyfields, line1->key.text, line1->keylen, 0, - line2->key.text, line2->keylen, 0); - if (tem) - { - if (keyfields->reverse) - return -tem; - return tem; - } - - text1 = line1->text; - text2 = line2->text; - - /* Compare using the second keyfield; - if that does not distinguish the lines, try the third keyfield; - and so on. */ - - for (i = 1; i < num_keyfields; i++) - { - long length1, length2; - char *start1 = find_field (&keyfields[i], text1, &length1); - char *start2 = find_field (&keyfields[i], text2, &length2); - int tem = compare_field (&keyfields[i], start1, length1, text1 - text_base, - start2, length2, text2 - text_base); - if (tem) - { - if (keyfields[i].reverse) - return -tem; - return tem; - } - } - - return 0; /* Lines match exactly. */ -} - -/* Like compare_full but more general. - You can pass any strings, and you can say how many keyfields to use. - POS1 and POS2 should indicate the nominal positional ordering of - the two lines in the input. */ - -int -compare_general (str1, str2, pos1, pos2, use_keyfields) - char *str1, *str2; - long pos1, pos2; - int use_keyfields; -{ - int i; - - /* Compare using the first keyfield; - if that does not distinguish the lines, try the second keyfield; - and so on. */ - - for (i = 0; i < use_keyfields; i++) - { - long length1, length2; - char *start1 = find_field (&keyfields[i], str1, &length1); - char *start2 = find_field (&keyfields[i], str2, &length2); - int tem = compare_field (&keyfields[i], start1, length1, pos1, - start2, length2, pos2); - if (tem) - { - if (keyfields[i].reverse) - return -tem; - return tem; - } - } - - return 0; /* Lines match exactly. */ -} - -/* Find the start and length of a field in STR according to KEYFIELD. - A pointer to the starting character is returned, and the length - is stored into the int that LENGTHPTR points to. */ - -char * -find_field (keyfield, str, lengthptr) - struct keyfield *keyfield; - char *str; - long *lengthptr; -{ - char *start; - char *end; - char *(*fun) (); - - if (keyfield->braced) - fun = find_braced_pos; - else - fun = find_pos; - - start = (*fun) (str, keyfield->startwords, keyfield->startchars, - keyfield->ignore_blanks); - if (keyfield->endwords < 0) - { - if (keyfield->braced) - end = find_braced_end (start); - else - { - end = start; - while (*end && *end != '\n') - end++; - } - } - else - { - end = (*fun) (str, keyfield->endwords, keyfield->endchars, 0); - if (end - str < start - str) - end = start; - } - *lengthptr = end - start; - return start; -} - -/* Return a pointer to a specified place within STR, - skipping (from the beginning) WORDS words and then CHARS chars. - If IGNORE_BLANKS is nonzero, we skip all blanks - after finding the specified word. */ - -char * -find_pos (str, words, chars, ignore_blanks) - char *str; - int words, chars; - int ignore_blanks; -{ - int i; - char *p = str; - - for (i = 0; i < words; i++) - { - char c; - /* Find next bunch of nonblanks and skip them. */ - while ((c = *p) == ' ' || c == '\t') - p++; - while ((c = *p) && c != '\n' && !(c == ' ' || c == '\t')) - p++; - if (!*p || *p == '\n') - return p; - } - - while (*p == ' ' || *p == '\t') - p++; - - for (i = 0; i < chars; i++) - { - if (!*p || *p == '\n') - break; - p++; - } - return p; -} - -/* Like find_pos but assumes that each field is surrounded by braces - and that braces within fields are balanced. */ - -char * -find_braced_pos (str, words, chars, ignore_blanks) - char *str; - int words, chars; - int ignore_blanks; -{ - int i; - int bracelevel; - char *p = str; - char c; - - for (i = 0; i < words; i++) - { - bracelevel = 1; - while ((c = *p++) != '{' && c != '\n' && c) - /* Do nothing. */ ; - if (c != '{') - return p - 1; - while (bracelevel) - { - c = *p++; - if (c == '{') - bracelevel++; - if (c == '}') - bracelevel--; - if (c == 0 || c == '\n') - return p - 1; - } - } - - while ((c = *p++) != '{' && c != '\n' && c) - /* Do nothing. */ ; - - if (c != '{') - return p - 1; - - if (ignore_blanks) - while ((c = *p) == ' ' || c == '\t') - p++; - - for (i = 0; i < chars; i++) - { - if (!*p || *p == '\n') - break; - p++; - } - return p; -} - -/* Find the end of the balanced-brace field which starts at STR. - The position returned is just before the closing brace. */ - -char * -find_braced_end (str) - char *str; -{ - int bracelevel; - char *p = str; - char c; - - bracelevel = 1; - while (bracelevel) - { - c = *p++; - if (c == '{') - bracelevel++; - if (c == '}') - bracelevel--; - if (c == 0 || c == '\n') - return p - 1; - } - return p - 1; -} - -long -find_value (start, length) - char *start; - long length; -{ - while (length != 0L) - { - if (isdigit (*start)) - return atol (start); - length--; - start++; - } - return 0l; -} - -/* Vector used to translate characters for comparison. - This is how we make all alphanumerics follow all else, - and ignore case in the first sorting. */ -int char_order[256]; - -void -init_char_order () -{ - int i; - for (i = 1; i < 256; i++) - char_order[i] = i; - - for (i = '0'; i <= '9'; i++) - char_order[i] += 512; - - for (i = 'a'; i <= 'z'; i++) - { - char_order[i] = 512 + i; - char_order[i + 'A' - 'a'] = 512 + i; - } -} - -/* Compare two fields (each specified as a start pointer and a character count) - according to KEYFIELD. - The sign of the value reports the relation between the fields. */ - -int -compare_field (keyfield, start1, length1, pos1, start2, length2, pos2) - struct keyfield *keyfield; - char *start1; - long length1; - long pos1; - char *start2; - long length2; - long pos2; -{ - if (keyfields->positional) - { - if (pos1 > pos2) - return 1; - else - return -1; - } - if (keyfield->numeric) - { - long value = find_value (start1, length1) - find_value (start2, length2); - if (value > 0) - return 1; - if (value < 0) - return -1; - return 0; - } - else - { - char *p1 = start1; - char *p2 = start2; - char *e1 = start1 + length1; - char *e2 = start2 + length2; - - while (1) - { - int c1, c2; - - if (p1 == e1) - c1 = 0; - else - c1 = *p1++; - if (p2 == e2) - c2 = 0; - else - c2 = *p2++; - - if (char_order[c1] != char_order[c2]) - return char_order[c1] - char_order[c2]; - if (!c1) - break; - } - - /* Strings are equal except possibly for case. */ - p1 = start1; - p2 = start2; - while (1) - { - int c1, c2; - - if (p1 == e1) - c1 = 0; - else - c1 = *p1++; - if (p2 == e2) - c2 = 0; - else - c2 = *p2++; - - if (c1 != c2) - /* Reverse sign here so upper case comes out last. */ - return c2 - c1; - if (!c1) - break; - } - - return 0; - } -} - -/* A `struct linebuffer' is a structure which holds a line of text. - `readline' reads a line from a stream into a linebuffer - and works regardless of the length of the line. */ - -struct linebuffer -{ - long size; - char *buffer; -}; - -/* Initialize LINEBUFFER for use. */ - -void -initbuffer (linebuffer) - struct linebuffer *linebuffer; -{ - linebuffer->size = 200; - linebuffer->buffer = (char *) xmalloc (200); -} - -/* Read a line of text from STREAM into LINEBUFFER. - Return the length of the line. */ - -long -readline (linebuffer, stream) - struct linebuffer *linebuffer; - FILE *stream; -{ - char *buffer = linebuffer->buffer; - char *p = linebuffer->buffer; - char *end = p + linebuffer->size; - - while (1) - { - int c = getc (stream); - if (p == end) - { - buffer = (char *) xrealloc (buffer, linebuffer->size *= 2); - p += buffer - linebuffer->buffer; - end += buffer - linebuffer->buffer; - linebuffer->buffer = buffer; - } - if (c < 0 || c == '\n') - { - *p = 0; - break; - } - *p++ = c; - } - - return p - buffer; -} - -/* Sort an input file too big to sort in core. */ - -void -sort_offline (infile, nfiles, total, outfile) - char *infile; - int nfiles; - long total; - char *outfile; -{ - /* More than enough. */ - int ntemps = 2 * (total + MAX_IN_CORE_SORT - 1) / MAX_IN_CORE_SORT; - char **tempfiles = (char **) xmalloc (ntemps * sizeof (char *)); - FILE *istream = fopen (infile, "r"); - int i; - struct linebuffer lb; - long linelength; - int failure = 0; - - initbuffer (&lb); - - /* Read in one line of input data. */ - - linelength = readline (&lb, istream); - - if (lb.buffer[0] != '\\' && lb.buffer[0] != '@') - { - error ("%s: not a texinfo index file", infile); - return; - } - - /* Split up the input into `ntemps' temporary files, or maybe fewer, - and put the new files' names into `tempfiles' */ - - for (i = 0; i < ntemps; i++) - { - char *outname = maketempname (++tempcount); - FILE *ostream = fopen (outname, "w"); - long tempsize = 0; - - if (!ostream) - pfatal_with_name (outname); - tempfiles[i] = outname; - - /* Copy lines into this temp file as long as it does not make file - "too big" or until there are no more lines. */ - - while (tempsize + linelength + 1 <= MAX_IN_CORE_SORT) - { - tempsize += linelength + 1; - fputs (lb.buffer, ostream); - putc ('\n', ostream); - - /* Read another line of input data. */ - - linelength = readline (&lb, istream); - if (!linelength && feof (istream)) - break; - - if (lb.buffer[0] != '\\' && lb.buffer[0] != '@') - { - error ("%s: not a texinfo index file", infile); - failure = 1; - goto fail; - } - } - fclose (ostream); - if (feof (istream)) - break; - } - - free (lb.buffer); - -fail: - /* Record number of temp files we actually needed. */ - - ntemps = i; - - /* Sort each tempfile into another tempfile. - Delete the first set of tempfiles and put the names of the second - into `tempfiles'. */ - - for (i = 0; i < ntemps; i++) - { - char *newtemp = maketempname (++tempcount); - sort_in_core (&tempfiles[i], MAX_IN_CORE_SORT, newtemp); - if (!keep_tempfiles) - unlink (tempfiles[i]); - tempfiles[i] = newtemp; - } - - if (failure) - return; - - /* Merge the tempfiles together and indexify. */ - - merge_files (tempfiles, ntemps, outfile); -} - -/* Sort INFILE, whose size is TOTAL, - assuming that is small enough to be done in-core, - then indexify it and send the output to OUTFILE (or to stdout). */ - -void -sort_in_core (infile, total, outfile) - char *infile; - long total; - char *outfile; -{ - char **nextline; - char *data = (char *) xmalloc (total + 1); - char *file_data; - long file_size; - int i; - FILE *ostream = stdout; - struct lineinfo *lineinfo; - - /* Read the contents of the file into the moby array `data'. */ - - int desc = open (infile, O_RDONLY, 0); - - if (desc < 0) - fatal ("failure reopening %s", infile); - for (file_size = 0;;) - { - i = read (desc, data + file_size, total - file_size); - if (i <= 0) - break; - file_size += i; - } - file_data = data; - data[file_size] = 0; - - close (desc); - - if (file_size > 0 && data[0] != '\\' && data[0] != '@') - { - error ("%s: not a texinfo index file", infile); - return; - } - - init_char_order (); - - /* Sort routines want to know this address. */ - - text_base = data; - - /* Create the array of pointers to lines, with a default size - frequently enough. */ - - nlines = total / 50; - if (!nlines) - nlines = 2; - linearray = (char **) xmalloc (nlines * sizeof (char *)); - - /* `nextline' points to the next free slot in this array. - `nlines' is the allocated size. */ - - nextline = linearray; - - /* Parse the input file's data, and make entries for the lines. */ - - nextline = parsefile (infile, nextline, file_data, file_size); - if (nextline == 0) - { - error ("%s: not a texinfo index file", infile); - return; - } - - /* Sort the lines. */ - - /* If we have enough space, find the first keyfield of each line in advance. - Make a `struct lineinfo' for each line, which records the keyfield - as well as the line, and sort them. */ - - lineinfo = (struct lineinfo *) malloc ((nextline - linearray) * sizeof (struct lineinfo)); - - if (lineinfo) - { - struct lineinfo *lp; - char **p; - - for (lp = lineinfo, p = linearray; p != nextline; lp++, p++) - { - lp->text = *p; - lp->key.text = find_field (keyfields, *p, &lp->keylen); - if (keyfields->numeric) - lp->key.number = find_value (lp->key.text, lp->keylen); - } - - qsort (lineinfo, nextline - linearray, sizeof (struct lineinfo), compare_prepared); - - for (lp = lineinfo, p = linearray; p != nextline; lp++, p++) - *p = lp->text; - - free (lineinfo); - } - else - qsort (linearray, nextline - linearray, sizeof (char *), compare_full); - - /* Open the output file. */ - - if (outfile) - { - ostream = fopen (outfile, "w"); - if (!ostream) - pfatal_with_name (outfile); - } - - writelines (linearray, nextline - linearray, ostream); - if (outfile) - fclose (ostream); - - free (linearray); - free (data); -} - -/* Parse an input string in core into lines. - DATA is the input string, and SIZE is its length. - Data goes in LINEARRAY starting at NEXTLINE. - The value returned is the first entry in LINEARRAY still unused. - Value 0 means input file contents are invalid. */ - -char ** -parsefile (filename, nextline, data, size) - char *filename; - char **nextline; - char *data; - long size; -{ - char *p, *end; - char **line = nextline; - - p = data; - end = p + size; - *end = 0; - - while (p != end) - { - if (p[0] != '\\' && p[0] != '@') - return 0; - - *line = p; - while (*p && *p != '\n') - p++; - if (p != end) - p++; - - line++; - if (line == linearray + nlines) - { - char **old = linearray; - linearray = (char **) xrealloc (linearray, sizeof (char *) * (nlines *= 4)); - line += linearray - old; - } - } - - return line; -} - -/* Indexification is a filter applied to the sorted lines - as they are being written to the output file. - Multiple entries for the same name, with different page numbers, - get combined into a single entry with multiple page numbers. - The first braced field, which is used for sorting, is discarded. - However, its first character is examined, folded to lower case, - and if it is different from that in the previous line fed to us - a \initial line is written with one argument, the new initial. - - If an entry has four braced fields, then the second and third - constitute primary and secondary names. - In this case, each change of primary name - generates a \primary line which contains only the primary name, - and in between these are \secondary lines which contain - just a secondary name and page numbers. */ - -/* The last primary name we wrote a \primary entry for. - If only one level of indexing is being done, this is the last name seen. */ -char *lastprimary; -/* Length of storage allocated for lastprimary. */ -int lastprimarylength; - -/* Similar, for the secondary name. */ -char *lastsecondary; -int lastsecondarylength; - -/* Zero if we are not in the middle of writing an entry. - One if we have written the beginning of an entry but have not - yet written any page numbers into it. - Greater than one if we have written the beginning of an entry - plus at least one page number. */ -int pending; - -/* The initial (for sorting purposes) of the last primary entry written. - When this changes, a \initial {c} line is written */ - -char *lastinitial; - -int lastinitiallength; - -/* When we need a string of length 1 for the value of lastinitial, - store it here. */ - -char lastinitial1[2]; - -/* Initialize static storage for writing an index. */ - -void -init_index () -{ - pending = 0; - lastinitial = lastinitial1; - lastinitial1[0] = 0; - lastinitial1[1] = 0; - lastinitiallength = 0; - lastprimarylength = 100; - lastprimary = (char *) xmalloc (lastprimarylength + 1); - bzero (lastprimary, lastprimarylength + 1); - lastsecondarylength = 100; - lastsecondary = (char *) xmalloc (lastsecondarylength + 1); - bzero (lastsecondary, lastsecondarylength + 1); -} - -/* Indexify. Merge entries for the same name, - insert headers for each initial character, etc. */ - -void -indexify (line, ostream) - char *line; - FILE *ostream; -{ - char *primary, *secondary, *pagenumber; - int primarylength, secondarylength = 0, pagelength; - int nosecondary; - int initiallength; - char *initial; - char initial1[2]; - register char *p; - - /* First, analyze the parts of the entry fed to us this time. */ - - p = find_braced_pos (line, 0, 0, 0); - if (*p == '{') - { - initial = p; - /* Get length of inner pair of braces starting at `p', - including that inner pair of braces. */ - initiallength = find_braced_end (p + 1) + 1 - p; - } - else - { - initial = initial1; - initial1[0] = *p; - initial1[1] = 0; - initiallength = 1; - - if (initial1[0] >= 'a' && initial1[0] <= 'z') - initial1[0] -= 040; - } - - pagenumber = find_braced_pos (line, 1, 0, 0); - pagelength = find_braced_end (pagenumber) - pagenumber; - if (pagelength == 0) - abort (); - - primary = find_braced_pos (line, 2, 0, 0); - primarylength = find_braced_end (primary) - primary; - - secondary = find_braced_pos (line, 3, 0, 0); - nosecondary = !*secondary; - if (!nosecondary) - secondarylength = find_braced_end (secondary) - secondary; - - /* If the primary is different from before, make a new primary entry. */ - if (strncmp (primary, lastprimary, primarylength)) - { - /* Close off current secondary entry first, if one is open. */ - if (pending) - { - fputs ("}\n", ostream); - pending = 0; - } - - /* If this primary has a different initial, include an entry for - the initial. */ - if (initiallength != lastinitiallength || - strncmp (initial, lastinitial, initiallength)) - { - fprintf (ostream, "\\initial {"); - fwrite (initial, 1, initiallength, ostream); - fprintf (ostream, "}\n", initial); - if (initial == initial1) - { - lastinitial = lastinitial1; - *lastinitial1 = *initial1; - } - else - { - lastinitial = initial; - } - lastinitiallength = initiallength; - } - - /* Make the entry for the primary. */ - if (nosecondary) - fputs ("\\entry {", ostream); - else - fputs ("\\primary {", ostream); - fwrite (primary, primarylength, 1, ostream); - if (nosecondary) - { - fputs ("}{", ostream); - pending = 1; - } - else - fputs ("}\n", ostream); - - /* Record name of most recent primary. */ - if (lastprimarylength < primarylength) - { - lastprimarylength = primarylength + 100; - lastprimary = (char *) xrealloc (lastprimary, - 1 + lastprimarylength); - } - strncpy (lastprimary, primary, primarylength); - lastprimary[primarylength] = 0; - - /* There is no current secondary within this primary, now. */ - lastsecondary[0] = 0; - } - - /* Should not have an entry with no subtopic following one with a subtopic. */ - - if (nosecondary && *lastsecondary) - error ("entry %s follows an entry with a secondary name", line); - - /* Start a new secondary entry if necessary. */ - if (!nosecondary && strncmp (secondary, lastsecondary, secondarylength)) - { - if (pending) - { - fputs ("}\n", ostream); - pending = 0; - } - - /* Write the entry for the secondary. */ - fputs ("\\secondary {", ostream); - fwrite (secondary, secondarylength, 1, ostream); - fputs ("}{", ostream); - pending = 1; - - /* Record name of most recent secondary. */ - if (lastsecondarylength < secondarylength) - { - lastsecondarylength = secondarylength + 100; - lastsecondary = (char *) xrealloc (lastsecondary, - 1 + lastsecondarylength); - } - strncpy (lastsecondary, secondary, secondarylength); - lastsecondary[secondarylength] = 0; - } - - /* Here to add one more page number to the current entry. */ - if (pending++ != 1) - fputs (", ", ostream); /* Punctuate first, if this is not the first. */ - fwrite (pagenumber, pagelength, 1, ostream); -} - -/* Close out any unfinished output entry. */ - -void -finish_index (ostream) - FILE *ostream; -{ - if (pending) - fputs ("}\n", ostream); - free (lastprimary); - free (lastsecondary); -} - -/* Copy the lines in the sorted order. - Each line is copied out of the input file it was found in. */ - -void -writelines (linearray, nlines, ostream) - char **linearray; - int nlines; - FILE *ostream; -{ - char **stop_line = linearray + nlines; - char **next_line; - - init_index (); - - /* Output the text of the lines, and free the buffer space. */ - - for (next_line = linearray; next_line != stop_line; next_line++) - { - /* If -u was specified, output the line only if distinct from previous one. */ - if (next_line == linearray - /* Compare previous line with this one, using only the - explicitly specd keyfields. */ - || compare_general (*(next_line - 1), *next_line, 0L, 0L, num_keyfields - 1)) - { - char *p = *next_line; - char c; - - while ((c = *p++) && c != '\n') - /* Do nothing. */ ; - *(p - 1) = 0; - indexify (*next_line, ostream); - } - } - - finish_index (ostream); -} - -/* Assume (and optionally verify) that each input file is sorted; - merge them and output the result. - Returns nonzero if any input file fails to be sorted. - - This is the high-level interface that can handle an unlimited - number of files. */ - -#define MAX_DIRECT_MERGE 10 - -int -merge_files (infiles, nfiles, outfile) - char **infiles; - int nfiles; - char *outfile; -{ - char **tempfiles; - int ntemps; - int i; - int value = 0; - int start_tempcount = tempcount; - - if (nfiles <= MAX_DIRECT_MERGE) - return merge_direct (infiles, nfiles, outfile); - - /* Merge groups of MAX_DIRECT_MERGE input files at a time, - making a temporary file to hold each group's result. */ - - ntemps = (nfiles + MAX_DIRECT_MERGE - 1) / MAX_DIRECT_MERGE; - tempfiles = (char **) xmalloc (ntemps * sizeof (char *)); - for (i = 0; i < ntemps; i++) - { - int nf = MAX_DIRECT_MERGE; - if (i + 1 == ntemps) - nf = nfiles - i * MAX_DIRECT_MERGE; - tempfiles[i] = maketempname (++tempcount); - value |= merge_direct (&infiles[i * MAX_DIRECT_MERGE], nf, tempfiles[i]); - } - - /* All temporary files that existed before are no longer needed - since their contents have been merged into our new tempfiles. - So delete them. */ - flush_tempfiles (start_tempcount); - - /* Now merge the temporary files we created. */ - - merge_files (tempfiles, ntemps, outfile); - - free (tempfiles); - - return value; -} - -/* Assume (and optionally verify) that each input file is sorted; - merge them and output the result. - Returns nonzero if any input file fails to be sorted. - - This version of merging will not work if the number of - input files gets too high. Higher level functions - use it only with a bounded number of input files. */ - -int -merge_direct (infiles, nfiles, outfile) - char **infiles; - int nfiles; - char *outfile; -{ - struct linebuffer *lb1, *lb2; - struct linebuffer **thisline, **prevline; - FILE **streams; - int i; - int nleft; - int lossage = 0; - int *file_lossage; - struct linebuffer *prev_out = 0; - FILE *ostream = stdout; - - if (outfile) - { - ostream = fopen (outfile, "w"); - } - if (!ostream) - pfatal_with_name (outfile); - - init_index (); - - if (nfiles == 0) - { - if (outfile) - fclose (ostream); - return 0; - } - - /* For each file, make two line buffers. - Also, for each file, there is an element of `thisline' - which points at any time to one of the file's two buffers, - and an element of `prevline' which points to the other buffer. - `thisline' is supposed to point to the next available line from the file, - while `prevline' holds the last file line used, - which is remembered so that we can verify that the file is properly sorted. */ - - /* lb1 and lb2 contain one buffer each per file. */ - lb1 = (struct linebuffer *) xmalloc (nfiles * sizeof (struct linebuffer)); - lb2 = (struct linebuffer *) xmalloc (nfiles * sizeof (struct linebuffer)); - - /* thisline[i] points to the linebuffer holding the next available line in file i, - or is zero if there are no lines left in that file. */ - thisline = (struct linebuffer **) - xmalloc (nfiles * sizeof (struct linebuffer *)); - /* prevline[i] points to the linebuffer holding the last used line - from file i. This is just for verifying that file i is properly - sorted. */ - prevline = (struct linebuffer **) - xmalloc (nfiles * sizeof (struct linebuffer *)); - /* streams[i] holds the input stream for file i. */ - streams = (FILE **) xmalloc (nfiles * sizeof (FILE *)); - /* file_lossage[i] is nonzero if we already know file i is not - properly sorted. */ - file_lossage = (int *) xmalloc (nfiles * sizeof (int)); - - /* Allocate and initialize all that storage. */ - - for (i = 0; i < nfiles; i++) - { - initbuffer (&lb1[i]); - initbuffer (&lb2[i]); - thisline[i] = &lb1[i]; - prevline[i] = &lb2[i]; - file_lossage[i] = 0; - streams[i] = fopen (infiles[i], "r"); - if (!streams[i]) - pfatal_with_name (infiles[i]); - - readline (thisline[i], streams[i]); - } - - /* Keep count of number of files not at eof. */ - nleft = nfiles; - - while (nleft) - { - struct linebuffer *best = 0; - struct linebuffer *exch; - int bestfile = -1; - int i; - - /* Look at the next avail line of each file; choose the least one. */ - - for (i = 0; i < nfiles; i++) - { - if (thisline[i] && - (!best || - 0 < compare_general (best->buffer, thisline[i]->buffer, - (long) bestfile, (long) i, num_keyfields))) - { - best = thisline[i]; - bestfile = i; - } - } - - /* Output that line, unless it matches the previous one and we - don't want duplicates. */ - - if (!(prev_out && - !compare_general (prev_out->buffer, - best->buffer, 0L, 1L, num_keyfields - 1))) - indexify (best->buffer, ostream); - prev_out = best; - - /* Now make the line the previous of its file, and fetch a new - line from that file. */ - - exch = prevline[bestfile]; - prevline[bestfile] = thisline[bestfile]; - thisline[bestfile] = exch; - - while (1) - { - /* If the file has no more, mark it empty. */ - - if (feof (streams[bestfile])) - { - thisline[bestfile] = 0; - /* Update the number of files still not empty. */ - nleft--; - break; - } - readline (thisline[bestfile], streams[bestfile]); - if (thisline[bestfile]->buffer[0] || !feof (streams[bestfile])) - break; - } - } - - finish_index (ostream); - - /* Free all storage and close all input streams. */ - - for (i = 0; i < nfiles; i++) - { - fclose (streams[i]); - free (lb1[i].buffer); - free (lb2[i].buffer); - } - free (file_lossage); - free (lb1); - free (lb2); - free (thisline); - free (prevline); - free (streams); - - if (outfile) - fclose (ostream); - - return lossage; -} - -/* Print error message and exit. */ - -void -fatal (s1, s2) - char *s1, *s2; -{ - error (s1, s2); - exit (TI_FATAL_ERROR); -} - -/* Print error message. S1 is printf control string, S2 is arg for it. */ - -void -error (s1, s2) - char *s1, *s2; -{ - printf ("%s: ", program_name); - printf (s1, s2); - printf ("\n"); -} - -void -perror_with_name (name) - char *name; -{ - char *s; - - if (errno < sys_nerr) - s = concat ("", sys_errlist[errno], " for %s"); - else - s = "cannot open %s"; - error (s, name); -} - -void -pfatal_with_name (name) - char *name; -{ - char *s; - - if (errno < sys_nerr) - s = concat ("", sys_errlist[errno], " for %s"); - else - s = "cannot open %s"; - fatal (s, name); -} - -/* Return a newly-allocated string whose contents concatenate those of - S1, S2, S3. */ - -char * -concat (s1, s2, s3) - char *s1, *s2, *s3; -{ - int len1 = strlen (s1), len2 = strlen (s2), len3 = strlen (s3); - char *result = (char *) xmalloc (len1 + len2 + len3 + 1); - - strcpy (result, s1); - strcpy (result + len1, s2); - strcpy (result + len1 + len2, s3); - *(result + len1 + len2 + len3) = 0; - - return result; -} - -/* Just like malloc, but kills the program in case of fatal error. */ -void * -xmalloc (nbytes) - int nbytes; -{ - void *temp = (void *) malloc (nbytes); - - if (nbytes && temp == (void *)NULL) - memory_error ("xmalloc", nbytes); - - return (temp); -} - -/* Like realloc (), but barfs if there isn't enough memory. */ -void * -xrealloc (pointer, nbytes) - void *pointer; - int nbytes; -{ - void *temp; - - if (!pointer) - temp = (void *)xmalloc (nbytes); - else - temp = (void *)realloc (pointer, nbytes); - - if (nbytes && !temp) - memory_error ("xrealloc", nbytes); - - return (temp); -} - -memory_error (callers_name, bytes_wanted) - char *callers_name; - int bytes_wanted; -{ - char printable_string[80]; - - sprintf (printable_string, - "Virtual memory exhausted in %s ()! Needed %d bytes.", - callers_name, bytes_wanted); - - error (printable_string); - abort (); -} - -#ifndef STDC_HEADERS -void -bzero (b, length) - register char *b; - register int length; -{ -#ifdef VMS - short zero = 0; - long max_str = 65535; - - while (length > max_str) - { - (void) LIB$MOVC5 (&zero, &zero, &zero, &max_str, b); - length -= max_str; - b += max_str; - } - (void) LIB$MOVC5 (&zero, &zero, &zero, &length, b); -#else - while (length-- > 0) - *b++ = 0; -#endif /* not VMS */ -} -#endif /* not STDC_HEADERS */ |