Due: Electronic turnin of entire compiler, including test output and written report, due Sunday, Dec. 10, by 11:00 pm.
You may work with a partner on this assignment. If you have a partner from the previous compiler assignments, you should continue working with that person.
For this assignment, add code generation to your compiler. When the finished compiler is executed, it should open a D source program file, compile it, and produce a .s assembler text file containing an x86 assembly language version of the D program. Source lines from the D file, including comments and whitespace, should appear as comments in the assembler code, with each source line near the code generated from it.
Most of the work in this assignment consists of adding new code to the existing parser. While you might find it useful to create some extra functions or data structures, the bulk of the changes will be additions to existing parser functions. A separate handout contains details about code generation for D programs.
The easiest way to run the compiled x86 code
is to call it from a trivial C program as if it were an ordinary function. That
ensures that the stack is properly set up when the compiled code begins executing,
and provides a
convenient place to put functions that provide an interface between the compiled
code and the
external world (get
and put
).
The bootstrap program is named druntime.c (right click on the file name to download a copy). You should use this program to run your compiled code. The file contains the get and put functions as well as the main program. Here is the key part that executes your compiled code.
int d$main(); /* prototype for external function */ int main() { printf("\nValue returned from D main: %d.\n", d$main()); return 0; }
A key point is that the "real" main program is here. The main function in
your compiled code should have a label with the name d$main
, and that name
should appear in a .globl
declaration in the compiled code to make it visible
to the bootstrap program.
The output of your compiler is an ordinary text file. It can have any name you would like, but it is customary on Unix systems to give assembler source files a name ending with ".s".
Assuming that your compiled code is stored in a file named, e.g., code.s
,
you can use gcc to assemble this file, compile the bootstrap file, and load
the result with a single command:
gcc code.s runtime.c
That produces
an ordinary a.out
file on linux systems contining the complete program,
which can be run normally.
As with previous assignments, it's helpful to figure out what piece of the compiler can be done first, without having to finish everything at once. Here are some suggestions.
To get going, try implementing just enough to generate labels for functions
and the ret
instruction that ends a return statement. That should
be enough to generate a text (.s
) file containing an empty main
program that can be called and return to the bootstrap without crashing.
Once you've done that, try implementing factor()
for integer
constants. Then return statements with constant values should work. From
there you could implement arithmetic operations, which gives you return statements
with expressions involving constants. You can test the code by writing small
programs each of which has a main methods with a different return expression.
The next big step could be to figure out the details of stack frame layouts and the offsets assigned to parameters and local variables. Check your work by compiling some sample programs, print the local symbol tables, and verify that the offsets are correct. From there you should be able to add assignment statements and expressions (factors) that include integer variables.
There are several possible ways to go from here. Probably the most useful
is to get function prologues and epilogues (the rest of return) to work.
At this point you should have straight-line code with function
calls, including calls to get
and put
, working properly.
Finally, look at code generation for conditions (rel-exp and bool-exp) and
if
and while
statements. The issues here are getting the labels planted in
the right place, and picking the right conditional jumps to the correct labels.
Several D test programs are available from the
course web. Feel free to create additional tests to demonstrate or debug
your compiler. If you create any new test programs, please feel free to
share them with others or contribute them to the collection on the course web
(send mail to cse413-staff@cs
).
Turn in the following electronically using this online turnin form. The electronic turnin should include all of the source code for your compiler, as well as test cases, output, and your written report. Include: