# How does new handle alignment?

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

## Recommended Posts

OK, I'm working on some fairly low level structure (C++ struct/class) manipulation type stuff. Essentially, I'm manually alocating a structure. The idea is to replicate the behaviour of C++ itself. Now, at the moment, I'm simply doing new char[] to alocate a buffer. However I don't know what the alignment of that would be. I noticed MSVC has an aligned_malloc function (sub-question: what is the GCC equvilent?), so I was going to move over to this. It then occured to me that I should see how operator new does it. Now operator new only takes one argument (size). How you'd magically generate the information to call aligned_malloc, which takes size and alignment, I don't understand. So question is: How does C++ handle alignment? Note: I know the required alignment of my structures already.

##### Share on other sites
Quote:
 (sub-question: what is the GCC equvilent?)

POSIX 1003.1d defines the function posix_memalign (so named because an earlier, now obsolete function memalign found on many systems). Also, all glibc malloc implementations always return 8-byte aligned addresses.

##### Share on other sites
What the standard says is:
Quote:
 The pointer returned shall be suitably aligned so that it can be convertedto a pointer of any complete object type and then used to access the object or array in the storageallocated (until the storage is explicitly deallocated by a call to a corresponding deallocation function).

basicly that means on an x86 system you could get mostly anything (though most implementations does return at least 4byte aligned addresses) and on something like 68k/PPC and other systems where odd addresses gives bus-errors for non byte types you are guaranteed to get an even address.

And that's it.

##### Share on other sites
OK, so new calls malloc (right?), which will always give an 8-byte aligned address (at least on glibc). So I could just call new char[whatever] or indeed new whatever, and the resultant pointer would be aligned to 8 bytes (nothing needs anything bigger, right?).

Basically, I just don't want to alocate something with new char[] and find that when I placement-new over the top of that, the buffer has a lower alignment that the struct I'm dropping on it.

So... is new char[] the equivelent of what C++ does anyway? Does it just always give you an 8-byte aligned pointer (effectivly making alignment a non-issue)?

##### Share on other sites
This should answer all your questions on portable alignment: Boost::Pool on Alignment

Essentially, new is guaranteed to properly align a block of size X to hold an array of any structure of size X or smaller. Thus, allocating 10 bytes with new would be aligned to hold anything 1 to 10 bytes in size, and it could be 2 objects of size 5 or 3 objects of size 3 etc. It gets somewhat tricky when you want to put different sizes in a single block, but it is still easily doable.

Also, boost has a templated value that will return the alignment requirements of any type.

##### Share on other sites
should work with any c++ compiler:
void* AlignedMalloc(size_t size,int byteAlign){	void *mallocPtr = malloc(size + byteAlign + sizeof(void*));	size_t ptrInt = (size_t)mallocPtr;	ptrInt = (ptrInt + byteAlign + sizeof(void*)) / byteAlign * byteAlign;	*(((void**)ptrInt) - 1) = mallocPtr;    return (void*)ptrInt;}void AlignedFree(void *ptr){	free(*(((void**)ptr) - 1));}

##### Share on other sites
Ah, ok, I gotcha. From the boost thing:

Quote:
 Predicate 2: Any block of memory allocated as an array of characters through operator new[] (hereafter referred to as the block) is properly aligned for any object of that size or smaller

Which basically means that the memory allocation will round up to the nearest 2^N boundary when it allocates (up to 8 byte alignment?). Meaning an struct of 6 chars, which needs an alignment of 1, will just get an alignment of 8 (and bugger the wasted 2 bytes). An 8 byte alignment being suitable for 1 byte alignment data.

So I can use new char[] and safely drop anything on it, as long as it fits and it's properly aligned within itself? (I am thinking "yes")

Of course, this raises an interesting question - say my 6-char structure - if I made an array of 3 of them, would it use 18 bytes, or 24? Unless it knew that it only needs 1-byte alignment, it would have to be 24, right?

Or does that 6-byte struct get padded into 8 bytes by the compiler anyway?

##### Share on other sites
Quote:
 Original post by Andrew RussellOK, so new calls malloc (right?)

Not nessecaraly it's up to compiler vendor to-do so.

On a slightly unrelated note don't bother using new char, any form of implicit invocation of new will initialize memory, just invoke operator new & delete explicitly with the size required it will allocate a chunk of uninitialized memory e.g.:

#include <new>void* buf = ::operator new(sizeof(foo)); // allocates only//...foo* f = ::new(buf) foo(/* ... */);      // constructs only//...f->~foo();                               //destructs only//...::operator delete(buf);                  // deallocates only

Another alternative is to overload operators new/delete for a whole class hierarchy then the compiler will also give you the correct size to allocate also there is a special variant signature of delete for class or class hierarchies which the last parameter gives you the size of the actual memory passed including void pointer:

struct foo {  void* operator new(std::size_t n);  //...  // compiler automatically passes the size for you implicitly.  void operator delete(void* p, std::size_t n);

##### Share on other sites
Ah great, thanks for that - I'll go with the first one in that case (implicit call to operator new). I don't have a class hirachy to put a member operator new in.

##### Share on other sites
Quote:
 Original post by Andrew Russell[...]So I can use new char[] and safely drop anything on it, as long as it fits and it's properly aligned within itself? (I am thinking "yes")
Yes

Quote:
 Of course, this raises an interesting question - say my 6-char structure - if I made an array of 3 of them, would it use 18 bytes, or 24? Unless it knew that it only needs 1-byte alignment, it would have to be 24, right?Or does that 6-byte struct get padded into 8 bytes by the compiler anyway?
The structure must be properly padded by the compiler such that putting two of them with 0 bytes between will result in both being properly aligned if the first one is.

I don't know if char[x] must be properly aligned for an x-byte structure, but using 'new char[x]' will meet that requirement.

1. 1
Rutin
27
2. 2
3. 3
4. 4
5. 5

• 11
• 9
• 9
• 9
• 14
• ### Forum Statistics

• Total Topics
633311
• Total Posts
3011312
• ### Who's Online (See full list)

There are no registered users currently online

×