结构件对齐 - 是否可以假设没有填充
struct member alignment - is it possible to assume no padding
>想象一个由 32 位、16 位和 8 位成员值组成的结构。其中,成员值的顺序是每个成员都位于其自然边界上。
struct Foo
{
uint32_t a;
uint16_t b;
uint8_t c;
uint8_t d;
uint32_t e;
};
记录了可视C++的成员对齐和填充规则。 sizeof(Foo( 在 VC++ 上,上面的结构可以预见地是"12"。
现在,我很确定规则是不应该对填充和对齐做出任何假设,但在实践中,其他操作系统上的其他编译器是否做出类似的保证?
如果没有,GCC 上是否有等效的"#pragma pack(1("?
实际上,在存在uintXX_t
类型的任何系统上,您将获得所需的对齐方式,无需填充。不要抛出丑陋的gcc主义来试图保证它。
编辑:详细说明为什么使用attribute packed
或aligned
可能是有害的,当用作较大结构的成员或在堆栈上时,可能会导致整个结构错位。这肯定会损害性能,并且在非 x86 计算机上,将生成更大的代码。这也意味着将指针指向结构的任何成员都是无效的,因为通过指针访问值的代码不会意识到它可能未对齐,因此可能会出错。
至于为什么没有必要,请记住,attribute
特定于 gcc 和 gcc-workalike 编译器。C 标准不会未定义或未指定对齐方式。它是实现定义的,这意味着实现需要进一步指定和记录它的行为方式。GCC 的行为是,并且一直是,将每个结构成员对齐在其自然对齐的下一个边界上(与在结构外部使用时的对齐方式相同,它必然是一个平均划分类型大小的数字(。由于attribute
是一个 gcc 功能,如果你使用它,你已经假设了一个类似 gcc 的编译器,但通过假设你已经有了你想要的对齐方式。
一般来说,您是正确的,这不是一个安全的假设,尽管您通常会在许多系统上获得您期望的包装。使用 gcc 时,您可能希望在类型上使用 packed
属性。
例如
struct __attribute__((packed)) Blah { /* ... */ };
在实际提供这些类型的系统上,它极有可能工作。例如,在36位系统上,这些类型首先不可用。
GCC 提供了一个属性
__attribute__ ((packed))
具有类似的效果。
- 在c++中用vector填充一个简单的动态数组
- 如何使用用户输入在C++中正确填充2D数组
- 如何找到大小'x'数组是否完全填充,在C++?
- Cuda C++:设备上的Malloc类,并用来自主机的数据填充它
- 通过for循环使用用户输入填充列表
- 根据用户输入用字母填充矢量,并将"开始"和"结束"放在四肢
- 如何正确填充在堆上分配的二维数组?
- 将数字转换为填充字符串
- 有没有办法在一行中填充矢量图
- 用C++中的数字和条件填充向量
- 用真值填充矢量
- 使用结构成员指针在C++中填充结构
- 流填充字符的默认定位
- 使用不同算法的 PKCS1v15 填充进行加密 ++ 签名
- C++:使用缓冲区中的数据填充结构
- 如何将零填充的多维数组传递给 C++ 中的函数?
- Cryptopp:获取密码输入的填充字符串
- 填充上编译器生成的复制构造函数之间的不一致
- RcppEigen 模板化函数,用于填充单位法线
- 结构件对齐 - 是否可以假设没有填充