Warning: This file is not a C or C++ file. It does not have highlighting.

1//===----------------------------------------------------------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
9#ifndef _LIBCPP___CXX03___ATOMIC_CXX_ATOMIC_IMPL_H
10#define _LIBCPP___CXX03___ATOMIC_CXX_ATOMIC_IMPL_H
11
12#include <__cxx03/__atomic/memory_order.h>
13#include <__cxx03/__atomic/to_gcc_order.h>
14#include <__cxx03/__config>
15#include <__cxx03/__memory/addressof.h>
16#include <__cxx03/__type_traits/is_assignable.h>
17#include <__cxx03/__type_traits/is_trivially_copyable.h>
18#include <__cxx03/__type_traits/remove_const.h>
19#include <__cxx03/cstddef>
20
21#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
22# pragma GCC system_header
23#endif
24
25_LIBCPP_BEGIN_NAMESPACE_STD
26
27#if defined(_LIBCPP_HAS_GCC_ATOMIC_IMP)
28
29// [atomics.types.generic]p1 guarantees _Tp is trivially copyable. Because
30// the default operator= in an object is not volatile, a byte-by-byte copy
31// is required.
32template <typename _Tp, typename _Tv, __enable_if_t<is_assignable<_Tp&, _Tv>::value, int> = 0>
33_LIBCPP_HIDE_FROM_ABI void __cxx_atomic_assign_volatile(_Tp& __a_value, _Tv const& __val) {
34 __a_value = __val;
35}
36template <typename _Tp, typename _Tv, __enable_if_t<is_assignable<_Tp&, _Tv>::value, int> = 0>
37_LIBCPP_HIDE_FROM_ABI void __cxx_atomic_assign_volatile(_Tp volatile& __a_value, _Tv volatile const& __val) {
38 volatile char* __to = reinterpret_cast<volatile char*>(std::addressof(__a_value));
39 volatile char* __end = __to + sizeof(_Tp);
40 volatile const char* __from = reinterpret_cast<volatile const char*>(std::addressof(__val));
41 while (__to != __end)
42 *__to++ = *__from++;
43}
44
45template <typename _Tp>
46struct __cxx_atomic_base_impl {
47 _LIBCPP_HIDE_FROM_ABI __cxx_atomic_base_impl() _NOEXCEPT : __a_value() {}
48 explicit __cxx_atomic_base_impl(_Tp value) _NOEXCEPT : __a_value(value) {}
49 _Tp __a_value;
50};
51
52template <typename _Tp>
53_LIBCPP_HIDE_FROM_ABI void __cxx_atomic_init(volatile __cxx_atomic_base_impl<_Tp>* __a, _Tp __val) {
54 __cxx_atomic_assign_volatile(__a->__a_value, __val);
55}
56
57template <typename _Tp>
58_LIBCPP_HIDE_FROM_ABI void __cxx_atomic_init(__cxx_atomic_base_impl<_Tp>* __a, _Tp __val) {
59 __a->__a_value = __val;
60}
61
62_LIBCPP_HIDE_FROM_ABI inline void __cxx_atomic_thread_fence(memory_order __order) {
63 __atomic_thread_fence(__to_gcc_order(__order));
64}
65
66_LIBCPP_HIDE_FROM_ABI inline void __cxx_atomic_signal_fence(memory_order __order) {
67 __atomic_signal_fence(__to_gcc_order(__order));
68}
69
70template <typename _Tp>
71_LIBCPP_HIDE_FROM_ABI void
72__cxx_atomic_store(volatile __cxx_atomic_base_impl<_Tp>* __a, _Tp __val, memory_order __order) {
73 __atomic_store(std::addressof(__a->__a_value), std::addressof(__val), __to_gcc_order(__order));
74}
75
76template <typename _Tp>
77_LIBCPP_HIDE_FROM_ABI void __cxx_atomic_store(__cxx_atomic_base_impl<_Tp>* __a, _Tp __val, memory_order __order) {
78 __atomic_store(std::addressof(__a->__a_value), std::addressof(__val), __to_gcc_order(__order));
79}
80
81template <typename _Tp>
82_LIBCPP_HIDE_FROM_ABI _Tp __cxx_atomic_load(const volatile __cxx_atomic_base_impl<_Tp>* __a, memory_order __order) {
83 _Tp __ret;
84 __atomic_load(std::addressof(__a->__a_value), std::addressof(__ret), __to_gcc_order(__order));
85 return __ret;
86}
87
88template <typename _Tp>
89_LIBCPP_HIDE_FROM_ABI void
90__cxx_atomic_load_inplace(const volatile __cxx_atomic_base_impl<_Tp>* __a, _Tp* __dst, memory_order __order) {
91 __atomic_load(std::addressof(__a->__a_value), __dst, __to_gcc_order(__order));
92}
93
94template <typename _Tp>
95_LIBCPP_HIDE_FROM_ABI void
96__cxx_atomic_load_inplace(const __cxx_atomic_base_impl<_Tp>* __a, _Tp* __dst, memory_order __order) {
97 __atomic_load(std::addressof(__a->__a_value), __dst, __to_gcc_order(__order));
98}
99
100template <typename _Tp>
101_LIBCPP_HIDE_FROM_ABI _Tp __cxx_atomic_load(const __cxx_atomic_base_impl<_Tp>* __a, memory_order __order) {
102 _Tp __ret;
103 __atomic_load(std::addressof(__a->__a_value), std::addressof(__ret), __to_gcc_order(__order));
104 return __ret;
105}
106
107template <typename _Tp>
108_LIBCPP_HIDE_FROM_ABI _Tp
109__cxx_atomic_exchange(volatile __cxx_atomic_base_impl<_Tp>* __a, _Tp __value, memory_order __order) {
110 _Tp __ret;
111 __atomic_exchange(
112 std::addressof(__a->__a_value), std::addressof(__value), std::addressof(__ret), __to_gcc_order(__order));
113 return __ret;
114}
115
116template <typename _Tp>
117_LIBCPP_HIDE_FROM_ABI _Tp __cxx_atomic_exchange(__cxx_atomic_base_impl<_Tp>* __a, _Tp __value, memory_order __order) {
118 _Tp __ret;
119 __atomic_exchange(
120 std::addressof(__a->__a_value), std::addressof(__value), std::addressof(__ret), __to_gcc_order(__order));
121 return __ret;
122}
123
124template <typename _Tp>
125_LIBCPP_HIDE_FROM_ABI bool __cxx_atomic_compare_exchange_strong(
126 volatile __cxx_atomic_base_impl<_Tp>* __a,
127 _Tp* __expected,
128 _Tp __value,
129 memory_order __success,
130 memory_order __failure) {
131 return __atomic_compare_exchange(
132 std::addressof(__a->__a_value),
133 __expected,
134 std::addressof(__value),
135 false,
136 __to_gcc_order(__success),
137 __to_gcc_failure_order(__failure));
138}
139
140template <typename _Tp>
141_LIBCPP_HIDE_FROM_ABI bool __cxx_atomic_compare_exchange_strong(
142 __cxx_atomic_base_impl<_Tp>* __a, _Tp* __expected, _Tp __value, memory_order __success, memory_order __failure) {
143 return __atomic_compare_exchange(
144 std::addressof(__a->__a_value),
145 __expected,
146 std::addressof(__value),
147 false,
148 __to_gcc_order(__success),
149 __to_gcc_failure_order(__failure));
150}
151
152template <typename _Tp>
153_LIBCPP_HIDE_FROM_ABI bool __cxx_atomic_compare_exchange_weak(
154 volatile __cxx_atomic_base_impl<_Tp>* __a,
155 _Tp* __expected,
156 _Tp __value,
157 memory_order __success,
158 memory_order __failure) {
159 return __atomic_compare_exchange(
160 std::addressof(__a->__a_value),
161 __expected,
162 std::addressof(__value),
163 true,
164 __to_gcc_order(__success),
165 __to_gcc_failure_order(__failure));
166}
167
168template <typename _Tp>
169_LIBCPP_HIDE_FROM_ABI bool __cxx_atomic_compare_exchange_weak(
170 __cxx_atomic_base_impl<_Tp>* __a, _Tp* __expected, _Tp __value, memory_order __success, memory_order __failure) {
171 return __atomic_compare_exchange(
172 std::addressof(__a->__a_value),
173 __expected,
174 std::addressof(__value),
175 true,
176 __to_gcc_order(__success),
177 __to_gcc_failure_order(__failure));
178}
179
180template <typename _Tp>
181struct __skip_amt {
182 enum { value = 1 };
183};
184
185template <typename _Tp>
186struct __skip_amt<_Tp*> {
187 enum { value = sizeof(_Tp) };
188};
189
190// FIXME: Haven't figured out what the spec says about using arrays with
191// atomic_fetch_add. Force a failure rather than creating bad behavior.
192template <typename _Tp>
193struct __skip_amt<_Tp[]> {};
194template <typename _Tp, int n>
195struct __skip_amt<_Tp[n]> {};
196
197template <typename _Tp, typename _Td>
198_LIBCPP_HIDE_FROM_ABI _Tp
199__cxx_atomic_fetch_add(volatile __cxx_atomic_base_impl<_Tp>* __a, _Td __delta, memory_order __order) {
200 return __atomic_fetch_add(std::addressof(__a->__a_value), __delta * __skip_amt<_Tp>::value, __to_gcc_order(__order));
201}
202
203template <typename _Tp, typename _Td>
204_LIBCPP_HIDE_FROM_ABI _Tp __cxx_atomic_fetch_add(__cxx_atomic_base_impl<_Tp>* __a, _Td __delta, memory_order __order) {
205 return __atomic_fetch_add(std::addressof(__a->__a_value), __delta * __skip_amt<_Tp>::value, __to_gcc_order(__order));
206}
207
208template <typename _Tp, typename _Td>
209_LIBCPP_HIDE_FROM_ABI _Tp
210__cxx_atomic_fetch_sub(volatile __cxx_atomic_base_impl<_Tp>* __a, _Td __delta, memory_order __order) {
211 return __atomic_fetch_sub(std::addressof(__a->__a_value), __delta * __skip_amt<_Tp>::value, __to_gcc_order(__order));
212}
213
214template <typename _Tp, typename _Td>
215_LIBCPP_HIDE_FROM_ABI _Tp __cxx_atomic_fetch_sub(__cxx_atomic_base_impl<_Tp>* __a, _Td __delta, memory_order __order) {
216 return __atomic_fetch_sub(std::addressof(__a->__a_value), __delta * __skip_amt<_Tp>::value, __to_gcc_order(__order));
217}
218
219template <typename _Tp>
220_LIBCPP_HIDE_FROM_ABI _Tp
221__cxx_atomic_fetch_and(volatile __cxx_atomic_base_impl<_Tp>* __a, _Tp __pattern, memory_order __order) {
222 return __atomic_fetch_and(std::addressof(__a->__a_value), __pattern, __to_gcc_order(__order));
223}
224
225template <typename _Tp>
226_LIBCPP_HIDE_FROM_ABI _Tp
227__cxx_atomic_fetch_and(__cxx_atomic_base_impl<_Tp>* __a, _Tp __pattern, memory_order __order) {
228 return __atomic_fetch_and(std::addressof(__a->__a_value), __pattern, __to_gcc_order(__order));
229}
230
231template <typename _Tp>
232_LIBCPP_HIDE_FROM_ABI _Tp
233__cxx_atomic_fetch_or(volatile __cxx_atomic_base_impl<_Tp>* __a, _Tp __pattern, memory_order __order) {
234 return __atomic_fetch_or(std::addressof(__a->__a_value), __pattern, __to_gcc_order(__order));
235}
236
237template <typename _Tp>
238_LIBCPP_HIDE_FROM_ABI _Tp __cxx_atomic_fetch_or(__cxx_atomic_base_impl<_Tp>* __a, _Tp __pattern, memory_order __order) {
239 return __atomic_fetch_or(std::addressof(__a->__a_value), __pattern, __to_gcc_order(__order));
240}
241
242template <typename _Tp>
243_LIBCPP_HIDE_FROM_ABI _Tp
244__cxx_atomic_fetch_xor(volatile __cxx_atomic_base_impl<_Tp>* __a, _Tp __pattern, memory_order __order) {
245 return __atomic_fetch_xor(std::addressof(__a->__a_value), __pattern, __to_gcc_order(__order));
246}
247
248template <typename _Tp>
249_LIBCPP_HIDE_FROM_ABI _Tp
250__cxx_atomic_fetch_xor(__cxx_atomic_base_impl<_Tp>* __a, _Tp __pattern, memory_order __order) {
251 return __atomic_fetch_xor(std::addressof(__a->__a_value), __pattern, __to_gcc_order(__order));
252}
253
254# define __cxx_atomic_is_lock_free(__s) __atomic_is_lock_free(__s, 0)
255
256#elif defined(_LIBCPP_HAS_C_ATOMIC_IMP)
257
258template <typename _Tp>
259struct __cxx_atomic_base_impl {
260 _LIBCPP_HIDE_FROM_ABI __cxx_atomic_base_impl() _NOEXCEPT : __a_value() {}
261 explicit __cxx_atomic_base_impl(_Tp __value) _NOEXCEPT : __a_value(__value) {}
262 _LIBCPP_DISABLE_EXTENSION_WARNING _Atomic(_Tp) __a_value;
263};
264
265# define __cxx_atomic_is_lock_free(__s) __c11_atomic_is_lock_free(__s)
266
267_LIBCPP_HIDE_FROM_ABI inline void __cxx_atomic_thread_fence(memory_order __order) _NOEXCEPT {
268 __c11_atomic_thread_fence(static_cast<__memory_order_underlying_t>(__order));
269}
270
271_LIBCPP_HIDE_FROM_ABI inline void __cxx_atomic_signal_fence(memory_order __order) _NOEXCEPT {
272 __c11_atomic_signal_fence(static_cast<__memory_order_underlying_t>(__order));
273}
274
275template <class _Tp>
276_LIBCPP_HIDE_FROM_ABI void __cxx_atomic_init(__cxx_atomic_base_impl<_Tp> volatile* __a, _Tp __val) _NOEXCEPT {
277 __c11_atomic_init(std::addressof(__a->__a_value), __val);
278}
279template <class _Tp>
280_LIBCPP_HIDE_FROM_ABI void __cxx_atomic_init(__cxx_atomic_base_impl<_Tp>* __a, _Tp __val) _NOEXCEPT {
281 __c11_atomic_init(std::addressof(__a->__a_value), __val);
282}
283
284template <class _Tp>
285_LIBCPP_HIDE_FROM_ABI void
286__cxx_atomic_store(__cxx_atomic_base_impl<_Tp> volatile* __a, _Tp __val, memory_order __order) _NOEXCEPT {
287 __c11_atomic_store(std::addressof(__a->__a_value), __val, static_cast<__memory_order_underlying_t>(__order));
288}
289template <class _Tp>
290_LIBCPP_HIDE_FROM_ABI void
291__cxx_atomic_store(__cxx_atomic_base_impl<_Tp>* __a, _Tp __val, memory_order __order) _NOEXCEPT {
292 __c11_atomic_store(std::addressof(__a->__a_value), __val, static_cast<__memory_order_underlying_t>(__order));
293}
294
295template <class _Tp>
296_LIBCPP_HIDE_FROM_ABI _Tp
297__cxx_atomic_load(__cxx_atomic_base_impl<_Tp> const volatile* __a, memory_order __order) _NOEXCEPT {
298 using __ptr_type = __remove_const_t<decltype(__a->__a_value)>*;
299 return __c11_atomic_load(
300 const_cast<__ptr_type>(std::addressof(__a->__a_value)), static_cast<__memory_order_underlying_t>(__order));
301}
302template <class _Tp>
303_LIBCPP_HIDE_FROM_ABI _Tp __cxx_atomic_load(__cxx_atomic_base_impl<_Tp> const* __a, memory_order __order) _NOEXCEPT {
304 using __ptr_type = __remove_const_t<decltype(__a->__a_value)>*;
305 return __c11_atomic_load(
306 const_cast<__ptr_type>(std::addressof(__a->__a_value)), static_cast<__memory_order_underlying_t>(__order));
307}
308
309template <class _Tp>
310_LIBCPP_HIDE_FROM_ABI void
311__cxx_atomic_load_inplace(__cxx_atomic_base_impl<_Tp> const volatile* __a, _Tp* __dst, memory_order __order) _NOEXCEPT {
312 using __ptr_type = __remove_const_t<decltype(__a->__a_value)>*;
313 *__dst = __c11_atomic_load(
314 const_cast<__ptr_type>(std::addressof(__a->__a_value)), static_cast<__memory_order_underlying_t>(__order));
315}
316template <class _Tp>
317_LIBCPP_HIDE_FROM_ABI void
318__cxx_atomic_load_inplace(__cxx_atomic_base_impl<_Tp> const* __a, _Tp* __dst, memory_order __order) _NOEXCEPT {
319 using __ptr_type = __remove_const_t<decltype(__a->__a_value)>*;
320 *__dst = __c11_atomic_load(
321 const_cast<__ptr_type>(std::addressof(__a->__a_value)), static_cast<__memory_order_underlying_t>(__order));
322}
323
324template <class _Tp>
325_LIBCPP_HIDE_FROM_ABI _Tp
326__cxx_atomic_exchange(__cxx_atomic_base_impl<_Tp> volatile* __a, _Tp __value, memory_order __order) _NOEXCEPT {
327 return __c11_atomic_exchange(
328 std::addressof(__a->__a_value), __value, static_cast<__memory_order_underlying_t>(__order));
329}
330template <class _Tp>
331_LIBCPP_HIDE_FROM_ABI _Tp
332__cxx_atomic_exchange(__cxx_atomic_base_impl<_Tp>* __a, _Tp __value, memory_order __order) _NOEXCEPT {
333 return __c11_atomic_exchange(
334 std::addressof(__a->__a_value), __value, static_cast<__memory_order_underlying_t>(__order));
335}
336
337_LIBCPP_HIDE_FROM_ABI inline memory_order __to_failure_order(memory_order __order) {
338 // Avoid switch statement to make this a constexpr.
339 return __order == memory_order_release
340 ? memory_order_relaxed
341 : (__order == memory_order_acq_rel ? memory_order_acquire : __order);
342}
343
344template <class _Tp>
345_LIBCPP_HIDE_FROM_ABI bool __cxx_atomic_compare_exchange_strong(
346 __cxx_atomic_base_impl<_Tp> volatile* __a,
347 _Tp* __expected,
348 _Tp __value,
349 memory_order __success,
350 memory_order __failure) _NOEXCEPT {
351 return __c11_atomic_compare_exchange_strong(
352 std::addressof(__a->__a_value),
353 __expected,
354 __value,
355 static_cast<__memory_order_underlying_t>(__success),
356 static_cast<__memory_order_underlying_t>(__to_failure_order(__failure)));
357}
358template <class _Tp>
359_LIBCPP_HIDE_FROM_ABI bool __cxx_atomic_compare_exchange_strong(
360 __cxx_atomic_base_impl<_Tp>* __a, _Tp* __expected, _Tp __value, memory_order __success, memory_order __failure)
361 _NOEXCEPT {
362 return __c11_atomic_compare_exchange_strong(
363 std::addressof(__a->__a_value),
364 __expected,
365 __value,
366 static_cast<__memory_order_underlying_t>(__success),
367 static_cast<__memory_order_underlying_t>(__to_failure_order(__failure)));
368}
369
370template <class _Tp>
371_LIBCPP_HIDE_FROM_ABI bool __cxx_atomic_compare_exchange_weak(
372 __cxx_atomic_base_impl<_Tp> volatile* __a,
373 _Tp* __expected,
374 _Tp __value,
375 memory_order __success,
376 memory_order __failure) _NOEXCEPT {
377 return __c11_atomic_compare_exchange_weak(
378 std::addressof(__a->__a_value),
379 __expected,
380 __value,
381 static_cast<__memory_order_underlying_t>(__success),
382 static_cast<__memory_order_underlying_t>(__to_failure_order(__failure)));
383}
384template <class _Tp>
385_LIBCPP_HIDE_FROM_ABI bool __cxx_atomic_compare_exchange_weak(
386 __cxx_atomic_base_impl<_Tp>* __a, _Tp* __expected, _Tp __value, memory_order __success, memory_order __failure)
387 _NOEXCEPT {
388 return __c11_atomic_compare_exchange_weak(
389 std::addressof(__a->__a_value),
390 __expected,
391 __value,
392 static_cast<__memory_order_underlying_t>(__success),
393 static_cast<__memory_order_underlying_t>(__to_failure_order(__failure)));
394}
395
396template <class _Tp>
397_LIBCPP_HIDE_FROM_ABI _Tp
398__cxx_atomic_fetch_add(__cxx_atomic_base_impl<_Tp> volatile* __a, _Tp __delta, memory_order __order) _NOEXCEPT {
399 return __c11_atomic_fetch_add(
400 std::addressof(__a->__a_value), __delta, static_cast<__memory_order_underlying_t>(__order));
401}
402template <class _Tp>
403_LIBCPP_HIDE_FROM_ABI _Tp
404__cxx_atomic_fetch_add(__cxx_atomic_base_impl<_Tp>* __a, _Tp __delta, memory_order __order) _NOEXCEPT {
405 return __c11_atomic_fetch_add(
406 std::addressof(__a->__a_value), __delta, static_cast<__memory_order_underlying_t>(__order));
407}
408
409template <class _Tp>
410_LIBCPP_HIDE_FROM_ABI _Tp*
411__cxx_atomic_fetch_add(__cxx_atomic_base_impl<_Tp*> volatile* __a, ptrdiff_t __delta, memory_order __order) _NOEXCEPT {
412 return __c11_atomic_fetch_add(
413 std::addressof(__a->__a_value), __delta, static_cast<__memory_order_underlying_t>(__order));
414}
415template <class _Tp>
416_LIBCPP_HIDE_FROM_ABI _Tp*
417__cxx_atomic_fetch_add(__cxx_atomic_base_impl<_Tp*>* __a, ptrdiff_t __delta, memory_order __order) _NOEXCEPT {
418 return __c11_atomic_fetch_add(
419 std::addressof(__a->__a_value), __delta, static_cast<__memory_order_underlying_t>(__order));
420}
421
422template <class _Tp>
423_LIBCPP_HIDE_FROM_ABI _Tp
424__cxx_atomic_fetch_sub(__cxx_atomic_base_impl<_Tp> volatile* __a, _Tp __delta, memory_order __order) _NOEXCEPT {
425 return __c11_atomic_fetch_sub(
426 std::addressof(__a->__a_value), __delta, static_cast<__memory_order_underlying_t>(__order));
427}
428template <class _Tp>
429_LIBCPP_HIDE_FROM_ABI _Tp
430__cxx_atomic_fetch_sub(__cxx_atomic_base_impl<_Tp>* __a, _Tp __delta, memory_order __order) _NOEXCEPT {
431 return __c11_atomic_fetch_sub(
432 std::addressof(__a->__a_value), __delta, static_cast<__memory_order_underlying_t>(__order));
433}
434template <class _Tp>
435_LIBCPP_HIDE_FROM_ABI _Tp*
436__cxx_atomic_fetch_sub(__cxx_atomic_base_impl<_Tp*> volatile* __a, ptrdiff_t __delta, memory_order __order) _NOEXCEPT {
437 return __c11_atomic_fetch_sub(
438 std::addressof(__a->__a_value), __delta, static_cast<__memory_order_underlying_t>(__order));
439}
440template <class _Tp>
441_LIBCPP_HIDE_FROM_ABI _Tp*
442__cxx_atomic_fetch_sub(__cxx_atomic_base_impl<_Tp*>* __a, ptrdiff_t __delta, memory_order __order) _NOEXCEPT {
443 return __c11_atomic_fetch_sub(
444 std::addressof(__a->__a_value), __delta, static_cast<__memory_order_underlying_t>(__order));
445}
446
447template <class _Tp>
448_LIBCPP_HIDE_FROM_ABI _Tp
449__cxx_atomic_fetch_and(__cxx_atomic_base_impl<_Tp> volatile* __a, _Tp __pattern, memory_order __order) _NOEXCEPT {
450 return __c11_atomic_fetch_and(
451 std::addressof(__a->__a_value), __pattern, static_cast<__memory_order_underlying_t>(__order));
452}
453template <class _Tp>
454_LIBCPP_HIDE_FROM_ABI _Tp
455__cxx_atomic_fetch_and(__cxx_atomic_base_impl<_Tp>* __a, _Tp __pattern, memory_order __order) _NOEXCEPT {
456 return __c11_atomic_fetch_and(
457 std::addressof(__a->__a_value), __pattern, static_cast<__memory_order_underlying_t>(__order));
458}
459
460template <class _Tp>
461_LIBCPP_HIDE_FROM_ABI _Tp
462__cxx_atomic_fetch_or(__cxx_atomic_base_impl<_Tp> volatile* __a, _Tp __pattern, memory_order __order) _NOEXCEPT {
463 return __c11_atomic_fetch_or(
464 std::addressof(__a->__a_value), __pattern, static_cast<__memory_order_underlying_t>(__order));
465}
466template <class _Tp>
467_LIBCPP_HIDE_FROM_ABI _Tp
468__cxx_atomic_fetch_or(__cxx_atomic_base_impl<_Tp>* __a, _Tp __pattern, memory_order __order) _NOEXCEPT {
469 return __c11_atomic_fetch_or(
470 std::addressof(__a->__a_value), __pattern, static_cast<__memory_order_underlying_t>(__order));
471}
472
473template <class _Tp>
474_LIBCPP_HIDE_FROM_ABI _Tp
475__cxx_atomic_fetch_xor(__cxx_atomic_base_impl<_Tp> volatile* __a, _Tp __pattern, memory_order __order) _NOEXCEPT {
476 return __c11_atomic_fetch_xor(
477 std::addressof(__a->__a_value), __pattern, static_cast<__memory_order_underlying_t>(__order));
478}
479template <class _Tp>
480_LIBCPP_HIDE_FROM_ABI _Tp
481__cxx_atomic_fetch_xor(__cxx_atomic_base_impl<_Tp>* __a, _Tp __pattern, memory_order __order) _NOEXCEPT {
482 return __c11_atomic_fetch_xor(
483 std::addressof(__a->__a_value), __pattern, static_cast<__memory_order_underlying_t>(__order));
484}
485
486#endif // _LIBCPP_HAS_GCC_ATOMIC_IMP, _LIBCPP_HAS_C_ATOMIC_IMP
487
488template <typename _Tp, typename _Base = __cxx_atomic_base_impl<_Tp> >
489struct __cxx_atomic_impl : public _Base {
490 static_assert(is_trivially_copyable<_Tp>::value, "std::atomic<T> requires that 'T' be a trivially copyable type");
491
492 _LIBCPP_HIDE_FROM_ABI __cxx_atomic_impl() _NOEXCEPT = default;
493 _LIBCPP_HIDE_FROM_ABI explicit __cxx_atomic_impl(_Tp __value) _NOEXCEPT : _Base(__value) {}
494};
495
496_LIBCPP_END_NAMESPACE_STD
497
498#endif // _LIBCPP___CXX03___ATOMIC_CXX_ATOMIC_IMPL_H
499

Warning: This file is not a C or C++ file. It does not have highlighting.

source code of libcxx/include/__cxx03/__atomic/cxx_atomic_impl.h