为什么在我的实现中,所有数组都对齐到 16 个字节?



我非常简单的代码如下所示

#include <iostream>
#include <stdalign.h>
int main() {
char array_char[2] = {'a', 'b'};
float array_float[2] = {1, 2};
std::cout << "alignof(array_char): " << alignof(array_char) << std::endl;
std::cout << "alignof(array_float): " << alignof(array_float) << std::endl;
std::cout << "address of array_char: " << (void *) array_char << std::endl;
std::cout << "address of array_float: " << array_float << std::endl;
}

此代码的输出为

对齐方式(array_char(: 1

对齐方式(array_float(: 4

array_char地址:0x7fff5e8ec580

array_float地址:0x7fff5e8ec570

alignof运算符的结果低于预期,但两个数组的实际地址与它们不一致。无论我尝试多少次,地址始终是 16 字节对齐的。

我在 Ubuntu 16.04 上使用 gcc 5.4.0 和英特尔酷睿 i5 第 7 代 CPU。

我找到了这个补丁。

这似乎是GCC 6.4中修复x86_64错误。

System V x86-64 ABI 要求聚合类型(如数组和struct(至少为 16 个字节(如果它们至少为 16 个字节(。根据 ABI 规范中的注释,这是为了方便使用 SSE 指令。

GCC 似乎错误地将该规则应用于大小为 16 位(而不是字节(或更大的聚合。

我建议您将编译器升级到更新的 GCC 版本。


然而,这只是一个优化问题,而不是一个正确性问题。对变量进行更严格的对齐并没有错,并且(与提到的 SSE 一样(在某些情况下,过度对齐可能会带来性能优势,这些优势超过了浪费堆栈内存的成本。

最新更新