Bison/Flex声明混乱......我应该如何包含/声明在哪里?

Emi*_*son 7 include bison flex-lexer

我正在使用Bison和Flex来制作一个可重入的扫描器/解析器对,但无法将我的头包裹在所有要包含和声明的内容中.

首先,我正在使用可重入的Flex,因此我需要首先将yyscan_t扫描仪类型传递给Bison %parse-param {yyscan_t scanner},然后通过声明将Bison传递给Flex %lex-param {yyscan_t scanner}.但是yyscan_tBison没有声明,所以我必须在我的Bison文件中包含Flex生成的扫描程序头文件(我将其命名为scanner.flex.h).但由于我的Flex文件包含了我的Bison标题,而我的Bison标题现在包含了Flex标题,因此我得到循环包含以不可预测的方式混淆内容!

让我们说我想%locations在我的Bison文件和%bison-locations我的Flex文件中添加位置跟踪.现在我需要更改我的yyerror和yylex的声明(似乎我必须定义yylex AGAIN,即使它是在Flex生成的头中定义的但我不能包括那个,记得吗?)我的Bison文件中的函数包含YYLTYPE指针.但现在呢?似乎在插入序言之后放置了默认的YYLTYPE声明,因此我不能在我的yyerror和yylex的声明中使用这个默认的YYLTYPE.

我意识到这些问题有很多变通方法......但是你应该怎么做呢?它完全逃脱了我,这只是让我头晕目眩......

Joe*_*Joe 4

在野牛文件的顶部,您需要转发声明这些值。您可以在包含 flex 和 bison 文件之前在公共标头或代码文件中执行此操作。yyscan_t只是 void * 的 typedef,所以我将参数声明为 void 指针以使其正常工作。

通用头文件.h

int yylex (union YYSTYPE * yyval_param, struct YYLTYPE * yylloc_param, void * yyscanner);
int yyerror(struct YYLTYPE * yylloc_param, void *scanner, const char *s);
Run Code Online (Sandbox Code Playgroud)

yy错误的示例

int yyerror(struct YYLTYPE * yylloc_param, void *scanner, const char *s)
{
    printf("*** Lexical Error %s %d.%d-%d.%d\n", s, 
         yylloc_param->first_line, yylloc_param->first_column, 
         yylloc_param->last_line, yylloc_param->last_column);
}
Run Code Online (Sandbox Code Playgroud)