我正在开发一个具有 CAN 通信功能的微 Controller ,它有 32 个邮箱用于通信。 在制造商提供的头文件中,它们有以下声明:
struct CANMSGID_BITS { // bits description
Uint16 EXTMSGID_L:16; // 15:0
Uint16 EXTMSGID_H:2; // 17:16
Uint16 STDMSGID:11; // 28:18
Uint16 AAM:1; // 29
Uint16 AME:1; // 30
Uint16 IDE:1; // 31
};
/* Allow access to the bit fields or entire register */
union CANMSGID_REG {
Uint32 all;
struct CANMSGID_BITS bit;
};
/* eCAN Message Control Register (MSGCTRL) bit definitions */
struct CANMSGCTRL_BITS { // bits description
Uint16 DLC:4; // 3:0
Uint16 RTR:1; // 4
Uint16 rsvd1:3; // 7:5 reserved
Uint16 TPL:5; // 12:8
Uint16 rsvd2:3; // 15:13 reserved
Uint16 rsvd3:16; // 31:16 reserved
};
/* Allow access to the bit fields or entire register */
union CANMSGCTRL_REG {
Uint32 all;
struct CANMSGCTRL_BITS bit;
};
/* eCAN Message Data Register low (MDR_L) word definitions */
struct CANMDL_WORDS { // bits description
Uint16 LOW_WORD:16; // 15:0
Uint16 HI_WORD:16; // 31:16
};
/* eCAN Message Data Register low (MDR_L) byte definitions */
struct CANMDL_BYTES { // bits description
Uint16 BYTE3:8; // 7:0
Uint16 BYTE2:8; // 15:8
Uint16 BYTE1:8; // 23:16
Uint16 BYTE0:8; // 31:24
};
/* Allow access to the bit fields or entire register */
union CANMDL_REG {
Uint32 all;
struct CANMDL_WORDS word;
struct CANMDL_BYTES byte;
};
/* eCAN Message Data Register high (MDR_H) word definitions */
struct CANMDH_WORDS { // bits description
Uint16 LOW_WORD:16; // 15:0
Uint16 HI_WORD:16; // 31:16
};
/* eCAN Message Data Register low (MDR_H) byte definitions */
struct CANMDH_BYTES { // bits description
Uint16 BYTE7:8; // 7:0
Uint16 BYTE6:8; // 15:8
Uint16 BYTE5:8; // 23:16
Uint16 BYTE4:8; // 31:24
};
/* Allow access to the bit fields or entire register */
union CANMDH_REG {
Uint32 all;
struct CANMDH_WORDS word;
struct CANMDH_BYTES byte;
};
struct MBOX {
union CANMSGID_REG MSGID;
union CANMSGCTRL_REG MSGCTRL;
union CANMDL_REG MDL;
union CANMDH_REG MDH;
};
这是针对单个邮箱的,但有 32 个邮箱,因此邮箱的定义如下:
struct ECAN_MBOXES {
struct MBOX MBOX0;
struct MBOX MBOX1;
struct MBOX MBOX2;
.
.
.
struct MBOX MBOX30;
struct MBOX MBOX31;
};
最后我们有:
extern volatile struct ECAN_MBOXES ECanaMboxes;
其中“ECanaMboxes”在链接器命令文件中定义。
我仅用以下声明替换了struct ECAN_MBOXES
:
struct ECAN_MBOXES {
struct MBOX MBOX[32];
};
这是一个有效的更改还是不允许我们从位域中创建数组? 我已经尝试了两种方式的代码,并且无论哪种方式,代码都运行良好。我更喜欢阵列,因为它更容易出于特定目的访问特定邮箱,而且所有邮箱的配置都可以以迭代方式完成。我想知道结构体声明是否会导致意外问题?
最佳答案
是否struct ECAN_MBOXES
包含 struct MBOX
的 32 个不同实例或 32 struct MBOX
的数组与如何struct MBOX
无关是内部布局的。
后者显然更可取,因为您可以索引数组,但它不会破坏 struct MBOX
的任何内容。 ,无论它是否包含 union 和位域。
请注意,您实际上并没有创建位域数组,而是创建包含位域的结构体数组。实际的位域数组不是合法的构造,如果您尝试这样做,编译器会给您一个错误。
关于我可以将多个位域结构替换为 C 中的数组吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59305681/