We have no idea on how to track errors in yacc parser.
We're trying to use yylineno
in our lex file and tried adding %option yylineno
but it's still not workin', we cannot access these variables in yacc.
All we want is to print out the syntax error using the error
in yacc together with the line number.
here's our .l
file
%{
#include <stdio.h>
#include <stdlib.h>
#include "y.tab.h"
int yylineno=1;
%}
%option yylineno
identifier [a-zA-Z_][a-zA-Z0-9_]*
int_constant [0-9]+
delimiter ;
%%
"int" {return INT;}
{int_constant} return INT_CONST;
{identifier} return IDENT;
\= {return ASOP;}
\+ {return PLUS;}
\- {return MINUS;}
\* {return MULT;}
\/ {return DIV;}
\, {return COMMA;}
\( {return OP;} /*OP CP = Opening Closing Parenthesis*/
\) {return CP;}
\[ {return OB;} /*OB CB = Opening Closing Brace*/
\] {return CB;}
\{ {return OCB;} /*OCB CCB = Opening Closing Curly Brace*/
\} {return CCB;}
{delimiter} return DEL;
[ \t]
[\n] {yylineno++;}
%%
now here's our .y
file
%{
#include <stdio.h>
#include <string.h>
#include "y.tab.h"
extern FILE *yyin;
%}
%token INT INT_CONST IDENT ASOP PLUS MINUS MULT DIV DEL COMMA CP CB CCB
%left OP OB OCB
%%
program: program_unit;
program_unit: program_unit component | component
component: var_decl DEL | func_decl DEL | func_defn ;
var_decl: dt list;
dt: INT;
list: list COMMA var | var
| error {printf("before ';' token\n"); yyerrok;}
| error INT_CONST {printf("before numeric constant\n"); yyerrok;};
var: IDENT
|IDENT init;
init: ASOP IDENT init | ASOP expr | ASOP IDENT ;
expr: IDENT op expr | const op expr | const | OP expr CP;
const: INT_CONST;
op: PLUS | MINUS | MULT | DIV;
func_decl: dt mult_func;
mult_func: mult_func COMMA mfunc | sfunc;
mfunc: IDENT OP CP;
sfunc: IDENT OP CP OCB func_body CCB;
func_body: program_unit;
func_defn: dt IDENT OP CP OCB func_body CCB
| IDENT OP CP OCB func_body CCB;
%%
int yyerror(char *s){
extern int yylineno;
fprintf(stderr,"At line %d %s ",s,yylineno);
}
int yywrap(){
return 1;
}
int main(int argc, char *argv[]){
yyin=fopen("test.c","r");
yyparse();
fclose(yyin);
return 0;
}