I'm using C51 v3.20, and when I compiled the following structure, the compiler allocates 6 bytes for it.
typedef struct t_channel_info { int target_temp:9; unsigned char control_mode:2; unsigned char status:2; unsigned char warming:1; int current_temp:9; unsigned char warm_proportion; } t_channel_info;
The best you can do with a simple struct is 5 bytes:
typedef struct t_channel_info { //int at 0-1 int target_temp:9; unsigned int control_mode:2; unsigned int status:2; unsigned int warming:1; //int at 2-3 int current_temp:9; //char at 4 unsigned char warm_proportion:8; } t_channel_info; t_channel_info . . . . . . . . . . . . * TAG * ----- STRUCT ----- 5 target_temp. . . . . . . . . . . . . MEMBER ----- FIELD 0000H 9.0 control_mode . . . . . . . . . . . . MEMBER ----- FIELD 0000H 2.9 status . . . . . . . . . . . . . . . MEMBER ----- FIELD 0000H 2.11 warming. . . . . . . . . . . . . . . MEMBER ----- FIELD 0000H 1.13 current_temp . . . . . . . . . . . . MEMBER ----- FIELD 0002H 9.0 warm_proportion. . . . . . . . . . . MEMBER ----- FIELD 0004H 8.0
struct PartA { //int at 0-1 int target_temp:9; unsigned int control_mode:2; unsigned int status:2; unsigned int warming:1; } a; struct PartB { //char at 0 char dummy1; //int at 1-2 int dummy2:7; int current_temp:9; //char at 3 unsigned char warm_proportion; }; typedef union { struct PartA a; struct PartB b; } t_channel_info2; t_channel_info2. . . . . . . . . . . . TYPEDEF ----- UNION ----- 4 a. . . . . . . . . . . . . . . . . . MEMBER ----- STRUCT 0000H 2 b. . . . . . . . . . . . . . . . . . MEMBER ----- STRUCT 0000H 4 PartA. . . . . . . . . . . . . . . . . * TAG * ----- STRUCT ----- 2 target_temp. . . . . . . . . . . . . MEMBER ----- FIELD 0000H 9.0 control_mode . . . . . . . . . . . . MEMBER ----- FIELD 0000H 2.9 status . . . . . . . . . . . . . . . MEMBER ----- FIELD 0000H 2.11 warming. . . . . . . . . . . . . . . MEMBER ----- FIELD 0000H 1.13 PartB. . . . . . . . . . . . . . . . . * TAG * ----- STRUCT ----- 4 dummy1 . . . . . . . . . . . . . . . MEMBER ----- CHAR 0000H 1 dummy2 . . . . . . . . . . . . . . . MEMBER ----- FIELD 0001H 7.0 current_temp . . . . . . . . . . . . MEMBER ----- FIELD 0001H 9.7 warm_proportion. . . . . . . . . . . MEMBER ----- U_CHAR 0003H 1
Thanks for your kind replies. Based on your comments and links, I modified the struct as follows:
typedef struct tt_channel_info { unsigned int warm_proportion:7; int target_temp:9; unsigned int control_mode:2; unsigned int status:2; unsigned int warming:1; int current_temp:9; } tt_channel_info; tt_channel_info. . . . . . . . . . . . TYPEDEF ----- STRUCT ----- 4 warm_proportion. . . . . . . . . . . MEMBER ----- FIELD 0000H 7.0 target_temp. . . . . . . . . . . . . MEMBER DATA FIELD 0000H 9.7 control_mode . . . . . . . . . . . . MEMBER DATA FIELD 0002H 2.0 status . . . . . . . . . . . . . . . MEMBER DATA FIELD 0002H 2.2 warming. . . . . . . . . . . . . . . MEMBER DATA FIELD 0002H 1.4 current_temp . . . . . . . . . . . . MEMBER DATA FIELD 0002H 9.5
Since you have control over the layout, I suggest the following modification to reduce code size and increase speed.
typedef struct tt_channel_info { int target_temp:9; //keep the fields > 8 bits at int offset 0 unsigned int warm_proportion:7; int current_temp:9; //keep the fields > 8 bits at int offset 0 unsigned int control_mode:2; unsigned int status:2; unsigned int warming:1; } tt_channel_info;
hmm, thanks for the hint