Solved

Bit fields

Posted on 1998-05-14
15
193 Views
Last Modified: 2010-04-10
I have created a structure which looks like the following:
struct my_struct {
   unsigned short my_short : 8;
   int            my_int;
};
I would expect the size of this structure to be 5 bytes, yet when I compile and run this I get 6 bytes.  I have used the pragma pack(1) and the /Zp1 project settings and get the same results.  This program is running on a WinNT computer.  Is there any way to get the structure to be 5 bytes instead of 6?  Why does the bit field not seem to work?
0
Comment
Question by:jerm
  • 6
  • 6
  • 2
  • +1
15 Comments
 
LVL 22

Accepted Solution

by:
nietod earned 50 total points
ID: 1177328
answer coming.
0
 
LVL 22

Expert Comment

by:nietod
ID: 1177329
shorts are two bytes so

short my_short:8;

says allcoate rome for two bytes, but use only 8 bits of it.
char are one byte so use char instead of short and you should be fine.

struct my_struct {
       unsigned char my_short : 8;
       int            my_int;
    };
0
 
LVL 10

Expert Comment

by:RONSLOW
ID: 1177330
nietod is correct.  I tried that suggestion and the size of the structure was 5 bytes.  It did not matter if the char was the first element or the second.  It also did not mattter if char was signed or unsigned.  Thanks
0
 

Author Comment

by:jerm
ID: 1177331
Roger, you would be right, if it weren't for the fact that the structure was packed.  He said in the question he used

#pragma pack(1)

which prevents alignment.  Both the character type field AND the no-packing option are needed.  Since he had one, I just mentioned the other.
0
 
LVL 22

Expert Comment

by:nietod
ID: 1177332
Aha .. just found the reason...

>>>>>>>>>>
Microsoft Specific ®

Bit fields defined as int are treated as signed. A Microsoft extension to the ANSI C standard allows char and long types (both signed and unsigned) for bit fields. Unnamed bit fields with base type long, short, or char (signed or unsigned) force alignment to a boundary appropriate to the base type.
>>>>>>>>>>

Although this is ONLY mentioned in the C language bitfield info, and not the C++ section.

In C++ you can ues any integral type for a bitfield type, but there is no mention of this C extension in this case.

The explanation given by nietod is sort-of-correct (mine was not at all :-()

The results one gets are interesting...

struct S {
  long x:1;
  long y:1;
  long z:1;
}
sizeof (S) = 4 (1 long with 3 1-bit fields used)

struct S {
  long x:1;
  char y:1;
  long z:1;
}
sizeof (S) = 9 (1 long with 1 bit used, 1 char with 1 bit and another long with 1 bit)

It appears VC groups sucessive bitfields of the same type together and takes the all those bit field out of a single object of that type (eg. above, 3 1-bit field from a long). Whenever a new type for a bitfield is found, then this starts again.

This appears to be weird behaviour.

0
 
LVL 10

Expert Comment

by:RONSLOW
ID: 1177333
nietod .. with your explanation

struct S {
  long x:1;
  long y:1;
  long z:1;
}
would give a size of 12 (3 longs with 1-bit used of each.

but when actually trying it (yes.. I tried it after seeing that my reading of the docs didn't match the reported experimental evidence)

sizeof (S) = 4 (1 long with 3 1-bit fields used)

and this is with packing of 1.

0
 
LVL 10

Expert Comment

by:RONSLOW
ID: 1177334
Actually, I would have expected

struct S {
        long x:1;
        long y:1;
        long z:1;
      }
to be 4, which is right.  Add I would have expected

struct S {
        long x:1;
        char y:1;
        long z:1;
      }

to be... well ... a positive number, which is also right!  I checked in the Stroustrup book and there is no clear explantion of how this is supposed to work.  I guess it is implimentation defined.  however the VC docs seem to suggest that allowing char or short types is a Microsoft extension.  That is not true, according to Stroustrup it can be any integer type or bool.
0
How your wiki can always stay up-to-date

Quip doubles as a “living” wiki and a project management tool that evolves with your organization. As you finish projects in Quip, the work remains, easily accessible to all team members, new and old.
- Increase transparency
- Onboard new hires faster
- Access from mobile/offline

 
LVL 22

Expert Comment

by:nietod
ID: 1177335
It can be any (integral) type (that is standard) .. but what the MS extension is, is how that integral type is interpreted .. (ie the effect that it has on alignment/padding).

The nasty thing about that is that if you set up

struct X {
  bool b : 1;
};

in an attempt to get as small a bool type as possible, under VC you'll still get the same size as

struct Y {
  bool b;
};

bitfields only seem to make a difference when you have several of the same type consecutively, otherwise the storage requirements are the same as for the base type.

I don't think that is very nice :-(

0
 
LVL 10

Expert Comment

by:RONSLOW
ID: 1177336
I must say that I have enjoyed and learned a lot from the comments to my question.  I appreciate you help.  I wound up using a combination of your suggestions in my project.  Furthermore, I do not like the way bit fields seem to work.  All of the documentation I have read seems to indicate that bit fields should affect the size of the struct element, therefore the size of the struct.  Unfortunately it only affects the portion of the element which may be used.  Not sure if this is a MS thing, since I got the same results with gcc.  Have a nice day.
0
 

Author Comment

by:jerm
ID: 1177337
You said,

>> All of the documentation I have read seems to indicate that bit
>>  fields should affect the size of the struct element, therefore the
>>  size of the struct

You do know that this in byte increments, don't you? (or as we see here in multipliles of byte increments)  You should not expect

struct
{
   long x:1;
}

to create a structure that is one bit long.  The size of a structure is going to be in whole bytes so the debate was whethor that should be 1 byte or 4 bytes, not 1 bit.  Does that make sense?

If it does make sense, you should accept the answer.  If not, I'll try to explain.
0
 
LVL 22

Expert Comment

by:nietod
ID: 1177338
Technically (nit picking here) the size is in multiples of the size of a char - in most/many systems (PC certainly), this is one 8-bit byte.

This discussion has been enlightening and surprising for me.  Bit fields in VC certainly behave differently than I would have thought also.

0
 
LVL 10

Expert Comment

by:RONSLOW
ID: 1177339
Bang!  The autograder hits again!
0
 
LVL 11

Expert Comment

by:alexo
ID: 1177340
??? Do you post that on all auto grades now?  
0
 
LVL 22

Expert Comment

by:nietod
ID: 1177341
Acutally .. I think that EE should post a comment saying that the question has been auto-graded.

At least the right person got the points for this one.
0
 
LVL 10

Expert Comment

by:RONSLOW
ID: 1177342
>> Do you post that on all auto grades now?
Whenever I get an email notification, check out the question and find out it's an autograder false alarm, then, yes, I voice my complaint.
0

Featured Post

Better Security Awareness With Threat Intelligence

See how one of the leading financial services organizations uses Recorded Future as part of a holistic threat intelligence program to promote security awareness and proactively and efficiently identify threats.

Join & Write a Comment

When writing generic code, using template meta-programming techniques, it is sometimes useful to know if a type is convertible to another type. A good example of when this might be is if you are writing diagnostic instrumentation for code to generat…
This article shows you how to optimize memory allocations in C++ using placement new. Applicable especially to usecases dealing with creation of large number of objects. A brief on problem: Lets take example problem for simplicity: - I have a G…
The viewer will learn how to clear a vector as well as how to detect empty vectors in C++.
The viewer will be introduced to the member functions push_back and pop_back of the vector class. The video will teach the difference between the two as well as how to use each one along with its functionality.

746 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

10 Experts available now in Live!

Get 1:1 Help Now