2 Copyright © 1995-2012, The AROS Development Team. All rights reserved.
5 AROS extension function malloc_align().
8 #include <exec/types.h>
10 #include "__memalign.h"
14 #define powerof2(x) ((((x)-1)&(x))==0)
16 /*****************************************************************************
28 Allocate aligned memory.
31 size - How much memory to allocate.
32 alignment - Alignment of allocated memory. The address of the
33 allocated memory will be a multiple of this value, which
34 must be a power of two and a multiple of sizeof(void *).
37 A pointer to the allocated memory or NULL.
40 errno is set to EINVAL if the alignment parameter was not a power of
41 two, or was not a multiple of sizeof(void *).
42 errno is set to ENOMEM if there was insufficient memory to fulfill
44 Memory allocated by malloc_align() should be freed with free(). If
45 not, it will be freed when the program terminates.
47 This function is AROS specific.
54 calloc(), free(), malloc()
58 ******************************************************************************/
60 char *mem
= NULL
, *orig
, *tmp
;
62 /* check the alignment is valid */
63 if (alignment
% sizeof(void *) != 0 || !powerof2(alignment
))
69 /* allocate enough space to satisfy the alignment and save some info */
70 mem
= malloc(size
+ alignment
+ AROS_ALIGN(sizeof(size_t)) + AROS_ALIGN(sizeof(void *)));
77 /* if it's already aligned correctly, then we just use it as-is */
78 if (((IPTR
) mem
& (alignment
-1)) == 0)
83 /* move forward to an even alignment boundary */
84 mem
= (char *) (((IPTR
) mem
+ alignment
- 1) & -alignment
);
87 /* store a magic number in the place that free() will look for the
88 * allocation size, so it can handle this specially */
89 tmp
-= AROS_ALIGN(sizeof(size_t *));
90 *((size_t *) tmp
) = MEMALIGN_MAGIC
;
92 /* then store the original pointer before it, for free() to find */
93 tmp
-= sizeof(void *);
94 *((void **) tmp
) = orig
;
97 } /* posix_memalign */