
As noted in a comment, the __gnu_cxx::__aligned_membuf class template can be simplified, because alignof(T) and alignas(T) use the correct alignment for a data member. That's true since GCC 8 and Clang 8. The EDG front end (as used by Intel icc, aka "Intel C++ Compiler Classic") does not implement the PR c++/69560 change, so keep using the old implementation when __EDG__ is defined, to avoid an ABI change for icc. For __gnu_cxx::__aligned_buffer<T> all supported compilers agree on the value of __alignof__(T), but we can still simplify it by removing the dependency on std::aligned_storage<sizeof(T), __alignof__(T)>. Add a test that checks that the aligned buffer types have the expected alignment, so that we can tell if changes like this affect their ABI properties. libstdc++-v3/ChangeLog: * include/ext/aligned_buffer.h (__aligned_membuf): Use alignas(T) directly instead of defining a struct and using 9its alignment. (__aligned_buffer): Remove use of std::aligned_storage. * testsuite/abi/aligned_buffers.cc: New test.
42 lines
1.4 KiB
C++
42 lines
1.4 KiB
C++
// { dg-do compile { target c++11 } }
|
|
|
|
// Check alignment of the buffer types used for uninitialized storage.
|
|
|
|
#include <ext/aligned_buffer.h>
|
|
|
|
template<typename T> using membuf = __gnu_cxx::__aligned_membuf<T>;
|
|
template<typename T> using objbuf = __gnu_cxx::__aligned_buffer<T>;
|
|
|
|
template<typename T>
|
|
constexpr bool
|
|
check_alignof_membuf()
|
|
{
|
|
return alignof(membuf<T>) == alignof(T)
|
|
&& __alignof__(membuf<T>) == alignof(T);
|
|
}
|
|
|
|
template<typename T>
|
|
constexpr bool
|
|
check_alignof_objbuf()
|
|
{
|
|
#if _GLIBCXX_INLINE_VERSION
|
|
// For the gnu-versioned-namespace ABI __aligned_buffer == __aligned_membuf.
|
|
return check_alignof_membuf<T>();
|
|
#else
|
|
return alignof(objbuf<T>) == __alignof__(T)
|
|
&& __alignof__(objbuf<T>) == __alignof__(T);
|
|
#endif
|
|
}
|
|
|
|
struct S { long long l; };
|
|
struct alignas(128) X { char x; };
|
|
static_assert( check_alignof_membuf<int>(), "membuf<int>" );
|
|
static_assert( check_alignof_membuf<long long>(), "membuf<long long>" );
|
|
static_assert( check_alignof_membuf<void*>(), "membuf<void*>" );
|
|
static_assert( check_alignof_membuf<S>(), "membuf<S>" );
|
|
static_assert( check_alignof_membuf<X>(), "membuf<X>" );
|
|
static_assert( check_alignof_objbuf<int>(), "objbuf<int>" );
|
|
static_assert( check_alignof_objbuf<long long>(), "objbuf<long long>" );
|
|
static_assert( check_alignof_objbuf<void*>(), "objbuf<void*>" );
|
|
static_assert( check_alignof_objbuf<S>(), "objbuf<S>" );
|
|
static_assert( check_alignof_objbuf<X>(), "objbuf<X>" );
|