[gcc r17-4152] libstdc++: Implement C++29 P3793R2 - Better shifting (except simd)
Jakub Jelinek
jakub@gcc.gnu.org
Fri Sep 11 07:31:12 GMT 2026
https://gcc.gnu.org/g:4ff92b02340cfc54939d0411e057a7af20974d59
commit r17-4152-g4ff92b02340cfc54939d0411e057a7af20974d59
Author: Jakub Jelinek <jakub@redhat.com>
Date: Fri Sep 11 09:29:53 2026 +0200
libstdc++: Implement C++29 P3793R2 - Better shifting (except simd)
The following patch implements the <bit> part of
C++29 P3793R2 - Better shifting
paper.
2026-09-11 Jakub Jelinek <jakub@redhat.com>
* include/std/bit: Implement C++29 P3793R2 - Better shifting.
(std::__signed_or_unsigned_integer): New concept.
(std::shl, std::shr): New function templates.
* include/bits/version.def (bitops): Add different value for C++29.
* include/bits/version.h: Regenerate.
* src/c++23/std.cc.in (std::shl, std::shr): Export for C++29.
* testsuite/26_numerics/bit/bit.shift/shl.cc: New test.
* testsuite/26_numerics/bit/bit.shift/shr.cc: New test.
Reviewed-by: Jonathan Wakely <jwakely@redhat.com>
Diff:
---
libstdc++-v3/include/bits/version.def | 4 +
libstdc++-v3/include/bits/version.h | 7 +-
libstdc++-v3/include/std/bit | 31 +++-
libstdc++-v3/src/c++23/std.cc.in | 4 +
.../testsuite/26_numerics/bit/bit.shift/shl.cc | 159 +++++++++++++++++++++
.../testsuite/26_numerics/bit/bit.shift/shr.cc | 159 +++++++++++++++++++++
6 files changed, 362 insertions(+), 2 deletions(-)
diff --git a/libstdc++-v3/include/bits/version.def b/libstdc++-v3/include/bits/version.def
index 26d37e75b261..3f314ffe1ee0 100644
--- a/libstdc++-v3/include/bits/version.def
+++ b/libstdc++-v3/include/bits/version.def
@@ -890,6 +890,10 @@ ftms = {
ftms = {
name = bitops;
+ values = {
+ v = 202606;
+ cxxmin = 29;
+ };
values = {
v = 201907;
cxxmin = 20;
diff --git a/libstdc++-v3/include/bits/version.h b/libstdc++-v3/include/bits/version.h
index de78de21ad14..16b7425269a3 100644
--- a/libstdc++-v3/include/bits/version.h
+++ b/libstdc++-v3/include/bits/version.h
@@ -989,7 +989,12 @@
#undef __glibcxx_want_bit_cast
#if !defined(__cpp_lib_bitops)
-# if (__cplusplus >= 202002L)
+# if (__cplusplus > 202603L)
+# define __glibcxx_bitops 202606L
+# if defined(__glibcxx_want_all) || defined(__glibcxx_want_bitops)
+# define __cpp_lib_bitops 202606L
+# endif
+# elif (__cplusplus >= 202002L)
# define __glibcxx_bitops 201907L
# if defined(__glibcxx_want_all) || defined(__glibcxx_want_bitops)
# define __cpp_lib_bitops 201907L
diff --git a/libstdc++-v3/include/std/bit b/libstdc++-v3/include/std/bit
index b735044ca18b..46fa8b65032c 100644
--- a/libstdc++-v3/include/std/bit
+++ b/libstdc++-v3/include/std/bit
@@ -407,9 +407,38 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
/// @cond undocumented
template<typename _Tp>
concept __unsigned_integer = __is_unsigned_integer<_Tp>::value;
+
+ template<typename _Tp>
+ concept __signed_or_unsigned_integer
+ = __is_signed_or_unsigned_integer<_Tp>::value;
/// @endcond
- // [bit.rot], rotating
+#if __cpp_lib_bitops >= 202606L // >= C++29
+ // [bit.shift], shifting
+ template<__signed_or_unsigned_integer _Tp, __signed_or_unsigned_integer _Sp>
+ [[nodiscard]] constexpr _Tp
+ shl(_Tp __x, _Sp __s) noexcept
+ {
+ constexpr auto _Nd = __gnu_cxx::__int_traits<_Tp>::__digits
+ + is_signed_v<_Tp>;
+ if (__s < 0)
+ return __s > -_Nd ? __x >> -__s : static_cast<_Tp>(__x < 0 ? -1 : 0);
+ return __s < _Nd ? __x << __s : static_cast<_Tp>(0);
+ }
+
+ template<__signed_or_unsigned_integer _Tp, __signed_or_unsigned_integer _Sp>
+ [[nodiscard]] constexpr _Tp
+ shr(_Tp __x, _Sp __s) noexcept
+ {
+ constexpr auto _Nd = __gnu_cxx::__int_traits<_Tp>::__digits
+ + is_signed_v<_Tp>;
+ if (__s < 0)
+ return __s > -_Nd ? __x << -__s : static_cast<_Tp>(0);
+ return __s < _Nd ? __x >> __s : static_cast<_Tp>(__x < 0 ? -1 : 0);
+ }
+#endif
+
+ // [bit.rotate], rotating
/// Rotate `x` to the left by `s` bits.
template<__unsigned_integer _Tp>
diff --git a/libstdc++-v3/src/c++23/std.cc.in b/libstdc++-v3/src/c++23/std.cc.in
index aea66750adf7..928281699db9 100644
--- a/libstdc++-v3/src/c++23/std.cc.in
+++ b/libstdc++-v3/src/c++23/std.cc.in
@@ -695,6 +695,10 @@ export namespace std
#if __cpp_lib_byteswap // >= C++23
using std::byteswap;
#endif
+#if __cpp_lib_bitops >= 202606L // >= C++29
+ using std::shl;
+ using std::shr;
+#endif
}
// 22.9 <bitset>
diff --git a/libstdc++-v3/testsuite/26_numerics/bit/bit.shift/shl.cc b/libstdc++-v3/testsuite/26_numerics/bit/bit.shift/shl.cc
new file mode 100644
index 000000000000..fa2ec3f703fc
--- /dev/null
+++ b/libstdc++-v3/testsuite/26_numerics/bit/bit.shift/shl.cc
@@ -0,0 +1,159 @@
+// { dg-do compile { target c++29 } }
+
+#include <bit>
+#include <limits>
+
+template<typename Int, typename SInt>
+constexpr bool
+test_negative_shifts()
+{
+ constexpr unsigned digits = std::numeric_limits<Int>::digits
+ + std::is_signed_v<Int>;
+
+ Int xarr[] = { (Int)-1, 0, 1, 3, 6, 7, 0x10, 0x11, 0x22, 0x44, (Int)0x80,
+ (Int)-55, (Int)-927 };
+ SInt sarr[] = { 1, 4, 5, digits - 1, digits, (SInt)-12 };
+ for (Int x : xarr)
+ for (SInt s : sarr)
+ if (std::shl(x, -s) != std::shr(x, s))
+ return false;
+ return true;
+}
+
+template<typename Int, typename SInt>
+constexpr auto
+test(Int x, SInt y)
+-> decltype(std::shl(x, y))
+{
+ static_assert( noexcept(std::shl(x, 0)) );
+
+ constexpr unsigned digits = std::numeric_limits<Int>::digits
+ + std::is_signed_v<Int>;
+
+ static_assert( std::shl((Int)0, (SInt)0) == 0 );
+ static_assert( std::shl((Int)0, (SInt)1) == 0 );
+ static_assert( std::shl((Int)0, (SInt)4) == 0 );
+ static_assert( std::shl((Int)0, (SInt)8) == 0 );
+ static_assert( std::shl((Int)0, (SInt)-4) == 0 );
+ static_assert( std::shl((Int)-1, (SInt)0) == (Int)((Int)-1 << 0) );
+ static_assert( std::shl((Int)-1, (SInt)1) == (Int)((Int)-1 << 1) );
+ static_assert( std::shl((Int)-1, (SInt)4) == (Int)((Int)-1 << 4) );
+ static_assert( std::shl((Int)-1, (SInt)8) == (Int)((Int)-1 << 8) );
+ static_assert( std::shl((Int)-1, (SInt)-4)
+ == ((SInt)-4 < 0 ? (Int)-1 >> (SInt)4
+ : (SInt)-4 >= digits ? 0
+ : (Int)((Int)-1 << ((SInt)-4 < 0 ? 0 : (SInt)-4))) );
+
+ static_assert( std::shl((Int)1, (SInt)0) == (Int)1 << 0 );
+ static_assert( std::shl((Int)1, (SInt)1) == (Int)1 << 1 );
+ static_assert( std::shl((Int)1, (SInt)4) == (Int)1 << 4 );
+ static_assert( std::shl((Int)1, (SInt)digits) == (Int)0 );
+ static_assert( std::shl((Int)7, (SInt)digits) == (Int)0 );
+ static_assert( std::shl((Int)6, (SInt)digits - 1) == (Int)0 );
+ static_assert( std::shl((Int)3, (SInt)6) == (Int)((Int)3 << 6) );
+
+ static_assert( std::shl((Int)0b0110'1100, (SInt)1) == (Int)0b1101'1000 );
+ static_assert( std::shl((Int)0b0110'1100, (SInt)digits - 1) == 0 );
+
+ static_assert( std::shl((Int)0x01, (SInt)0 ) == 0x01 );
+ static_assert( std::shl((Int)0x10, (SInt)0 ) == 0x10 );
+ static_assert( std::shl((Int)0x10, (SInt)1 ) == 0x20 );
+ static_assert( std::shl((Int)0x10, (SInt)2 ) == 0x40 );
+ static_assert( std::shl((Int)0x10, (SInt)3 ) == (Int)0x80 );
+ static_assert( std::shl((Int)0x11, (SInt)1 ) == 0x22 );
+ static_assert( std::shl((Int)0x11, (SInt)2 ) == 0x44 );
+ static_assert( std::shl((Int)0x11, (SInt)-2 )
+ == ((SInt)-2 < 0 ? 4
+ : (SInt)-2 >= digits ? 0
+ : (Int)0x11 << ((SInt)-2 < 0 ? 0 : (SInt)-2)) );
+
+ if constexpr (std::numeric_limits<Int>::digits > 8)
+ {
+ static_assert( std::shl((Int)0b0011'0111, (SInt)3) == 0b1'1011'1000 );
+ static_assert( std::shl((Int)0b1010'0101, (SInt)4) == 0b1010'0101'0000 );
+ }
+
+ if constexpr (std::is_signed_v<SInt>)
+ static_assert( test_negative_shifts<Int, SInt>() );
+
+ return true;
+}
+
+static_assert( test( (unsigned char)0, (unsigned short)0 ) );
+static_assert( test( (unsigned short)0, (unsigned int)0 ) );
+static_assert( test( (unsigned int)0, (unsigned long)0 ) );
+static_assert( test( (unsigned long)0, (unsigned long long)0 ) );
+static_assert( test( (unsigned long long)0, (unsigned char)0 ) );
+static_assert( test( (signed char)0, (unsigned int)0 ) );
+static_assert( test( (signed short)0, (unsigned long)0 ) );
+static_assert( test( (signed int)0, (unsigned long long)0 ) );
+static_assert( test( (signed long)0, (unsigned char)0 ) );
+static_assert( test( (signed long long)0, (unsigned short)0 ) );
+static_assert( test( (unsigned char)0, (signed long long)0 ) );
+static_assert( test( (unsigned short)0, (signed char)0 ) );
+static_assert( test( (unsigned int)0, (signed short)0 ) );
+static_assert( test( (unsigned long)0, (signed int)0 ) );
+static_assert( test( (unsigned long long)0, (signed long)0 ) );
+static_assert( test( (signed char)0, (signed char)0 ) );
+static_assert( test( (signed short)0, (signed short)0 ) );
+static_assert( test( (signed int)0, (signed int)0 ) );
+static_assert( test( (signed long)0, (signed long)0 ) );
+static_assert( test( (signed long long)0, (signed long long)0 ) );
+
+struct X { constexpr bool did_not_match() { return true; } };
+constexpr X test(...) { return X{}; }
+static_assert( test( (bool)0, 0 ).did_not_match() );
+static_assert( test( (char)0, 0 ).did_not_match() );
+static_assert( test( (char16_t)0, 0 ).did_not_match() );
+static_assert( test( (float)0, 0 ).did_not_match() );
+static_assert( test( (void*)0, 0 ).did_not_match() );
+static_assert( test( X{}, 0 ).did_not_match() );
+static_assert( test( 0U, (bool)0 ).did_not_match() );
+static_assert( test( 0U, (char)0 ).did_not_match() );
+static_assert( test( 0U, (char16_t)0 ).did_not_match() );
+static_assert( test( 0, (float)0 ).did_not_match() );
+static_assert( test( 0, (void*)0 ).did_not_match() );
+static_assert( test( 0, X{} ).did_not_match() );
+enum E : unsigned { e };
+static_assert( test( e, 0 ).did_not_match() );
+static_assert( test( 0U, e ).did_not_match() );
+
+#if !defined(__STRICT_ANSI__) && defined __SIZEOF_INT128__
+static_assert( test( (unsigned __int128)0, (__int128)0 ) );
+static_assert( test( (__int128)0, (unsigned __int128)0 ) );
+static_assert( test( (unsigned __int128)0, 0U ) );
+static_assert( test( (__int128)0, 0 ) );
+#endif
+#if defined(__GLIBCXX_TYPE_INT_N_0)
+static_assert( test( (unsigned __GLIBCXX_TYPE_INT_N_0)0, (__GLIBCXX_TYPE_INT_N_0)0 ) );
+static_assert( test( (__GLIBCXX_TYPE_INT_N_0)0, (unsigned __GLIBCXX_TYPE_INT_N_0)0 ) );
+static_assert( test( (unsigned __GLIBCXX_TYPE_INT_N_0)0, 0U ) );
+static_assert( test( (__GLIBCXX_TYPE_INT_N_0)0, 0 ) );
+#endif
+#if defined(__GLIBCXX_TYPE_INT_N_1)
+static_assert( test( (unsigned __GLIBCXX_TYPE_INT_N_1)0, (__GLIBCXX_TYPE_INT_N_1)0 ) );
+static_assert( test( (__GLIBCXX_TYPE_INT_N_1)0, (unsigned __GLIBCXX_TYPE_INT_N_1)0 ) );
+static_assert( test( (unsigned __GLIBCXX_TYPE_INT_N_1)0, 0U ) );
+static_assert( test( (__GLIBCXX_TYPE_INT_N_1)0, 0 ) );
+#endif
+#if defined(__GLIBCXX_TYPE_INT_N_2)
+static_assert( test( (unsigned __GLIBCXX_TYPE_INT_N_2)0, (__GLIBCXX_TYPE_INT_N_2)0 ) );
+static_assert( test( (__GLIBCXX_TYPE_INT_N_2)0, (unsigned __GLIBCXX_TYPE_INT_N_2)0 ) );
+static_assert( test( (unsigned __GLIBCXX_TYPE_INT_N_2)0, 0U ) );
+static_assert( test( (__GLIBCXX_TYPE_INT_N_2)0, 0 ) );
+#endif
+#if defined(__GLIBCXX_TYPE_INT_N_3)
+static_assert( test( (unsigned __GLIBCXX_TYPE_INT_N_3)0, (__GLIBCXX_TYPE_INT_N_3)0 ) );
+static_assert( test( (__GLIBCXX_TYPE_INT_N_3)0, (unsigned __GLIBCXX_TYPE_INT_N_3)0 ) );
+static_assert( test( (unsigned __GLIBCXX_TYPE_INT_N_3)0, 0U ) );
+static_assert( test( (__GLIBCXX_TYPE_INT_N_3)0, 0 ) );
+#endif
+
+static_assert( std::shl(-1, 0x7fffffff00000001LL) == 0 );
+static_assert( std::shl(2, 0x7fffffff00000001LL) == 0 );
+static_assert( std::shl(-1, -0x7fffffff00000001LL) == -1 );
+static_assert( std::shl(2, -0x7fffffff00000001LL) == 0 );
+
+#include <cstddef>
+static_assert( test( (std::byte)0, 0 ).did_not_match() );
+static_assert( test( 0, (std::byte)0 ).did_not_match() );
diff --git a/libstdc++-v3/testsuite/26_numerics/bit/bit.shift/shr.cc b/libstdc++-v3/testsuite/26_numerics/bit/bit.shift/shr.cc
new file mode 100644
index 000000000000..136f35e64caf
--- /dev/null
+++ b/libstdc++-v3/testsuite/26_numerics/bit/bit.shift/shr.cc
@@ -0,0 +1,159 @@
+// { dg-do compile { target c++29 } }
+
+#include <bit>
+#include <limits>
+
+template<typename Int, typename SInt>
+constexpr bool
+test_negative_shifts()
+{
+ constexpr unsigned digits = std::numeric_limits<Int>::digits
+ + std::is_signed_v<Int>;
+
+ Int xarr[] = { (Int)-1, 0, 1, 3, 6, 7, 0x10, 0x11, 0x22, 0x44, (Int)0x80,
+ (Int)-55, (Int)-927 };
+ SInt sarr[] = { 1, 4, 5, digits - 1, digits, (SInt)-12 };
+ for (Int x : xarr)
+ for (SInt s : sarr)
+ if (std::shr(x, -s) != std::shl(x, s))
+ return false;
+ return true;
+}
+
+template<typename Int, typename SInt>
+constexpr auto
+test(Int x, SInt y)
+-> decltype(std::shr(x, y))
+{
+ static_assert( noexcept(std::shr(x, 0)) );
+
+ constexpr unsigned digits = std::numeric_limits<Int>::digits
+ + std::is_signed_v<Int>;
+
+ static_assert( std::shr((Int)0, (SInt)0) == 0 );
+ static_assert( std::shr((Int)0, (SInt)1) == 0 );
+ static_assert( std::shr((Int)0, (SInt)4) == 0 );
+ static_assert( std::shr((Int)0, (SInt)8) == 0 );
+ static_assert( std::shr((Int)0, (SInt)-4) == 0 );
+ static_assert( std::shr((Int)-1, (SInt)0) == (Int)((Int)-1 >> 0) );
+ static_assert( std::shr((Int)-1, (SInt)1) == (Int)((Int)-1 >> 1) );
+ static_assert( std::shr((Int)-1, (SInt)4) == (Int)((Int)-1 >> 4) );
+ static_assert( std::shr((Int)-1, (SInt)8) == (Int)((Int)-1 >> 8) );
+ static_assert( std::shr((Int)-1, (SInt)-4)
+ == ((SInt)-4 < 0 ? (Int)((Int)-1 << (SInt)4)
+ : (SInt)-4 >= digits ? ((Int)-1 < 0 ? (Int)-1 : 0)
+ : (Int)((Int)-1 >> ((SInt)-4 < 0 ? 0 : (SInt)-4))) );
+
+ static_assert( std::shr((Int)1, (SInt)0) == (Int)1 >> 0 );
+ static_assert( std::shr((Int)1, (SInt)1) == (Int)1 >> 1 );
+ static_assert( std::shr((Int)1, (SInt)4) == (Int)1 >> 4 );
+ static_assert( std::shr((Int)1, (SInt)digits) == (Int)0 );
+ static_assert( std::shr((Int)7, (SInt)digits) == (Int)0 );
+ static_assert( std::shr((Int)6, (SInt)digits - 1) == (Int)0 );
+ static_assert( std::shr((Int)3, (SInt)6) == (Int)((Int)3 >> 6) );
+
+ static_assert( std::shr((Int)0b0110'1100, (SInt)1) == (Int)0b0011'0110 );
+ static_assert( std::shr((Int)0b0110'1100, (SInt)digits - 1) == 0 );
+
+ static_assert( std::shr((Int)0x01, (SInt)0 ) == 0x01 );
+ static_assert( std::shr((Int)0x10, (SInt)0 ) == 0x10 );
+ static_assert( std::shr((Int)0x10, (SInt)1 ) == 0x08 );
+ static_assert( std::shr((Int)0x10, (SInt)2 ) == 0x04 );
+ static_assert( std::shr((Int)0x10, (SInt)3 ) == 0x02 );
+ static_assert( std::shr((Int)0x22, (SInt)1 ) == 0x11 );
+ static_assert( std::shr((Int)0x22, (SInt)2 ) == 0x08 );
+ static_assert( std::shr((Int)0x11, (SInt)-2 )
+ == ((SInt)-2 < 0 ? 0x44
+ : (SInt)-2 >= digits ? 0
+ : (Int)0x11 >> ((SInt)-2 < 0 ? 0 : (SInt)-2)) );
+
+ if constexpr (std::numeric_limits<Int>::digits > 8)
+ {
+ static_assert( std::shr((Int)0b1'1011'1000, (SInt)3) == 0b0011'0111 );
+ static_assert( std::shr((Int)0b1'1011'1000, (SInt)4) == 0b0001'1011 );
+ }
+
+ if constexpr (std::is_signed_v<SInt>)
+ static_assert( test_negative_shifts<Int, SInt>() );
+
+ return true;
+}
+
+static_assert( test( (unsigned char)0, (unsigned short)0 ) );
+static_assert( test( (unsigned short)0, (unsigned int)0 ) );
+static_assert( test( (unsigned int)0, (unsigned long)0 ) );
+static_assert( test( (unsigned long)0, (unsigned long long)0 ) );
+static_assert( test( (unsigned long long)0, (unsigned char)0 ) );
+static_assert( test( (signed char)0, (unsigned int)0 ) );
+static_assert( test( (signed short)0, (unsigned long)0 ) );
+static_assert( test( (signed int)0, (unsigned long long)0 ) );
+static_assert( test( (signed long)0, (unsigned char)0 ) );
+static_assert( test( (signed long long)0, (unsigned short)0 ) );
+static_assert( test( (unsigned char)0, (signed long long)0 ) );
+static_assert( test( (unsigned short)0, (signed char)0 ) );
+static_assert( test( (unsigned int)0, (signed short)0 ) );
+static_assert( test( (unsigned long)0, (signed int)0 ) );
+static_assert( test( (unsigned long long)0, (signed long)0 ) );
+static_assert( test( (signed char)0, (signed char)0 ) );
+static_assert( test( (signed short)0, (signed short)0 ) );
+static_assert( test( (signed int)0, (signed int)0 ) );
+static_assert( test( (signed long)0, (signed long)0 ) );
+static_assert( test( (signed long long)0, (signed long long)0 ) );
+
+struct X { constexpr bool did_not_match() { return true; } };
+constexpr X test(...) { return X{}; }
+static_assert( test( (bool)0, 0 ).did_not_match() );
+static_assert( test( (char)0, 0 ).did_not_match() );
+static_assert( test( (char16_t)0, 0 ).did_not_match() );
+static_assert( test( (float)0, 0 ).did_not_match() );
+static_assert( test( (void*)0, 0 ).did_not_match() );
+static_assert( test( X{}, 0 ).did_not_match() );
+static_assert( test( 0U, (bool)0 ).did_not_match() );
+static_assert( test( 0U, (char)0 ).did_not_match() );
+static_assert( test( 0U, (char16_t)0 ).did_not_match() );
+static_assert( test( 0, (float)0 ).did_not_match() );
+static_assert( test( 0, (void*)0 ).did_not_match() );
+static_assert( test( 0, X{} ).did_not_match() );
+enum E : unsigned { e };
+static_assert( test( e, 0 ).did_not_match() );
+static_assert( test( 0U, e ).did_not_match() );
+
+#if !defined(__STRICT_ANSI__) && defined __SIZEOF_INT128__
+static_assert( test( (unsigned __int128)0, (__int128)0 ) );
+static_assert( test( (__int128)0, (unsigned __int128)0 ) );
+static_assert( test( (unsigned __int128)0, 0U ) );
+static_assert( test( (__int128)0, 0 ) );
+#endif
+#if defined(__GLIBCXX_TYPE_INT_N_0)
+static_assert( test( (unsigned __GLIBCXX_TYPE_INT_N_0)0, (__GLIBCXX_TYPE_INT_N_0)0 ) );
+static_assert( test( (__GLIBCXX_TYPE_INT_N_0)0, (unsigned __GLIBCXX_TYPE_INT_N_0)0 ) );
+static_assert( test( (unsigned __GLIBCXX_TYPE_INT_N_0)0, 0U ) );
+static_assert( test( (__GLIBCXX_TYPE_INT_N_0)0, 0 ) );
+#endif
+#if defined(__GLIBCXX_TYPE_INT_N_1)
+static_assert( test( (unsigned __GLIBCXX_TYPE_INT_N_1)0, (__GLIBCXX_TYPE_INT_N_1)0 ) );
+static_assert( test( (__GLIBCXX_TYPE_INT_N_1)0, (unsigned __GLIBCXX_TYPE_INT_N_1)0 ) );
+static_assert( test( (unsigned __GLIBCXX_TYPE_INT_N_1)0, 0U ) );
+static_assert( test( (__GLIBCXX_TYPE_INT_N_1)0, 0 ) );
+#endif
+#if defined(__GLIBCXX_TYPE_INT_N_2)
+static_assert( test( (unsigned __GLIBCXX_TYPE_INT_N_2)0, (__GLIBCXX_TYPE_INT_N_2)0 ) );
+static_assert( test( (__GLIBCXX_TYPE_INT_N_2)0, (unsigned __GLIBCXX_TYPE_INT_N_2)0 ) );
+static_assert( test( (unsigned __GLIBCXX_TYPE_INT_N_2)0, 0U ) );
+static_assert( test( (__GLIBCXX_TYPE_INT_N_2)0, 0 ) );
+#endif
+#if defined(__GLIBCXX_TYPE_INT_N_3)
+static_assert( test( (unsigned __GLIBCXX_TYPE_INT_N_3)0, (__GLIBCXX_TYPE_INT_N_3)0 ) );
+static_assert( test( (__GLIBCXX_TYPE_INT_N_3)0, (unsigned __GLIBCXX_TYPE_INT_N_3)0 ) );
+static_assert( test( (unsigned __GLIBCXX_TYPE_INT_N_3)0, 0U ) );
+static_assert( test( (__GLIBCXX_TYPE_INT_N_3)0, 0 ) );
+#endif
+
+static_assert( std::shr(-1, 0x7fffffff00000001LL) == -1 );
+static_assert( std::shr(2, 0x7fffffff00000001LL) == 0 );
+static_assert( std::shr(-1, -0x7fffffff00000001LL) == 0 );
+static_assert( std::shr(2, -0x7fffffff00000001LL) == 0 );
+
+#include <cstddef>
+static_assert( test( (std::byte)0, 0 ).did_not_match() );
+static_assert( test( 0, (std::byte)0 ).did_not_match() );
More information about the Libstdc++-cvs
mailing list