[NTLUG:Discuss] Processor architecture related queries

Steve Baker sjbaker1 at airmail.net
Wed Dec 3 08:19:31 CST 2003


Vaidya, Harshal (Cognizant) wrote:

> To achieve portable code it is specifically mentioned that the structures in C/C++ should be arranged
 > in such a way that the objects having larger sizes should be placed prior to the objects having lower
 > sizes.


OK - so there are actually two completely separate reasons for doing this.

The background is that in some architectures, 'int' and 'float' variables
have to be stored at an address which is an exact multiple of 4, 'short's
at exact multiples of 2 bytes and 'double's at exact multiples of 8.

On other platforms, that's not 100% required - but the CPU runs more
slowly for variables that are not aligned as above.  On these platforms,
there is typically a compiler option to use padding or strip it out.

On yet other platforms, it makes no difference whether things are aligned
or not.

On still other platforms, double's only have to be on 4 byte boundaries - not
8.

Now, if (in C or C++ say) you write a structure containing an int, a char
and another int, if the compiler just stuck those end-to-end, then if
the first integer was at address 'N', then the char would be at N+4
and the second integer would be at 'N+5' - which would make it mis-aligned.

On architectures where the alignment matters, the compiler will insert three
'padding' bytes after the 'char' variable so that the second integer ends
up at 'N+8' and is once again aligned correctly.

This is done automatically - and aside from the 'sizeof' your structure
being different on some platforms, you aren't really aware of it happening.

Now, if you change the structure to put the two 'int' variables first and
the 'char' second, then the first int is at 'N', the second at 'N+4' and
the char is at N+8...and no padding is needed unless there is an array of
those structures or something.

So - why is this important for portability?

1) CACHE COHERENCY.

This is a bit of a stretch - but the hardware will be more likely to be able
to keep the structure in cache if there is less padding inside it and if all
the 'useful' parts of the memory block are consecutive.  Hence it's worth
re-ordering your structures to gain a little bit of speed.

Personally, unless this code is really time-critical, I wouldn't change the
structures for this reason.  I doubt that you'd notice the performance change
on most architectures.   However, when writing new code, it's worth bearing in
mind.

2) BINARY DATA COMPATIBILITY.

If your code was running on a platform that didn't need padding - and you are moving
to one that does, you need to be aware that some sloppy programmers will write
data to disk - or to a network by writing something like:

      fwrite ( & my_structure, sizeof(my_structure), 1, filedescriptor ) ;

...but if the architecture requires padding, then the padding will be written to disk
along with the data.   Hence, you won't be able to swap files between one architecture
and another - and who knows what else could go wrong.

Well-written programs never do that.  A lot of programs do that!

---------------------------- Steve Baker -------------------------
HomeEmail: <sjbaker1 at airmail.net>    WorkEmail: <sjbaker at link.com>
HomePage : http://www.sjbaker.org
Projects : http://plib.sf.net    http://tuxaqfh.sf.net
            http://tuxkart.sf.net http://prettypoly.sf.net
-----BEGIN GEEK CODE BLOCK-----
GCS d-- s:+ a+ C++++$ UL+++$ P--- L++++$ E--- W+++ N o+ K? w--- !O M-
V-- PS++ PE- Y-- PGP-- t+ 5 X R+++ tv b++ DI++ D G+ e++ h--(-) r+++ y++++
-----END GEEK CODE BLOCK-----




More information about the Discuss mailing list