Bison:syntax error at the end of parsing -
hello bison grammar file mini-programming language:
%{ #include <stdlib.h> #include <stdio.h> #include <math.h> #include "projectbison.tab.h" void yyerror(char const *); extern file *yyin; extern file *yyout; extern int yylval; extern int yyparse(void); extern int n; int errnum = 0; int fornum = 0; %} %left plus minus %left mult div mod %nonassoc equal nequal less greater lequal gequal %token integer boolean string void %token id %token , %token beginp %token endp %token extern %token comma %token eq %token return1 %token if1 else1 while1 for1 do1 %token lor land lnot %token true false %token equal nequal less greater lequal gequal %token lb1 rb1 %token lcb1 rcb1 %token semic %token newline %token plus minus %token mult div mod %token digit string1 %start program %% /*50*/ program : external-decl program-header defin-field command-field ; external-decl : external-decl external-prototype | ; external-prototype : extern prototype-func newline ; program-header : void id lb1 rb1 newline ; defin-field : defin-field definition | ; definition : variable-defin | func-defin | prototype-func ; variable-defin : data-type var-list semic newline ; data-type : integer | boolean | string ; var-list : id extra-ids ; extra-ids : comma var-list | ; func-defin : func-header defin-field command-field ; prototype-func : func-header semic ; func-header : data-type id lb1 lists rb1 newline ; lists: list-typ-param | ; list-typ-param : typical-param typical-params ; typical-params : comma list-typ-param | ; typical-param : data-type , id ; command-field : beginp commands newline endp newline ; commands : commands newline command | ; command : simple-command semic | struct-command | complex-command ; complex-command : lcb1 newline command newline rcb1 ; struct-command : if-command | while-command | for-command ; simple-command : assign | func-call | return-command | null-command ; if-command : if1 lb1 gen-expr rb1 newline command else-clause ; else-clause: else1 newline command ; while-command : while1 lb1 gen-expr rb1 do1 newline rcb1 command lcb1 ; for-command : for1 lb1 conditions rb1 newline rcb1 command lcb1 ; conditions : condition semic condition semic condition semic ; condition : gen-expr | ; assign : id eq gen-expr ; func-call : id lb1 real-params-list rb1 | id lb1 rb1 ; real-params-list : real-param real-params ; real-params : comma real-param real-params | ; real-param : gen-expr ; return-command : return1 gen-expr ; null-command : ; gen-expr : gen-terms gen-term ; gen-terms : gen-expr lor | ; gen-term : gen-factors gen-factor ; gen-factors : gen-term land | ; gen-factor : lnot first-gen-factor | first-gen-factor ; first-gen-factor : simple-expr comparison | simple-expr ; comparison : compare-operator simple-expr ; compare-operator : equal | nequal | less | greater | lequal | gequal ; simple-expr : expresion simple-term ; expresion : simple-expr plus |simple-expr minus | ; simple-term : mul-expr simple-parag ; mul-expr: simple-term mult | simple-term div | simple-term mod | ; simple-parag : simple-prot-oros | minus simple-prot-oros ; simple-prot-oros : id | constant | func-call | lb1 gen-expr rb1 ; constant : digit | string1 | true | false ; newline:newline | ; %% void yyerror(char const *msg) { errnum++; fprintf(stderr, "%s\n", msg); } int main(int argc, char **argv) { ++argv; --argc; if ( argc > 0 ) {yyin= fopen( argv[0], "r" ); } else {yyin = stdin; yyout = fopen ( "output", "w" );} int = yyparse(); if(a==0) {printf("done parsing\n");} else {printf("yparxei lathos sti grammi: %d\n", n);} printf("estimated number of errors: %d\n", errnum); return 0; }
for simple input :
void main() integer k; boolean l; begin aek=32; end
i following :
$ ./myparser.exe file2.txt void , id ,left bracket , right bracket integer , id ,semicolon boolean , id ,semicolon begin program id ,equals , digit ,semicolon end program syntax error yparxei lathos sti grammi: 8 estimated number of errors: 1
and whatever change make input file syntax error @ end....why , can do??thanks lot in advance!here flex file in case needs :
%{ #include "projectbison.tab.h" #include <stdio.h> #include <stdlib.h> #include <string.h> int n=1; %} %option noyywrap digit [0-9]+ id [a-za-z][a-za-z0-9]* %% "(" {printf("left bracket , "); return lb1;} ")" {printf("right bracket\n"); return rb1;} "{" {printf("left curly bracket , "); return lcb1;} "}" {printf("right curly bracket\n"); return rcb1;} "==" {printf("isotita ,"); return equal;} "!=" {printf("diafora ,"); return nequal;} "<" {printf("less_than ,"); return less;} ">" {printf("greater_than ,"); return greater;} "<=" {printf("less_eq ,"); return lequal;} ">=" {printf("greater_eq ,"); return gequal;} "||" {printf("lor\n"); return lor;} "&&" {printf("land\n"); return land;} "&" {printf("and ,"); return and;} "!" {printf("lnot ,"); return lnot;} "+" {printf("plus ,"); return plus; } "-" {printf("minus ,"); return minus;} "*" {printf("multiply ,"); return mult;} "/" {printf("division ,"); return div;} "%" {printf("mod ,"); return mod;} ";" {printf("semicolon \n"); return semic;} "=" {printf("equals , "); return eq;} "," {printf("comma ,"); return comma;} "\n" {n++; return newline;} void {printf("void ,"); return void;} return {printf("return ,"); return return1;} extern {printf("extern\n"); return extern;} integer {printf("integer ,"); return integer;} boolean {printf("boolean ,"); return boolean;} string {printf("string ,"); return string;} begin {printf("begin program\n"); return beginp;} end {printf("end program\n"); return endp;} {printf("for\n"); return for1;} true {printf("true ,"); return true;} false {printf("false ,"); return false;} if {printf("if\n"); return if1; } else {printf("else\n"); return else1; } while {printf("while\n"); return while1;} {id} {printf("id ,"); return id;} {digit} {printf("digit ,"); return digit;} [a-za-z0-9]+ {return string1;} ` {/*catchcall*/ printf("mystery character %s\n", yytext); } <<eof>> { static int once = 0; return once++ ? 0 : '\n'; } %%
your scanner pretty guarantees 2 newline characters sent @ end of input: 1 newline present in input, , 1 result of trapping <<eof>>
. however, grammar doesn't appear accept unexpected newlines, second newline trigger syntax error.
the simplest solution remove <<eof>>
rule, since text files without terminating newline rare, , entirely legitimate consider them syntax errors. more general solution allow number of newline characters appear newline expected, defining like:
newlines: '\n' | newlines '\n';
(using actual characters single-character tokens makes grammar much more readable, , simplifies scanner. that's side issue.)
you might ask whether need enforce newline terminators, since grammar seems use ;
statement terminator, making newline redundant (aside stylistic considerations). removing newlines grammar (and ignoring them, other whitespace, in scanner) simplify code.
Comments
Post a Comment