2 //===----------------------------------------------------------------------===//
4 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
5 // See https://llvm.org/LICENSE.txt for license information.
6 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
8 //===----------------------------------------------------------------------===//
22 static constexpr ptrdiff_t max() noexcept;
24 constexpr explicit latch(ptrdiff_t __expected);
27 latch(const latch&) = delete;
28 latch& operator=(const latch&) = delete;
30 void count_down(ptrdiff_t __update = 1);
31 bool try_wait() const noexcept;
33 void arrive_and_wait(ptrdiff_t __update = 1);
36 ptrdiff_t __counter; // exposition only
43 #include <__availability>
48 #if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
49 #pragma GCC system_header
52 #ifdef _LIBCPP_HAS_NO_THREADS
53 # error <latch> is not supported on this single threaded system
57 #include <__undef_macros>
59 #if _LIBCPP_STD_VER >= 14
61 _LIBCPP_BEGIN_NAMESPACE_STD
65 __atomic_base<ptrdiff_t> __a;
68 static constexpr ptrdiff_t max() noexcept {
69 return numeric_limits<ptrdiff_t>::max();
72 inline _LIBCPP_INLINE_VISIBILITY
73 constexpr explicit latch(ptrdiff_t __expected) : __a(__expected) { }
76 latch(const latch&) = delete;
77 latch& operator=(const latch&) = delete;
79 inline _LIBCPP_AVAILABILITY_SYNC _LIBCPP_INLINE_VISIBILITY
80 void count_down(ptrdiff_t __update = 1)
82 auto const __old = __a.fetch_sub(__update, memory_order_release);
86 inline _LIBCPP_INLINE_VISIBILITY
87 bool try_wait() const noexcept
89 return 0 == __a.load(memory_order_acquire);
91 inline _LIBCPP_AVAILABILITY_SYNC _LIBCPP_INLINE_VISIBILITY
94 auto const __test_fn = [=]() -> bool {
97 __cxx_atomic_wait(&__a.__a_, __test_fn);
99 inline _LIBCPP_AVAILABILITY_SYNC _LIBCPP_INLINE_VISIBILITY
100 void arrive_and_wait(ptrdiff_t __update = 1)
102 count_down(__update);
107 _LIBCPP_END_NAMESPACE_STD
109 #endif // _LIBCPP_STD_VER >= 14
113 #endif //_LIBCPP_LATCH