声明与GCC和Flex / Bison无效警告

时间:2009-10-30 12:56:29

标签: c bison yacc lex flex-lexer

使用gcc和-Wall选项编译我的项目时,我收到一条警告,说明在我的flex文件的不存在的最后一行中没有效果的语句:

警告:

gcc -Wall -O0 -ggdb3 -DNOSUDO -DJOBC -DDEBUG -c lex.yy.c
tokenizer.l: In function ‘yylex’:
tokenizer.l:179: warning: statement with no effect

Shell命令:

$ wc -l tokenizer.l
178 tokenizer.l

lex文件的最后一部分:

; {
    return SEMI;
}

任何人都知道为什么我会收到此警告?

如果我取消所有#line指令,则错误为:

lex.yy.c: In function ‘yylex’:
lex.yy.c:1021: warning: statement with no effect

其中指的是ECHO项目:

case 30:
YY_RULE_SETUP
ECHO;
    YY_BREAK
case YY_STATE_EOF(INITIAL):
case YY_STATE_EOF(inQuote):
case YY_STATE_EOF(inWord):
    yyterminate();

4 个答案:

答案 0 :(得分:5)

一般情况下,你会从任何包含无条件'return'的lex规则中得到错误,因为flex最终生成的代码看起来像(在宏扩展之后):

case xxx:
    return SEMI;
    break;

问题在于“休息”无法到达。它需要存在,以防你的规则没有返回(因此代码不会落入下一个令牌的代码,而是继续识别下一个令牌。)Flex不够智能,无法实际解析您的规则代码并进行流分析以确定何时不需要中断,因此它始终将其放在那里。一般来说,在flex(或bison)的输出上使用-Wall会给你很多警告......

答案 1 :(得分:2)

我觉得;是一个没有效果的陈述。试着引用它:

";" {
    return SEMI;
}

答案 2 :(得分:1)

我遇到了同样的问题并且看了一下。事实证明,我在flex源文件(.l文件)中的一个“#includes”间接地包含了标准库termios.h文件,该文件定义了一个名为“ECHO”的宏(作为“0000010”)。 另一方面,flex生成的源文件也想创建一个名为“ECHO”的宏,之前有一个“#ifndef ECHO”。但当然,包含termios.h,“ifndef”评估为false,而ECHO未定义为预期。这导致了错误。

长解释,简短解决方案:我把

#ifdef ECHO
#undef ECHO
#endif

低于我的.l文件中的所有包含,这就是诀窍。

我知道这个讨论主题已经有点老了,但是当我搜索警告时它首先出现了,所以我的贡献可能对人们有用。

答案 3 :(得分:0)

正如其他答案所说,问题是“回归”后的'休息'无法达到。

过去可以满足编译器,通过伪造条件返回来找到“中断”的方法:

if (1) return SEMI;

我怀疑一些现代编译器是否足够聪明才能看清楚这一点 - 这实际上是适得其反。 “是的,你是对的,Compiler先生,但我无法避免这样STFU”。