1

The context is: One would like to get a fairly well aligned memory, e.g. for allowing the compiler to use AVX, AVX2 . At the same time, one attempts to keep the code as portable as reasonably possible. Allocating using aligned_alloc sound nice, but C11 lists this as undefined behaviour:

"The alignment requested of the aligned_alloc function is not valid or not supported by the implementation, or the size requested is not an integral multiple of the alignment"

Thus, using for example aligned_alloc(32, 128) can have great results often, but the other day, it can be UB in some other compiler.

For that case, less strict alignment would suffice, resulting in slower, but correct code. Thus some ideal approach would request strictest alignment available up to 128 in this case. Is there any way to achieve something like this?

-- The question is mainly about using aligned_alloc, instead up creating one's own allocator.

==EDIT==

Already answered in comment, it is _Alignof (max_align_t)

thx chux , I overlooked that one!

Gábor Buella
  • 1,840
  • 14
  • 22
  • If portability is important, you can guarantee you get your alignment by allocating n+alignment-1 bytes and self adjusting your pointer. – Cory Nelson Jan 13 '15 at 23:12
  • 3
    Look into `max_align_t` : "which is an object type whose alignment is as great as is supported by the implementation in all contexts;" – chux - Reinstate Monica Jan 13 '15 at 23:18
  • 1
    [inferring-memory-alignment](http://codereview.stackexchange.com/questions/73712/inferring-memory-alignment/75211) may be useful. – chux - Reinstate Monica Jan 13 '15 at 23:21
  • I'll leave it to others to write a detailed answer. GTG – chux - Reinstate Monica Jan 13 '15 at 23:28
  • http://coliru.stacked-crooked.com/a/c2172c55743636d8 Overallocate and align yourself? – Mooing Duck Jan 13 '15 at 23:29
  • @BuellaGábor: `size+alignment` will _always_ have at least one byte extra. (check with allocating 1 char, allocates 2 bytes). If the original allocation was already aligned, then there's a second potential aligned location in that allocation touching the end. I always return the second, which means there's always at least one extra in the beginning. – Mooing Duck Jan 13 '15 at 23:35
  • Sorry, I just read it already stores the uchar, not the char*, so yes. But `aligned_alloc` still looks better. – Gábor Buella Jan 13 '15 at 23:38

1 Answers1

1

Or you can just always align. If you're scared of UB, you can write your aligned allocator, the only real issue is that you need to free the unaligned pointer:

auto align 16;
auto aqbuf = malloc(alignedSize);
auto aligned = (unsigned char*)(((intptr_t)(aqbuf) + (align-1)) & ~(align-1));//aqbuf != aligned sometimes...
free(aqbuf);//forget about aligned
Mikhail
  • 7,749
  • 11
  • 62
  • 136
  • 1
    `size_t` is required to hold the size of the largest object you can create. it is not required to be equal to a pointer in size. For that, use `intptr_t`. – Cory Nelson Jan 13 '15 at 23:13
  • I note that the post is tagged C and C11 but not C++, so `reinterpret_cast` might be out-of-scope for the question. – danfuzz Jan 13 '15 at 23:15
  • @CoryNelson Maybe I don't know, anyways I changed `size_t` to `intptr_t` – Mikhail Jan 13 '15 at 23:15
  • 1
    @danfuzz, hah okay I changed them to C style casts. – Mikhail Jan 13 '15 at 23:16
  • `C11`, the whole point is to use `aligned_alloc` from , so there would be no need hack up a custom allocator. I can already do that. Also, that `auto` ain't going to work in C either. But thanks anyways. – Gábor Buella Jan 13 '15 at 23:16
  • 1
    If you're going to provide code, it might as well make it easy for callers: http://coliru.stacked-crooked.com/a/54a0d7c5e93d9d63 – Mooing Duck Jan 13 '15 at 23:31