All, Spurred on by my growing expertise in using %dprec and %merge I returned to a problem I solved in a rather unsatisfactory way sometime ago.
I am trying to parse C source using a grammar that is as close to that given in the C standard as possible (the project is connected with the measurements I made for my C book, http://www.knosof.co.uk/cbook/usefigtab.pdf). Given the input: int f(p); (a common enough declaration in C source; think of replacing p by int) there are two possible parses: 1) the declaration of the function f returning int and having a single parameter, 2) the declaration of an object p to have type int f (where f is a typedef and ignoring the fact that this combinations is not semantically permitted). The () around p are redundant, something the syntax allows. I cannot get this ambiguity to go away without some fairly big changes to the grammar. I had thought of using %dprec in two different sets of productions, but this does not work as expected. Does anybody have any ideas? Have I simply exceeded the limits of what can currently be done using %dprec and %merge? ps. On this cut down example I also get a null pointer dereference at line 1616 of the generated .c file. %glr-parser %token INT IDENT %{ #include <ctype.h> #include <stdio.h> static const char *input = "I j(k);"; // int j(k); #define YYSTYPE char * #define YYDEBUG 1 static void yyerror (const char *s) { printf ("%s\n", s); } static int yylex (); %} %% TU: translation_unit { } ; translation_unit: declaration { } ; declaration: declaration_specifiers ';' %dprec 1 { } | declaration_specifiers init_declarator ';' %dprec 2 { } ; decl_specifier: type_specifier { } ; declaration_specifiers: decl_specifier { } | declaration_specifiers decl_specifier { } ; init_declarator: direct_declarator { } ; type_specifier: INT { } | typedef_name { } ; direct_declarator: IDENT %dprec 2 { } | '(' direct_declarator ')' { } | direct_declarator '(' identifier_list ')' { } ; identifier_list: IDENT { } | identifier_list ',' IDENT { } ; typedef_name: IDENT %dprec 1 { } ; %% static int yylex (void) { char c; c = (*input ? *input++ : 0); while (isspace(c)) c = *input++; asprintf (&yylval, "%c", c); printf("> %c\n", c); return (c == 'I') ? INT : (isalpha(c) ? IDENT : c); } int main (void) { yydebug=1; printf ("%i\n", yyparse ()); } -- Derek M. Jones tel: +44 (0) 1252 520 667 Knowledge Software Ltd mailto:[EMAIL PROTECTED] Applications Standards Conformance Testing http://www.knosof.co.uk _______________________________________________ help-bison@gnu.org http://lists.gnu.org/mailman/listinfo/help-bison