繁体   English   中英

x64 和 arm64 之间的隐式类型转换和不同行为

[英]Implicit type conversion and different behavior between x64 and arm64

在 arm64 上测试我的软件时,我遇到了一个奇怪的问题。

我写了一些代码来重现这个问题:

char c;
int sum = 0;
for (int i = 0; i <= 255; i++)
{
   c = i;
   int a = c * 10;
   sum += a;
   std::cout << a << std::endl;
}

当我在 Windows(使用 Visual Studio 2017 构建)或 Ubuntu x64(gcc 9.3.0-17)上运行它时,我得到以下结果:

0
10
...
1260
1270
-1280
-1270
-20
-10
sum=-1280

如果我在 Ubuntu arm64 (gcc 9.3.0-17) 上运行相同的代码,我会得到不同的结果:

0
10
...
1260
1270
1280
1290
...
2540
2550
sum=326400

我不知道 arm64 上的 gcc 是否有一些额外的优化(使用 -O3),或者是否有一些我看不到的问题? 关于如何解决这个问题的任何想法?

char数据类型可以是signedunsigned 在前者的情况下(似乎是针对 x64 的情况), c = i语句将导致for循环的129迭代(有signed char的最大值为 127)和它的值溢出正在分配的“环绕”为负值。

但是,当以 arm64 为目标时,您的编译器似乎使用unsigned char类型(范围为0255 ),因此该语句中没有溢出,并且算术“按预期”进行。


要确认(或以其他方式)上述诊断,只需检查不同构建环境中的CHAR_MAX常量(在<climits>头文件中定义)的值。

char由标准签名。
然而,ARM 几十年前决定默认不签名。

就这么简单。

char用 8 位表示,并有符号。 在第一位被解释为负数之后,您可以存储 0-127。 也许最好使用uint8_t或类似的代替char

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM