1

i've got a problem with my some of my rules of my grammar.

The grammar is like the following:

defLINES : carrRet
         | defLine carrRet
         | defLines defLine carrRet
         ;

defLine  : error carrRet                             {yyerrok();}
         | "DEF" kwType attrbt ID
         | "DEF" kwType ID fieldSuff
         ;

kwType   : "INT"
         | "REAL"
         ;

fieldSuff: "[" expr "]"
         | "[" expr "," expr "]"
         ;

attrbt   : /* nothing */
         | "PHU" intValue
         ;

With the Input to check:

DEF INT testvar1
DEF REAL testvar2

For this Input the second rule of the production with the head "defLine" should be used.

Why doesn't it? The third rule will always be used and throws an error

Unexpected 'carRet', '[' expected.

Thanks a lot for help, Alex

Alex
  • 369
  • 4
  • 16

1 Answers1

1

That grammar surely produced at least one shift/reduce conflict along with a warning that the production attrbt: /* nothing */ is useless because of the conflict. (If that's not the case, it's because GPPG doesn't provide as many warnings as bison. But I'm certain that it will at least flag the shift/reduce conflict.)

The conflict arises in the rules:

defLine  : "DEF" kwType attrbt ID
defLine  : "DEF" kwType ID fieldSuff

because attrbt can be empty, but cannot precede ID in the second rule. Suppose the parser has encountered DEF INT and the next symbol is ID. At this point, the parser does not know which of the two productions for defLine to use, but the difference matters. In the first case, the parser must reduce an empty attrbt before shifting the ID. In the second case, creating the attrbt would be a mistake.

Yacc-like parser generators always resolve shift/reduce conflicts in favour of shifting (unless there are precedence declarations), so in this case the ID will always be shifted. That means that it is impossible to ever reduce the production attrbt: /* nothing */. (Bison, at least, would warn you about this fact.

Furthermore, since the shift of ID will occur in that case, only the second production for defLine will be available, so the parser will require fieldStuff to follow the ID, and fieldStuff must start with [. Hence the parsing error you encounter.

To fix this, you need to remove the shift/reduce conflict. One simple way would be to allow attrbt in both defLine productions (you can detect the error in the semantic action). Another possibility is to remove the empty production for attrbt and explicitly allow it to be missing:

attrbt   : "PHU" intValue

defLine  : "DEF" kwType ID
         | "DEF" kwType attrbt ID
         | "DEF" kwType ID fieldSuff
rici
  • 234,347
  • 28
  • 237
  • 341
  • Ok, thank you for your great help! I decided to solve the problem in the semantic Action and allow the attrbt. Thanks... =) – Alex Apr 08 '16 at 13:39