How to check alignment of returned data in malloc () implementation?

malloc(sz) returns memory whose alignment works for any object.

On x86 32-bit machines, this means that the address value returned by malloc() should be evenly divisible by 4. But in practice, 32-bit malloc implementations return 8-byte aligned memory, which means that the returned addresses are always uniformly divisible by 8. You must do this too. (On x86-64 / IA-64 machines, the maximum data alignment is 8, but the malloc implementation returns 16-byte aligned memory.)

I have a test for this situation.

 // Check alignment of returned data. int main() { double* ptr = (double*) malloc(sizeof(double)); assert((uintptr_t) ptr % __alignof__(double) == 0); assert((uintptr_t) ptr % __alignof__(unsigned long long) == 0); char* ptr2 = (char*) malloc(1); assert((uintptr_t) ptr2 % __alignof__(double) == 0); assert((uintptr_t) ptr2 % __alignof__(unsigned long long) == 0); } 

My malloc code allocates more space than requested by the user. The first part of this space is used to store distribution metadata, including allocated size.

sizeof(metadata) % 8 == 0

But my bunch

  static char heap[Heap_Capacity]; 

starting from a value that is not divisible by 8

 metadata* block = (metadata*)heap; (uintptr_t)block % 8 != 0 

My tests fail, what can I do in this situation? How to make sure an array starts with an address that

 metadata* block = (metadata*)heap; (uintptr_t)block % 8 == 0 

?

+5
source share
1 answer

You can use union to force alignment (see alignment of Union elements ) or calculate the starting index to align alignment correctly (which can reduce your heap capacity by up to 7 bytes).

+2
source

All Articles