tags:

views:

1574

answers:

5

K&R (2nd ed.) and other C-language texts I have read that cover implementation of a dynamic memory allocator in the style of malloc() and free() usually also mention, in passing, something about alignment restrictions. Apparently certain platforms restrict how you can store and address certain values, requiring, for example, integers to be stored at addresses that are multiples of four. Do any major platforms (Intel & AMD, SPARC, Alpha) still impose these kinds of restrictions, or can I safely ignore it?

+3  A: 

Alignment is still quite important today. Some processors (the 68k family jumps to mind) would throw an exception if you tried to access a word value on an odd boundary. Today, most processors will run two memory cycles to fetch an unaligned word, but this will definitely be slower than an aligned fetch. Some other processors won't even throw an exception, but will fetch an incorrect value from memory!

If for no other reason than performance, it is wise to try to follow your processor's alignment preferences. Usually, your compiler will take care of all the details, but if you're doing anything where you lay out the memory structure yourself, then it's worth considering.

Greg Hewgill
+1  A: 

You still need to be aware of alignment issues when laying out a class or struct in C(++). In these cases the compiler will do the right thing for you, but the overall size of the struct/class may be more wastefull than necessary

For example:

struct
{ 
    char A;
    int B;
    char C;
    int D;
};

Would have a size of 4 * 4 = 16 bytes (assume Windows on x86) whereas

struct
{ 
    char A;
    char C;
    int B;
    int D;
};

Would have a size of 4*3 = 12 bytes.

This is because the compiler enforces a 4 byte alignment for integers, but only 1 byte for chars.

In general pack member variables of the same size (type) together to minimize wasted space.

Rob Walker
+1  A: 

As Greg mentioned it is still important today (perhaps more so in some ways) and compilers usually take care of the alignment based on the target of the architecture. In managed environments, the JIT compiler can optimize the alignment based on the runtime architecture.

You may see pragma directives (in C/C++) that change the alignment. This should only be used when very specific alignment is required.

// For example, this changes the pack to 2 byte alignment.
#pragma pack(2)
dpp
+3  A: 

Sparc, MIPS, Alpha, and most other "classical RISC" architectures only allow aligned accesses to memory, even today. An unaligned access will cause an exception, but some operating systems will handle the exception by copying from the desired address in software using smaller loads and stores. The application code won't know there was a problem, except that the performance will be very bad.

MIPS has special instructions (lwl and lwr) which can be used to access 32 bit quantities from unaligned addresses. Whenever the compiler can tell that the address is likely unaligned it will use this two instruction sequence instead of a normal lw instruction.

x86 can handle unaligned memory accesses in hardware without an exception, but there is still a performance hit of up to 3X compared to aligned accesses.

Ulrich Drepper wrote a comprehensive paper on this and other memory-related topics, What Every Programmer Should Know About Memory. It is a very long writeup, but filled with chewy goodness.

DGentry
A: 

Note that even on IA-32 and the AMD64, some of the SSE instructions/intrinsics require aligned data. These instructions will throw an exception if the data is unaligned, so at least you won't have to debug "wrong data" bugs. There are equivalent unaligned instructions as well, but like Denton says, they're are slower.

If you're using VC++, then besides the #pragma pack directives, you also have the __declspec(align) directives for precise alignment. VC++ documentation also mentions an __aligned_malloc function for specific alignment requirements.

As a rule of thumb, unless you are moving data across compilers/languages or are using the SSE instructions, you can probably ignore alignment issues.

Pramod