class 字段的对齐方式与 C++ 中对象实例的对齐方式之间的关系?

Relationship between alignment of class fields and alignment of object instances in C++?

给定以下 C++ class:

class X {
public:
    uint8_t a;
    uint32_t b[256] __attribute__((aligned(32)));
};

X 的实例可能是字对齐时,编译器如何确保 b 的存储是 32 字节对齐的? aligned 属性是否仅指定相对于对象实例起始地址的对齐方式?如果是这样,使 b 相对于地址 space 对齐 32 字节的正确方法是什么?我应该使用 using class alignof(32) X {...}?

简单地指定对象实例对齐吗

标准如下:

[basic.align/2]

A fundamental alignment is represented by an alignment less than or equal to the greatest alignment supported by the implementation in all contexts, which is equal to alignof(std​::​max_­align_­t) ([support.types]). The alignment required for a type may be different when it is used as the type of a complete object and when it is used as the type of a subobject. [Example 1:

struct B { long double d; };
struct D : virtual B { char c; };

When D is the type of a complete object, it will have a subobject of type B, so it must be aligned appropriately for a long double. If D appears as a subobject of another object that also has B as a virtual base class, the B subobject might be part of a different subobject, reducing the alignment requirements on the D subobject. — end example]

[dcl.align/5]

The combined effect of all alignment-specifiers in a declaration shall not specify an alignment that is less strict than the alignment that would be required for the entity being declared if all alignment-specifiers appertaining to that entity were omitted.

[Example 1:
struct alignas(8) S {};
struct alignas(1) U {
 S s;
};  // error: U specifies an alignment that is less strict than if the alignas(1) >were omitted.
— end example]

因此,从上面的部分(尤其是示例的解释)可以假设对象的对齐方式是在其成员中解析为最严格的。

class X {
public:
    uint8_t a;
    alignas(32) uint32_t b[256];
};

int main() {
    X x1;
    // alignas(16) X x; // Clang error: requested alignment is less than minimum alignment of 32 for type 'X'    
    alignas(64) X x2; // OK 
    alignof(X); // 32
    alignof(x1); //32
    alignof(x2); //64
    alignof(x2.b); //32
    return 0;
}