Go to the first, previous, next, last section, table of contents.
The principle concepts of WEB programming are laid out in Knuth's book, the reference to which is given in section INTRODUCTION to FWEB. FWEB follows most conventions introduced by WEB and CWEB, except that the names of some commands have been changed for consistency, symmetry, and/or clarity.
Following Knuth's original design, FWEB consists of two processors, FTANGLE and FWEAVE. Both operate on a single source file, say `test.web'. FTANGLE produces compilable code, say `test.c', whereas FWEAVE produces a TeX file, `test.tex', that can (in principle) be processed with either TeX or LaTeX. (If a file `test.tex' already exists, FWEAVE will ask for confirmation before overwriting it if it does not think that the file was created by a previous run of FWEAVE.)
Future FWEB development will be based on LaTeX; it is no longer guaranteed that Plain TeX will work in all circumstances. For detailed descriptions of the LaTeX support, see section LaTeX support.
An FWEB source file is structured into sections, which correspond to logical subunits of the code (either a function or a fragment of a function). Each section consists of three parts, each of which is optional: the
- TeX part;
- definition part; and
- code part.
The code parts of (possibly noncontiguous) sections can be combined into larger units called modules, as explained in section Modules.
A simple example of an FWEB source file consisting of three sections is as follows:
@n % Set \FWEB\ language to \Fortran. \Title{example.web} % \Title is an \FWEB\ \TeX\ macro. \author{J. A. Krommes} % \author is a \LaTeX\ macro. @* INTRODUCTION. This code is intended to illustrate the use of the |write| statement. It also provides a simple example of the FWEB macro preprocessor. @m PI 3.14159 // FWEB preprocessor macro definition. @a program main call compute end @ The computational routine is pretty boring. @a subroutine compute write(*,*) 'pi = ', PI end @* \INDEX.
Commands to FWEB are begun by the `@' symbol (see section FWEB COMMANDS). In this example, the first command, `@n', sets the global language to FORTRAN-77. One should always begin one's code with a language-setting command. For more information about languages, see section LANGUAGES.
The `@*' command begins a major or named section
(corresponding to
LaTeX's \section
command); this command is followed by the
section name, terminated by a period. Major sections are entered in an
automatically generated
Table of Contents. They are also printed at the top of each output
page. If the full name is too long to so print, one can shorten it with
an optional argument, as in
@* [INTRO]INTRODUCTION.
The command `@*n' (not illustrated in the above example) begins a major (sub)section of level n, where `@*0' is equivalent to the simple `@*', `@*1' indicates a subsection, and `@*2' indicates a subsubsection. The highest permissible major level is 2 (a subsubsection). Such subsections are also entered in the Table of Contents. For more information, see section Sections in LaTeX.
As the example demonstrates, the name of the very last section, which
should be starred, should be `\INDEX'. Note the backslash;
`\INDEX' is a TeX macro. This command tells FWEAVE to
write out the index in a special two-column format. By default,
`\INDEX' expands to `INDEX', but this name can be overridden
by the style-file parameter `index.name' (see section index.???
). For
more discussion of the indexing features of FWEB, see section FWEB's INDEX..
Minor (unnamed) sections are begun by `@ ' ("at-space"); these have no associated names and are not entered into the Table of Contents. A newline counts as a space.
All sections begin with (optional) TeX commentary. Within that commentary, one can temporarily shift into code mode by enclosing the code within vertical bars. That code is typeset just like code in the code part (see below), except that newlines are replaced by spaces. Thus, one can say things like
Consider the C code fragment |@c for(i=0; i<10; i++){}|, which ...
(If the global language were C instead of FORTRAN, the `@c' inside the vertical bars would not be necessary.) The ability to switch back and forth between text mode and code mode at will allows for a very convenient and flexible style of exposition.
TeX commentary is followed by an optional definition part. The beginning of the definition part is signaled by the appearance of any one of the commands `@d', `@f', `@m', `@v', or `@W' (explained later). In the previous example, the first section has a definition part consisting of one FWEB macro definition (`@m'); the second section has no definition part. For more information, see section MACROS and PREPROCESSING.
An unnamed code part is begun by `@a'. A named code part is begun by the appearance of a module name, such as `@<Global variables@>', followed by an equals sign; see section Modules.
The portion of the source file before the first section (i.e., before
the first `@*' or `@ ') is called in limbo or the limbo
section.
The only `@' commands that are allowed in limbo (in
addition to `@@', which stands for the character `@' and is
allowed anywhere) are the
language-changing commands, and one of those, such as `@c', should
appear. Other text
in limbo is ignored by FTANGLE and is copied by FWEAVE to the
output file. Thus, one can make TeX macro definitions in limbo that
override the defaults in FWEB's macro package `fwebmac.sty'.
In the above example, see the \Title
command. This is defined in
`fwebmac.sty', and basically issues LaTeX's \title
command.
(Another way of getting TeX text into the limbo section is by means of the `@l' command; see section `@l': Specify limbo text.)
LaTeX users may need to know that TeX commands in limbo are executed after the `\begin{document}' command. For more information, see section LaTeX support.
The code parts of (possibly noncontiguous) sections can be combined into modules. Modules can be named or unnamed. There is just one unnamed module.
The contents of a module, either unnamed or named, consists of a mixture of code and comments. FTANGLE ignores the comments; FWEAVE treats them as TeX text. Within any TeX text, including comments, constructions delimited by `|...|' signify a temporary shift into code mode. In the present design, one cannot enclose a comment within the vertical bars.
The unnamed code module is introduced by the command `@a'. Subsequent uses of `@a' accrete code to the unnamed module. The fundamental operation of FTANGLE is that FTANGLE outputs the unnamed module. Thus, there must be at least one `@a' in the source file or FTANGLE will output nothing.
(Why is the command called `@a'? Historically, it was the first letter of the alphabet, as befits its prominent status. However, one can also think of it as "accrete".)
@< Arbitrary TeX text @>
Leading and trailing white space around the name text is ignored. The name text can include the `|...|' construction, which tells FWEAVE to typeset a code fragment.
To define a named module, replace the `@a' that begins the unnamed code part of a section by `@< module name @>='. If one uses this construction with the same name in a later section, the effect is to accrete to the contents of the module. Thus, a named module might ultimately consist of the code from sections 2, 5, and 9, for example.
To use a named module, simply use the name anywhere in a code part; FTANGLE will insert the contents of the module at the point where the name is used. For example,
@c @ Here's how to use a named module. @a for(i=1; i<n; i++) @< Inner loop @>@; @ Here's how to define a named module. Definitions may occur after use. @< Inner...@>= { a[i] = i; }
There are several details to notice about the above example. First, it uses the pseudo-semicolon `@;'; for more discussion of its use, see section `@;': Pseudo-semicolon. Second, after a name has appeared once in full, it may be abbreviated by a unique prefix followed by 3 dots, as demonstrated in the above example. By convention, a complete module name cannot be a subset of another. For example, `@<Test@>' and `@<Test of graphics@>' will elicit an error message.
Commonly the first unnamed section in the code indicates its modular structure. For example, a C code might begin with
@c @* DEMO. @a @<Include files@>@; @<Typedefs@>@; @<Function prototypes@>@; @<Global variables@>@;
Subsequently one can accrete to the above named sections, as often as desired and in any order. This way, definitions of global variables can be introduced as logical and pedagogical exposition dictates, but will be guaranteed to appear at the top of the code. Function prototypes could be handled this way as well; alternatively, they could all be collected into one section, perhaps at the end of the source file. (The above organization still guarantees that they will appear at the beginning of the output.) Functions could be introduced one at a time in unnamed sections.
Very rarely, one might try the following construction:
@ @a @< Left side @> = @< Right side @>@;
Here the intent is to construct an assignment statement. However, this will be flagged as an error because it thinks you may be trying to define the named module `@<Left side@>', which you shouldn't be doing while in code mode. To make it work, just put the invisible expression `@e' (see section Pseudo (invisible) operators) before the equals sign.
The FWEB processors perform their work in several distinct phases. (The following is somewhat technical. Scan it, then use it for reference later if necessary.)
FTANGLE has two phases. In phase 1, the source file is read; in phase 2, compilable code is written out in the order specified by the web.
More specifically, phase 1
- discards TeX documentation;
- tokenizes source;
- expands preprocessor commands such as `@#if' (see section Preprocessing);
- expands `@'...'' (see section Conversion to ASCII), `@"..."' (see section `@"': Convert string to ASCII), and `0b...' (in FORTRAN, also `0...' and `0x...');
- stores code text in appropriate modules;
- memorizes macro definitions (`@d' and `@m') (see section `@d': Define outer macro, and mark and section `@m': Define FWEB macro, and mark).
Phase 2
- outputs outer macro definitions (`@d');
- outputs the unnamed module (`@a');
- expands FWEB macros (`@m');
- expands built-in macros such as `$IF' or `$PI' (see section Built-in functions);
- translates RATFOR statements (see section RATFOR).
FWEAVE has three phases. In phase 1, the source file is read and cross-reference information is collected. In phase2, the source file is read again, then pretty-printed (including some cross-reference information). In phase 3, an automatically-generated Index, List of Modules, and Table of Contents are written.
More specifically, phase 1
- tokenizes and stores identifiers and module names;
- collects cross-reference information (including, in C and C++, the scanning of `#include' files for `typedef' and/or `class' declarations (see section `-H': Scan C/C++ include files (FWEAVE));
- stores limbo text definitions made with `@l' (see section `@l': Specify limbo text);
- collects information about overloaded operators (`@v') and identifiers (`@W'). See section `@v': Overload operator and section `@W': Overload identifier.
Phase 2
- outputs limbo text;
- outputs special TeX macros for overloaded operators;
- copies TeX material directly to output;
- treats material between vertical bars (`|...|') as code to be typeset;
- tokenizes and stores contents of each code section;
- analyzes code syntax and converts to appropriate TeX macros.
Phase 3 writes out cross-reference information. (To eliminate some of that, see section `-x': Eliminate or reduce cross-reference information (FWEAVE)..) Specifically, it
- writes out the Index (`INDEX.tex' by default, but see section Output files and section Customizing FWEAVE's index);
- writes out a list of named modules (`MODULES.tex' by default, but see section Output files and section Customizing the module list);
- writes out macros to generate the Table of Contents. (Table of Contents information is actually processed by LaTeX, not FWEAVE. The information is written to the `aux' file.)
Go to the first, previous, next, last section, table of contents.