If I define a simple type with a certain alignment requirement, shouldn't a std::vector<t>
of said type honour the alignment for every single element?
Consider the following example
typedef std::array<double,3> alignas(32) avx_point;
std::vector<avx_point> x(10);
assert(!(std::ptrdiff_t(&(x[0]))&31) && // assert that x[0] is 32-byte aligned
!(std::ptrdiff_t(&(x[1]))&31)); // assert that x[1] is 32-byte aligned
I found that the alignment requirement is silently (without any warning) violated by clang 3.2 (with or without -stdlib=libc++
), while gcc 4.8.0 issues a warning that it ignores the attributes on the template argument to std::vector
(the intel compiler is too daft to understand alignas
, but if I use __declspec(align(32))
instead, it behaves like clang). Both create code that triggers the assert.
So, is this correct behaviour or a bug of clang (and icpc) and an issue with gcc?
edit
to answer a question raised in the comments: if I define
typedef typename std::aligned_storage<sizeof (avx_point),
alignof(avx_point)>::type avx_storage;
I get
sizeof (avx_storage) == 32;
alignof(avx_storage) == 32;
but std::vector<avx_storage>
still fails to align the first element (and hence all the others too) for clang and gcc (without warning this time). So there are apparently two issues with the implementations: first, that std::allocator<type>
ignores any alignment requirements even for the first element (illegal?) and second, that no padding is applied to ensure alignment of subsequent elements.
––––––––––––
edit There is a related, more practical question for how to obtain memory suitably aligned for SSE/AVX operations. In contrast, I want to know whether std::vector<>
(or std::allocator<>
) shouldn't honour alignas
as of the C++ standard (as of 2011). None of the answers to that other question are suitable answers to this one.
See Question&Answers more detail:
os 与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…