[libcxx-commits] [libcxx] 3347e7d - [libc++] [LWG3656] Update the return type of std::bit_width.

Arthur O'Dwyer via libcxx-commits libcxx-commits at lists.llvm.org
Fri Mar 4 14:31:21 PST 2022


Author: Arthur O'Dwyer
Date: 2022-03-04T17:31:09-05:00
New Revision: 3347e7d40fd83ae762dcdb7c6161550e4190d6cf

URL: https://github.com/llvm/llvm-project/commit/3347e7d40fd83ae762dcdb7c6161550e4190d6cf
DIFF: https://github.com/llvm/llvm-project/commit/3347e7d40fd83ae762dcdb7c6161550e4190d6cf.diff

LOG: [libc++] [LWG3656] Update the return type of std::bit_width.

Fixes LWG3656, "Inconsistent bit operations returning a count".
https://cplusplus.github.io/LWG/issue3656

The fix has been approved for C++23 and left to vendors' discretion
in C++20 (but it sounds like everyone's on the same page that
of course it should be DR'ed back to C++20 too).

Differential Revision: https://reviews.llvm.org/D120444

Added: 
    

Modified: 
    libcxx/docs/Status/Cxx2bIssues.csv
    libcxx/include/bit
    libcxx/test/std/numerics/bit/bit.pow.two/bit_width.pass.cpp

Removed: 
    


################################################################################
diff  --git a/libcxx/docs/Status/Cxx2bIssues.csv b/libcxx/docs/Status/Cxx2bIssues.csv
index ba8aea2ffcf39..0b2dbf4eef9e2 100644
--- a/libcxx/docs/Status/Cxx2bIssues.csv
+++ b/libcxx/docs/Status/Cxx2bIssues.csv
@@ -157,7 +157,8 @@
 "`3654 <https://wg21.link/LWG3654>`__","``basic_format_context::arg(size_t)`` should be ``noexcept`` ","February 2022","|Complete|","15.0","|format|"
 "`3657 <https://wg21.link/LWG3657>`__","``std::hash<std::filesystem::path>`` is not enabled","February 2022","",""
 "`3660 <https://wg21.link/LWG3660>`__","``iterator_traits<common_iterator>::pointer`` should conform to ยง[iterator.traits]","February 2022","|Complete|","14.0"
-"`3661 <https://wg21.link/LWG3661>`__","``constinit atomic<shared_ptr<T>> a (nullptr);`` should work","February 2022","",""
+"`3661 <https://wg21.link/LWG3661>`__","``constinit atomic<shared_ptr<T>> a(nullptr);`` should work","February 2022","",""
 "","","","",""
-`3645 <https://wg21.link/LWG3645>`__,"``resize_and_overwrite`` is overspecified to call its callback with lvalues", "Not voted in","|Complete|","14.0",""
+"`3645 <https://wg21.link/LWG3645>`__","``resize_and_overwrite`` is overspecified to call its callback with lvalues","Not voted in","|Complete|","14.0",""
+"`3656 <https://wg21.link/LWG3656>`__","Inconsistent bit operations returning a count","Not voted in","|Complete|","15.0",""
 "","","","",""

diff  --git a/libcxx/include/bit b/libcxx/include/bit
index 7f9318ecde1ee..aaefd8a362cfa 100644
--- a/libcxx/include/bit
+++ b/libcxx/include/bit
@@ -30,7 +30,7 @@ namespace std {
   template <class T>
     constexpr T bit_floor(T x) noexcept;         // C++20
   template <class T>
-    constexpr T bit_width(T x) noexcept;         // C++20
+    constexpr int bit_width(T x) noexcept;       // C++20
 
   // [bit.rotate], rotating
   template<class T>
@@ -322,7 +322,7 @@ bit_ceil(_Tp __t) noexcept
 
 template <class _Tp>
 _LIBCPP_INLINE_VISIBILITY constexpr
-enable_if_t<__libcpp_is_unsigned_integer<_Tp>::value, _Tp>
+enable_if_t<__libcpp_is_unsigned_integer<_Tp>::value, int>
 bit_width(_Tp __t) noexcept
 {
     return __t == 0 ? 0 : __bit_log2(__t) + 1;

diff  --git a/libcxx/test/std/numerics/bit/bit.pow.two/bit_width.pass.cpp b/libcxx/test/std/numerics/bit/bit.pow.two/bit_width.pass.cpp
index 84b00efa7ed49..c191015e16eee 100644
--- a/libcxx/test/std/numerics/bit/bit.pow.two/bit_width.pass.cpp
+++ b/libcxx/test/std/numerics/bit/bit.pow.two/bit_width.pass.cpp
@@ -9,7 +9,7 @@
 // UNSUPPORTED: c++03, c++11, c++14, c++17
 
 // template <class T>
-//   constexpr T bit_width(T x) noexcept;
+//   constexpr int bit_width(T x) noexcept;
 
 // Constraints: T is an unsigned integer type
 // Returns: If x == 0, 0; otherwise one plus the base-2 logarithm of x, with any fractional part discarded.
@@ -29,28 +29,28 @@ enum class E2 : unsigned char { red };
 template <class T>
 constexpr bool test()
 {
-    ASSERT_SAME_TYPE(decltype(std::bit_width(T())), T);
+    ASSERT_SAME_TYPE(decltype(std::bit_width(T())), int);
     ASSERT_NOEXCEPT(std::bit_width(T()));
     T max = std::numeric_limits<T>::max();
 
-    assert(std::bit_width(T(0)) == T(0));
-    assert(std::bit_width(T(1)) == T(1));
-    assert(std::bit_width(T(2)) == T(2));
-    assert(std::bit_width(T(3)) == T(2));
-    assert(std::bit_width(T(4)) == T(3));
-    assert(std::bit_width(T(5)) == T(3));
-    assert(std::bit_width(T(6)) == T(3));
-    assert(std::bit_width(T(7)) == T(3));
-    assert(std::bit_width(T(8)) == T(4));
-    assert(std::bit_width(T(9)) == T(4));
-    assert(std::bit_width(T(125)) == T(7));
-    assert(std::bit_width(T(126)) == T(7));
-    assert(std::bit_width(T(127)) == T(7));
-    assert(std::bit_width(T(128)) == T(8));
-    assert(std::bit_width(T(129)) == T(8));
-    assert(std::bit_width(T(130)) == T(8));
-    assert(std::bit_width(T(max - 1)) == T(std::numeric_limits<T>::digits));
-    assert(std::bit_width(max) == T(std::numeric_limits<T>::digits));
+    assert(std::bit_width(T(0)) == 0);
+    assert(std::bit_width(T(1)) == 1);
+    assert(std::bit_width(T(2)) == 2);
+    assert(std::bit_width(T(3)) == 2);
+    assert(std::bit_width(T(4)) == 3);
+    assert(std::bit_width(T(5)) == 3);
+    assert(std::bit_width(T(6)) == 3);
+    assert(std::bit_width(T(7)) == 3);
+    assert(std::bit_width(T(8)) == 4);
+    assert(std::bit_width(T(9)) == 4);
+    assert(std::bit_width(T(125)) == 7);
+    assert(std::bit_width(T(126)) == 7);
+    assert(std::bit_width(T(127)) == 7);
+    assert(std::bit_width(T(128)) == 8);
+    assert(std::bit_width(T(129)) == 8);
+    assert(std::bit_width(T(130)) == 8);
+    assert(std::bit_width(T(max - 1)) == std::numeric_limits<T>::digits);
+    assert(std::bit_width(max) == std::numeric_limits<T>::digits);
 
 #ifndef TEST_HAS_NO_INT128
     if constexpr (std::is_same_v<T, __uint128_t>) {


        


More information about the libcxx-commits mailing list