THE MAIN FUNCTION
Main(), and the other functions mentioned below, can be located in the compiler listings (Appendix C) by referring to the function index in Appendix H. Textual references are also given so that further investigation of these functions can be easily pursued.
Displaying the Signon Message
The file NOTICE.H contains macro definitions for two symbols which specify version and copyright information. VERSION specifies the version and revision numbers of the compiler, and CRIGHT1 contains copyright information. NOTICE.H is included into part one of the compiler, making these notices available to main() for display on the console.
Allocating Storage
Calloc() is called repeatedly to allocate the switch queue, the staging buffer, the while queue, the literal pool, the macro name and text buffers, the line buffers, and the symbol table. This process also involves saving the addresses of these data structures in pointers and placing buffer ending addresses in other pointers.
Initializing Variables
Most global objects are initialized either by default or by the use of initializers. Main() initializes others which must be set at run time. Those are argcs, argvs, locptr, and glbptr. Of course, the setting of pointers to allocated blocks of memory, described above, is also an initializing activity.
Processing Command-Line Switches
Command-line switches are processed by ask(). Basically, this consists of setting default values for several global variables, then scanning the command line for switches that specify different values for them. These variables are described below:
To gain access to the command-line arguments, ask() calls the Small C library function getarg(). Any arguments without a leading hyphen are considered to be filenames and so are ignored by ask(). By converting switch characters to uppercase and comparing them to uppercase constants ask() is effectively case blind.
Opening Files
Before compiling begins main() calls openfile() to open the first source file that might be specified in the command line (also an output file of the same name but with an ASM extension). Later, openfile() will be called, at a lower level, to look for the next source file when the current file has been exhausted.
Like ask(), openfile() calls getarg() repeatedly looking for file names (any argument not preceded by a hyphen). That failing, it sets input to the value of stdin, thereby establishing the default input device. (Recall that the standard input file may be redirected to any file or input device.) On the other hand, if it finds a filename, openfile() tries to open it for input. First, however, it supplies C as a default extension if none was given. If an input file was given, openfile() assumes that the output should go to a file of the same name, but with an extension of ASM--unless the standard output file was redirected from the screen, that is. Redirecting it implies that the user has other ideas, and so the output should be left alone. If openfile() cannot open a file, it displays an error message and aborts the run.
After opening the first input file, main() calls preprocess() to fetch the first input line for parsing.
Controlling Program Flow
With these preliminaries out of the way, main() calls five functions to effect high level control over the compiler. In order of execution, they are as follows: