将整数分配给枚举时如何获得警告?

How to get a warning when assigning integer to enum?

提问人:Szabolcs 提问时间:8/13/2022 最后编辑:Szabolcs 更新时间:9/5/2022 访问量:591

问:

有没有办法让 Clang 或 GCC 在将普通整数分配给枚举类型的变量时发出警告?这个问题指的是 C,而不是 C++。

例:

typedef enum foo_e { A=1, B=2 } foo_t;

foo_t fun() {
    foo_t x = A; // this is fine
    foo_t y = 2; // should trigger a warning
    int z = B;   // this is fine
    return 1;    // should trigger a warning, as the return type is foo_t
}

“经典”英特尔编译器会针对这些情况发出警告:警告 #188,“枚举类型与另一种类型混合”。这揭示了我们代码中的几个真正的错误。然而,这是一个由志愿者运行的开源项目,我们不可能定期使用这个非自由编译器进行测试,也无法将其集成到 CI 管道中。在看到这些检查的价值后,我想知道是否有办法通过 Clang 或 GCC 获得它们。

C GCC 枚举 Clang 警告

评论

0赞 Some programmer dude 8/13/2022
这并不是无效的。枚举和枚举常量实际上基本上只是普通整数。实际上,使用枚举作为按位标志,并使用按位 OR () 构造掩码或位集,然后分配给枚举类型的变量是很常见的。|
1赞 Szabolcs 8/13/2022
@Someprogrammerdude 不,它不是无效的。这并不意味着对此进行诊断没有用。
1赞 chux - Reinstate Monica 8/13/2022
@Szabolcs“枚举类型与另一种类型混合”看起来像是C++编译器警告。在 C 语言中,不是一个新类型。“should trigger a warning”对于 C 不正确。foo_t
1赞 Eric Postpischil 8/13/2022
@chux-ReinstateMonica:所以有一个解决方案。编写代码的该部分,以便将其编译为 C/C++。编译为 C++ 以检查警告。编译为 C 语言,以便在程序中实际使用。
0赞 chux - Reinstate Monica 8/13/2022
@EricPostpischil 有趣的方法。

答:

2赞 Eric Postpischil 8/13/2022 #1

检查 GCC 警告文档显示没有可以按照您的请求执行的选项。

有用于语句 ( 和) 中缺少枚举值的选项、不同枚举类型的值之间的比较 () 以及不同枚举类型之间的转换 ()。switch-Wswitch-Wswitch-enum-Wenum-compare-Wenum-conversion

编译器开发人员可能认为,有关将值分配给枚举类型的左值的警告将没有用处,因为它会警告普通的所需赋值,例如:inti = i+1

for (enum weather i = sunny; i <= rain; i = i+1)
    …

其中,是 an 因为是 和 的操作数被转换为公共类型,然后将其分配给 .i+1int1int+intenum weatheri

有一些 kludge 可以使用具有某种类型安全性的枚举