c - 我怎样才能摆脱 QAC 警告?

标签 c gcc c99 static-analysis c89

我正在使用 QAC,我收到了相应源代码行的以下消息。我怎样才能转换它以便 QAC 能够“理解”它?

使用的编译器是 gcc - 它不会警告这个问题,因为它被设置为“iso c99”。

#define DIAGMGR_SIGNED_2_BYTES_178           ((s16)178)

sK  = (s16)(sE1 / DIAGMGR_SIGNED_2_BYTES_178);
                  ^

Result of signed division or remainder operation may be implementation defined

.

A division ('/') or remainder ('%') operation is being performed in a signed integer type and the result may be implementation-defined. Message 3103 is generated for an integer division or remainder operation in a signed type where:

  • One or both operands are non-constant and of signed integer type, or
  • Both operands are integer constant expressions, one of negative value and one of positive value

A signed integer division or remainder operation in which one operand is positive and the other is negative may be performed in one of two ways:

  • The division will round towards zero and any non-zero remainder will be a negative value
  • The division will round away from zero and any non-zero remainder will be a positive value In the ISO:C99 standard the first approach is always used. In the ISO:C90 standard either approach may be used - the result is implementation defined. For example:

/PRQA S 3120,3198,3408,3447 ++/

extern int r;

extern int si;

extern void foo(void)
{
    r = -7 / 4;     /* Message 3103 *//* Result is -1 in C99 but may be -2 in C90 */

    r = -7 % 4;     /* Message 3103 *//* Result is -3 in C99 but may be  1 in C90 */
    si = si / r;    /* Message 3103 */
}

最佳答案

您需要配置该工具,使其能够理解您的代码是 C99。在旧的 C90 标准中,负数除法可以通过两种不同的方式实现,see this .这是 C90 标准中的一个已知“错误”,自 C99 以来已得到修复。

这是大多数静态分析工具的标准警告,尤其是当它们设置为检查 MISRA-C 合规性时。 MISRA-C:2004 和 2012 都要求程序员了解这个 C 标准“错误”。


C90 中的解决方法:

如果您确定操作数不是负数,只需将它们转换为无符号类型,或使用无符号类型作为开头。

如果您知道操作数可能为负数:

  • 如果任一操作数为负数,则设置标志以指示它是哪一个。
  • 取两个操作数的绝对值。
  • 对绝对值进行除法。
  • 重新给数字加上符号。

不幸的是,这是 C90 中唯一的可移植变通方法。或者,您可以添加静态断言以防止代码在向下截断负数的系统上编译。

如果您使用的是 C99,则不需要变通方法,因为它总是截断为零。然后您可以安全地禁用警告。

关于c - 我怎样才能摆脱 QAC 警告?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35630366/

相关文章:

更改常量全局变量

c - C 中最快的抖动/半色调库

c++ - 无法理解 kern.osversion ‘14.5.0

GCC 4.7,包括 <stdatomic.h>

我可以部分/选择性地内联函数吗?

c - 初始化复杂结构,GCC 警告 : initialized field with side-effects overwritten

c - 用 C 编辑列表程序

c - 传递和更改数组,通过引用传递,使用 C 中的指针

c - 在 MacOS El Captain 上使用 gcc 编译时未找到库

c - 用户定义的最小和最大函数的奇怪行为