我正在实施无线电标准,并且在结构和内存大小方面遇到了问题。在下面的例子中,我需要这个结构位于单个字节的内存中(按照无线电标准),但它目前给我2个字节的大小。经过多次挖掘,我明白这是因为联盟的规模"是字节而不是3位......但还没有解决这个问题。 我看过了:
但似乎都没有给我一个解决方案。
有什么想法吗?
谢谢!
#ifdef WIN32
#pragma pack(push)
#pragma pack(1)
#endif
typedef struct three_bit_struct
{
unsigned char bit_a : 1;
unsigned char bit_b : 1;
unsigned char bit_c : 1;
}three_bit_struct_T;
typedef union
{
three_bit_struct_T three_bit_struct;
unsigned char another_three_bits : 3;
}weird_union_T;
typedef struct
{
weird_union_T problem_union;
unsigned char another_bit : 1;
unsigned char reserved : 4;
}my_structure_T;
int _tmain(int argc, _TCHAR* argv[])
{
int size;
size = sizeof(my_structure_T);
return 0;
}
#ifdef WIN32
#pragma pack(pop)
#endif
答案 0 :(得分:6)
问题是three_bit_struct_T
的大小将四舍五入到最接近的字节 * ,而不管它在其位域中只包含三位。结构简单地不能具有部分字节的大小。因此,当您使用my_structure_T
中的额外字段对其进行扩充时,不可避免地会将大小溢出到第二个字节中。
要将所有内容填充到单个字节中,您必须将所有位域成员放在外部my_structure_T
中,而不是将它们作为内部结构/联合。
我认为你能做的最好就是将整个事情作为一个联盟。
typedef struct
{
unsigned char bit_a : 1;
unsigned char bit_b : 1;
unsigned char bit_c : 1;
unsigned char another_bit : 1;
unsigned char reserved : 4;
} three_bit_struct_T;
typedef struct
{
unsigned char another_three_bits : 3;
unsigned char another_bit : 1;
unsigned char reserved : 4;
} another_three_bit_struct_T;
typedef union
{
three_bit_struct_T three_bit_struct;
another_three_bit_struct_T another_three_bit_struct;
} my_union_T;
(*)或word,取决于对齐/打包设置。
答案 1 :(得分:0)
两个好的建议:从不在数据协议中使用struct / union,在任何情况下都可以使用never use bit-fields。
实现这一点的最佳方法是通过位掩码和逐位运算符。
#define BYTE_BIT7 0x80u
uint8_t byte;
byte |= BYTE_BIT_7; // set bit to 1
byte &= ~BYTE_BIT_7; // set bit to 0
if(byte & BYTE_BIT_7) // check bit value
此代码可移植到世界上的每个C编译器以及C ++。