c - 带有 gcc 和无符号整数的 SIGFPE

标签 c gcc floating-point c11 sigfpe

我从用不同版本的 gcc 编译的可执行文件中得到了这种奇怪的行为,所有版本都发出 SIGFPE 信号,最好的部分是我没有 float 我的代码中的任何一种;如果有人可以阐明这一点......我真的不知道从哪里开始调试它,这太奇怪了,这个错误是由我从 4.96.0

这是重现问题的片段

// Floating point exception - SIGFPE
#include <stdio.h>
typedef unsigned int T;
int main()
{
#define N 256 
  for (T i = 0; i < N; ++i)
    {
      i += (i % i);
      printf("%u\t", i);
    }
}
// bug uncovered with
// gcc version 4.9.2 (Debian 4.9.2-10)
// gcc version 5.1.0 (GCC)
// gcc version 6.0.0 20150517 (experimental) (GCC)
// using -std=c11 or -std=c99

这段代码的目的是重现问题,我知道它的逻辑并没有太大意义(模部分)但是 clang 通过了测试,没有版本gcc 做同样的事情,如果对这种行为有技术解释,我想知道为什么。

最佳答案

运行代码后,这是在 cygwin 下,gdb 转储了跟踪。

$ cat sigfpe.exe.stackdump
Exception: STATUS_INTEGER_DIVIDE_BY_ZERO at rip=00100401115
rax=0000000000000000 rbx=000000000022CB20 rcx=0000000000000001
rdx=0000000000000000 rsi=000000060003A2F0 rdi=0000000000000000
r8 =0000000000000000 r9 =0000000000000000 r10=0000000000230000
r11=0000000000000002 r12=0000000000000000 r13=0000000000000001
r14=000000000022CB63 r15=000000000022CB64
rbp=000000000022CAD0 rsp=000000000022CAA0
program=C:\cygwin64\home\luser\sigfpe.exe, pid 6808, thread main
cs=0033 ds=002B es=002B fs=0053 gs=002B ss=002B
Stack trace:
Frame        Function    Args
0000022CAD0  00100401115 (00000000020, 30001000000FF00, 0018004830F, 0000022D680                                                                                                                )
0000022CBC0  00180048380 (00000000000, 00000000000, 00000000000, 00000000000)
00000000000  0018004607C (00000000000, 0003E704021, 00000000000, 0000000002D)
00000000000  00180046114 (00000000000, 00000000000, 00000000000, 00000000000)
00000000000  00100401191 (00000000000, 00000000000, 00000000000, 00000000000)
00000000000  00100401010 (00000000000, 00000000000, 00000000000, 00000000000)
00000000000  000772E59CD (00000000000, 00000000000, 00000000000, 00000000000)
00000000000  0007741B981 (00000000000, 00000000000, 00000000000, 00000000000)
End of stack trace

线索在操作i += (i % i)

当循环初值为0时,当然除以零错误。

你试过捕捉信号吗?

查看C11 standard在第 265 页上,SIGFPE - 错误的算术运算,例如除零或导致溢出的运算

这不是编译器错误,而是实现定义的。

关于c - 带有 gcc 和无符号整数的 SIGFPE,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30632566/

相关文章:

gcc - RDSEED 和 RDRAND 之间的性能差异可以忽略不计

floating-point - 是否有适合压缩 GPS 航路点的算法?

python - 为什么 math.log 接受大整数值?

c - At&T Assembly 索引数组和声明数组

python - 是什么导致 C 程序不能在 Arduino 中正确地递增变量?

C++17 编译器不应该发现对未定义值的引用传递吗?

c - 如何在C中生成随机 float

c - 二进制文件读取 - 写入不起作用

c - C 中的语法错误

c - 将变量类型与 token 合并