From ed17dd82f2d52e6c701202c632f1638635f11509 Mon Sep 17 00:00:00 2001 From: "A. Jiang" Date: Tue, 19 Jul 2022 10:43:46 +0800 Subject: [PATCH 1/7] Test case for LWG-3656 --- .../P0556R3_bit_integral_power_of_two_operations/test.cpp | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/tests/std/tests/P0556R3_bit_integral_power_of_two_operations/test.cpp b/tests/std/tests/P0556R3_bit_integral_power_of_two_operations/test.cpp index 40bbfc0f000..1986776e05f 100644 --- a/tests/std/tests/P0556R3_bit_integral_power_of_two_operations/test.cpp +++ b/tests/std/tests/P0556R3_bit_integral_power_of_two_operations/test.cpp @@ -3,6 +3,7 @@ #include #include #include +#include #include using namespace std; @@ -82,6 +83,10 @@ constexpr bool test_bit_width() { for (int i = 1; i < digits; ++i) { assert(bit_width(static_cast(T{1} << i)) == static_cast(i + 1)); } + + // LWG-3656: bit_width returns int + static_assert(is_same_v); + return true; } From b8bb580ce55ccbbaea3687a2de26c4dcf907d58a Mon Sep 17 00:00:00 2001 From: "A. Jiang" Date: Tue, 19 Jul 2022 10:45:14 +0800 Subject: [PATCH 2/7] Implement LWG-3656 --- stl/inc/bit | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/stl/inc/bit b/stl/inc/bit index eeed2dcd357..abe75303054 100644 --- a/stl/inc/bit +++ b/stl/inc/bit @@ -82,7 +82,7 @@ _NODISCARD constexpr _Ty bit_floor(const _Ty _Val) noexcept { } template , int> = 0> -_NODISCARD constexpr _Ty bit_width(const _Ty _Val) noexcept { +_NODISCARD constexpr int bit_width(const _Ty _Val) noexcept { return static_cast<_Ty>(numeric_limits<_Ty>::digits - _STD countl_zero(_Val)); } From f3526ccc52510ecfb16f7cda9c34e2ab4d79845f Mon Sep 17 00:00:00 2001 From: "A. Jiang" Date: Tue, 19 Jul 2022 19:29:39 +0800 Subject: [PATCH 3/7] Remove inappropriate static_cast --- stl/inc/bit | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/stl/inc/bit b/stl/inc/bit index abe75303054..6f793dd46c9 100644 --- a/stl/inc/bit +++ b/stl/inc/bit @@ -83,7 +83,7 @@ _NODISCARD constexpr _Ty bit_floor(const _Ty _Val) noexcept { template , int> = 0> _NODISCARD constexpr int bit_width(const _Ty _Val) noexcept { - return static_cast<_Ty>(numeric_limits<_Ty>::digits - _STD countl_zero(_Val)); + return numeric_limits<_Ty>::digits - _STD countl_zero(_Val); } template , int> = 0> From 64ac21824caf46d5a9789e6cd8c2bcbcea1ca665 Mon Sep 17 00:00:00 2001 From: "A. Jiang" Date: Tue, 19 Jul 2022 19:46:38 +0800 Subject: [PATCH 4/7] Remove inappropriate static_cast, again --- .../tests/P0556R3_bit_integral_power_of_two_operations/test.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/std/tests/P0556R3_bit_integral_power_of_two_operations/test.cpp b/tests/std/tests/P0556R3_bit_integral_power_of_two_operations/test.cpp index 1986776e05f..9fdfb540901 100644 --- a/tests/std/tests/P0556R3_bit_integral_power_of_two_operations/test.cpp +++ b/tests/std/tests/P0556R3_bit_integral_power_of_two_operations/test.cpp @@ -81,7 +81,7 @@ constexpr bool test_bit_width() { assert(bit_width(numeric_limits::max()) == digits); assert(bit_width(T{1}) == T{1}); for (int i = 1; i < digits; ++i) { - assert(bit_width(static_cast(T{1} << i)) == static_cast(i + 1)); + assert(bit_width(static_cast(T{1} << i)) == i + 1); } // LWG-3656: bit_width returns int From f9a6a90a95b93e07895716fc072ea517f6de933d Mon Sep 17 00:00:00 2001 From: "A. Jiang" Date: Tue, 19 Jul 2022 20:03:21 +0800 Subject: [PATCH 5/7] Skip one libcxx test Just because MSVC STL doesn't refer to the updated test files... --- tests/libcxx/expected_results.txt | 3 +++ tests/libcxx/skipped_tests.txt | 3 +++ 2 files changed, 6 insertions(+) diff --git a/tests/libcxx/expected_results.txt b/tests/libcxx/expected_results.txt index eb882b5a45f..45f0b1ceb26 100644 --- a/tests/libcxx/expected_results.txt +++ b/tests/libcxx/expected_results.txt @@ -652,6 +652,9 @@ std/utilities/charconv/charconv.msvc/test.pass.cpp FAIL std/ranges/range.adaptors/range.transform/end.pass.cpp FAIL std/ranges/range.adaptors/range.transform/iterator/base.pass.cpp FAIL +# libc++ doesn't yet implement LWG-3656 (https://reviews.llvm.org/D120444) +std/numerics/bit/bit.pow.two/bit_width.pass.cpp FAIL + # MaybePOCCAAllocator doesn't meet the allocator requirements std/containers/sequences/vector/vector.cons/assign_copy.pass.cpp FAIL diff --git a/tests/libcxx/skipped_tests.txt b/tests/libcxx/skipped_tests.txt index fdc14350d39..4140ce51f3e 100644 --- a/tests/libcxx/skipped_tests.txt +++ b/tests/libcxx/skipped_tests.txt @@ -652,6 +652,9 @@ utilities\charconv\charconv.msvc\test.pass.cpp ranges\range.adaptors\range.transform\end.pass.cpp ranges\range.adaptors\range.transform\iterator\base.pass.cpp +# libc++ doesn't yet implement LWG-3656 (https://reviews.llvm.org/D120444) +numerics\bit\bit.pow.two\bit_width.pass.cpp FAIL + # MaybePOCCAAllocator doesn't meet the allocator requirements containers\sequences\vector\vector.cons\assign_copy.pass.cpp From 81cc74dacc734fcec72c388d24ea748e1cd084cf Mon Sep 17 00:00:00 2001 From: "A. Jiang" Date: Tue, 19 Jul 2022 20:08:28 +0800 Subject: [PATCH 6/7] Remove copy-pasta --- tests/libcxx/skipped_tests.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/libcxx/skipped_tests.txt b/tests/libcxx/skipped_tests.txt index 4140ce51f3e..92b7be72bd6 100644 --- a/tests/libcxx/skipped_tests.txt +++ b/tests/libcxx/skipped_tests.txt @@ -653,7 +653,7 @@ ranges\range.adaptors\range.transform\end.pass.cpp ranges\range.adaptors\range.transform\iterator\base.pass.cpp # libc++ doesn't yet implement LWG-3656 (https://reviews.llvm.org/D120444) -numerics\bit\bit.pow.two\bit_width.pass.cpp FAIL +numerics\bit\bit.pow.two\bit_width.pass.cpp # MaybePOCCAAllocator doesn't meet the allocator requirements containers\sequences\vector\vector.cons\assign_copy.pass.cpp From 4255994cae6514fcf6cfc4bcff9be692a54029f8 Mon Sep 17 00:00:00 2001 From: "Stephan T. Lavavej" Date: Tue, 26 Jul 2022 17:46:43 -0700 Subject: [PATCH 7/7] Code review feedback. --- stl/inc/format | 2 +- .../P0556R3_bit_integral_power_of_two_operations/test.cpp | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/stl/inc/format b/stl/inc/format index 3e89553d827..b1db83122a2 100644 --- a/stl/inc/format +++ b/stl/inc/format @@ -2939,7 +2939,7 @@ _NODISCARD _OutputIt _Fmt_write( // Add 3 to the bit width so we always round up on the division. // Divide that by the amount of bits a hexit represents (log2(16) = log2(2^4) = 4). // Add 2 for the 0x prefix. - _Width = static_cast(2 + (_STD bit_width(reinterpret_cast(_Value)) + 3) / 4); + _Width = 2 + (_STD bit_width(reinterpret_cast(_Value)) + 3) / 4; } return _Write_aligned(_STD move(_Out), _Width, _Specs, _Fmt_align::_Right, diff --git a/tests/std/tests/P0556R3_bit_integral_power_of_two_operations/test.cpp b/tests/std/tests/P0556R3_bit_integral_power_of_two_operations/test.cpp index 25e14905a02..f727684f619 100644 --- a/tests/std/tests/P0556R3_bit_integral_power_of_two_operations/test.cpp +++ b/tests/std/tests/P0556R3_bit_integral_power_of_two_operations/test.cpp @@ -77,9 +77,9 @@ constexpr bool test_bit_floor() { template constexpr bool test_bit_width() { constexpr int digits = numeric_limits::digits; - assert(bit_width(T{0}) == T{0}); + assert(bit_width(T{0}) == 0); assert(bit_width(numeric_limits::max()) == digits); - assert(bit_width(T{1}) == T{1}); + assert(bit_width(T{1}) == 1); for (int i = 1; i < digits; ++i) { assert(bit_width(static_cast(T{1} << i)) == i + 1); }