所以,我试图在flex / bison中创建一个简单的C语法分析器,我只需要解析函数和变量声明及其用法。
示例,使用yyin = fopen()我想解析这个.c文件:
#include <stdio.h>
int main()
{
int firstNumber, secondNumber, sumOfTwoNumbers;
printf("Enter two integers: ");
// Two integers entered by user is stored using scanf() function
scanf("%d %d", &firstNumber, &secondNumber);
// sum of two numbers in stored in variable sumOfTwoNumbers
sumOfTwoNumbers = firstNumber + secondNumber;
// Displays sum
printf("%d + %d = %d", firstNumber, secondNumber, sumOfTwoNumbers);
return 0;
}
解析器应检测
int firstNumber, secondNumber, sumOfTwoNumbers;
作为变量声明,并计算变量的每次使用。
我已经可以这样做了,事情是,我只需要解析那些特定情况,而不是像“=,+”标记或//注释那样,但它们可以在文件中。
我希望有一种方法可以忽略每个令牌但是那些匹配规则的令牌,以便yyparse在无法识别令牌时不会调用yyerror,所以解析文件的时候我只做函数/ var声明的动作,其他所有内容都可以顺利运行直到EOF。
答案 0 :(得分:0)
您的第一个要求相对容易满足:C中的每个变量声明都以说明符和限定符列表开头,因此您的规则可能如下所示:
var_declaration: spec_or_qual_list identifiers ';' { ... }
以及一些规则,例如
func:
spec_or_qual_list identifier '(' well_nested_tokens ')'';' {...}
| spec_or_qual_list identifier
'(' well_nested_tokens ')''{' body_tokens '}' {...}
| other_token well_nested_tokens ';' { ... process uses ... }
body_tokens:
%empty {...}
| body_tokens var_declaration {...}
| body_tokens func {...}
请注意,上述简单规则只能解析“平面”问题。 C文件就像你在问题中给出的那样(没有结构声明的函数和声明列表或者函数体之外的其他块)。
一旦你决定添加块,你就必须添加类似于上面func
的规则,这样你就可以递归下降到块并解析那里的声明。你不能简单地忽略它们,因为那样你就会错过块之后可能出现的声明的开头。如果你让结构进入,你有一个更难以区分结构成员和变量的任务(或者你可能不希望在哪种情况下结构可以作为块处理,仅在语法上,因为范围规则是非常不同的)。请注意,所有这些方法都忽略了作用域规则,因此,在您的情况下,您将无法跟踪变量与其声明之间的关联(因为变量可以在块内重新声明为完全不同的东西)。最后,如果你允许使用typedef名称,那么所有的地狱都会崩溃(查找&#39; lexer hack&#39;)你也可以写一个完整的解析器。
所有这些的道德是:如果你试图解析的文件有任何类型的非平凡结构,你最终将解析C语法的重要部分。我可以建议的另一个简化技巧是为C 表达式编写一个(完整)解析器并使用它来解析C 声明符(例如(* pfunc)(int)
)。这不适用于所有C11声明者,但会处理大多数普通的声明。那些。你仍然需要处理块。