【问题标题】:Force the padding inside a C struct强制在 C 结构内填充
【发布时间】:2015-07-02 21:03:31
【问题描述】:

我想知道是否有办法强制填充 C 结构的字段。 我将尝试用一个例子更好地解释它: 如果我有以下结构:

struct foo{
    int32 a,
    int16 b,
    int8 c,
    int32 d,
    int32 e
};

我会按以下方式映射它(考虑0x00作为起始地址:

&foo.a = 0x00
&foo.b = 0x08
&foo.c = 0x0A
&foo.d = 0x10
&foo.e = 0x18

以便将字段打包成 4 个字节,每个 8 个字节。

我显然知道我可以插入“填充字段”,但这是唯一的解决方案吗?

【问题讨论】:

  • 哪个编译器?对于 GCC,请参阅 here 以获取 aligned 属性
  • 出于什么目的?您可以使用多个属性来控制 gcc 中的对齐和填充,但如果您不注意自己在做什么,您很容易迫使 gcc 生成令人讨厌的缓慢和无效的代码。 gcc 通常会为平台本身做正确的事情,除非您正在做一些非常特别的事情。
  • 是的,gcc 没问题。无论如何,平台是一个定制的微。
  • Olgac,aligned 属性工作得很好,谢谢。无论如何,似乎没有办法对结构内的数组使用相同的对齐方式。即 int16 a[4]: &a[0] = 0x00, &a[1]=0x02, &a[2]=0x08, &a[3]=0x0A..
  • C11 有_Alignas 说明符

标签: c struct padding


【解决方案1】:

C11 有 _Alignas 说明符。本声明:

#include <stdio.h>
#include <stdint.h>

struct foo {
    _Alignas(8) int32_t a;
    _Alignas(4) int16_t b;
    _Alignas(4) int8_t c;
    _Alignas(8) int32_t d;
    _Alignas(8) int32_t e;
};

#define OFF(s, f)   ((uintptr_t)(&(s).f) - (uintptr_t)(&(s)))

int main() {
    char x;
    struct foo foo;

    printf("%p %x %x %x %x %x\n", (uintptr_t)(&foo), OFF(foo, a), OFF(foo, b), 
                                OFF(foo, c), OFF(foo, d), OFF(foo, e));
}

提供您要求的精确对齐:

0x7fff6cbf2780 0 4 8 10 18

在 x86_64 上使用带有 -std=gnu11 的 gcc 4.8.3 编译。

【讨论】:

    【解决方案2】:

    这个结构定义:

    struct foo{
        int32 a,
        int16 b,
        int8 c,
        int32 d,
        int32 e
    };
    

    根据以下内容填充:

    struct foo{  <-- aligned on a 32 bit address boundary by compiler
        int32 a, <-- +0 
        int16 b, <-- +4
        int8 c,  <-- +6
                 <-- +7 (1 byte padding)
        int32 d, <-- +8
        int32 e  <-- +12  (not +16 as indicated in posted code)
    };
    

    【讨论】:

      猜你喜欢
      • 2010-10-24
      • 2015-04-25
      • 1970-01-01
      • 1970-01-01
      • 2014-10-12
      • 2012-06-25
      • 2023-04-03
      • 2017-06-08
      • 2015-09-04
      相关资源
      最近更新 更多