01.03.2015 Views

Modern compiler design [PDF]

Modern compiler design [PDF]

Modern compiler design [PDF]

SHOW MORE
SHOW LESS

Create successful ePaper yourself

Turn your PDF publications into a flip-book with our unique Google optimized e-Paper software.

%{<br />

#include <br />

#include "errors.h" /* Definition of global variable current_line_number, */<br />

/* whose value is set by the lexer */<br />

void yyerror(char *s) {<br />

fprintf(stderr,"line %d, %s \n",current_line_number, s);<br />

}<br />

%}<br />

%token PLUS MINUS TIMES DIVIDE IDENTIFIER<br />

%%<br />

exp : exp PLUS term<br />

| exp MINUS term<br />

| term<br />

term : term TIMES IDENTIFIER<br />

| term DIVIDE IDENTIFIER<br />

| IDENTIFIER<br />

Figure 5.2: A yacc .grm file that deals with errors in a more elegant fashion<br />

5.1.3 Tokens With Values<br />

So far, we have ignored the values of tokens. Many tokens – such as PLUS, MINUS, and IF, do not need<br />

values, while other tokens – such as INTEGER LITERAL and IDENTIFIER, do need values. Our lexical<br />

analyzer actually gave values to all tokens – each token was tagged with the line number on which that token<br />

appeared. While we won’t be using the values of the tokens just yet, we do need to tell yacc which tokens<br />

have values, and what those values are. First, we have to let yacc know what the possible token values are.<br />

We do this with a %union declaration in the yacc definitions segment of the file. For instance, a<br />

%union {<br />

int integer_value;<br />

char *string_value;<br />

}<br />

declaration in the yacc definitions segment of the file tells yacc that some of the tokens will have int<br />

values, and some will have char * values. We now need to tell yacc which of the tokens can have what<br />

values. A simple change to the token declarations does this for us. Consider the .grm file in Figure 5.3. The<br />

token ID has the value char *, the token INTEGER LITERAL has the value int, and all other tokens have<br />

no values.<br />

Figure 5.4 shows a yacc file with that handles tokens with more complicated values, like those in the<br />

programming project.<br />

5.1.4 When Yacc Has Conflicts<br />

Not all grammars are LR(1).Occasionally, when building the LR parse table, yacc will find duplicate entries.<br />

There are two kinds of duplicate entries – shift-reduce conflicts and reduce-reduce conflicts. We will look at<br />

each in turn<br />

Shift-Reduce Conflicts<br />

Shift-reduce conflicts arise when yacc can’t determine if a token should be shifted, or if a reduce should be<br />

done instead. The canonical example of this problem is the dangling else. Consider the following two rules<br />

23

Hooray! Your file is uploaded and ready to be published.

Saved successfully!

Ooh no, something went wrong!