Jump to content
  • Advertisement

Archived

This topic is now archived and is closed to further replies.

mackscynox

c++ struct size ?

This topic is 5332 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

hi everybody i want know that if the size doesnot show true or i make a mistake in calculating the size? struct _s1{ long int i; //4 }; //size of s1 is 4 compiler says //then consider this struct _s2{ long int i; //4 char c; //1 ? }; //size of s2 is 8 (not a joke) //this is 8 too struct _s3{ long int i; //4 char c[2]; //2 ? }; //but still 8 struct _s4{ long int i; //4 char c[5]; //5 ? }; //size of s4 is 12 i try to think about why 4 + 1 is 8 here in s2 does structs have a restriction about size? compiler is BCC55 free command line compiler but also tried in dev-c and same results thanks

Share this post


Link to post
Share on other sites
Advertisement
It''s not a restriction, but the compilers align the members on certain addresses. In MSVC exists a pragma directive pack, that can set the alignment of the members ...

Share this post


Link to post
Share on other sites
Remember the stack on a 32Bit system *MUST* be four bytes aligned, so a char a short int and a long int all take up 4Bytes on the stack. Thus any data structure must too be four-byte aligned.

If you don''''t gosub a program loop you''''ll never get a sub-routine - Kryten Red Dwarf

Share this post


Link to post
Share on other sites
Compilers generally offer options for packing structures. In VC++, the default is 8-byte alignment, but you can change it. As noted, there''s a pragma ''pack'' that can let you control that packing on a structure-by-structure basis ... not sure about your compiler. If you change the packing to a one-byte boundary, your int and char will become a 5-byte structure. While 32 bit processors will operate best (most efficiently) with 4 or 8-byte packing, they will work with any packing size, and it can become necessary to change the structure packing if you have to share data structure between different languages .. like between C and VB, for instance.

Share this post


Link to post
Share on other sites
Disabling struct packing in Borland:

#pragma option push -a1

/* Et cetera */

#pragma option pop

I use two headers in my projects. One to enable packing and the other to reset it to the default afterward.

For example, to enable packing:

#if defined(__GNUC__)
#define PACKED __attribute__((packed))
#elif defined(_MSC_VER) || defined(__LCC__)
#pragma pack (push, 1)
#elif defined(__BORLANDC__)
#pragma option push -a1
#elif defined(__MWERKS__)
#pragma options align=packed
#else
#error Could not disable structure padding.
#endif

#ifndef PACKED
#define PACKED
#endif

Then, to disable packing:

#undef PACKED

#if defined(_MSC_VER) || defined(__LCC__)
#pragma pack (pop)
#elif defined(__BORLANDC__)
#pragma option pop
#elif defined(__MWERKS__)
#pragma options align=reset
#endif

Used like so:

#include "pack_begin.h"

struct something {
int a PACKED;
char b PACKED;
short c PACKED;
};

#include "pack_end.h"

(Sometimes, one can get away with just putting "PACKED" at the structure level, but other times not. So, just to be safe, I put it after every member.)

Now I''ll bookmark this thread so I never have to post this again .

Share this post


Link to post
Share on other sites
As was mentioned earlier, alignment is the reason. If you take your structure _s2, it actually contains 5 bytes of data. But if you create an array of _s2, then each member inside the structure must still be aligned on its boundary. For a character an alignment on any address is sufficent, but for a 32 bit integer (as is ''long int i''), it must be aligned on a 32 bit boundary. Therefore the compiler inserts extra padding bytes to increase the structure size to 8 bytes for _s2 or 12 bytes for _s4.

Conclusion:
The alignment of a structure is the biggest alignment of one of its members.
The size of the structure is a multiple of its alignment.

Share this post


Link to post
Share on other sites
I think someone mentioned this, but supposedly you get a bit better performance by letting the compiler align like this.

If you do let the compiler align how it wants to, putting your members in order from largest to smallest will help lower th size of the struct.

In the following example, s1 is smaller than s2, even though they contain the same members.

struct s1{
long int i1;
long int i2;
long int i3;
long int i4;
char c1;
char c2;
char c3;
char c4;
}; // sizeof == 20

struct s2{
char c1;
long int i1;
char c2;
long int i2;
char c3;
long int i3;
char c4;
long int i4;
}; // sizeof == 32



Drakonite

Shoot Pixels Not People

Share this post


Link to post
Share on other sites
i want to ask something else about the usage of pragma and the usage of PACKED in "Null and void" member''s example

- what is the logic of the usage PACKED here and what happens if i dont include it (i have tried it and seen that the size changes to 8 as i didnot expect to see) [also i didnot understand the meanaing of that sentence i build above ]
- why the size doesnot still change after we defined the PACKED thing but if we didnot include it in struct definition?

thanks again

Share this post


Link to post
Share on other sites

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!