From 14b54cab1bb0701482b5b18643e13a96cc15ac7b Mon Sep 17 00:00:00 2001 From: "Stephan T. Lavavej" Date: Thu, 27 Jun 2024 13:39:27 -0700 Subject: [PATCH] Fix `atomic_ref::is_lock_free()` on x64 (#4729) Co-authored-by: Alex Guteniev --- stl/inc/atomic | 4 +++- tests/std/tests/P0019R8_atomic_ref/test.cpp | 17 +++++++++++++++++ 2 files changed, 20 insertions(+), 1 deletion(-) diff --git a/stl/inc/atomic b/stl/inc/atomic index 5f7e730049..307168b01e 100644 --- a/stl/inc/atomic +++ b/stl/inc/atomic @@ -2370,8 +2370,10 @@ public: #else // ^^^ _ATOMIC_HAS_DCAS / !_ATOMIC_HAS_DCAS vvv if constexpr (is_always_lock_free) { return true; - } else { + } else if constexpr (_Is_potentially_lock_free) { return __std_atomic_has_cmpxchg16b() != 0; + } else { + return false; } #endif // ^^^ !_ATOMIC_HAS_DCAS ^^^ } diff --git a/tests/std/tests/P0019R8_atomic_ref/test.cpp b/tests/std/tests/P0019R8_atomic_ref/test.cpp index 61c25f68eb..6cdfd4518a 100644 --- a/tests/std/tests/P0019R8_atomic_ref/test.cpp +++ b/tests/std/tests/P0019R8_atomic_ref/test.cpp @@ -447,6 +447,22 @@ void test_gh_4472() { assert(ar.is_lock_free()); } +// GH-4728 ": On x64, atomic_ref::is_lock_free() incorrectly returns true when it shouldn't" +void test_gh_4728() { + struct Large { + char str[100]{}; + }; + + alignas(std::atomic_ref::required_alignment) Large lg{}; + + static_assert(std::atomic_ref::required_alignment == alignof(Large)); + + static_assert(!std::atomic_ref::is_always_lock_free); + + std::atomic_ref ar{lg}; + assert(!ar.is_lock_free()); +} + int main() { test_ops(); test_ops(); @@ -500,6 +516,7 @@ int main() { test_gh_1497(); test_gh_4472(); + test_gh_4728(); } #endif // ^^^ run test ^^^