EMPLOYING A STRUCTURE

FOR THE ELEMENTS OF SYMBOL STACK

In both Lex and Yacc employ the following #defines:

typedefstruct {

int kind_of_location;

int location; } yystype;

#define YYSTYPE yystype

#define SYMREF 0 /* short for symbol table reference */

#define REGISTER 1

IN LEX

Let the code associated with the r.e. for an identifier set:

yylval.kind_of_location = SYMREF;

yylval.location = (the index into symbol list for the identifier) ;

The code associated with other r.e.'s do not need to set the values of these yylval components.

IN YACC

#define SYMREF_SYMREF 0

#define SYMREF_REGISTER 1

#define REGISTER_SYMREF2

#define REGISTER_REGISTER3

int registerstack[ ] = {9, 11, 14, 15} /* the codes defined for CX, BX, SI, DI */

int registerstack_i = 4;

int reg;

The code for e.g.: expression → expression + term

switch($1.kind_of_location*2 + $3.kind_of_location) {

case SYMREF_SYMREF:

reg = getreg(); /* see below for sample code */

move(reg, DIRECT, symbol_table[$1.location].offset); /* move & add */

add(reg, DIRECT, symbol_table[$3.location].offset);

$$.kind_of_location = REGISTER;

$$.location = reg;

break;

case SYMREF_REGISTER:

add($3.location, DIRECT, symbol_table[$1.location].offset);

$$ = $3;

break;

case REGISTER_SYMREF:

add($1.location, DIRECT, symbol_table[$3.location].offset);

break;

case REGISTER_REGISTER:

reg = $3.location;

add($1.location, reg, 0);

free(reg); /* see below for sample code */

break;

} /* end of switch for + */

The code for e.g.: expression → expression - term

The code is exactly the sames as that described above for

expression → expression + term,

except that all the occurrences of add should be replaced by sub, and the instruction neg($3) should be inserted before the call to add in the SYMREF_REGISTER case.

The code for: term → ( expression )

$$ = $2;

Note: No code is required in Yacc for: term → identifier

Sample code for getreg() and free(register)

int getreg() {

--registerstack_i;

return (registerstack[registerstack_i]);

}

void free(int Register) {

registerstack[registerstack_i] = Register;

++registerstack_i;

}

Machine code for multiplication

The general Assembler form of one of the imul instructions is:

imul reg, other-argument

The “reg” refers to a 16-bit register (coded as defined in the handout in machine instructions) and “other-argument” is an argument of any type except immediate. The calculation involved is of the form:

reg = reg * other-argument

The machine code is:

0Fh AFh mod reg r/m displ. low displ. high

where mod, r/m, and the optional fields displ, low and displ. high are as defined in the handout on machine instructions