final version

This commit is contained in:
kaashoek 1988-05-16 13:16:03 +00:00
parent 1099f24bbf
commit a3ad389064

View file

@ -15,7 +15,11 @@ Amsterdam, The Netherlands
Introduction
.PP
A \fBcode expander\fR (\fBce\fR for short) is a part of the
Amsterdam Compiler Kit (\fBACK\fR) and provides the user with
Amsterdam Compiler Kit
.[
toolkit
.]
(\fBACK\fR) and provides the user with
high-speed generation of medium-quality code. Although conceptually
equivalent to the more usual \fBcode generator\fR, it differs in some
aspects.
@ -24,7 +28,7 @@ Normally, a program to be compiled with \fBACK\fR
is first fed to the preprocessor. The output of the preprocessor goes
into the appropriate front end, which produces EM
.[
Tanenbaum toolkit
block
.]
(a
machine independent low level intermediate code). The generated EM code is fed
@ -131,10 +135,10 @@ routines from the EM_CODE interface that generate object code directly.
.PP
As already indicated, the compound table does not exist either. Instead, each
assembly instruction in the as_table is converted to a routine generating C
code
.[
Kernighan
.]
code
to generate C code to call the \fBback\fR-primitives. The EM_table is
converted into a program that for each EM instruction generates a routine,
using the routines generated from the as_table. Execution of the latter program
@ -647,7 +651,7 @@ When the code expander generator is used for generating assembly instead of
object code (see section 5), not all the above mentioned constants
and functions have to
be defined. In this
case, the constants ``BYTES_REVERSED'' and ``WORDS_REVERSED'' are not used.
case, the constants ``BYTES_REVERSED'' and ``WORDS_\%REVERSED'' are not used.
.NH 1
Description of the as_table
.PP
@ -796,7 +800,10 @@ PUSH src ==> /* save in ax */
mov_instr( AX_oper, src);
/* set flag */
@assign( push_waiting, TRUE).
\fR
.DE
.DS
\f5
POP dst ==> @if ( push_waiting)
/* ``mov_instr'' is asg-generated */
mov_instr( dst, AX_oper);
@ -858,7 +865,7 @@ the type of the operand in the following way.
center tab(#);
l c l.
reference#::=#``%'' conversion
##``('' operand-name ``\(->'' field-name ``)''
##``('' operand-name ``\->'' field-name ``)''
conversion#::=# printformat
#|#``$''
#|#``dist''
@ -983,9 +990,10 @@ and ``references'' (see 4.2.4) also work in the functions defined in ``as.c''.
.PP
The following example shows the representative and essential parts of the
8086 ``as.h'' and ``as.c'' files.
.DS L
.nr PS 10
.nr VS 12
.LP
.DS L
\f5
/* Constants and type definitions in as.h */
@ -1027,12 +1035,13 @@ struct t_operand {
extern struct t_operand saved_op, *AX_oper;
\fR
.DE
.nr PS 12
.nr VS 14
.DE
.DS L
.LP
.nr PS 10
.nr VS 12
.DS L
\f5
/* Some functions in as.c. */
@ -1045,19 +1054,6 @@ extern struct t_operand saved_op, *AX_oper;
#define RIGHT ')'
#define DOLLAR '$'
process_label( l)
char *l;
{
}
process_mnemonic( m)
char *m;
{
}
process_operand( str, op)
char *str;
struct t_operand *op;
@ -1107,74 +1103,74 @@ struct t_operand *op;
* Note the $-operators
*/
{
if ( REG( op))
R233( 0x3, reg, op->reg);
else if ( ADDR( op)) {
R233( 0x0, reg, 0x6);
@reloc2( %$(op->lab), %$(op->off), ABSOLUTE);
}
else if ( strcmp( op->expr, "0") == 0)
switch( op->reg) {
case SI : R233( 0x0, reg, 0x4);
break;
if ( REG( op))
R233( 0x3, reg, op->reg);
else if ( ADDR( op)) {
R233( 0x0, reg, 0x6);
@reloc2( %$(op->lab), %$(op->off), ABSOLUTE);
}
else if ( strcmp( op->expr, "0") == 0)
switch( op->reg) {
case SI : R233( 0x0, reg, 0x4);
break;
case DI : R233( 0x0, reg, 0x5);
break;
case DI : R233( 0x0, reg, 0x5);
break;
case BP : R233( 0x1, reg, 0x6); /* exception! */
@text1( 0);
break;
case BP : R233( 0x1, reg, 0x6); /* exception! */
@text1( 0);
break;
case BX : R233( 0x0, reg, 0x7);
break;
case BX : R233( 0x0, reg, 0x7);
break;
default : fprint( STDERR, "Wrong index register %d\n",
op->reg);
}
else {
@if ( fit_byte( %$(op->expr)))
switch( op->reg) {
case SI : R233( 0x1, reg, 0x4);
break;
default : fprint( STDERR, "Wrong index register %d\en",
op->reg);
}
else {
@if ( fit_byte( %$(op->expr)))
switch( op->reg) {
case SI : R233( 0x1, reg, 0x4);
break;
case DI : R233( 0x1, reg, 0x5);
break;
case DI : R233( 0x1, reg, 0x5);
break;
case BP : R233( 0x1, reg, 0x6);
break;
case BP : R233( 0x1, reg, 0x6);
break;
case BX : R233( 0x1, reg, 0x7);
break;
case BX : R233( 0x1, reg, 0x7);
break;
default : fprint( STDERR, "Wrong index register %d\n",
op->reg);
}
@text1( %$(op->expr));
@else
switch( op->reg) {
case SI : R233( 0x2, reg, 0x4);
break;
default : fprint( STDERR, "Wrong index register %d\en",
op->reg);
}
@text1( %$(op->expr));
@else
switch( op->reg) {
case SI : R233( 0x2, reg, 0x4);
break;
case DI : R233( 0x2, reg, 0x5);
break;
case DI : R233( 0x2, reg, 0x5);
break;
case BP : R233( 0x2, reg, 0x6);
break;
case BP : R233( 0x2, reg, 0x6);
break;
case BX : R233( 0x2, reg, 0x7);
break;
case BX : R233( 0x2, reg, 0x7);
break;
default : fprint( STDERR, "Wrong index register %d\n",
op->reg);
}
@text2( %$(op->expr));
@fi
}
default : fprint( STDERR, "Wrong index register %d\en",
op->reg);
}
@text2( %$(op->expr));
@fi
}
}
\fR
.DE
.nr PS 12
.nr VS 14
.DE
.NH 2
Generating assembly code
.PP
@ -1229,7 +1225,9 @@ tested (e.g., by running the compiler on the EM test set). If an error occurs,
change the EM_table and type
.IP
.br
\f5update\fR \fBC_instr\fR
\f5
update\fR \fBC_instr
\fR
.br
.LP
where \fBC_instr\fR stands for the name of the erroneous EM-instruction.
@ -1247,9 +1245,9 @@ Remove the ``ce'' and ``ceg'' directories.
Write the ``as_table'', ``as.h'', and ``as.c'' files.
.IP \0\03:
type
.br
.sp
\f5 install_ceg -obj \fR
.br
.sp
The option \f5-obj\fR means that ``back.a'' will contain a library
for generating
ACK.OUT(5ACK) object files, see appendix B.
@ -1264,16 +1262,14 @@ The as_table is ready to be tested. If an error occurs, adapt the table.
Then there are two ways to proceed:
.IP \0\01:
recompile the whole EM_table,
.br
\f5
update ALL
\fR
.sp
\f5 update ALL \fR
.sp
.IP \0\02:
recompile just the few EM-instructions that contained the error,
\f5
.br
update \fBC_instr\fR
.br
.sp
\f5 update \fBC_instr\fR
.sp
where \fBC_instr\fR is an erroneous EM-instruction.
This has to be done for every EM-instruction that contained the erroneous
assembly instruction.