I am writing a reEntrant parser using Bison, with lots of help from SO, but have really not tested the reEntrant part thoroughly. I just reviewed the .tab.c file generated by Bison and was suprised to see that all of the code in the sections such as %{ }% or the various %code sections is global. I was expecting them to be local to yyparse().
I presume that any variables to be used locally in the parser must be passed using %parse-param.
Surprisingly the documentation of %code does not make any reference to reEntrant usage.
Example:
%{
mystruct *someStruct;
}%
So multiple invocations of yyparse() would refer to the same variable (storage). To get around this, I would have to create a
%parse-param myStruct *someStruct;
And then modify yyparse() and yyerror() invocations with the additional argument which is potentially passed through from the wrapper function that invokes yyparse() so that it is truly local.
Is my observation correct?
Yes, that's correct.
Bison only ensures that it's own code uses no globals. There is, unfortunately, no mechanism for adding local variables to the parser other than passing them as an additional parameter. This is true even if you use a push-parser (which I strongly recommend), which has an explicit parser context object.
If you use the C++ interface, you'll find other possibilities, since in that API the generated parse function is a member function of an extendable class.
For what it's worth, I don't find it surprising that the %code
documentation makes no mention of the reentrant API, since the primary purpose of %code
sections is to hold declarations and preprocessor directives. (Particularly true of the %code
sections which are copied into the generated header file.) But documentation bugfixes are always welcome (as I understand it).