1/*
2 * Distributed under the Boost Software License, Version 1.0.
3 * (See accompanying file LICENSE_1_0.txt or copy at
4 * http://www.boost.org/LICENSE_1_0.txt)
5 *
6 * Copyright (c) 2011 Helge Bahmann
7 * Copyright (c) 2013 Tim Blechmann
8 * Copyright (c) 2014, 2020 Andrey Semashev
9 */
10/*!
11 * \file atomic/atomic.hpp
12 *
13 * This header contains definition of \c atomic template.
14 */
15
16#ifndef BOOST_ATOMIC_ATOMIC_HPP_INCLUDED_
17#define BOOST_ATOMIC_ATOMIC_HPP_INCLUDED_
18
19#include <cstddef>
20#include <boost/cstdint.hpp>
21#include <boost/memory_order.hpp>
22#include <boost/atomic/capabilities.hpp>
23#include <boost/atomic/detail/config.hpp>
24#include <boost/atomic/detail/classify.hpp>
25#include <boost/atomic/detail/atomic_impl.hpp>
26#include <boost/atomic/detail/type_traits/is_trivially_copyable.hpp>
27#include <boost/atomic/detail/type_traits/is_nothrow_default_constructible.hpp>
28#include <boost/atomic/detail/header.hpp>
29
30#ifdef BOOST_HAS_PRAGMA_ONCE
31#pragma once
32#endif
33
34namespace boost {
35namespace atomics {
36
37//! Atomic object
38template< typename T >
39class atomic :
40 public atomics::detail::base_atomic< T, typename atomics::detail::classify< T >::type, false >
41{
42private:
43 typedef atomics::detail::base_atomic< T, typename atomics::detail::classify< T >::type, false > base_type;
44 typedef typename base_type::value_arg_type value_arg_type;
45
46public:
47 typedef typename base_type::value_type value_type;
48
49 static_assert(sizeof(value_type) > 0u, "boost::atomic<T> requires T to be a complete type");
50#if !defined(BOOST_ATOMIC_DETAIL_NO_CXX11_IS_TRIVIALLY_COPYABLE)
51 static_assert(atomics::detail::is_trivially_copyable< value_type >::value, "boost::atomic<T> requires T to be a trivially copyable type");
52#endif
53
54public:
55 BOOST_FORCEINLINE BOOST_ATOMIC_DETAIL_CONSTEXPR_UNION_INIT atomic() BOOST_NOEXCEPT_IF(atomics::detail::is_nothrow_default_constructible< value_type >::value) : base_type()
56 {
57 }
58
59 BOOST_FORCEINLINE BOOST_ATOMIC_DETAIL_CONSTEXPR_UNION_INIT atomic(value_arg_type v) BOOST_NOEXCEPT : base_type(v)
60 {
61 }
62
63 BOOST_FORCEINLINE value_type operator= (value_arg_type v) BOOST_NOEXCEPT
64 {
65 this->store(v);
66 return v;
67 }
68
69 BOOST_FORCEINLINE value_type operator= (value_arg_type v) volatile BOOST_NOEXCEPT
70 {
71 this->store(v);
72 return v;
73 }
74
75 BOOST_FORCEINLINE operator value_type() const volatile BOOST_NOEXCEPT
76 {
77 return this->load();
78 }
79
80 BOOST_DELETED_FUNCTION(atomic(atomic const&))
81 BOOST_DELETED_FUNCTION(atomic& operator= (atomic const&))
82 BOOST_DELETED_FUNCTION(atomic& operator= (atomic const&) volatile)
83};
84
85typedef atomic< char > atomic_char;
86typedef atomic< unsigned char > atomic_uchar;
87typedef atomic< signed char > atomic_schar;
88typedef atomic< uint8_t > atomic_uint8_t;
89typedef atomic< int8_t > atomic_int8_t;
90typedef atomic< unsigned short > atomic_ushort;
91typedef atomic< short > atomic_short;
92typedef atomic< uint16_t > atomic_uint16_t;
93typedef atomic< int16_t > atomic_int16_t;
94typedef atomic< unsigned int > atomic_uint;
95typedef atomic< int > atomic_int;
96typedef atomic< uint32_t > atomic_uint32_t;
97typedef atomic< int32_t > atomic_int32_t;
98typedef atomic< unsigned long > atomic_ulong;
99typedef atomic< long > atomic_long;
100typedef atomic< uint64_t > atomic_uint64_t;
101typedef atomic< int64_t > atomic_int64_t;
102#ifdef BOOST_HAS_LONG_LONG
103typedef atomic< boost::ulong_long_type > atomic_ullong;
104typedef atomic< boost::long_long_type > atomic_llong;
105#endif
106typedef atomic< void* > atomic_address;
107typedef atomic< bool > atomic_bool;
108typedef atomic< wchar_t > atomic_wchar_t;
109#if defined(__cpp_char8_t) && __cpp_char8_t >= 201811
110typedef atomic< char8_t > atomic_char8_t;
111#endif
112#if !defined(BOOST_NO_CXX11_CHAR16_T)
113typedef atomic< char16_t > atomic_char16_t;
114#endif
115#if !defined(BOOST_NO_CXX11_CHAR32_T)
116typedef atomic< char32_t > atomic_char32_t;
117#endif
118
119typedef atomic< int_least8_t > atomic_int_least8_t;
120typedef atomic< uint_least8_t > atomic_uint_least8_t;
121typedef atomic< int_least16_t > atomic_int_least16_t;
122typedef atomic< uint_least16_t > atomic_uint_least16_t;
123typedef atomic< int_least32_t > atomic_int_least32_t;
124typedef atomic< uint_least32_t > atomic_uint_least32_t;
125typedef atomic< int_least64_t > atomic_int_least64_t;
126typedef atomic< uint_least64_t > atomic_uint_least64_t;
127typedef atomic< int_fast8_t > atomic_int_fast8_t;
128typedef atomic< uint_fast8_t > atomic_uint_fast8_t;
129typedef atomic< int_fast16_t > atomic_int_fast16_t;
130typedef atomic< uint_fast16_t > atomic_uint_fast16_t;
131typedef atomic< int_fast32_t > atomic_int_fast32_t;
132typedef atomic< uint_fast32_t > atomic_uint_fast32_t;
133typedef atomic< int_fast64_t > atomic_int_fast64_t;
134typedef atomic< uint_fast64_t > atomic_uint_fast64_t;
135typedef atomic< intmax_t > atomic_intmax_t;
136typedef atomic< uintmax_t > atomic_uintmax_t;
137
138#if !defined(BOOST_ATOMIC_NO_FLOATING_POINT)
139typedef atomic< float > atomic_float_t;
140typedef atomic< double > atomic_double_t;
141typedef atomic< long double > atomic_long_double_t;
142#endif
143
144typedef atomic< std::size_t > atomic_size_t;
145typedef atomic< std::ptrdiff_t > atomic_ptrdiff_t;
146
147#if defined(BOOST_HAS_INTPTR_T)
148typedef atomic< boost::intptr_t > atomic_intptr_t;
149typedef atomic< boost::uintptr_t > atomic_uintptr_t;
150#endif
151
152// Select the lock-free atomic types that has natively supported waiting/notifying operations.
153// Prefer 32-bit types the most as those have the best performance on current 32 and 64-bit architectures.
154#if BOOST_ATOMIC_INT32_LOCK_FREE == 2 && BOOST_ATOMIC_HAS_NATIVE_INT32_WAIT_NOTIFY == 2
155typedef atomic< uint32_t > atomic_unsigned_lock_free;
156typedef atomic< int32_t > atomic_signed_lock_free;
157#elif BOOST_ATOMIC_INT64_LOCK_FREE == 2 && BOOST_ATOMIC_HAS_NATIVE_INT64_WAIT_NOTIFY == 2
158typedef atomic< uint64_t > atomic_unsigned_lock_free;
159typedef atomic< int64_t > atomic_signed_lock_free;
160#elif BOOST_ATOMIC_INT16_LOCK_FREE == 2 && BOOST_ATOMIC_HAS_NATIVE_INT16_WAIT_NOTIFY == 2
161typedef atomic< uint16_t > atomic_unsigned_lock_free;
162typedef atomic< int16_t > atomic_signed_lock_free;
163#elif BOOST_ATOMIC_INT8_LOCK_FREE == 2 && BOOST_ATOMIC_HAS_NATIVE_INT8_WAIT_NOTIFY == 2
164typedef atomic< uint8_t > atomic_unsigned_lock_free;
165typedef atomic< int8_t > atomic_signed_lock_free;
166#elif BOOST_ATOMIC_INT32_LOCK_FREE == 2
167typedef atomic< uint32_t > atomic_unsigned_lock_free;
168typedef atomic< int32_t > atomic_signed_lock_free;
169#elif BOOST_ATOMIC_INT64_LOCK_FREE == 2
170typedef atomic< uint64_t > atomic_unsigned_lock_free;
171typedef atomic< int64_t > atomic_signed_lock_free;
172#elif BOOST_ATOMIC_INT16_LOCK_FREE == 2
173typedef atomic< uint16_t > atomic_unsigned_lock_free;
174typedef atomic< int16_t > atomic_signed_lock_free;
175#elif BOOST_ATOMIC_INT8_LOCK_FREE == 2
176typedef atomic< uint8_t > atomic_unsigned_lock_free;
177typedef atomic< int8_t > atomic_signed_lock_free;
178#else
179#define BOOST_ATOMIC_DETAIL_NO_LOCK_FREE_TYPEDEFS
180#endif
181
182} // namespace atomics
183
184using atomics::atomic;
185
186using atomics::atomic_char;
187using atomics::atomic_uchar;
188using atomics::atomic_schar;
189using atomics::atomic_uint8_t;
190using atomics::atomic_int8_t;
191using atomics::atomic_ushort;
192using atomics::atomic_short;
193using atomics::atomic_uint16_t;
194using atomics::atomic_int16_t;
195using atomics::atomic_uint;
196using atomics::atomic_int;
197using atomics::atomic_uint32_t;
198using atomics::atomic_int32_t;
199using atomics::atomic_ulong;
200using atomics::atomic_long;
201using atomics::atomic_uint64_t;
202using atomics::atomic_int64_t;
203#ifdef BOOST_HAS_LONG_LONG
204using atomics::atomic_ullong;
205using atomics::atomic_llong;
206#endif
207using atomics::atomic_address;
208using atomics::atomic_bool;
209using atomics::atomic_wchar_t;
210#if defined(__cpp_char8_t) && __cpp_char8_t >= 201811
211using atomics::atomic_char8_t;
212#endif
213#if !defined(BOOST_NO_CXX11_CHAR16_T)
214using atomics::atomic_char16_t;
215#endif
216#if !defined(BOOST_NO_CXX11_CHAR32_T)
217using atomics::atomic_char32_t;
218#endif
219
220using atomics::atomic_int_least8_t;
221using atomics::atomic_uint_least8_t;
222using atomics::atomic_int_least16_t;
223using atomics::atomic_uint_least16_t;
224using atomics::atomic_int_least32_t;
225using atomics::atomic_uint_least32_t;
226using atomics::atomic_int_least64_t;
227using atomics::atomic_uint_least64_t;
228using atomics::atomic_int_fast8_t;
229using atomics::atomic_uint_fast8_t;
230using atomics::atomic_int_fast16_t;
231using atomics::atomic_uint_fast16_t;
232using atomics::atomic_int_fast32_t;
233using atomics::atomic_uint_fast32_t;
234using atomics::atomic_int_fast64_t;
235using atomics::atomic_uint_fast64_t;
236using atomics::atomic_intmax_t;
237using atomics::atomic_uintmax_t;
238
239#if !defined(BOOST_ATOMIC_NO_FLOATING_POINT)
240using atomics::atomic_float_t;
241using atomics::atomic_double_t;
242using atomics::atomic_long_double_t;
243#endif
244
245using atomics::atomic_size_t;
246using atomics::atomic_ptrdiff_t;
247
248#if defined(BOOST_HAS_INTPTR_T)
249using atomics::atomic_intptr_t;
250using atomics::atomic_uintptr_t;
251#endif
252
253#if !defined(BOOST_ATOMIC_DETAIL_NO_LOCK_FREE_TYPEDEFS)
254using atomics::atomic_unsigned_lock_free;
255using atomics::atomic_signed_lock_free;
256#endif
257#undef BOOST_ATOMIC_DETAIL_NO_LOCK_FREE_TYPEDEFS
258
259} // namespace boost
260
261#include <boost/atomic/detail/footer.hpp>
262
263#endif // BOOST_ATOMIC_ATOMIC_HPP_INCLUDED_
264

source code of boost/libs/atomic/include/boost/atomic/atomic.hpp