为什么我的结构元素带有填充字节?

时间:2015-01-08 14:00:17

标签: c windows memory alignment padding

我对结构元素的内存对齐有一个令人困惑的行为。考虑这两种结构:

typedef struct s_inner {
    unsigned long ul1;
    double        dbl1;
    fourth_struct s4;
    unsigned long ul2;
    int           i1;
} t_inner;

typedef struct s_outer {
    other_struct    member1; /* 4-byte aligned, 40 bytes in terms of sizeof() */
    unsigned long   member2;
    t_inner         member3; /* see above */
} t_outer;

当我检查t_outer的内存布局时,我可以看到member1的元素是4字节对齐的,就像我期望的那样。 此外,member3的内存布局符合预期:ul1附加了4个填充字节,以便dbl1在8字节边框上对齐(在Win32上正常)。

但是,当我检查member2的内存布局时,我可以看到该成员附加了4个填充字节。 有谁可以解释为什么地球member2会收到填充字节?我的期望是member2没有填充。


编辑1: 请参阅此内存转储。在填写结构元素之前,我memset整个t_outer结构p&#39>:

  • 红色区域为member1
  • 蓝色区域为member2
  • 绿色区域为member3
  • 黄色区域标记dbl1
  • member3的位置

memory-layout


约束

  • 编译器是VS2012
  • other_struct的实际结构在这里无关紧要,它是一个40字节大小的4字节对齐结构
  • 想要对行为进行任何变通办法(重新排序,打包......),但要解释为什么会这样做。

2 个答案:

答案 0 :(得分:2)

VS2012 docs describe its padding behavior。特别是,它们指定struct的对齐要求是其任何成员的最大对齐要求。成员member3的类型t_inner的成员类型为double,对齐要求为8字节,因此member3总体上具有8字节对齐要求(而且,t_outer具有8字节对齐要求)。在member2member3之间需要填充以获得member3的8字节对齐。

答案 1 :(得分:2)

  

使dbl1在8字节边框上对齐

不确定。但是,如果结构本身也不与8对齐,则对齐保证意味着bupkis。这是数据部分和堆栈帧的编译器地址选择提供的正常的保证。或内存分配器。所有保证至少与8对齐。

但是当您在 s_outer 中嵌入结构时,需要在 member3(而不是在member2之后)填充的4个字节才能获得对齐保证。

另请注意,结构可以在最后一个成员之后填充。当结构存储在数组中时,可能需要确保成员仍然对齐。同样的原因。