c - C 中小于 8 位的位字段并集的打包结构的大小

标签 c sizeof bit-fields packed

在C中有没有可能让下面的结构体的大小为2?

#include <stdio.h>

struct union_struct {
    char foo;
    char bar : 2;
    union {
        char foobar1 : 6;
        char foobar2 : 6;
    };
};

int main(void)
{
    printf("size of union struct: %d\n", sizeof(struct union_struct));
    return 0;
}

输出,用gcc编译:

union 结构的大小:3

最佳答案

如果您依赖于实现定义的行为,那么是的,但您必须以不同的方式组织它:

#ifdef UNNAMED_BITFIELDS_ARE_WELL_DEFINED
#define ANON
#else
#define ANON3(X) anonymous__## X ##__
#define ANON2(X) ANON3(X)
#define ANON ANON2(__LINE__)
#endif

struct union_struct {
    char foo;
    union {
        struct {
            char bar     : 2;
            char ANON    : 6;
        };
        struct {
            char ANON    : 2;
            char foobar1 : 6;
        };
        struct {
            char ANON    : 2;
            char foobar2 : 6;
        };
    };
};

第一个字节是foo,第二个字节是匿名 union 。然后匿名 union 有 3 个单字节匿名结构。每个结构(可选)使用未命名的位字段以允许 foobar1foobar2 表示 bar 之后的相同 6 位。

根据我对 C.11 标准的理解,当 UNNAMED_BITFIELDS_ARE_WELL_DEFINED 被定义时,上面的代码是正确的。但是,关于未命名的位域是否具有明确定义的语义似乎存在争议(请参阅下面的评论)。如果未命名的位域没有明确定义的语义,则上面的代码可以将每个 ANON 宏扩展为位域的名称。

但是,C.11 标准仅在 _Boolintunsigned 上定义了位域,而使用任何其他位字段的类型是实现定义的(C.11 §6.7.2.1 ¶5)。

关于c - C 中小于 8 位的位字段并集的打包结构的大小,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18647383/

相关文章:

c - 为什么我从代码中带有位域的 C union 获得此输出?

c++ - boolean 值对位域的优势

c - unsigned int 函数的返回类型

c - 以编程方式挂载 block 设备而无需 root 权限

c - 为什么从管道读取时 read() 不会返回零

c++ - 计算创建为双指针的两个暗数组的大小

c++ - 如何在不创建实例的情况下获取std::array <T,N>中的元素数?

c - 在方法头中后缀变量类型的星号有何意义?

c++ - 数组元素数量

无法将 C 中的位域初始化为全局