我正在尝试建立自己的库,用于在不同端号的整数和有符号表示之间进行转换。其中一部分涉及直接访问作为相同大小整数的字符缓冲区(主要用于快速比较)。我非常关注此项目的可移植性。我希望此库在所有方面都可用旧的和新的机器和c编译器,不仅仅是linux上的gcc或clang。
最初,我对整数成员使用c99固定宽度整数类型。这很好。当我从固定宽度整数切换到相同大小的位字段时,问题就开始了。我这样做是为了通过不依赖c99功能来提高可移植性
问题是,当我使用位字段时,gcc抱怨填充已插入(-Werror和-Wpadded已传递给gcc):
错误:将结构大小填充到对齐边界
以下是其中一个工会的例子:
旧版本,运行良好:

typedef union
{
    unsigned char bytes[4];
    uint32_t uvalue;
} upicl_uint32_be;

新版本,添加不需要的填充:
typedef union
{
    unsigned char bytes[4];
    unsigned long uvalue : 32;
} upicl_uint32_be;

我不知道当32位字段已经对齐时,为什么要将填充添加到联合中。
有更好的办法吗?

最佳答案

可能long是8字节长,因此位字段将占用8字节,因为它的大小与uint32_t不同。
union类型的名称表明您希望位字段基于uint32_t而不是unsigned long(或者假设两者相同,这显然是不正确的)。

关于c - 编译器向已对齐的 union 位字段成员添加填充,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/29242603/

10-11 18:52