File indexing completed on 2025-01-30 09:33:54
0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014 #ifndef BOOST_ATOMIC_DETAIL_EXTRA_OPS_EMULATED_HPP_INCLUDED_
0015 #define BOOST_ATOMIC_DETAIL_EXTRA_OPS_EMULATED_HPP_INCLUDED_
0016
0017 #include <cstddef>
0018 #include <boost/memory_order.hpp>
0019 #include <boost/atomic/detail/config.hpp>
0020 #include <boost/atomic/detail/storage_traits.hpp>
0021 #include <boost/atomic/detail/extra_operations_fwd.hpp>
0022 #include <boost/atomic/detail/header.hpp>
0023
0024 #ifdef BOOST_HAS_PRAGMA_ONCE
0025 #pragma once
0026 #endif
0027
0028 namespace boost {
0029 namespace atomics {
0030 namespace detail {
0031
0032
0033 template< typename Base, std::size_t Size, bool Signed >
0034 struct extra_operations_emulated :
0035 public Base
0036 {
0037 typedef Base base_type;
0038 typedef typename base_type::storage_type storage_type;
0039 typedef typename base_type::scoped_lock scoped_lock;
0040
0041 static storage_type fetch_negate(storage_type volatile& storage, memory_order) BOOST_NOEXCEPT
0042 {
0043 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0044 storage_type& s = const_cast< storage_type& >(storage);
0045 scoped_lock lock(&storage);
0046 storage_type old_val = s;
0047 s = static_cast< storage_type >(-old_val);
0048 return old_val;
0049 }
0050
0051 static storage_type negate(storage_type volatile& storage, memory_order) BOOST_NOEXCEPT
0052 {
0053 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0054 storage_type& s = const_cast< storage_type& >(storage);
0055 scoped_lock lock(&storage);
0056 storage_type new_val = static_cast< storage_type >(-s);
0057 s = new_val;
0058 return new_val;
0059 }
0060
0061 static storage_type add(storage_type volatile& storage, storage_type v, memory_order) BOOST_NOEXCEPT
0062 {
0063 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0064 storage_type& s = const_cast< storage_type& >(storage);
0065 scoped_lock lock(&storage);
0066 storage_type new_val = s;
0067 new_val += v;
0068 s = new_val;
0069 return new_val;
0070 }
0071
0072 static storage_type sub(storage_type volatile& storage, storage_type v, memory_order) BOOST_NOEXCEPT
0073 {
0074 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0075 storage_type& s = const_cast< storage_type& >(storage);
0076 scoped_lock lock(&storage);
0077 storage_type new_val = s;
0078 new_val -= v;
0079 s = new_val;
0080 return new_val;
0081 }
0082
0083 static storage_type bitwise_and(storage_type volatile& storage, storage_type v, memory_order) BOOST_NOEXCEPT
0084 {
0085 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0086 storage_type& s = const_cast< storage_type& >(storage);
0087 scoped_lock lock(&storage);
0088 storage_type new_val = s;
0089 new_val &= v;
0090 s = new_val;
0091 return new_val;
0092 }
0093
0094 static storage_type bitwise_or(storage_type volatile& storage, storage_type v, memory_order) BOOST_NOEXCEPT
0095 {
0096 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0097 storage_type& s = const_cast< storage_type& >(storage);
0098 scoped_lock lock(&storage);
0099 storage_type new_val = s;
0100 new_val |= v;
0101 s = new_val;
0102 return new_val;
0103 }
0104
0105 static storage_type bitwise_xor(storage_type volatile& storage, storage_type v, memory_order) BOOST_NOEXCEPT
0106 {
0107 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0108 storage_type& s = const_cast< storage_type& >(storage);
0109 scoped_lock lock(&storage);
0110 storage_type new_val = s;
0111 new_val ^= v;
0112 s = new_val;
0113 return new_val;
0114 }
0115
0116 static storage_type fetch_complement(storage_type volatile& storage, memory_order) BOOST_NOEXCEPT
0117 {
0118 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0119 storage_type& s = const_cast< storage_type& >(storage);
0120 scoped_lock lock(&storage);
0121 storage_type old_val = s;
0122 s = static_cast< storage_type >(~old_val);
0123 return old_val;
0124 }
0125
0126 static storage_type bitwise_complement(storage_type volatile& storage, memory_order) BOOST_NOEXCEPT
0127 {
0128 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0129 storage_type& s = const_cast< storage_type& >(storage);
0130 scoped_lock lock(&storage);
0131 storage_type new_val = static_cast< storage_type >(~s);
0132 s = new_val;
0133 return new_val;
0134 }
0135
0136 static BOOST_FORCEINLINE void opaque_add(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
0137 {
0138 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0139 base_type::fetch_add(storage, v, order);
0140 }
0141
0142 static BOOST_FORCEINLINE void opaque_sub(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
0143 {
0144 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0145 base_type::fetch_sub(storage, v, order);
0146 }
0147
0148 static BOOST_FORCEINLINE void opaque_negate(storage_type volatile& storage, memory_order order) BOOST_NOEXCEPT
0149 {
0150 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0151 fetch_negate(storage, order);
0152 }
0153
0154 static BOOST_FORCEINLINE void opaque_and(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
0155 {
0156 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0157 base_type::fetch_and(storage, v, order);
0158 }
0159
0160 static BOOST_FORCEINLINE void opaque_or(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
0161 {
0162 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0163 base_type::fetch_or(storage, v, order);
0164 }
0165
0166 static BOOST_FORCEINLINE void opaque_xor(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
0167 {
0168 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0169 base_type::fetch_xor(storage, v, order);
0170 }
0171
0172 static BOOST_FORCEINLINE void opaque_complement(storage_type volatile& storage, memory_order order) BOOST_NOEXCEPT
0173 {
0174 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0175 fetch_complement(storage, order);
0176 }
0177
0178 static BOOST_FORCEINLINE bool add_and_test(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
0179 {
0180 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0181 return !!add(storage, v, order);
0182 }
0183
0184 static BOOST_FORCEINLINE bool sub_and_test(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
0185 {
0186 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0187 return !!sub(storage, v, order);
0188 }
0189
0190 static BOOST_FORCEINLINE bool negate_and_test(storage_type volatile& storage, memory_order order) BOOST_NOEXCEPT
0191 {
0192 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0193 return !!negate(storage, order);
0194 }
0195
0196 static BOOST_FORCEINLINE bool and_and_test(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
0197 {
0198 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0199 return !!bitwise_and(storage, v, order);
0200 }
0201
0202 static BOOST_FORCEINLINE bool or_and_test(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
0203 {
0204 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0205 return !!bitwise_or(storage, v, order);
0206 }
0207
0208 static BOOST_FORCEINLINE bool xor_and_test(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
0209 {
0210 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0211 return !!bitwise_xor(storage, v, order);
0212 }
0213
0214 static BOOST_FORCEINLINE bool complement_and_test(storage_type volatile& storage, memory_order order) BOOST_NOEXCEPT
0215 {
0216 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0217 return !!bitwise_complement(storage, order);
0218 }
0219
0220 static BOOST_FORCEINLINE bool bit_test_and_set(storage_type volatile& storage, unsigned int bit_number, memory_order order) BOOST_NOEXCEPT
0221 {
0222 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0223 storage_type mask = static_cast< storage_type >(static_cast< storage_type >(1u) << bit_number);
0224 storage_type old_val = base_type::fetch_or(storage, mask, order);
0225 return !!(old_val & mask);
0226 }
0227
0228 static BOOST_FORCEINLINE bool bit_test_and_reset(storage_type volatile& storage, unsigned int bit_number, memory_order order) BOOST_NOEXCEPT
0229 {
0230 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0231 storage_type mask = static_cast< storage_type >(static_cast< storage_type >(1u) << bit_number);
0232 storage_type old_val = base_type::fetch_and(storage, ~mask, order);
0233 return !!(old_val & mask);
0234 }
0235
0236 static BOOST_FORCEINLINE bool bit_test_and_complement(storage_type volatile& storage, unsigned int bit_number, memory_order order) BOOST_NOEXCEPT
0237 {
0238 static_assert(!base_type::is_interprocess, "Boost.Atomic: operation invoked on a non-lock-free inter-process atomic object");
0239 storage_type mask = static_cast< storage_type >(static_cast< storage_type >(1u) << bit_number);
0240 storage_type old_val = base_type::fetch_xor(storage, mask, order);
0241 return !!(old_val & mask);
0242 }
0243 };
0244
0245 template< typename Base, std::size_t Size, bool Signed >
0246 struct extra_operations< Base, Size, Signed, false > :
0247 public extra_operations_emulated< Base, Size, Signed >
0248 {
0249 };
0250
0251 }
0252 }
0253 }
0254
0255 #include <boost/atomic/detail/footer.hpp>
0256
0257 #endif