除以零不会导致 Nvidia Jetson 上的运行时异常 [英] Division by zero not causing runtime exception on Nvidia Jetson

查看:25
本文介绍了除以零不会导致 Nvidia Jetson 上的运行时异常的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我不太熟悉 ARM 处理器的内部细节,但我不明白我的 Nvidia Jetson Nano 开发板上的以下行为.

I'm not very familiar with the internal details of ARM processors, but I do not understand the following behaviour on my Nvidia Jetson Nano dev board.

C 代码示例...

//main.c

#include <stdio.h>

int main()
{
    int fred = 123;
    int i;

    for(i = -10 ; i <= 10 ; i++)
        printf("%d / %d == %d\n", fred, i, fred / i);

    return 0;
}

编译:

gcc main.c -ggdb

运行生成的 a.out 可执行文件会产生以下输出...

Running the resulting a.out executable yields the following output...

123 / -10 == -12
123 / -9 == -13
123 / -8 == -15
123 / -7 == -17
123 / -6 == -20
123 / -5 == -24
123 / -4 == -30
123 / -3 == -41
123 / -2 == -61
123 / -1 == -123
123 / 0 == 0                  //unexpected!
123 / 1 == 123
123 / 2 == 61
123 / 3 == 41
123 / 4 == 30
123 / 5 == 24
123 / 6 == 20
123 / 7 == 17
123 / 8 == 15
123 / 9 == 13
123 / 10 == 12

使用 gcc 3.7 在古老的 Pentium 4 上编译的完全相同的代码导致(如预期的那样)当 i 达到 0 并导致除以零时抛出运行时异常.

The exact same code compiled on an ancient Pentium 4 using gcc 3.7 causes (as expected) a runtime exception to be thrown when i reaches 0 and causes a division by zero.

Nvidia 开发板运行的是 Ubuntu 18.04 LTS、gcc 7.4.0(最新版),并且在其他所有方面都运行良好.我还编译了此代码的等效 Ada 语言版本,并且如预期的那样引发了运行时异常(因为 Ada 代表我提前进行了安全检查).

The Nvidia board is running Ubuntu 18.04 LTS, gcc version 7.4.0 (latest) and in every other respect runs beautifully. I have also compiled the equivalent Ada language version of this code and a runtime exception is raised as one would expect (because Ada does safety checks ahead of time on my behalf).

我意识到在 C 中,除以零会产生未定义的行为";可能是对此的解释,但是对于同一个编译器套件的两个版本,对同一个操作给出如此不同的结果让我感到困惑.

I realise that in C, "division by zero yields undefined behaviour" is likely the explanation for this, but for two versions of the same compiler suite to give such different results to the same operation is puzzling to me.

什么情况会导致 Nvidia Tegra ARM(64 位)CPU 允许被零除以被操作系统忽略?

What circumstances could cause an Nvidia Tegra ARM (64 bit) CPU to allow a division by zero to pass by unnoticed by the OS?

来自/etc/cpuinfo... 的 CPU 详细信息...

Details about the CPU from /etc/cpuinfo...

$ cat /proc/cpuinfo
processor       : 0
model name      : ARMv8 Processor rev 1 (v8l)
BogoMIPS        : 38.40
Features        : fp asimd evtstrm aes pmull sha1 sha2 crc32
CPU implementer : 0x41
CPU architecture: 8
CPU variant     : 0x1
CPU part        : 0xd07
CPU revision    : 1

.... truncated ....

推荐答案

Nvidia Jetson Nano 开发板使用 ARM Cortex-A57 (链接),基于 ARMv8 架构.基于ARMv8的指令集spec整数 除以零 返回零 并且不会被困.

Nvidia Jetson Nano dev board uses ARM Cortex-A57 (Link) which is based on ARMv8 architecture. Based on the instruction set spec of ARMv8, integer division by zero returns zero and not trapped.

2.3 划分说明

ARMv8-A 支持 32 位和 64 位大小值的有符号和无符号除法.

ARMv8-A supports signed and unsigned division of 32-bit and 64-bit sized values.

指令说明

SDIV 签名除法

UDIV 无符号除法

...

溢出和被零除不会被困:

• 任何整数除以零返回零

• Any integer division by zero returns zero

因此编译器在这种情况下生成 sdiv(参见示例)并且CPU无一例外地返回0.当您在不同平台上编译相同的代码时,每个其他 CPU 对除以零的反应可能不同.正如您在问题中提到的,在除以 0 的情况下,C 标准未定义的行为.

So the compiler generates sdiv in this case (see example) and the CPU returns 0 without any exception. When you compile the same code on different platforms, each other CPU may reacts differently to division by zero. As you mentioned in your question, in case of division by 0, the behavior is undefined by the C standard.

这篇关于除以零不会导致 Nvidia Jetson 上的运行时异常的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆