We are running a survey to help us improve the experience for all of our members. If you see the survey appear, please take the time to tell us about your experience if you can.
please explain me why the sizeof (C51) returns 6 bytes for this struct instead of 5:
typedef struct DEKO_COMM_HEADER { UINT16 m_uiMsgOpcode; UCHAR8 m_sblMsgPriority :2; UINT16 m_sblDataLength :11; UINT16 m_sblMsgTimeStamp :11; }DEKO_COMM_HEADER, *PDEKO_COMM_HEADER;
UINT16 is typedef for unsigned int UCHAR8 is typedef for unsigned char
thanks
I don't know how you expected to get the size 5.
11+11+2 is 24 bits, but they can normally not be formed from 3 separate bytes, since a single byte can't store a bitfield with 11 bits. The compiler really want all fields for a bit field to be stored in the same byte/word/dword/xxx to allow all bits to be assignable with a single assign.
The compiler may use a single 32-bit number for all bit fields (giving a total size of 6).
The compiler may also allocate 2 16-bit numbers (one for each 11-bit value) and then decide to piggyback the 2-bit value into one of these 16-bit integers. This gives a total size of 6.
The compiler may decide that the 2-bit field should not be piggybacked, thereby consuming 5 bytes for the bit fields, and 2 bytes for the opcode. For a 8-bit processor, this may result in a 7 byte large struct. A 16 or 32-bit processor would then have to pad the struct to make sure that an array of structs always places the 16-bit integer on an even address, i.e. making the struct 8 bytes large.
mr dovalle
you can n0t assumme how compiler alllocates fields in a structure in a structure
it is undefineded in c standard you know is implermentation specifac!!!!
you should use sizeof so compiler says how much space
some compileer s use pragma as control alignemenent
why you not write code to see asssemblery of compielr producingh???
sorry for my mistake
why you not write code to see asssembler of compiler producing???
you use SRC</b option box
"it is undefineded in c standard "
To be precise, the 'C' standard states that it is Implementation-Defined - this means that the implementation can choose to do whatever it likes, but this must be documented.
sir andy
you are right you know ;)
my book says inplementation specifac
thannk you for my mistake
"thannk you for my mistake"
No mistake - just a clarification, perhaps!
Which compiler are you using ? Compiling your example shows a size of 7 which is correct since an UINT16 can hold a max. of 16 bits. Please look at the symbol listing for details on size and layout of the fields.
C51 COMPILER V8.08a, COMPILATION OF MODULE Q OBJECT MODULE PLACED IN q.OBJ COMPILER INVOKED BY: c51.exe q.c CODE SB line level source 1 typedef unsigned char UCHAR8; 2 typedef unsigned int UINT16; 3 4 typedef struct DEKO_COMM_HEADER { 5 UINT16 m_uiMsgOpcode; 6 UCHAR8 m_sblMsgPriority : 2; 7 UINT16 m_sblDataLength :11; 8 UINT16 m_sblMsgTimeStamp :11; 9 } DEKO_COMM_HEADER; 10 11 12 unsigned char z; 13 14 void main (void) { 15 1 z = sizeof (DEKO_COMM_HEADER); 16 1 } ASSEMBLY LISTING OF GENERATED OBJECT CODE ; FUNCTION main (BEGIN) ; SOURCE LINE # 14 ; SOURCE LINE # 15 0000 750007 R MOV z,#07H ; SOURCE LINE # 16 0003 22 RET ; FUNCTION main (END) NAME CLASS MSPACE TYPE OFFSET SIZE ==== ===== ====== ==== ====== ==== main . . . . . . . . . . . . . . . . . PUBLIC CODE PROC 0000H ----- UINT16 . . . . . . . . . . . . . . . . TYPEDEF ----- U_INT ----- 2 UCHAR8 . . . . . . . . . . . . . . . . TYPEDEF ----- U_CHAR ----- 1 DEKO_COMM_HEADER . . . . . . . . . . . TYPEDEF ----- STRUCT ----- 7 m_uiMsgOpcode. . . . . . . . . . . . MEMBER ----- U_INT 0000H 2 m_sblMsgPriority . . . . . . . . . . MEMBER ----- FIELD 0002H 2.0 m_sblDataLength. . . . . . . . . . . MEMBER ----- FIELD 0003H 11.0 m_sblMsgTimeStamp. . . . . . . . . . MEMBER ----- FIELD 0005H 11.0 DEKO_COMM_HEADER . . . . . . . . . . . * TAG * ----- STRUCT ----- 7 m_uiMsgOpcode. . . . . . . . . . . . MEMBER ----- U_INT 0000H 2 m_sblMsgPriority . . . . . . . . . . MEMBER ----- FIELD 0002H 2.0 m_sblDataLength. . . . . . . . . . . MEMBER ----- FIELD 0003H 11.0 m_sblMsgTimeStamp. . . . . . . . . . MEMBER ----- FIELD 0005H 11.0 z. . . . . . . . . . . . . . . . . . . PUBLIC DATA U_CHAR 0000H 1
why you not write code to see asssembler of compiler producing??? you use SRC option box
I would not do that. It may be that you are so bright that you never forget to remove the SRC statement, I am not. For that reason, "to see asssembler" I look at the .lst file which does not affect anything.
Erik
sir eric
you are also right again you know!
thanks you for my mistake ;)
Strictly speaking, per C89, a bitfield always occupies an "int". Despite the signed-ness of that declaration, the actual value of the bitfield may be signed or unsigned. (That is, an implementation may sign-extend a bitfield when it's used in comparisons, passed as a parameter, and so on. The "1" you assigned to a 1-bit bitfield might turn into a -1.) It's up to the implementation what order bitfields are allocated in those ints, and whether it uses bits MSB-to-LSB or vice versa.
(In fact, bitfields are pretty much non-portable and implementation-dependent. Add in the fact that most compilers generate worse code for bitfield access than when you use mask-and-shift operations, and I generally just recommend against using them at all.)
Though it's not standard, every compiler I've ever used allows you to specify a type other than "int" to hold bitfields. Usually, this is to conserve space.
Note that in your example you shift types from U8 to U16. This is almost certainly guaranteed to prevent the compiler from putting the bitfields in the same struct member, as it can do when the types remain the same.
C compilers are not allowed to reorder fields in a structure. They must occur in memory in the order of declaration. (C++ compilers are allowed to reorder structs unless they're declared 'extern "C"', but I've never met a compiler that actually does so.)
So:
U8 :2 // two bits come out of the first byte U16 :11 // can't fit in the U8, move on to the next int U16 : 11 // can't fit in the previous U16, use another
I'd expect this structure to occupy 7 bytes.