有一段代码如下:
typedef union
{
struct bits
{
uint32_t bit0 : 1;
uint32_t bit1 : 1;
uint32_t bit2 : 1;
...
...
uint32_t bit14 : 1;
}
uint32_t value;
} MyUnion;
重要的是要防止编译器对位域重新排序,否则 value
的值将根据平台发生变化,甚至可能根据编译后的二进制文件的大小发生变化。
有没有办法告诉编译器“不要重新排序这些字段”?
将 MyUnion
类型的变量声明为 volatile
会实现这一点吗?
如果 union
是packed
和aligned(4)
,是否有可能确保位域不会被重新排序,如果您 100% 确定您将始终使用 32 位平台,并具有相同的字节顺序?
编辑
是否可以只针对一个特定的编译器完成上述操作?也就是说,如果不需要跨不同的编译器兼容。
最佳答案
我认为评论中已经给出了总体“否”的答案。通过这个答案,我想解决您关于 volatile
的问题:
Would declaring
MyUnion
asvolatile
achieve this?
volatile
关键字不会改变您在此处寻找的任何行为。此外,您不能将 union 声明为 volatile
。它是一个关键字,是变量声明的限定符。它告诉编译器变量值可以随时更改,因此应该始终重新加载该值(就像从内存中重新读取一样),而不是根据编译器看到的先前语句假设该值。
这用于当变量值可能因外部因素而改变时,例如当声明链接到实际物理值(例如微 Controller 中的寄存器)的变量时。
关于c++ - 防止 GCC 对结构 union 中的位域重新排序,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57392896/