Copyright © 1998, 2001 by Ian Horswill, see comment within this file.

Girl compiler interface

Calling the GRL compiler

The GRL compiler works by:

The generated code can either be run inside of scheme48 itself or written as a text file for input to a C or BASIC compiler.  After compilation, GRL code requires a small amount of run-time support for things like checking the system clock.

Until back-end code generation, the code is represented in a subset of Scheme called the intermediate language.  Intermediate code is non-recursive and doesn't perform any run-time type checking or storage allocation.   That is to say it might as well be C.  The back-end code generators are largely just pretty-printers that know, for example to print (set! x 4) as x=4.

The GRL compiler is split between several interlocking Scheme packages:

Compilation procedures are called with a list of roots.  Roots can be signals, lists of signals, lists of lists of signals, etc.  They're called roots because the compiler performs a depth-first search of the graph of all signals, starting from the roots.  Any signal that is encountered in the process of the walk is emitted as intermediate code.  Other signals are ignored.  Therefore, a library can define thousands of signals, but only those signals needed for the computation of the roots will actually appear in the compiled code.

Package GRL-top-level

The GRL-top-level package provides access to a set of procedures that allow you compile intermediate code from a list of roots.  Since they generate intermediate code, they are mostly useful for examining the code being generated by the compiler.   When compiling code for real, you will most likely use a back end tailored for your specific robot or target language.

(compile roots  ...)
Compiles roots to Scheme intermediate code and displays it on the screen or in the output file specified by the :output-file compiler option.
(compile-to-file file-name  roots  ...)
Compiles roots to Scheme intermediate code and writes it  to output-file.
(compile-and-run roots  ...)
Compiles roots to Scheme intermediate code and evals the code.  This lets you do limited testing on your desktop, or to run the GRL compiler directly on your robot if it supports Scheme48.  This is only useful if you have opened scheme48-run-time or some other package that provides the GRL run-time support. 

Package structure of the compiler

Package GRL-compiler

This package is mostly intended for programmers developing new back ends.   However, some of the options will also be useful for powerusers trying to tweak the code generated by the compiler.  The only procedure exported by the package that should be called by normal users is compiler-options.   It takes a list of keywords and values, a la Common Lisp.

User-level compiler options

:clock-period
:clock-frequncy
Specifies target frequency of main command loop.
:force-expression
Prevents inlining of some or all signals.  If #t, then no signals are inlined.   If 'roots, then only the signals specfied in the call the compiler will be prevented from being inlined.
:target-procedure-name
The name of the procedure that will contain the main while loop.
:temp-name-prefix
A string to be prepended to every temporary variable generated by the compiler.   Used to prevent name collisions when two different programs generated by the compiler are to be run in parallel.

Mostly used for compiler debugging

:show-raw-intermediate-code
Compiler pretty-prints Scheme intermediate code before partial evaluation.
:show-partially-evaluated-code
Compiler pretty-prints Scheme intermediate code after partial evaluation.
:show-expanded-signals
Compiles displays list of all signals encountered during its inital walk of the signal graph.
:show-sorted-signals
Compiles displays final sorted list of all primitive signals for which code is to be generated.

Internal compiler options

:code-printer
The procedure called to print the intermediate code
:output-file
The file to write the code to.  #f means write it to the screen.
:typed-declarations
Whether to add type information to variable declarations in the intermediate code
:global-variables
Forces all variables to be global
:generate-debug-info
Whether extra debugging information should be added to the object code
:generate-while-loop
Whether the code should be wrapped in a while loop
:never-inline-conditionals
Prevents if and nth calls from ever being inlined
:generate-lets
If false, lets will be changed into applications of lambdas.
:flatten-conditionals
Prevents if from being placed in an subexpressions.
:expand-cond
:expand-case
:expand-when-and-unless
Whether these should be translated into ifs.
:report-cycles
Whether the compiler should tell you about cycles in the signal graph