2
0
mirror of https://github.com/boostorg/atomic.git synced 2026-01-31 20:02:09 +00:00
Commit Graph

105 Commits

Author SHA1 Message Date
Andrey Semashev
195d0b9854 Added tests for relaxed loads and stores.
This will involve different branches of code in some asm-based backends.
2022-12-21 21:03:50 +03:00
Andrey Semashev
e44ef5fa3d Ported to BOOST_NO_CXX17_DEDUCTION_GUIDES from Boost.Config. 2022-06-17 01:16:55 +03:00
Andrey Semashev
a172675470 Added source directories to include directories.
This fixes compilation on systems where the compiler does not resolve
includes relative to the current source file directory.

Fixes https://github.com/boostorg/atomic/issues/56.
Closes https://github.com/boostorg/atomic/pull/57.
2022-03-07 01:21:19 +03:00
Andrey Semashev
f4037199b7 Removed names of unused parameters to silence warnings. 2021-10-27 12:04:07 +03:00
Andrey Semashev
8a7aaa543d Make atomic default ctors value initialize the contained object.
This is in line with the C++20 change that requires the default constructor
of std::atomic to value initialize the atomic object.

Also, use is_nothrow_default_constructible to properly deduce noexceptness
of the default constructors of atomics.
2021-10-12 20:36:11 +03:00
Andrey Semashev
2211fee1d4 Added bitwise_cast implementation based on bit_cast intrinsics.
This allows to mark bitwise_cast constexpr when the conditions to use
bit_cast are met:

 - both source and target types have the same size, and
 - the source type has no padding bits.

The latter is checked using has_unique_object_representations trait, which
we also implement using intrinsics when not available in the standard
library.

This allows atomic constructors to become constexpr for structs and floating
point types with no padding and whose size matches the atomic storage size.
2021-10-12 18:55:13 +03:00
Andrey Semashev
746ea2649b Added support for types with padding. Made atomic ctors for enums constexpr.
Use __builtin_clear_padding and __builtin_zero_non_value_bits that were
introduced in gcc 11 and MSVC 19.27 to clear the padding bits in atomic
types. The intrinsics are used in bitwise_cast and atomic reference
constructors.

Also, separated atomic impl specializations for enums to allow using
static_cast to convert values to storage. This in turn allows to
relax compiler requirements to mark atomic constructors constexpr.

Updated docs and added tests for structs with padding and constexpr
atomic constructors.
2021-10-11 18:05:06 +03:00
Andrey Semashev
ef4dedb031 Added tests for HAS_NATIVE_WAIT_NOTIFY macros and static constants. 2021-10-09 21:22:20 +03:00
Andrey Semashev
cbf5ae1ad2 Allocate IPC atomic objects in dynamic memory instead of the stack.
This works around spurious test failures on Mac OS as the notifying operation
sometimes fails with ENOENT. Presumably, the OS sometimes invalidates the
internal identification of the stack memory region, which makes __ulock_wake
fail to find the ulock object that other threads are blocked on.

By using dynamic memory we (hopefully) are using a location in a normal mapped
memory region that should not be mangled by the OS. Ideally, we would use
process-shared memory for this test, but that makes it more difficult to make
it portable and runnable in parallel. Dynamic local memory should do for now.
2021-09-26 19:54:01 +03:00
Andrey Semashev
a548b3c15c Added template deduction guides and factory functions for atomic refs. 2021-06-16 02:22:40 +03:00
Andrey Semashev
e9374cb8db Disabled gcc and clang warnings caused by Boost.Preprocessor.
Boost.Preprocessor uses variadic macros and empty macro arguments
even in C++03 mode, which makes gcc and clang emit lots of warnings.
2021-02-01 01:29:43 +03:00
Andrey Semashev
ea5911a413 Added tests for arithmetic and bitwise ops with immediate constants.
This test verifies arithmetic and bitwise (logic) operations with
immediate constant arguments, which may affect instruction choice
in the operations. In particular, the test verifies that bug
https://github.com/boostorg/atomic/issues/41 is fixed.
2020-11-20 13:58:16 +03:00
Andrey Semashev
a40aa9ba6c Implemented SSE2 and SSE4.1 versions of address lookup algorithms. 2020-09-07 16:57:22 +03:00
Andrey Semashev
9e9d1f4398 Added AArch32 and AArch64 gcc asm-based backends.
This is the second iteration of the backends, which were both tested
on a QEMU VM and did not show any test failures. The essential difference
from the first version is that in AArch64 we now initialize the success flag
in the asm blocks in compare_exchange operations rather than relying on
compiler initializing it before passing into the asm block as an in-out
parameter. Apparently, this sometimes didn't work for some reason, which
made compare_exchange_strong return incorrect value, which broke futex-based
mutexes in the lock pool.

The above change was also applied to AArch32, along with minor corrections
in the asm blocks constraints.
2020-06-24 21:52:52 +03:00
Andrey Semashev
fd2326cf4d Added a check in notify_one tests if the first thread wakes up too late.
In that case the first thread may receive the value3 instead of value2.
2020-06-24 14:53:27 +03:00
Andrey Semashev
5ec2265754 Removed AArch32 and AArch64 gcc asm-based backends.
The backends will be moved to a separate branch for testing.
2020-06-24 14:41:33 +03:00
Andrey Semashev
a247342a13 Added support for newer gcc versions and ARMv8 AArch32 in lockfree test. 2020-06-23 22:55:14 +03:00
Andrey Semashev
e5bb7eca93 Corrected check for cmpxchg16b availability in lockfree test. 2020-06-23 21:57:18 +03:00
Andrey Semashev
06dcdf26c6 Added a configure check to test if synchronization.lib exists.
We need to explicitly link with synchronization.lib when the
WaitOnAddress API is enabled at compile time for ARM targets. Since
this library is only available on newer Windows SDKs, we have to perform
a configure check for whether it is available.
2020-06-21 19:07:28 +03:00
Andrey Semashev
b02b59fd3a Separated arch-specific core and fence operations to new ops structures.
The old operations template is replaced with core_operations, which falls
back to core_arch_operations, which falls back to core_operations_emulated.

The core_operations layer is intended for more or less architecture-neutral
backends, like the one based on gcc __atomic* intrinsics. It may fall back
to core_arch_operations where it is not supported by the compiler or where
the latter is more optimal. For example, where gcc does not implement 128-bit
atomic operations via __atomic* intrinsics, we support them in the
core_arch_operations backend, which uses inline assembler blocks.

The old emulated_operations template is largely unchanged and was renamed to
core_operations_emulated for naming consistency. All other operation templates
were also renamed for consistency (e.g. generic_wait_operations ->
wait_operations_generic).

Fence operations have been extracted to a separate set of structures:
fence_operations, fence_arch_opereations and fence_operations_emulated. These
are similar to the core operations described above. This structuring also
allows to fall back from fence_operations to fence_arch_opereations when
the latter is more optimal.

The net result of these changes is that 128-bit and 64-bit atomic operations
should now be consistently supported on all architectures that support them.
Previously, only x86 was supported via local hacks for gcc and clang.
2020-06-21 19:07:20 +03:00
Andrey Semashev
651dfd4afb Added gcc asm-based backend for AArch64.
The backend implements core and extra atomic operations using gcc asm blocks.
The implementation supports extensions added in ARMv8.1 and ARMv8.3. It supports
both little and big endian targets.

Currently, the code has not been tested on real hardware. It has been tested
on a QEMU VM.
2020-06-18 12:46:03 +00:00
Andrey Semashev
0cf7964f78 Another workaround for IPC notify_one failures on Windows.
The previous change to increase the delay didn't help, so we're instead
changing the expectation - the first woken thread is allowed to receive
value3 on wake up.
2020-06-14 19:12:33 +03:00
Andrey Semashev
3de4c6c865 Increase delay between notifications in IPC notify_one test.
Occasionally, IPC notify_one test fails on Windows because the first
of the woken threads receives value3 from wait(). This is possible if
the thread lingers in wait() for some reason. Increase the delay
before the second notification slightly to reduce the likelihood
of this happening.
2020-06-14 18:10:30 +03:00
Andrey Semashev
3929919495 Implement a special test_clock for Windows.
The implementation uses GetTickCount/GetTickCount64 internally,
which is a steady and sufficiently low precision time source.

We need the clock to have relatively low precision so that wait
tests don't fail spuriously because the blocked threads wake up
too soon, according to more precise clocks.

boost::chrono::system_clock currently has an acceptably low precision,
but it is not a steady clock.
2020-06-12 13:32:32 +03:00
Andrey Semashev
72c87ca51b Use a lower resolution clock on Windows to reduce spurious test failures. 2020-06-12 03:24:29 +03:00
Andrey Semashev
1b8ec1700b Reworked IPC atomic tests to check for the is_always_lockfree property.
Checking for the capability macros is not good enough because ipc_atomic_ref
can be not lock-free even when the macro (and ipc_atomic) indicates lock-free.

We now check the is_always_lockfree property to decide whether to run or skip
tests for a given IPC atomic type.

Also, made struct_3_bytes output more informative.
2020-06-12 01:58:12 +03:00
Andrey Semashev
58b618d299 Added a basic compile test for fences. 2020-06-12 00:57:59 +03:00
Andrey Semashev
80cfbfd0de Added implementation of inter-process atomics.
The inter-process atomics have ipc_ prefixes: ipc_atomic, ipc_atomic_ref
and ipc_atomic_flag. These types are similar to their unprefixed counterparts
with the following distinctions:

- The operations are provided with an added precondition that is_lock_free()
  returns true.
- All operations, including waiting/notifying operations, are address-free,
  so the types are suitable for inter-process communication.
- The new has_native_wait_notify() operation and always_has_native_wait_notify
  static constant allow to test if the target platform has native support for
  address-free waiting/notifying operations. If it does not, a generic
  implementation is used based on a busy wait.
- The new set of capability macros added. The macros are named
  BOOST_ATOMIC_HAS_NATIVE_<T>_IPC_WAIT_NOTIFY and indicate whether address-free
  waiting/notifying operations are supported natively for a given type.

Additionally, to unify interface and implementation of different components,
the has_native_wait_notify() operation and always_has_native_wait_notify
static constant were added to non-IPC atomic types as well. Added
BOOST_ATOMIC_HAS_NATIVE_<T>_WAIT_NOTIFY capability macros to indicate
native support for inter-thread waiting/notifying operations.

Also, added is_lock_free() and is_always_lock_free to atomic_flag.

This commit adds implementation, docs and tests.
2020-06-11 13:07:16 +03:00
Andrey Semashev
d5dc8f185a Added support for build-time configuration of the lock pool size.
The user may define BOOST_ATOMIC_LOCK_POOL_SIZE_LOG2 macro to specify
binary logarithm of the size of the internal lock pool. The macro
only has effect when building Boost.Atomic.
2020-06-03 01:48:48 +03:00
Andrey Semashev
b737d8357a Removed unused variables. 2020-06-03 01:48:48 +03:00
Andrey Semashev
76e25f36a3 Added generic implementation of C++20 waiting/notifying operations.
The generic implementation is based on the lock pool. A list of condition
variables (or waiting futexes) is added per lock. Basically, the lock
pool serves as a global hash table, where each lock represents
a bucket and each wait state is an element. Every wait operation
allocates a wait state keyed on the pointer to the atomic object. Notify
operations look up the wait state by the atomic pointer and notify
the condition variable/futex. The corresponding lock needs to be acquired
to protect the wait state list during all wait/notify operations.

Backends not involving the lock pool are going to be added later.

The implementation of wait operation extends the C++20 definition in that
it returns the newly loaded value instead of void. This allows the caller
to avoid loading the value himself.

The waiting/notifying operations are not address-free. Address-free variants
will be added later.

Added tests for the new operations and refactored existing tests for atomic
operations. Added docs for the new operations.
2020-06-03 01:39:20 +03:00
Andrey Semashev
e3dce0e226 Added missing const qualifiers in atomic_ref ops and updated tests to verify this. 2020-05-23 23:19:14 +03:00
Andrey Semashev
ddb9cbaadd Slightly cleaner way of aligning the storage pointer. 2020-05-23 23:07:16 +03:00
Andrey Semashev
28464fe1e0 Don't require atomic_ref lock-free if atomic uses padded storage. 2020-03-10 22:58:36 +03:00
Andrey Semashev
c22fc7d416 Added a workaround for gcc 4.7 not supporting constexpr ctors with unions.
gcc 4.7 does not support constexpr constructors that initialize one member
of an anonymous union data member of the class. atomic and atomic_flag
no longer have constexpr constructors on this compiler.
2020-03-01 18:05:01 +03:00
Andrey Semashev
34a2bc134c Fixed compilation on 32-bit x86, reduced code duplication.
On 32-bit x86, 64-bit integers have 4-byte alignment, which resulted in
a non-integral type being selected for storage type in case of lock-based
atomic_ref. This broke arithmetic and bitwise operations on atomic_ref.

We now select an integral type based on its native alignment, not the storage
alignment we require for atomic operations. This is fine in case of lock-based
backend.

Also, extended buffer_storage with support for specifying alignment and removed
aligned_buffer_storage and storage128_t.
2020-03-01 03:11:33 +03:00
Andrey Semashev
a1a31e14e2 Reduce alignment requirements of lock-based backend of atomic_ref.
Lock-based operations have no reason to require object alignment higher
than alignof(T). This commit implements a special storage type for
lock-based operations, which has the same alignment as value_type.

Also, added tests to verify required_alignment correctness both
in lock-free and lock-based cases.
2020-03-01 00:22:35 +03:00
Andrey Semashev
26c4d0dac4 Disabled int128 tests for clang-5 in Travis CI.
For some unknown reason, int128 bit operation tests started failing
in Travis CI for x86-64. The error does not reproduce locally. Given that
float128 were known to fail similarly (only on 32-bit target), it seems all
128-bit operations are broken in clang-5 (possibly caused by something
specific to Travis CI).

This commit re-enables 32-bit tests on clang-5, but disables int128 and
float128 tests on both 32 and 64-bit targets.
2020-02-28 22:38:58 +03:00
Andrey Semashev
19e0c794f5 Avoid using Boost.Align to allocate aligned memory.
This works around MinGW compilation issues[1] and removes the otherwise
unnecessary dependency. Aligned storage is allocated manually on the stack.

[1]: https://github.com/boostorg/align/issues/10
2020-02-27 23:38:19 +03:00
Andrey Semashev
4336ac66bd Added support for C++20 atomic_flag::test operation.
The operation allows to test whether the flag is in the set state.
Also added tests and docs.
2020-02-26 01:24:54 +03:00
Andrey Semashev
2ed311af18 Fixed wrong x86 code generated for bit_test_and_op for 8 and 16-bit atomics.
The implementation used to generate 32-bit bts/btr/btc for 8 and 16-bit
atomics, which could result in alignment and access violation and possibly
data corruption. 32 and 64-bit atomics are unaffected.

This commit fixes operaend width for 16-bit atomics. For 8-bit atomics the
generic implementation is used based on or/and/xor instructions since there
are no 8-bit bts/btr/btc.
2020-02-25 23:59:02 +03:00
Andrey Semashev
2d1b1adb10 Ported tests to boost/bind/bind.hpp. 2020-02-25 19:24:00 +03:00
Andrey Semashev
8b70628d91 Added compilation fixes for MSVC. 2020-02-25 17:09:22 +03:00
Andrey Semashev
904871c37d Implemented atomic_ref.
This commit adds C++20 atomic_ref implementation, documentation and tests.
2020-02-25 02:00:05 +03:00
Andrey Semashev
b2594ecbc0 Disable all pointer arithmetic tests on UBSAN. 2019-10-13 10:34:58 +03:00
Andrey Semashev
0d8ea24351 Added a workaround for clang UBSAN failures.
Clang UBSAN considers an UB subtracting from a null pointer, which is
required for one of the tests. Disable that test when UBSAN is enabled.
2019-10-13 01:33:43 +03:00
Andrey Semashev
e8ccfce2dc Added check for BOOST_NO_ALIGNMENT for float128 tests.
Atomic storage can be implemented without int128 support but when
explicit alignment specification is supported.
2019-10-13 01:24:53 +03:00
Andrey Semashev
c043562511 Disable floating point tests when BOOST_ATOMIC_NO_FLOATING_POINT is defined.
Also check that int128 is available for float128 tests. Int128 is used
as the storage for atomic variables.
2019-10-12 21:58:56 +03:00
Andrey Semashev
4c2fc16ab1 Work around signed overflow on min value negation.
This should fix UBSAN failures.
2019-10-12 21:20:33 +03:00
Andrey Semashev
0e810ea02f Updated license URLs to use https. 2019-01-02 15:32:10 +03:00