Collectives™ on Stack Overflow
Find centralized, trusted content and collaborate around the technologies you use most.
Learn more about Collectives
Teams
Q&A for work
Connect and share knowledge within a single location that is structured and easy to search.
Learn more about Teams
I'm begginer to Yacc programming and I have an easy task to write a program, which checks whether an input text file
contains a sequence of correctly paired parentheses. Any incorrect sequence
should be signaled as "Syntax error!". I use bison and flex.
Example correct data:
(()()((())())())
is incorrect.
My problem is that I think it should work, but it seems like yyerror is not working. Maybe I'm doing something wrong, please correct me.
Here's my code
Yacc code:
int yylex();
void yyerror(char* x);
S: S A
A: '('S')'
|'(' ')'
And the lex code:
#include "y.tab.h"
[\(\)] return(yytext[0]);
. {printf("%c - error!\n",yytext[0]);}
void yyerror(char* x)
printf("syntax error");
exit(1);
So the problem is that it doesn't fire a syntax error, it doesn't matter how much parentheses I write.
edit:
Here's how I compile it:
screen
–
You need to provide a
main()
function which (at the minimum) calls
yyparse()
. Otherwise, the
main
from
libfl
will be used. That
main
does not call
yyparse()
; rather, it repeatedly calls
yylex
until an EOF is signalled. (
libfl
is part of Flex, not bison, so it cannot rely on
yyparse
even existing.)
There is really no need to link with
-lfl
. The
main()
definition there is not useful to you and the only other thing in the library is a dummy definition of
yywrap()
. You don't define
yywrap()
, so the library function will be called; however, rather than depending on the library, you could simply add
%option noyywrap
to your flex code (just before the %%
), and then the generated scanner will not call yywrap()
.
There is also no need to use the -y
flag when you invoke bison. The only reason to use -y
is to be able to process legacy yacc files with bison. I suppose you are using the flag so that that generated parser is called y.tab.c
; without the flag, it would be called z5.tab.c
(and the header file will be z5.tab.h
); you could just use those names. (Or you could tell bison the precise filename you would like it to use, by using the -o
flag.)
Finally, two notes about your lex file:
The pattern for parentheses could just be written:
[()] { return yytext[0]; }
There is no need to backslash-escape parentheses inside a character class, because no characters other than ]
, -
and \
have special meaning inside a character class.
The pattern .
does not match a newline character, which is why the newline characters in your input are not producing error messages. In fact, none of your patterns match the newline character, so when you type a newline, the default rule is invoked. The default rule is equivalent to ECHO
, which bison defines to be something like:
fputs(yytext, yyout);
(or fprintf(yyout, "%s", yytext);
)
That's why an extra newline is output when you type a newline.
–
–
–
–
Thanks for contributing an answer to Stack Overflow!
- Please be sure to answer the question. Provide details and share your research!
But avoid …
- Asking for help, clarification, or responding to other answers.
- Making statements based on opinion; back them up with references or personal experience.
To learn more, see our tips on writing great answers.