gcc/libstdc++-v3/testsuite/abi/aligned_buffers.cc
Jonathan Wakely ac8c61b62e
libstdc++: Simplify <ext/aligned_buffer.h> class templates
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.
2024-06-28 20:19:02 +01:00

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>" );